UNPKG

@narangcia-oss/cryptic-auth-client-plain-ts

Version:

A TypeScript client for interacting with a cryptic-auth host web server, crafted by Narangcia OSS.

136 lines (116 loc) 3.32 kB
import type { AuthClient } from "../core/client"; import type { AuthTokens, AuthUser } from "../types/index"; import { extractOAuthParams, validateOAuthState, clearOAuthState, isOAuthCallback as checkIsOAuthCallback, } from "./oauth"; import { extractTokens } from "./tokens"; export interface OAuthCallbackResult { success: boolean; tokens?: AuthTokens; user?: AuthUser; error?: string; } /** * Core OAuth callback handler - framework agnostic * Handles the OAuth callback flow logic without any UI dependencies */ export class OAuthCallbackHandler { private authClient: AuthClient; constructor(authClient: AuthClient) { this.authClient = authClient; } /** * Checks if the current URL is an OAuth callback URL */ isOAuthCallback(): boolean { return checkIsOAuthCallback(); } /** * Processes the OAuth callback from the current URL * Returns the result without any UI side effects */ async processCallback(): Promise<OAuthCallbackResult> { try { if (!this.isOAuthCallback()) { return { success: false, error: "Not an OAuth callback URL", }; } const { code, state, error: oauthError } = extractOAuthParams(); if (oauthError) { return { success: false, error: `OAuth error: ${oauthError}`, }; } if (!code) { return { success: false, error: "Authorization code not found", }; } if (!state) { return { success: false, error: "State parameter not found", }; } if (!validateOAuthState(state)) { return { success: false, error: "Invalid state parameter - possible CSRF attack", }; } // Clean up stored state clearOAuthState(); // Extract provider from pathname (you might want to make this more robust) const provider = this.extractProviderFromUrl(); // Handle OAuth callback const response = await this.authClient.oauthLoginCallback(provider, { code, state, }); // Extract tokens from response const tokens = extractTokens(response); // Extract user information from response const user: AuthUser = { id: response.id, identifier: response.identifier, }; return { success: true, tokens, user, }; } catch (err) { const errorMessage = err instanceof Error ? err.message : "OAuth authentication failed"; return { success: false, error: errorMessage, }; } } /** * Extracts the OAuth provider from the current URL * Override this method for custom provider detection logic */ protected extractProviderFromUrl(): string { const pathname = window.location.pathname; if (pathname.includes("github")) return "github"; if (pathname.includes("google")) return "google"; if (pathname.includes("microsoft")) return "microsoft"; // Default fallback - you might want to throw an error instead return "github"; } /** * Cleans the OAuth parameters from the current URL */ cleanUrl(): void { window.history.replaceState({}, document.title, window.location.origin); } }