Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 | 4x 7x 7x 7x 7x 7x 7x 7x 3x 2x 2x 3x 7x 7x 1x 1x 1x 1x 7x | import { createContext, useContext, useState, useEffect, useCallback, ReactNode } from 'react'
import { api } from '../api/client'
import type { AuthProfile, PasskeyUser } from '../api/types'
interface AuthContextType {
user: PasskeyUser | null
profile: AuthProfile | null
isAdmin: boolean
isLoading: boolean
logout: () => Promise<void>
refreshSession: () => Promise<void>
}
const AuthContext = createContext<AuthContextType | null>(null)
// eslint-disable-next-line react-refresh/only-export-components -- Hook is tightly coupled to provider
export function useAuth() {
const context = useContext(AuthContext)
Iif (!context) {
throw new Error('useAuth must be used within an AuthProvider')
}
return context
}
// eslint-disable-next-line react-refresh/only-export-components -- Safe variant for mode-conditional usage
export function useOptionalAuth() {
return useContext(AuthContext)
}
export function AuthProvider({ children }: { children: ReactNode }) {
const [user, setUser] = useState<PasskeyUser | null>(null)
const [profile, setProfile] = useState<AuthProfile | null>(null)
const [isLoading, setIsLoading] = useState(true)
// Restore session on mount
useEffect(() => {
api.auth
.me()
.then((data) => {
setUser(data.user)
setProfile(data.profile)
})
.catch(() => {
// Not logged in
})
.finally(() => setIsLoading(false))
}, [])
const refreshSession = useCallback(async () => {
try {
const data = await api.auth.me()
setUser(data.user)
setProfile(data.profile)
} catch {
setUser(null)
setProfile(null)
}
}, [])
const logout = useCallback(async () => {
try {
await api.auth.logout()
} catch {
// Ignore errors on logout
}
setUser(null)
setProfile(null)
}, [])
return (
<AuthContext.Provider
value={{
user,
profile,
isAdmin: user?.is_admin ?? false,
isLoading,
logout,
refreshSession,
}}
>
{children}
</AuthContext.Provider>
)
}
|