How 2FA and Social Logins Work (Architectural Guide)
This guide describes the technical workflows of Two-Factor Authentication (2FA) and Social Logins inside the Fabrixly-IDS OIDC interaction engine, explaining how session state, tokens, and redirects are managed during multi-step logins.
Part A: Social Logins OIDC Workflow
Social Logins (Google, GitHub) hook directly into the OIDC interaction flow. Here is the step-by-step path from authorization redirect to interaction completion:
sequenceDiagram
participant ClientApp as Client Application (SPA/Backend)
participant IDS as Fabrixly-IDS (OIDC Issuer)
participant UI as Login / Interaction Screen
participant Google as Google OAuth Authority
ClientApp->>IDS: GET /oidc/auth (OIDC Authorization Redirect)
IDS->>UI: Redirect to /interaction/:uid (Consent/Login Screen)
UI->>Google: Click Login → GET /api/auth/google?client_id=...&uid=:uid
Google-->>IDS: Callback GET /api/auth/google/callback?code=...
Note over IDS: Verifies Google profile, links/creates User record, creates session
IDS->>UI: Redirect GET /interaction/:uid/google-callback?token=:jwtToken
Note over UI: Verifies temporary JWT, sets active session, calls interactionFinished
UI->>IDS: interactionFinished() callback
IDS->>ClientApp: Redirect to Callback URI with Auth Code
1. Initiation
The client application redirects the user to /oidc/auth. The OIDC provider detects no active session and redirects the browser to the interaction page: /interaction/:uid.
2. Social Login Redirection
The interaction UI displays Google/GitHub buttons. Clicking a button triggers a query containing the OIDC session identifier (uid): GET https://ids.fabrixly.com/api/auth/google?client_id=your-client-id&uid=oidc-session-uid
3. Callback & User Provisioning
After authenticating at Google, Google callbacks to /api/auth/google/callback with state containing the uid.
- Existing User: Links
googleIdif it is not already stored on the user's database record. - Just-in-Time (JIT) Provisioning: If the email doesn't exist, Fabrixly-IDS auto-registers the user under the client's parent organization.
- Session Creation: The server creates a session and redirects the browser to:
GET /interaction/:uid/google-callback?token=<signed-jwt-containing-userId>
4. Completing OIDC Flow
The interaction route (/:uid/google-callback) validates the temporary JWT token, marks the OIDC session login reference (amr: ['google']), and calls: provider.interactionFinished(req, res, { login: { accountId: userId } }) This redirects the user back to the client application with the standard OIDC authorization code.
Part B: Two-Factor Authentication (2FA) Workflow
2FA (password_and_otp) divides the login screen into a two-step verification process context-bound by the OIDC session.
1. Step 1: Password Verification
- The user enters their email and password on the login screen.
- The UI posts credentials to:
POST /interaction/:uid/login. - Upon matching the password hash, the backend:
- Generates a cryptographically secure 6-digit OTP code.
- Sends the code using the configured provider (SMTP or SMS).
- Stores the intermediate auth state (e.g.
is_password_verified: true) on the OIDC interaction session.
Returns:
{
"status": "otp_required",
"message": "Please enter the OTP verification code sent to your device."
}
2. Step 2: OTP Challenge
- The UI displays the OTP submission input box.
- The user submits the code:
POST /interaction/:uid/verify-otp. - The backend verifies the OTP code against expiration limits (default: 5 minutes):
- If correct, it completes the session, registers the user login event in the audit logs, and calls
interactionFinishedto complete the OIDC auth code redirect.
- If correct, it completes the session, registers the user login event in the audit logs, and calls
Part C: Interaction Between Social Logins and 2FA
When a user authenticates via a social identity provider (Google/GitHub), standard credential challenges (password and OTP) are bypassed by default because the identity provider has already confirmed the authentication.
Enforcing Multi-Factor on Social Login
If your security policies mandate that social users must still complete a second-factor challenge (e.g., verifying a mobile OTP):
- Ensure
enable_2fa: trueis toggled on the user profile record. - After the social callback completes
/interaction/:uid/google-callback, the interaction controller detectsenable_2fa: trueon the user entity. - Rather than finalizing the flow, the controller generates an OTP code, redirects the user to the
/interaction/:uid/mfachallenge screen, and expects the user to verify the code before callinginteractionFinished.