package middleware import ( "dk/internal/auth" "dk/internal/router" "github.com/valyala/fasthttp" ) const ( UserKey = "user" SessionKey = "session" ) // Auth creates an authentication middleware func Auth(authManager *auth.AuthManager) router.Middleware { return func(next router.Handler) router.Handler { return func(ctx router.Ctx, params []string) { sessionID := auth.GetSessionCookie(ctx) if sessionID != "" { if session, exists := authManager.GetSession(sessionID); exists { // Update session activity authManager.UpdateSession(sessionID) // Store session and user info in context ctx.SetUserValue(SessionKey, session) ctx.SetUserValue(UserKey, &auth.User{ ID: session.UserID, Username: session.Username, Email: session.Email, }) // Refresh the cookie auth.SetSessionCookie(ctx, sessionID) } } next(ctx, params) } } } // RequireAuth enforces authentication - redirects to login if not authenticated func RequireAuth(loginPath string) router.Middleware { return func(next router.Handler) router.Handler { return func(ctx router.Ctx, params []string) { if !IsAuthenticated(ctx) { ctx.Redirect(loginPath, fasthttp.StatusFound) return } next(ctx, params) } } } // RequireGuest enforces no authentication - redirects to dashboard if authenticated func RequireGuest(dashboardPath string) router.Middleware { return func(next router.Handler) router.Handler { return func(ctx router.Ctx, params []string) { if IsAuthenticated(ctx) { ctx.Redirect(dashboardPath, fasthttp.StatusFound) return } next(ctx, params) } } } // IsAuthenticated checks if the current request has a valid session func IsAuthenticated(ctx router.Ctx) bool { _, exists := ctx.UserValue(UserKey).(*auth.User) return exists } // GetCurrentUser returns the current authenticated user, or nil if not authenticated func GetCurrentUser(ctx router.Ctx) *auth.User { if user, ok := ctx.UserValue(UserKey).(*auth.User); ok { return user } return nil } // GetCurrentSession returns the current session, or nil if not authenticated func GetCurrentSession(ctx router.Ctx) *auth.Session { if session, ok := ctx.UserValue(SessionKey).(*auth.Session); ok { return session } return nil } // Login creates a session and sets the cookie func Login(ctx router.Ctx, authManager *auth.AuthManager, user *auth.User) { session := authManager.CreateSession(user) auth.SetSessionCookie(ctx, session.ID) // Set in context for immediate use ctx.SetUserValue(SessionKey, session) ctx.SetUserValue(UserKey, user) } // Logout destroys the session and clears the cookie func Logout(ctx router.Ctx, authManager *auth.AuthManager) { sessionID := auth.GetSessionCookie(ctx) if sessionID != "" { authManager.DeleteSession(sessionID) } auth.DeleteSessionCookie(ctx) // Clear from context ctx.SetUserValue(SessionKey, nil) ctx.SetUserValue(UserKey, nil) }