this repo has no description
1import { api, type Session, type CreateAccountParams, type CreateAccountResult, ApiError } from './api' 2 3const STORAGE_KEY = 'bspds_session' 4 5interface AuthState { 6 session: Session | null 7 loading: boolean 8 error: string | null 9} 10 11let state = $state<AuthState>({ 12 session: null, 13 loading: true, 14 error: null, 15}) 16 17function saveSession(session: Session | null) { 18 if (session) { 19 localStorage.setItem(STORAGE_KEY, JSON.stringify(session)) 20 } else { 21 localStorage.removeItem(STORAGE_KEY) 22 } 23} 24 25function loadSession(): Session | null { 26 const stored = localStorage.getItem(STORAGE_KEY) 27 if (stored) { 28 try { 29 return JSON.parse(stored) 30 } catch { 31 return null 32 } 33 } 34 return null 35} 36 37export async function initAuth() { 38 state.loading = true 39 state.error = null 40 const stored = loadSession() 41 if (stored) { 42 try { 43 const session = await api.getSession(stored.accessJwt) 44 state.session = { ...session, accessJwt: stored.accessJwt, refreshJwt: stored.refreshJwt } 45 } catch (e) { 46 if (e instanceof ApiError && e.status === 401) { 47 try { 48 const refreshed = await api.refreshSession(stored.refreshJwt) 49 state.session = refreshed 50 saveSession(refreshed) 51 } catch { 52 saveSession(null) 53 state.session = null 54 } 55 } else { 56 saveSession(null) 57 state.session = null 58 } 59 } 60 } 61 state.loading = false 62} 63 64export async function login(identifier: string, password: string): Promise<void> { 65 state.loading = true 66 state.error = null 67 try { 68 const session = await api.createSession(identifier, password) 69 state.session = session 70 saveSession(session) 71 } catch (e) { 72 if (e instanceof ApiError) { 73 state.error = e.message 74 } else { 75 state.error = 'Login failed' 76 } 77 throw e 78 } finally { 79 state.loading = false 80 } 81} 82 83export async function register(params: CreateAccountParams): Promise<CreateAccountResult> { 84 try { 85 const result = await api.createAccount(params) 86 return result 87 } catch (e) { 88 if (e instanceof ApiError) { 89 state.error = e.message 90 } else { 91 state.error = 'Registration failed' 92 } 93 throw e 94 } 95} 96 97export async function confirmSignup(did: string, verificationCode: string): Promise<void> { 98 state.loading = true 99 state.error = null 100 try { 101 const result = await api.confirmSignup(did, verificationCode) 102 const session: Session = { 103 did: result.did, 104 handle: result.handle, 105 accessJwt: result.accessJwt, 106 refreshJwt: result.refreshJwt, 107 email: result.email, 108 emailConfirmed: result.emailConfirmed, 109 preferredChannel: result.preferredChannel, 110 preferredChannelVerified: result.preferredChannelVerified, 111 } 112 state.session = session 113 saveSession(session) 114 } catch (e) { 115 if (e instanceof ApiError) { 116 state.error = e.message 117 } else { 118 state.error = 'Verification failed' 119 } 120 throw e 121 } finally { 122 state.loading = false 123 } 124} 125 126export async function resendVerification(did: string): Promise<void> { 127 try { 128 await api.resendVerification(did) 129 } catch (e) { 130 if (e instanceof ApiError) { 131 throw e 132 } 133 throw new Error('Failed to resend verification code') 134 } 135} 136 137export async function logout(): Promise<void> { 138 if (state.session) { 139 try { 140 await api.deleteSession(state.session.accessJwt) 141 } catch { 142 // Ignore errors on logout 143 } 144 } 145 state.session = null 146 saveSession(null) 147} 148 149export function getAuthState() { 150 return state 151} 152 153export function getToken(): string | null { 154 return state.session?.accessJwt ?? null 155} 156 157export function isAuthenticated(): boolean { 158 return state.session !== null 159} 160 161export function _testSetState(newState: { session: Session | null; loading: boolean; error: string | null }) { 162 state.session = newState.session 163 state.loading = newState.loading 164 state.error = newState.error 165} 166 167export function _testReset() { 168 state.session = null 169 state.loading = true 170 state.error = null 171 localStorage.removeItem(STORAGE_KEY) 172}