/**
 * Shared Companies Store Factory
 *
 * Creates a Pinia store for company selection that can be used by any ROA2WEB application.
 * Each app passes its own apiService and auth store instances.
 *
 * Usage:
 *   import { createCompaniesStore } from '@shared/frontend/stores/companies';
 *   import { apiService } from '../services/api';
 *   import { useAuthStore } from './auth';
 *   export const useCompanyStore = createCompaniesStore(apiService, useAuthStore);
 */

import { defineStore } from "pinia";
import { ref, computed, watch } from "vue";

/**
 * Factory function to create a companies store
 * @param {Object} apiService - Axios instance configured for the app's API
 * @param {Function} useAuthStore - Reference to the auth store function
 * @returns {Function} Pinia store definition
 */
export function createCompaniesStore(apiService, useAuthStore) {
  return defineStore("companies", () => {
    // State
    const companies = ref([]);
    const selectedCompany = ref(null);
    const isLoading = ref(false);
    const error = ref(null);

    // Initialize from localStorage - per user and per server (US-027)
    const initializeSelectedCompany = () => {
      const authStore = useAuthStore();
      const username = authStore.user?.username;
      const serverId = authStore.selectedServerId;

      if (!username) {
        console.log("[Companies] No username available for initialization");
        return null;
      }

      // Include server_id in key for multi-server support (US-027)
      const key = serverId
        ? `selected_company_${username}_${serverId}`
        : `selected_company_${username}`;
      const saved = localStorage.getItem(key);
      if (saved) {
        try {
          const company = JSON.parse(saved);
          console.log(`[Companies] Loaded saved company for ${username}${serverId ? ` on server ${serverId}` : ''}:`, company.name);
          return company;
        } catch (e) {
          console.error("Failed to parse saved company", e);
          localStorage.removeItem(key);
        }
      }
      return null;
    };

    // US-031 FIX: Watch for auth user changes but DON'T auto-restore company
    // The company will be restored in loadCompanies() AFTER validating
    // that the saved company exists in the server's company list.
    // This prevents restoring a company from server A when logging into server B.
    const authStore = useAuthStore();
    watch(
      () => authStore.user,
      (newUser) => {
        if (newUser && newUser.username) {
          console.log("[Companies] User authenticated:", newUser.username);
          // NOTE: Company restoration moved to loadCompanies() for validation
        }
      },
      { immediate: true }
    );

    // Getters
    const companyList = computed(() => companies.value);
    const hasCompanies = computed(() => companies.value.length > 0);
    const selectedCompanyId = computed(() => selectedCompany.value?.id_firma || null);

    const companyListFormatted = computed(() => {
      return companies.value.map((company) => ({
        ...company,
        displayName: company.fiscal_code
          ? `${company.name} (${company.fiscal_code})`
          : company.name,
      }));
    });

    // Actions
    const loadCompanies = async () => {
      isLoading.value = true;
      error.value = null;

      try {
        console.log("[Companies] Loading companies...");
        const response = await apiService.get("/companies");
        companies.value = response.data.companies || [];
        console.log("[Companies] Loaded", companies.value.length, "companies");

        // Get current server context
        const authStore = useAuthStore();
        const currentServerId = authStore.selectedServerId;

        // US-034 FIX: Always try to restore saved company for CURRENT server
        // This handles server switching where selectedCompany holds old server's company
        const savedCompany = initializeSelectedCompany();

        // Check if current selectedCompany matches current server
        const currentCompanyMatchesServer =
          selectedCompany.value &&
          selectedCompany.value._server_id === currentServerId;

        if (savedCompany) {
          // US-003: Validate server_id before restoring
          // Two servers can have companies with the same id_firma
          if (savedCompany._server_id && savedCompany._server_id !== currentServerId) {
            console.log("[Companies] Saved company server mismatch, ignoring");
            console.log(`[Companies] Saved server: ${savedCompany._server_id}, current: ${currentServerId}`);
            // Only clear if current selection also doesn't match
            if (!currentCompanyMatchesServer) {
              selectedCompany.value = null;
            }
          } else {
            // Validate that saved company exists in the current server's list
            const exists = companies.value.find(
              (c) => c.id_firma === savedCompany.id_firma
            );
            if (exists) {
              selectedCompany.value = savedCompany;
              console.log("[Companies] Restored saved company:", savedCompany.name);
            } else {
              console.warn("[Companies] Saved company not in current server list, ignoring:", savedCompany.name);
              selectedCompany.value = null;
            }
          }
        } else if (!currentCompanyMatchesServer) {
          // No saved company and current selection doesn't match server - clear it
          console.log("[Companies] No saved company for current server, clearing selection");
          selectedCompany.value = null;
        }

        // Validate if already selected company is still accessible
        if (selectedCompany.value) {
          const exists = companies.value.find(
            (c) => c.id_firma === selectedCompany.value.id_firma
          );
          if (!exists) {
            console.warn("[Companies] Selected company not accessible, clearing");
            selectedCompany.value = null;
          }
        }

        // Auto-select first company if none selected
        if (!selectedCompany.value && companies.value.length > 0) {
          const firstCompany = companies.value[0];
          console.log("[Companies] Auto-selecting first company:", firstCompany.name);
          setSelectedCompany(firstCompany);
        }

        return { success: true };
      } catch (err) {
        error.value = err.response?.data?.detail || "Failed to load companies";
        console.error("Failed to load companies:", err);
        return { success: false, error: error.value };
      } finally {
        isLoading.value = false;
      }
    };

    const setSelectedCompany = (company) => {
      selectedCompany.value = company;

      const authStore = useAuthStore();
      const username = authStore.user?.username;
      const serverId = authStore.selectedServerId;

      if (!username) {
        console.warn("[Companies] Cannot save - no username");
        return;
      }

      // Include server_id in key for multi-server support (US-027)
      const key = serverId
        ? `selected_company_${username}_${serverId}`
        : `selected_company_${username}`;
      if (company) {
        // US-003: Include _server_id in saved object for validation at restore
        // This prevents restoring a company from a different server with same id_firma
        const companyToSave = {
          ...company,
          _server_id: serverId
        };
        localStorage.setItem(key, JSON.stringify(companyToSave));
        console.log(`[Companies] Saved company for ${username}${serverId ? ` on server ${serverId}` : ''}:`, company.name);
      } else {
        localStorage.removeItem(key);
      }
    };

    const clearSelectedCompany = () => {
      selectedCompany.value = null;

      const authStore = useAuthStore();
      const username = authStore.user?.username;
      const serverId = authStore.selectedServerId;

      if (username) {
        // Include server_id in key for multi-server support (US-027)
        const key = serverId
          ? `selected_company_${username}_${serverId}`
          : `selected_company_${username}`;
        localStorage.removeItem(key);
      }
    };

    const getCompanyById = (id_firma) => {
      return companies.value.find(
        (company) => company.id_firma === parseInt(id_firma)
      );
    };

    const clearError = () => {
      error.value = null;
    };

    const reset = () => {
      companies.value = [];
      selectedCompany.value = null;
      isLoading.value = false;
      error.value = null;

      const authStore = useAuthStore();
      const username = authStore.user?.username;
      const serverId = authStore.selectedServerId;
      if (username) {
        // Include server_id in key for multi-server support (US-027)
        const key = serverId
          ? `selected_company_${username}_${serverId}`
          : `selected_company_${username}`;
        localStorage.removeItem(key);
      }
    };

    /**
     * US-031: Reset with explicit context (username, serverId)
     * Called from onLogout callback when authStore.user is already null.
     * This allows proper cleanup of localStorage keys.
     *
     * @param {string} username - Username saved before logout
     * @param {string} serverId - Server ID saved before logout
     */
    const resetWithContext = (username, serverId) => {
      companies.value = [];
      selectedCompany.value = null;
      isLoading.value = false;
      error.value = null;

      if (username) {
        // Clear the server-specific key (new format from US-027)
        if (serverId) {
          const newKey = `selected_company_${username}_${serverId}`;
          localStorage.removeItem(newKey);
          console.log(`[Companies] Cleared localStorage key: ${newKey}`);
        }

        // IMPORTANT: Also clear the old key (without server) for cleanup
        // This handles migration from old format and prevents stale data
        const oldKey = `selected_company_${username}`;
        localStorage.removeItem(oldKey);
        console.log(`[Companies] Cleared old localStorage key: ${oldKey}`);
      }
    };

    return {
      // State
      companies,
      selectedCompany,
      isLoading,
      error,

      // Getters
      companyList,
      companyListFormatted,
      hasCompanies,
      selectedCompanyId,

      // Actions
      loadCompanies,
      setSelectedCompany,
      clearSelectedCompany,
      getCompanyById,
      clearError,
      reset,
      resetWithContext, // US-031: Reset with explicit context for logout
    };
  });
}
