import { useState } from 'react'; import { useApp } from '../context/AppContext.js'; import { themeVars } from '../components/reader/readerThemes.js'; import { loginUser, registerUser, verifyMfaLogin, logoutUser } from '../syncService.js'; export default function AuthPage() { const { signIn, readerTheme } = useApp(); const shell = { style: themeVars(readerTheme) }; const [authMode, setAuthMode] = useState('login'); // 'login' | 'register' const [authForm, setAuthForm] = useState({ email: '', password: '' }); const [authError, setAuthError] = useState(''); const [authBusy, setAuthBusy] = useState(false); const [authMfaPending, setAuthMfaPending] = useState(false); // password ok, waiting on TOTP/backup code const [authMfaCode, setAuthMfaCode] = useState(''); const [authMfaUseBackup, setAuthMfaUseBackup] = useState(false); const submitAuth = async (e) => { e.preventDefault(); setAuthError(''); setAuthBusy(true); const action = authMode === 'login' ? loginUser : registerUser; const result = await action(authForm.email.trim(), authForm.password); setAuthBusy(false); if (!result.ok) { setAuthError(result.error ?? 'Something went wrong.'); return; } if (result.data?.mfaRequired) { setAuthMfaPending(true); return; } signIn(result.data); }; const submitMfa = async (e) => { e.preventDefault(); setAuthError(''); setAuthBusy(true); const result = await verifyMfaLogin( authMfaUseBackup ? { backupCode: authMfaCode.trim() } : { token: authMfaCode.trim() }, ); setAuthBusy(false); if (!result.ok) { setAuthError(result.error ?? 'Invalid code.'); return; } setAuthMfaPending(false); setAuthMfaCode(''); signIn(result.data); }; if (authMfaPending) { return (

Bible Study Project

Two-factor verification

{authMfaUseBackup ? 'Enter one of your saved backup codes.' : 'Enter the 6-digit code from your authenticator app.'}

setAuthMfaCode(e.target.value)} className="block w-full rounded-xl border border-[var(--r-line)] bg-[var(--r-bg)] px-3 py-2 text-[var(--r-text)] text-center text-lg tracking-widest focus:outline-none focus:ring-2 focus:ring-[var(--r-line)]" /> {authError &&

{authError}

}
); } return (
{/* Branding / feature panel — hidden on small screens to keep the form front and center there */}

Bible Study Project

Deep Bible study,
one chunk at a time.

Read Scripture in six translations, follow a reading plan into the text, and study a passage one chunk at a time with commentary, word studies, and cross-references beside it.

  • Read in BSB, ESV, NLT, CSB, NASB, or NET, with audio and search
  • Reading plans that open straight into the Reader
  • Observe, Interpret, Apply notes with Greek & Hebrew word studies
  • Turn your notes into a script, then export or share
  • Your studies stay private to your account, with optional 2FA
"Make every effort to present yourself approved to God, an unashamed workman who accurately handles the word of truth."
— 2 Timothy 2:15 (BSB)
{/* Sign in / register form */}

Bible Study Project

{authMode === 'login' ? 'Sign in' : 'Create an account'}

{authError &&

{authError}

}
); }