import { create } from "zustand";
import { persist } from "zustand/middleware";
import { useDashboardTabStore } from "./dashboardTabStore";

interface UseUserProfileStore {
  profile?: Record<string, any> | null;
  setUserProfile: (profile: Record<string, any>) => void;
  clearProfile: () => void;
}

const arePermissionsEqual = (
  permissions1?: Array<{ page_name: string; page_access: string[] }>,
  permissions2?: Array<{ page_name: string; page_access: string[] }>
): boolean => {
  if (!permissions1 && !permissions2) return true;
  if (!permissions1 || !permissions2) return false;
  if (permissions1.length !== permissions2.length) return false;

  const map1 = new Map<string, Set<string>>();
  const map2 = new Map<string, Set<string>>();

  permissions1.forEach((perm) => {
    map1.set(perm.page_name, new Set(perm.page_access.sort()));
  });

  permissions2.forEach((perm) => {
    map2.set(perm.page_name, new Set(perm.page_access.sort()));
  });

  if (map1.size !== map2.size) return false;

  for (const [pageName, pageAccess1] of map1.entries()) {
    const pageAccess2 = map2.get(pageName);
    if (!pageAccess2) return false;
    if (pageAccess1.size !== pageAccess2.size) return false;

    for (const access of pageAccess1) {
      if (!pageAccess2.has(access)) return false;
    }
  }

  return true;
};

const areProfilesEqual = (
  currentProfile: Record<string, any> | null | undefined,
  newProfile: Record<string, any>
): boolean => {
  if (!currentProfile) return false;

  if (
    !arePermissionsEqual(currentProfile.permissions, newProfile.permissions)
  ) {
    return false;
  }

  const currentKeys = Object.keys(currentProfile).filter(
    (key) => key !== "permissions"
  );
  const newKeys = Object.keys(newProfile).filter(
    (key) => key !== "permissions"
  );

  if (currentKeys.length !== newKeys.length) return false;

  for (const key of currentKeys) {
    if (
      JSON.stringify(currentProfile[key]) !== JSON.stringify(newProfile[key])
    ) {
      return false;
    }
  }

  return true;
};

export const useUserProfileStore = create<UseUserProfileStore>()(
  persist(
    (set, get) => ({
      profile: null,
      setUserProfile: (profile) => {
        const currentProfile = get().profile;

        if (!currentProfile) {
          set({ profile });
          return;
        }

        if (!areProfilesEqual(currentProfile, profile)) {
          set({ profile });
        }
      },
      clearProfile: () => set({ profile: null }),
    }),
    { name: "userprofile" }
  )
);

interface UseUserStore {
  auth?: string;
  setUser: (args: { auth: string }) => void;
  logOut?: () => void;
}

export const useUserStore = create<UseUserStore>()(
  persist(
    (set) => ({
      auth: "",
      setUser: ({ auth }) => set({ auth }),
      logOut: () => {
        set({ auth: "" });
        useUserProfileStore.getState().clearProfile();
        useDashboardTabStore.getState().clearTabs();
      },
    }),
    {
      name: "user",
    }
  )
);
