'use client';

// ═══════════════════════════════════════════════════════════════════════
// Dynamic permission system — identical flow to PreviousNcPage:
//   1. GET /modules          → find the module by slug, read button/column config
//   2. GET /user-permissions/user/:id → the actions this user holds
//   3. intersect them        → which columns render, which row buttons appear
//
// If either call fails, we fall back to FALLBACK_COLUMNS + all actions
// permitted, exactly like previous-nc does, so the page never hard-locks.
// ═══════════════════════════════════════════════════════════════════════

import { useCallback, useEffect, useMemo, useState } from 'react';
import { fetchApi } from '@/lib/api/http';

export interface ButtonConfig {
  key: string;
  icon: string;
  color: string;
  label: string;
  order: number;
  position: 'row' | 'toolbar';
}

export interface ColumnConfig {
  key: string;
  type: string;
  label: string;
  order: number;
  sortable: boolean;
  default_visible: boolean;
}

export interface ModuleConfig {
  id: number;
  name: string;
  slug: string;
  button_config: ButtonConfig[];
  column_config: ColumnConfig[];
}

const API_BASE_URL =
  process.env.NEXT_PUBLIC_API_URL || 'http://localhost:3007/api';

export const FALLBACK_COLUMNS: ColumnConfig[] = [
  { key: 'client_code', type: 'text', label: 'Code', order: 1, sortable: true, default_visible: true },
  { key: 'company_name', type: 'text', label: 'Company', order: 2, sortable: true, default_visible: true },
  { key: 'client_type', type: 'custom', label: 'Type', order: 3, sortable: true, default_visible: true },
  { key: 'contact_primary', type: 'text', label: 'Contact', order: 4, sortable: false, default_visible: true },
  { key: 'standard_name', type: 'custom', label: 'Standards', order: 5, sortable: false, default_visible: true },
  { key: 'email_id', type: 'text', label: 'Email', order: 6, sortable: false, default_visible: true },
  { key: 'Address', type: 'text', label: 'Location', order: 7, sortable: false, default_visible: true },
  { key: 'signeddocsname', type: 'custom', label: 'Signed doc', order: 8, sortable: false, default_visible: true },
  { key: 'status', type: 'custom', label: 'Status', order: 9, sortable: true, default_visible: true },
  { key: 'created_at', type: 'date', label: 'Created', order: 10, sortable: true, default_visible: true },
  { key: 'actions', type: 'actions', label: 'Actions', order: 99, sortable: false, default_visible: true },
];

/** Everything a user could possibly do here — used only in fallback mode. */
export const ALL_CLIENT_ACTIONS = [
  'view',
  'view-all',
  'edit',
  'delete',
  'export',
  'audit-request',
  'signed-doc',
];

export interface UseClientsPermissions {
  moduleConfig: ModuleConfig | null;
  permittedActions: Set<string>;
  visibleColumns: ColumnConfig[];
  headerColumns: ColumnConfig[];
  rowButtons: ButtonConfig[];
  hasActionsColumn: boolean;
  useDynamicMode: boolean;
  permissionsLoading: boolean;
  rawUserId: { userId: any; source: string } | null;
  debugLog: string[];
  can: (action: string) => boolean;
}

