Amba-Agent-App/lib/hooks/useUserProfile.ts
2026-01-16 00:22:35 +03:00

92 lines
2.6 KiB
TypeScript

import { useCallback, useEffect, useMemo, useRef } from 'react';
import { FirebaseAuthTypes } from '../firebase';
import { UserProfile } from '../services/authServices';
import { useUserProfileStore } from '../stores/userProfileStore';
import type { ProfileCacheEntry } from '../stores/userProfileStore';
import { useGlobalLoading } from './useGlobalLoading';
interface UseUserProfileReturn {
profile: UserProfile | null;
loading: boolean;
error: string | null;
refreshProfile: () => Promise<void>;
}
const defaultEntry: ProfileCacheEntry = {
profile: null,
loading: false,
error: null,
};
export const useUserProfile = (user: FirebaseAuthTypes.User | null): UseUserProfileReturn => {
const uid = user?.uid ?? null;
const lastUidRef = useRef<string | null>(null);
const ensureSubscription = useUserProfileStore((state) => state.ensureSubscription);
const refreshFromStore = useUserProfileStore((state) => state.refreshProfile);
const removeProfile = useUserProfileStore((state) => state.removeProfile);
const entry = useUserProfileStore(
useCallback(
(state) => (uid ? state.profiles[uid] ?? defaultEntry : defaultEntry),
[uid]
)
);
const { withLoading } = useGlobalLoading();
useEffect(() => {
// Clean up subscription from previous user when switching or logging out
if (lastUidRef.current && lastUidRef.current !== uid) {
removeProfile(lastUidRef.current);
}
lastUidRef.current = uid;
}, [uid, removeProfile]);
useEffect(() => {
if (!uid) {
return;
}
ensureSubscription(uid);
}, [uid, ensureSubscription]);
const refreshProfile = useCallback(async () => {
if (!uid) {
return;
}
await withLoading(() => refreshFromStore(uid));
}, [refreshFromStore, uid, withLoading]);
return useMemo(
() => ({
profile: entry.profile,
loading: uid ? entry.loading : false,
error: uid ? entry.error : null,
refreshProfile,
}),
[entry.error, entry.loading, entry.profile, refreshProfile, uid]
);
};
// Standalone function to fetch any user's profile (useful for admin features)
export const fetchUserProfile = async (uid: string, opts?: { force?: boolean }): Promise<UserProfile | null> => {
if (!uid) {
return null;
}
const { force = false } = opts ?? {};
const cached = force ? null : useUserProfileStore.getState().profiles[uid]?.profile;
if (cached) {
return cached;
}
try {
return await useUserProfileStore.getState().refreshProfile(uid);
} catch (error) {
console.error('Error fetching user profile:', error);
throw error;
}
};