import React, { createContext, useContext, useState, useEffect, useCallback } from 'react'
import { trpc } from './trpc-client'
import { useNavigate } from '@tanstack/react-router'

interface User {
  id: number
  name?: string | null | undefined
  mobile: string | null
  email: string | null
  profileImage: string | null

}

interface AuthState {
  user: User | null
  userDetails: any | null
  isAuthenticated: boolean
  isLoading: boolean
  token: string | null
}

interface AuthContextType extends AuthState {
  login: (token: string, user: User) => void
  loginWithToken: (token: string, user: User) => void
  register: (token: string, user: User) => void
  logout: () => void
  updateUser: (user: User) => void
  updateUserDetails: (details: any) => void
}

const AuthContext = createContext<AuthContextType | undefined>(undefined)

export function AuthProvider({ children }: { children: React.ReactNode }) {
  const [state, setState] = useState<AuthState>({
    user: null,
    userDetails: null,
    isAuthenticated: false,
    isLoading: true,
    token: null,
  })
  const navigate = useNavigate()

  // On mount, check for stored token
  useEffect(() => {
    const storedToken = localStorage.getItem('auth_token')
    const storedUserId = localStorage.getItem('user_id')
    if (storedToken && storedUserId) {
      setState((prev) => ({
        ...prev,
        token: storedToken,
        isAuthenticated: true,
      }))
    } else {
      setState((prev) => ({ ...prev, isLoading: false }))
    }
  }, [])

  // Fetch user data when token is available
  const { data: selfData } = trpc.user.user.getSelfData.useQuery(undefined, {
    enabled: !!state.token && state.isAuthenticated,
    retry: 1,
  })

  useEffect(() => {
    if (selfData?.data?.user) {
      setState((prev) => ({
        ...prev,
        user: selfData.data.user,
        userDetails: selfData.data.user,
        isLoading: false,
      }))
    } else if (selfData === undefined && state.token) {
      // Token might be invalid
    }
  }, [selfData, state.token])

  const login = useCallback((token: string, user: User) => {
    localStorage.setItem('auth_token', token)
    localStorage.setItem('user_id', String(user.id))
    setState({
      user,
      userDetails: user,
      isAuthenticated: true,
      isLoading: false,
      token,
    })
  }, [])

  const loginWithToken = useCallback((token: string, user: User) => {
    login(token, user)
  }, [login])

  const register = useCallback((token: string, user: User) => {
    login(token, user)
  }, [login])

  const logout = useCallback(() => {
    localStorage.removeItem('auth_token')
    localStorage.removeItem('user_id')
    setState({
      user: null,
      userDetails: null,
      isAuthenticated: false,
      isLoading: false,
      token: null,
    })
    navigate({ to: '/login' })
  }, [navigate])

  const updateUser = useCallback((user: User) => {
    setState((prev) => ({ ...prev, user }))
  }, [])

  const updateUserDetails = useCallback((details: any) => {
    setState((prev) => ({ ...prev, userDetails: details }))
  }, [])

  return (
    <AuthContext.Provider
      value={{
        ...state,
        login,
        loginWithToken,
        register,
        logout,
        updateUser,
        updateUserDetails,
      }}
    >
      {children}
    </AuthContext.Provider>
  )
}

export function useAuth() {
  const context = useContext(AuthContext)
  if (!context) {
    throw new Error('useAuth must be used within AuthProvider')
  }
  return context
}
