import { signInWithEmailAndPassword, signInWithPopup, GoogleAuthProvider, signOut as firebaseSignOut, onAuthStateChanged, getAuth } from 'firebase/auth' import { getApps, initializeApp } from 'firebase/app' import type { User } from 'firebase/auth' export const useAuth = () => { const user = ref(null) const isLoading = ref(true) const error = ref(null) const config = useRuntimeConfig() // Initialize Firebase if not already initialized const initializeFirebase = () => { if (process.client && getApps().length === 0) { const firebaseConfig = { apiKey: config.public.firebaseApiKey, authDomain: config.public.firebaseAuthDomain, projectId: config.public.firebaseProjectId, storageBucket: config.public.firebaseStorageBucket, messagingSenderId: config.public.firebaseMessagingSenderId, appId: config.public.firebaseAppId } initializeApp(firebaseConfig) } } // Get auth instance directly const getAuthInstance = () => { if (process.client) { initializeFirebase() return getAuth() } return null } // Initialize auth state listener const initAuth = () => { if (process.client) { try { const auth = getAuthInstance() if (auth) { onAuthStateChanged(auth, (firebaseUser) => { user.value = firebaseUser isLoading.value = false }) } } catch (err) { console.error('Failed to initialize auth:', err) isLoading.value = false } } } // Sign in with email and password const signInWithEmail = async (email: string, password: string) => { try { error.value = null isLoading.value = true const auth = getAuthInstance() if (!auth) { throw new Error('Firebase not initialized') } const userCredential = await signInWithEmailAndPassword(auth, email, password) const idToken = await userCredential.user.getIdToken() // Send token to backend await authenticateWithBackend(idToken) return userCredential.user } catch (err: any) { error.value = err.message throw err } finally { isLoading.value = false } } // Sign in with Google const signInWithGoogle = async () => { try { error.value = null isLoading.value = true const auth = getAuthInstance() if (!auth) { throw new Error('Firebase not initialized') } const provider = new GoogleAuthProvider() const userCredential = await signInWithPopup(auth, provider) const idToken = await userCredential.user.getIdToken() // Send token to backend await authenticateWithBackend(idToken) return userCredential.user } catch (err: any) { error.value = err.message throw err } finally { isLoading.value = false } } // Authenticate with backend const authenticateWithBackend = async (idToken: string) => { try { const response = await $fetch('/auth/login', { baseURL: config.public.backendUrl, method: 'POST', headers: { 'Content-Type': 'application/json' }, body: { idToken } }) return response } catch (err) { console.error('Backend authentication failed:', err) throw err } } // Sign out const signOut = async () => { try { const auth = getAuthInstance() if (!auth) { throw new Error('Firebase not initialized') } await firebaseSignOut(auth) user.value = null } catch (err: any) { error.value = err.message throw err } } // Get current user's ID token const getIdToken = async () => { if (!user.value) return null return await user.value.getIdToken() } return { user: readonly(user), isLoading: readonly(isLoading), error: readonly(error), initAuth, signInWithEmail, signInWithGoogle, signOut, getIdToken } }