export function useClientsPermissions(
  slug = 'clients',
  moduleName = 'Clients',
): UseClientsPermissions {
  const [moduleConfig, setModuleConfig] = useState<ModuleConfig | null>(null);
  const [userPermissions, setUserPermissions] = useState<any[]>([]);
  const [permissionsLoading, setPermissionsLoading] = useState(true);
  const [permissionSystemReady, setPermissionSystemReady] = useState(false);
  const [rawUserId, setRawUserId] = useState<{ userId: any; source: string } | null>(null);
  const [debugLog, setDebugLog] = useState<string[]>([]);

  const addDebug = useCallback((msg: string) => {
    console.log(`[CLIENTS-DEBUG] ${msg}`);
    setDebugLog((p) => [...p, `${new Date().toLocaleTimeString()} — ${msg}`]);
  }, []);

  const fetchModuleConfig = useCallback(async (): Promise<boolean> => {
    try {
      const response = await fetchApi<any>(`${API_BASE_URL}/modules`);
      const list = Array.isArray(response)
        ? response
        : response?.data
          ? Array.isArray(response.data)
            ? response.data
            : [response.data]
          : [response];
      const mod = list.find(
        (m: any) => m.slug === slug || m.name === moduleName,
      );
      if (mod) {
        setModuleConfig(mod);
        addDebug(`✅ ${slug} module (id:${mod.id})`);
        return true;
      }
      addDebug(`⚠️ ${slug} module NOT found — FALLBACK`);
      return false;
    } catch (err: any) {
      addDebug(`⚠️ module fetch: ${err.message}`);
      return false;
    }
  }, [addDebug, slug, moduleName]);

  const fetchUserPermissions = useCallback(async (): Promise<boolean> => {
    try {
      let userId: any = null;
      let source = '';
      if (typeof window !== 'undefined') {
        try {
          const s = localStorage.getItem('user');
          if (s) {
            const p = JSON.parse(s);
            userId = p?.id || p?.userId || p?.user_id;
            source = 'localStorage("user")';
          }
        } catch {}
        if (!userId) {
          try {
            const t =
              localStorage.getItem('token') ||
              localStorage.getItem('access_token');
            if (t) {
              const p = JSON.parse(atob(t.split('.')[1]));
              userId = p?.id || p?.userId || p?.sub;
              source = 'JWT';
            }
          } catch {}
        }
      }
      setRawUserId({ userId, source });
      if (!userId) {
        addDebug('⚠️ No userId — FALLBACK');
        setUserPermissions([]);
        return false;
      }
      const res = await fetchApi<any>(
        `${API_BASE_URL}/user-permissions/user/${userId}`,
      );
      const list = Array.isArray(res)
        ? res
        : res?.data
          ? Array.isArray(res.data)
            ? res.data
            : [res.data]
          : (res?.permissions ?? []);
      setUserPermissions(list);
      addDebug(`📦 ${list.length} permissions`);
      return true;
    } catch (err: any) {
      addDebug(`⚠️ perms: ${err.message}`);
      setUserPermissions([]);
      return false;
    }
  }, [addDebug]);

  useEffect(() => {
    const init = async () => {
      setPermissionsLoading(true);
      setDebugLog([]);
      addDebug('🚀 Clients permissions starting...');
      const [moduleOk, permsOk] = await Promise.all([
        fetchModuleConfig(),
        fetchUserPermissions(),
      ]);
      setPermissionSystemReady(moduleOk && permsOk);
      setPermissionsLoading(false);
    };
    init();
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, []);

  const visibleColumns = useMemo((): ColumnConfig[] => {
    if (!moduleConfig?.column_config?.length) return FALLBACK_COLUMNS;
    return [...moduleConfig.column_config].sort(
      (a, b) => (a.order ?? 99) - (b.order ?? 99),
    );
  }, [moduleConfig]);

  const permittedActions = useMemo((): Set<string> => {
    // No module row in the DB → open everything, same as previous-nc.
    if (!moduleConfig) return new Set(ALL_CLIENT_ACTIONS);

    const a = new Set<string>();
    for (const up of userPermissions) {
      const action = up.permission?.action ?? up.action;
      const moduleId =
        up.permission?.module?.id ??
        up.permission?.module_id ??
        up.module?.id ??
        up.module_id;
      if (!action) continue;
      if (moduleId === moduleConfig.id) a.add(action);
    }

    console.log('🎯 CLIENTS ACTIONS:', Array.from(a).join(', ') || '(empty)');
    return a;
  }, [moduleConfig, userPermissions]);

  const rowButtons = useMemo(() => {
    if (!moduleConfig?.button_config) return [];
    return moduleConfig.button_config
      .filter((b) => b.position === 'row' && permittedActions.has(b.key))
      .sort((a, b) => (a.order ?? 99) - (b.order ?? 99));
  }, [moduleConfig, permittedActions]);

  const headerColumns = useMemo(
    () => visibleColumns.filter((c) => c.key !== 'actions'),
    [visibleColumns],
  );

  const hasActionsColumn = useMemo(
    () => visibleColumns.some((c) => c.key === 'actions'),
    [visibleColumns],
  );

  const can = useCallback(
    (action: string) => permittedActions.has(action),
    [permittedActions],
  );

  return {
    moduleConfig,
    permittedActions,
    visibleColumns,
    headerColumns,
    rowButtons,
    hasActionsColumn,
    useDynamicMode: permissionSystemReady && moduleConfig !== null,
    permissionsLoading,
    rawUserId,
    debugLog,
    can,
  };
}
