/* Admin — simple login + view sign-in leads (no mock auth). */ const ADMIN_TOKEN_KEY = 'fp-admin-token'; function AdminScreen() { const [token, setToken] = useState(() => sessionStorage.getItem(ADMIN_TOKEN_KEY) || ''); const [user, setUser] = useState(''); const [pass, setPass] = useState(''); const [loginErr, setLoginErr] = useState(''); const [loginBusy, setLoginBusy] = useState(false); const [signins, setSignins] = useState([]); const [loadErr, setLoadErr] = useState(''); const [loading, setLoading] = useState(false); async function loadSignins(authToken) { setLoading(true); setLoadErr(''); try { const res = await fetch('/api/auth/admin/signins', { headers: { Authorization: 'Bearer ' + authToken, Accept: 'application/json' }, }); const data = await res.json().catch(() => ({})); if (res.status === 401) { sessionStorage.removeItem(ADMIN_TOKEN_KEY); setToken(''); throw new Error('Session expired — sign in again'); } if (!res.ok) throw new Error(data.error || 'Could not load sign-ins'); setSignins(data.signins || []); } catch (e) { setLoadErr(e.message); setSignins([]); } finally { setLoading(false); } } useEffect(() => { if (token) loadSignins(token); }, [token]); async function login(e) { e.preventDefault(); setLoginErr(''); setLoginBusy(true); try { const res = await fetch('/api/auth/admin/login', { method: 'POST', headers: { 'Content-Type': 'application/json', Accept: 'application/json' }, body: JSON.stringify({ username: user.trim(), password: pass }), }); const data = await res.json().catch(() => ({})); if (!res.ok) throw new Error(data.error || 'Login failed'); sessionStorage.setItem(ADMIN_TOKEN_KEY, data.token); setToken(data.token); setPass(''); } catch (ex) { setLoginErr(ex.message || 'Invalid credentials'); } finally { setLoginBusy(false); } } async function logout() { if (token) { try { await fetch('/api/auth/admin/logout', { method: 'POST', headers: { Authorization: 'Bearer ' + token }, }); } catch (_) { /* ignore */ } } sessionStorage.removeItem(ADMIN_TOKEN_KEY); setToken(''); setSignins([]); setUser(''); } if (!token) { return (

Admin Sign In

View visitor sign-ins collected after the 10-minute usage gate.

setUser(e.target.value)} autoComplete="username" /> setPass(e.target.value)} autoComplete="current-password" /> {loginErr &&
{loginErr}
}

Set ADMIN_USER and ADMIN_PASSWORD in your server environment.

); } return (

Sign-in Leads

{signins.length} submission{signins.length === 1 ? '' : 's'} stored

← Back to site
{loadErr &&
{loadErr}
}
{signins.length ? signins.map((s) => ( )) : ( )}
When Name Email Phone Visitor
{new Date(s.createdAt).toLocaleString('en-IN', { dateStyle: 'medium', timeStyle: 'short' })} {s.name} {s.email} {s.phone} {s.visitorId || '—'}
{loading ? 'Loading…' : 'No sign-ins yet. They appear when visitors pass the 10-minute gate.'}
); } Object.assign(window, { AdminScreen });