import { useContext, useEffect, useMemo, useRef } from 'react'; import { AuthContext, AuthState, RequiredUserInfo, } from '@app/contexts/AuthContext'; import { TOKEN_KEY, USERINFO_KEY } from '@app/constants'; import { removeAllItems, saveAllItems, saveItem, } from '@common/StorageHelper.ts'; const useAuth = (): { state: AuthState; actions: { login: (token: string, userInfo: RequiredUserInfo) => Promise; logout: () => Promise; update: (userInfo: RequiredUserInfo) => Promise; }; } => { const context = useContext(AuthContext); if (!context) { throw new Error('useAuth must be used in AuthProvider!'); } const contextRef = useRef(context); useEffect(() => { contextRef.current = context; }, [context]); const authActions = useMemo( () => ({ login: async (token: string, userInfo: RequiredUserInfo) => { await saveAllItems([ { key: TOKEN_KEY, data: token }, { key: USERINFO_KEY, data: JSON.stringify(userInfo) }, ]); contextRef.current.dispatch({ type: 'login', payload: { token: token, userInfo: userInfo, }, }); }, logout: async () => { await removeAllItems([TOKEN_KEY, USERINFO_KEY]); contextRef.current.dispatch({ type: 'logout', payload: undefined, }); }, update: async (userInfo: RequiredUserInfo) => { await saveItem(USERINFO_KEY, JSON.stringify(userInfo)); contextRef.current.dispatch({ type: 'update', payload: userInfo }); }, }), [], ); return { state: context.state, actions: authActions }; }; export { useAuth };