/**
 * useStore Hook
 * 
 * Manages feature store interactions: loading catalog, activating/deactivating features.
 * After each mutation, refreshes featureStore and dispatches 'features-changed' event
 * so navigation and other components update in real-time.
 */

import { useState, useCallback, useEffect } from 'react';
import {
  fetchStoreFeatures,
  activateStoreFeature,
  deactivateStoreFeature,
  fetchUserMandates,
  fetchSubscriptionInfo,
  type StoreFeature,
  type UserMandate,
  type SubscriptionInfo,
} from '../api/storeApi';
import { useFeatureStore } from '../stores/featureStore';

interface UseStoreReturn {
  features: StoreFeature[];
  mandates: UserMandate[];
  subscriptionInfo: SubscriptionInfo | null;
  loading: boolean;
  actionLoading: string | null;
  error: string | null;
  loadStore: () => Promise<void>;
  loadSubscriptionInfo: (mandateId?: string) => Promise<void>;
  activate: (featureCode: string, mandateId?: string) => Promise<void>;
  deactivate: (featureCode: string, mandateId: string, instanceId: string) => Promise<void>;
}

export function useStore(): UseStoreReturn {
  const [features, setFeatures] = useState<StoreFeature[]>([]);
  const [mandates, setMandates] = useState<UserMandate[]>([]);
  const [subscriptionInfo, setSubscriptionInfo] = useState<SubscriptionInfo | null>(null);
  const [loading, setLoading] = useState(true);
  const [actionLoading, setActionLoading] = useState<string | null>(null);
  const [error, setError] = useState<string | null>(null);
  const featureStore = useFeatureStore();

  const loadSubscriptionInfo = useCallback(async (mandateId?: string) => {
    try {
      const info = await fetchSubscriptionInfo(mandateId);
      setSubscriptionInfo(info);
    } catch {
      // non-critical
    }
  }, []);

  const loadStore = useCallback(async () => {
    setLoading(true);
    setError(null);
    try {
      const [data, userMandates] = await Promise.all([
        fetchStoreFeatures(),
        fetchUserMandates(),
      ]);
      setFeatures(data);
      setMandates(userMandates);
      const firstMandateId = userMandates.length > 0 ? userMandates[0].id : undefined;
      await loadSubscriptionInfo(firstMandateId);
    } catch (err: unknown) {
      const msg = err instanceof Error ? err.message : 'Failed to load store';
      setError(msg);
    } finally {
      setLoading(false);
    }
  }, [loadSubscriptionInfo]);

  useEffect(() => {
    loadStore();
  }, [loadStore]);

  const _refreshAfterAction = useCallback(async () => {
    await featureStore.loadFeatures();
    window.dispatchEvent(new CustomEvent('features-changed'));
    await loadStore();
  }, [featureStore, loadStore]);

  const activate = useCallback(async (featureCode: string, mandateId?: string) => {
    setActionLoading(featureCode);
    setError(null);
    try {
      await activateStoreFeature(featureCode, mandateId);
      await _refreshAfterAction();
    } catch (err: unknown) {
      const msg = err instanceof Error ? err.message : 'Activation failed';
      setError(msg);
    } finally {
      setActionLoading(null);
    }
  }, [_refreshAfterAction]);

  const deactivate = useCallback(async (featureCode: string, mandateId: string, instanceId: string) => {
    setActionLoading(featureCode);
    setError(null);
    try {
      await deactivateStoreFeature(featureCode, mandateId, instanceId);
      await _refreshAfterAction();
    } catch (err: unknown) {
      const msg = err instanceof Error ? err.message : 'Deactivation failed';
      setError(msg);
    } finally {
      setActionLoading(null);
    }
  }, [_refreshAfterAction]);

  return { features, mandates, subscriptionInfo, loading, actionLoading, error, loadStore, loadSubscriptionInfo, activate, deactivate };
}

export default useStore;
