import { updatePrivateAxiosInstance } from "@/configs/axiosConfig";
import { TOKEN_NAME } from "@/configs";
import { storage } from "@/configs/storage";
import { syncPushNotificationToken } from "@/services/notifications/pushNotificationService";
import {
  type AuthStore,
  createAuthStore,
  defaultInitState,
} from "@/stores/auth";
import { AppConfig } from "@/types/app_config";
import { createContext, ReactNode, useContext, useEffect, useRef } from "react";
import { useStore } from "zustand";

export type AuthStoreApi = ReturnType<typeof createAuthStore>;

export const AuthStoreContext = createContext<AuthStoreApi | undefined>(
  undefined,
);

export interface AuthProviderProps {
  children: ReactNode;
  appInfo?: AppConfig;
}

export const AuthStoreProvider = ({ children, appInfo }: AuthProviderProps) => {
  const store = useRef<AuthStoreApi>(createAuthStore(defaultInitState));

  useEffect(() => {
    const initAuth = async () => {
      const token = storage.getString(TOKEN_NAME);
      if (token) {
        // Read current state from the store snapshot, not from a closure
        const { isAuthenticated, getUser } = store.current.getState();
        if (!isAuthenticated) {
          updatePrivateAxiosInstance(token);
          await getUser();
          store.current.setState({
            isAuthenticated: true,
            token,
          });
          void syncPushNotificationToken();
        }
      } else {
        store.current.setState({
          isAuthenticated: false,
          token: "",
          user: null,
        });
      }
      store.current.setState({ appInfo });
    };

    initAuth();
  }, [appInfo]); // Only re-run when appInfo changes, not on auth state changes

  return (
    <AuthStoreContext.Provider value={store.current}>
      {children}
    </AuthStoreContext.Provider>
  );
};

export const useAuthStore = <T,>(selector: (store: AuthStore) => T): T => {
  const store = useContext(AuthStoreContext);

  if (!store) {
    throw new Error("useAuthStore must be used within a AuthStoreProvider");
  }

  return useStore(store, selector);
};

export const useKycVerification = () => {
  const { appInfo } = useAuthStore((state: any) => state);

  return (
    appInfo?.application_info?.extra_service?.system_config?.kyc_verification
      ?.is_enabled ?? false
  );
};
