first commit
This commit is contained in:
commit
34ea15a54d
246 changed files with 18660 additions and 0 deletions
88
frontend/src/context/AuthContext.jsx
Normal file
88
frontend/src/context/AuthContext.jsx
Normal file
|
|
@ -0,0 +1,88 @@
|
|||
import { createContext, useCallback, useContext, useEffect, useMemo, useState } from 'react'
|
||||
|
||||
import {
|
||||
clearAccessToken,
|
||||
fetchCurrentUser,
|
||||
getAccessToken,
|
||||
login as loginRequest,
|
||||
logout as logoutSession,
|
||||
register as registerRequest,
|
||||
} from '../services/auth'
|
||||
|
||||
const AuthContext = createContext(null)
|
||||
|
||||
export function AuthProvider({ children }) {
|
||||
const [user, setUser] = useState(null)
|
||||
const [status, setStatus] = useState('loading')
|
||||
|
||||
const refreshUser = useCallback(async () => {
|
||||
const token = getAccessToken()
|
||||
if (!token) {
|
||||
setUser(null)
|
||||
setStatus('anonymous')
|
||||
return null
|
||||
}
|
||||
setStatus('loading')
|
||||
try {
|
||||
const profile = await fetchCurrentUser()
|
||||
setUser(profile)
|
||||
setStatus('authenticated')
|
||||
return profile
|
||||
} catch {
|
||||
clearAccessToken()
|
||||
setUser(null)
|
||||
setStatus('anonymous')
|
||||
return null
|
||||
}
|
||||
}, [])
|
||||
|
||||
useEffect(() => {
|
||||
refreshUser()
|
||||
}, [refreshUser])
|
||||
|
||||
const login = useCallback(
|
||||
async (credentials) => {
|
||||
await loginRequest(credentials)
|
||||
return refreshUser()
|
||||
},
|
||||
[refreshUser],
|
||||
)
|
||||
|
||||
const register = useCallback(
|
||||
async (payload) => {
|
||||
await registerRequest(payload)
|
||||
return refreshUser()
|
||||
},
|
||||
[refreshUser],
|
||||
)
|
||||
|
||||
const logout = useCallback(() => {
|
||||
logoutSession()
|
||||
setUser(null)
|
||||
setStatus('anonymous')
|
||||
}, [])
|
||||
|
||||
const value = useMemo(
|
||||
() => ({
|
||||
user,
|
||||
status,
|
||||
isAuthenticated: status === 'authenticated' && Boolean(user),
|
||||
isLoading: status === 'loading',
|
||||
login,
|
||||
register,
|
||||
logout,
|
||||
refreshUser,
|
||||
}),
|
||||
[user, status, login, register, logout, refreshUser],
|
||||
)
|
||||
|
||||
return <AuthContext.Provider value={value}>{children}</AuthContext.Provider>
|
||||
}
|
||||
|
||||
export function useAuth() {
|
||||
const context = useContext(AuthContext)
|
||||
if (!context) {
|
||||
throw new Error('useAuth must be used within AuthProvider')
|
||||
}
|
||||
return context
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue