Improve security by requiring higher authentication levels for sensitive actions

Update authentication flows to enforce AAL2 requirements for MFA operations and identity disconnections, and adjust TOTP verification logic.

Replit-Commit-Author: Agent
Replit-Commit-Session-Id: da324197-4d44-4e4b-b342-fe8ae33cf0cf
Replit-Commit-Checkpoint-Type: intermediate_checkpoint
This commit is contained in:
pac7
2025-10-27 23:53:33 +00:00
parent 64f82c9ac2
commit d1f01d9228
5 changed files with 62 additions and 9 deletions

View File

@@ -90,12 +90,59 @@ export async function checkDisconnectSafety(
/**
* Disconnect an OAuth identity from the user's account
* Requires AAL2 session for security
*/
export async function disconnectIdentity(
provider: OAuthProvider
): Promise<IdentityOperationResult> {
try {
// Safety check first
// AAL2 check for security-critical operation (MUST fail closed)
const { data: { session } } = await supabase.auth.getSession();
// Get AAL level - fail closed on error
const { data: aalData, error: aalError } = await supabase.auth.mfa.getAuthenticatorAssuranceLevel();
if (aalError) {
logger.error('Failed to get AAL level for identity disconnect', {
action: 'disconnect_identity_aal_check',
error: aalError.message
});
return {
success: false,
error: 'Unable to verify security level. Please try again.',
requiresAAL2: true
};
}
const currentAal = aalData?.currentLevel || 'aal1';
// If not at AAL2, check if MFA is enrolled - fail closed on error
if (currentAal !== 'aal2') {
const { data: factors, error: factorsError } = await supabase.auth.mfa.listFactors();
if (factorsError) {
logger.error('Failed to list MFA factors for identity disconnect', {
action: 'disconnect_identity_mfa_check',
error: factorsError.message
});
return {
success: false,
error: 'Unable to verify MFA status. Please try again.',
requiresAAL2: true
};
}
const hasEnrolledMFA = factors?.totp?.some(f => f.status === 'verified') || false;
if (hasEnrolledMFA) {
return {
success: false,
error: 'Please verify your identity with MFA before disconnecting accounts',
requiresAAL2: true
};
}
}
// Safety check
const safetyCheck = await checkDisconnectSafety(provider);
if (!safetyCheck.canDisconnect) {
return {