-
Notifications
You must be signed in to change notification settings - Fork 1
Open
Labels
enhancementNew feature or requestNew feature or requestlow-priorityNice to have - address eventuallyNice to have - address eventuallysecuritySecurity-related features and fixesSecurity-related features and fixes
Milestone
Description
Parent Epic
Part of #168 - Authentication Security Improvements
Priority
LOW - Informational / Future Enhancement
Problem
Currently, users can reset their password to the same value they had before. This reduces the security benefit of password rotation.
Recommendation
Store hashes of the last N passwords (e.g., 5) and prevent reuse:
interface User {
// ... existing fields
passwordHistory?: string[]; // Array of bcrypt hashes
}
async function isPasswordReused(userId: string, newPassword: string): Promise<boolean> {
const user = await getUserById(userId);
if (!user?.passwordHistory) return false;
for (const oldHash of user.passwordHistory) {
if (await bcrypt.compare(newPassword, oldHash)) {
return true;
}
}
return false;
}Considerations
- Storage cost: ~60 bytes per hash × 5 history = 300 bytes per user
- Performance: Up to 5 bcrypt comparisons on password change
- UX: Clear error message explaining reuse restriction
Files to Modify
lib/types/user.ts- Add passwordHistory fieldlib/storage/users.ts- Update password change to maintain historylib/auth/password-reset.ts- Check history before allowing resetapp/api/account/security/password/route.ts- Check history
Acceptance Criteria
- Last 5 passwords tracked
- Cannot reuse recent passwords
- Clear error message for users
- Configurable history length
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
enhancementNew feature or requestNew feature or requestlow-priorityNice to have - address eventuallyNice to have - address eventuallysecuritySecurity-related features and fixesSecurity-related features and fixes