NeahNew/SESSION_DURATION_SECURITY_ANALYSIS.md

7.8 KiB

NextAuth Session Duration: 30 Days vs 4 Hours - Security Analysis

Current Configuration

Current Setting (app/api/auth/options.ts:190):

session: {
  strategy: "jwt",
  maxAge: 30 * 24 * 60 * 60, // 30 days (2,592,000 seconds)
}

Proposed Setting:

session: {
  strategy: "jwt",
  maxAge: 4 * 60 * 60, // 4 hours (14,400 seconds)
}

Security Analysis

Why 4 Hours is Better for Security

  1. Reduced Attack Window:

    • 30 days: If session is compromised, attacker has 30 days of access
    • 4 hours: If session is compromised, attacker has maximum 4 hours of access
    • Risk Reduction: 99.4% reduction in maximum exposure time
  2. Industry Best Practices:

    • NIST Guidelines: Recommend session timeouts of 2-8 hours for high-security applications
    • OWASP: Recommends session timeouts based on risk level (typically 2-8 hours)
    • Common Practice: Most enterprise applications use 4-8 hour sessions
  3. Device Security:

    • 30 days: Device left unattended = 30 days of potential unauthorized access
    • 4 hours: Device left unattended = maximum 4 hours of potential access
    • Better for: Shared devices, public computers, unattended workstations
  4. Compliance:

    • Many security standards (ISO 27001, SOC 2) require reasonable session timeouts
    • 30 days is often considered too long for compliance
    • 4 hours aligns better with security compliance requirements
  5. Stolen Session Cookie:

    • If session cookie is stolen (XSS, MITM), shorter duration limits damage
    • 4 hours gives attacker limited time to exploit
    • 30 days gives attacker extensive time to exploit

⚠️ Considerations & Trade-offs

  1. User Experience Impact:

    • 30 days: Users rarely need to re-authenticate (convenient)
    • 4 hours: Users need to re-authenticate every 4 hours (less convenient)
    • Impact: Moderate - users will need to log in more frequently
  2. Token Refresh Behavior:

    • Good News: Your code already handles token refresh automatically
    • How it works:
      • When NextAuth session expires (4 hours), JWT callback runs
      • If accessToken is expired, it calls refreshAccessToken()
      • Uses refreshToken to get new tokens from Keycloak
      • Session is automatically renewed (if refresh token is still valid)
    • Result: Users may not notice the 4-hour expiration if they're active
  3. Keycloak Refresh Token Lifetime:

    • Important: Keycloak refresh tokens typically last 7-30 days
    • What this means:
      • NextAuth session expires after 4 hours
      • But refresh token is still valid (e.g., 7 days)
      • NextAuth automatically refreshes tokens
      • User stays logged in seamlessly (if active)
    • Only expires if: User is inactive for longer than refresh token lifetime
  4. Keycloak Session Alignment:

    • Current Issue: Keycloak sessions typically expire in 30 minutes to a few hours
    • With 4-hour NextAuth session:
      • Better alignment with Keycloak session timeouts
      • Reduces session mismatch issues
      • Iframe applications will have more consistent session state

How It Will Work

Session Lifecycle with 4-Hour maxAge

User logs in
  ↓
NextAuth creates JWT session (expires in 4 hours)
  ↓
User is active for 2 hours
  ↓
User makes request → NextAuth checks session
  ↓
Session still valid (< 4 hours) → Continue
  ↓
User is active for 3 hours
  ↓
User makes request → NextAuth checks session
  ↓
Session still valid (< 4 hours) → Continue
  ↓
User is active for 4.5 hours (session expired)
  ↓
User makes request → NextAuth checks session
  ↓
Session expired → JWT callback runs
  ↓
Checks accessToken expiration
  ↓
If accessToken expired → Calls refreshAccessToken()
  ↓
Uses refreshToken to get new tokens from Keycloak
  ↓
If refreshToken still valid → New session created (another 4 hours)
  ↓
User continues seamlessly (no re-authentication needed)
  ↓
If refreshToken expired → User must re-authenticate

When User Must Re-authenticate

User must re-authenticate if:

  1. Inactive for longer than refresh token lifetime (typically 7-30 days)
  2. Refresh token is revoked (logout, admin action, security event)
  3. Keycloak session is invalidated (logout from another application)

User does NOT need to re-authenticate if:

  1. Active within refresh token lifetime (automatic token refresh)
  2. Session expires but refresh token is valid (automatic renewal)

Recommendations

Recommendation: Implement 4-Hour Session

Reasons:

  1. Significantly better security (99.4% reduction in exposure window)
  2. Aligns with industry best practices (NIST, OWASP)
  3. Better compliance (meets security standards)
  4. Better alignment with Keycloak sessions
  5. Minimal UX impact (automatic token refresh handles renewal)
  6. Code already supports it (token refresh mechanism exists)

⚠️ Important Considerations

  1. Verify Keycloak Refresh Token Lifetime:

    • Check Keycloak configuration for refresh token lifetime
    • Ensure it's longer than 4 hours (typically 7-30 days)
    • If shorter, users will need to re-authenticate frequently
  2. Monitor User Experience:

    • Track how often users need to re-authenticate
    • If too frequent, consider increasing to 6-8 hours
    • Balance security with usability
  3. Consider Activity-Based Extension:

    • Current implementation: Fixed 4-hour expiration
    • Alternative: Extend session on activity (sliding window)
    • Requires additional implementation (activity tracking)
  4. Keycloak Session Configuration:

    • Consider aligning Keycloak SSO session timeout with NextAuth
    • Or ensure Keycloak session is longer than NextAuth session
    • Prevents session mismatch issues

📋 Implementation Checklist

Before implementing:

  • Verify Keycloak refresh token lifetime (should be > 4 hours)
  • Test token refresh flow with 4-hour session
  • Monitor user re-authentication frequency
  • Consider user feedback on session duration
  • Document the change for users (if needed)
  • Update security documentation

Comparison Table

Aspect 30 Days 4 Hours Winner
Security Low (long exposure window) High (short exposure window) 4 Hours
User Convenience High (rare re-authentication) Medium (automatic refresh) 30 Days
Compliance Poor (too long) Good (meets standards) 4 Hours
Risk Reduction Low High (99.4% reduction) 4 Hours
Keycloak Alignment Poor (mismatch) Good (better alignment) 4 Hours
Token Refresh Works Works (same mechanism) Tie

Conclusion

Recommendation: Change to 4 hours

Why:

  • Significantly better security posture
  • Aligns with industry best practices
  • Better compliance with security standards
  • Minimal UX impact (automatic token refresh)
  • Better alignment with Keycloak session timeouts
  • Code already supports it

Implementation:

  • Simple change: maxAge: 4 * 60 * 60
  • No code changes needed (token refresh already works)
  • Monitor user experience and adjust if needed

Alternative Consideration:

  • If 4 hours is too aggressive, consider 6-8 hours as a middle ground
  • Still provides significant security improvement over 30 days
  • Better user experience than 4 hours

Final Verdict

Yes, change to 4 hours - This is a good security practice that:

  • Significantly reduces security risk
  • Aligns with industry standards
  • Has minimal UX impact (automatic refresh)
  • Works with existing code
  • Better aligns with Keycloak sessions

The only trade-off is slightly more frequent re-authentication for inactive users, but this is a reasonable security trade-off.