package auth import ( "crypto/rand" "crypto/sha256" "net/http" "strings" "time" ) const sessionExpiresInSeconds = 60 * 60 * 24 // 1 day const activityCheckInterval = 60 * 60 // 1 hour func GenerateSecureRandomString() (string, error) { // Human readable alphabet (a-z, 0-9 without l, o, 0, 1 to avoid confusion) alphabet := "abcdefghijklmnpqrstuvwxyz23456789" // Generate 24 bytes = 192 bits of entropy. // We're only going to use 5 bits per byte so the total entropy will be 192 * 5 / 8 = 120 bits bytes := make([]byte, 24) _, err := rand.Read(bytes) if err != nil { return "", err } var id strings.Builder for _, b := range bytes { // >> 3 "removes" the right-most 3 bits of the byte id.WriteByte(alphabet[b>>3]) } return id.String(), nil } func HashSecret(secret string) []byte { hash := sha256.Sum256([]byte(secret)) return hash[:] } func CheckNeedForBump(lastVerified time.Time) bool { return time.Since(lastVerified).Seconds() >= activityCheckInterval } func CheckExpiration(expirarion time.Time) bool { return time.Since(expirarion).Seconds() >= sessionExpiresInSeconds } func NewSessionCookie(token string, deleted bool) *http.Cookie { cookie := &http.Cookie{ Name: "session", Value: token, HttpOnly: true, SameSite: http.SameSiteLaxMode, MaxAge: sessionExpiresInSeconds, Path: "/", } if deleted { cookie = &http.Cookie{ Name: "session", Value: "", HttpOnly: true, SameSite: http.SameSiteLaxMode, MaxAge: -1, Path: "/", } } return cookie }