'use client';

import { useState, useCallback, useEffect, useMemo, useRef } from 'react';
import { useRouter } from 'next/navigation';
import Image from 'next/image';
import DataTable, { Column } from '@/components/ui/DataTable';
import Pagination from '@/components/ui/Pagination';
import FilterPanel from '@/components/ui/FilterPanel';
import Toolbar from '@/components/ui/Toolbar';
import Modal from '@/components/ui/CustomModal';
import CommonTimelineModal from '@/components/ui/CommonTimelineModal'; // ✅ Changed to CommonTimelineModal
import { toast } from 'react-hot-toast';
import { getApiErrorMessage } from '@/lib/utils/apiError';
import { useCurrencyStore } from '@/store/currencyStore';
import { 
  ArchiveRestore, History, SquarePen, Trash2, Check, X, 
  Package, Layers, Image as ImageIcon 
} from 'lucide-react';

// ─── Types ────────────────────────────────────────────────────────────────────

interface Product {
  id: string;
  sku: string;
  type: 'simple' | 'variable';
  price: number;
  compare_price: number | null;
  stock_quantity: number;
  stock_status: 'in_stock' | 'out_of_stock' | 'backorder';
  is_active: boolean;
  is_featured: boolean;
  default_name: string;
  translations_count: number;
  variations_count: number;
  has_image: boolean;
  category_name: string | null;
  deleted_at: string | null;
  created_at: string;
  updated_at: string;
}

interface PaginationData {
  page: number;
  limit: number;
  total: number;
  totalPages: number;
}

interface TabCounts {
  active: number;
  deleted: number;
}

interface Category {
  id: string;
  default_name: string;
}

interface ProductsTableProps {
  canEdit: boolean;
  canDelete: boolean;
  canBulkDelete: boolean;
  canViewDeleted: boolean;
  canPermanentDelete: boolean;
  canRestore: boolean;
  canBulkRestore: boolean;
  canViewTimeline: boolean;
  canActivateDeactivate: boolean;
  initialProducts: {
    products: Product[];
    pagination: PaginationData;
  };
  initialCounts: TabCounts;
  categories: Category[];
}

type TabType = 'active' | 'deleted';

interface ActiveFilters {
  search: string;
  category_id: string;
  type: string;
  status: string;
  min_price: string;
  max_price: string;
  startDate: string;
  endDate: string;
}

interface DeletedFilters {
  search: string;
  category_id: string;
  startDate: string;
  endDate: string;
}

interface ModalConfig {
  isOpen: boolean;
  type: 'danger' | 'warning' | 'info' | 'success';
  title: string;
  message: string;
  confirmText?: string;
  cancelText?: string;
  onConfirm: () => void;
}

// ─── Constants ────────────────────────────────────────────────────────────────

const ICON_STROKE = { fill: 'none', stroke: 'currentColor', strokeWidth: 2 } as const;

const EMPTY_ACTIVE_FILTERS: ActiveFilters = { 
  search: '', 
  category_id: '', 
  type: '', 
  status: '',
  min_price: '',
  max_price: '',
  startDate: '', 
  endDate: '' 
};

const EMPTY_DELETED_FILTERS: DeletedFilters = { 
  search: '', 
  category_id: '',
  startDate: '', 
  endDate: '' 
};

const MODAL_CLOSED: ModalConfig = {
  isOpen: false, 
  type: 'danger', 
  title: '', 
  message: '',
  confirmText: 'Confirm', 
  cancelText: 'Cancel', 
  onConfirm: () => {},
};

// ─── API Helpers ──────────────────────────────────────────────────────────────

async function fetchProductsApi(
  page: number,
  tab: TabType,
  active: ActiveFilters,
  deleted: DeletedFilters,
  signal: AbortSignal,
) {
  const params = new URLSearchParams({
    page: String(page),
    limit: '10',
    includeDeleted: tab === 'deleted' ? 'true' : 'false',
  });

  if (tab === 'deleted') {
    if (deleted.search.trim()) params.append('search', deleted.search.trim());
    if (deleted.category_id) params.append('category_id', deleted.category_id);
    if (deleted.startDate) params.append('deletedStartDate', deleted.startDate);
    if (deleted.endDate) params.append('deletedEndDate', deleted.endDate);
  } else {
    if (active.search.trim()) params.append('search', active.search.trim());
    if (active.category_id) params.append('category_id', active.category_id);
    if (active.type) params.append('type', active.type);
    if (active.status) params.append('status', active.status);
    if (active.min_price) params.append('min_price', active.min_price);
    if (active.max_price) params.append('max_price', active.max_price);
    if (active.startDate) params.append('startDate', active.startDate);
    if (active.endDate) params.append('endDate', active.endDate);
  }

  const res = await fetch(`/api/products?${params}`, { cache: 'no-store', signal });
  if (!res.ok) throw new Error('Failed to fetch products');
  return res.json() as Promise<{ data: { products: Product[]; pagination: PaginationData } }>;
}

async function fetchCountsApi(): Promise<TabCounts> {
  const res = await fetch('/api/products/counts', { cache: 'no-store' });
  if (!res.ok) throw new Error('Failed to fetch counts');
  const json = await res.json();
  return json.data as TabCounts;
}

// ─── Sub-components ───────────────────────────────────────────────────────────

function StatusBadge({ product }: { product: Product }) {
  if (product.deleted_at) {
    return (
      <span className="inline-flex px-2 py-1 text-xs font-medium rounded-full" style={{
        background: 'var(--color-danger-light)',
        color: 'var(--color-danger)',
      }}>
        Deleted
      </span>
    );
  }
  if (!product.is_active) {
    return (
      <span className="inline-flex px-2 py-1 text-xs font-medium rounded-full" style={{
        background: 'var(--color-warning-light)',
        color: 'var(--color-warning)',
      }}>
        Inactive
      </span>
    );
  }
  return (
    <span className="inline-flex px-2 py-1 text-xs font-medium rounded-full" style={{
      background: 'var(--color-success-light)',
      color: 'var(--color-success)',
    }}>
      Active
    </span>
  );
}

function StockBadge({ product }: { product: Product }) {
  const styles = {
    in_stock: {
      background: 'var(--color-success-light)',
      color: 'var(--color-success)',
    },
    out_of_stock: {
      background: 'var(--color-danger-light)',
      color: 'var(--color-danger)',
    },
    backorder: {
      background: 'var(--color-warning-light)',
      color: 'var(--color-warning)',
    },
  };

  const labels = {
    in_stock: 'In Stock',
    out_of_stock: 'Out of Stock',
    backorder: 'Backorder',
  };

  const style = styles[product.stock_status] || styles.out_of_stock;
  
  return (
    <span className="inline-flex px-2 py-1 text-xs font-medium rounded-full" style={style}>
      {labels[product.stock_status]} ({product.stock_quantity})
    </span>
  );
}

function ProductImage({ hasImage }: { hasImage: boolean }) {
  if (hasImage) {
    return (
      <div className="w-12 h-12 rounded-lg overflow-hidden flex items-center justify-center" style={{
        background: 'var(--color-surface-alt)',
      }}>
        <ImageIcon size={20} style={{ color: 'var(--color-text-tertiary)' }} />
      </div>
    );
  }
  
  return (
    <div className="w-12 h-12 rounded-lg flex items-center justify-center" style={{
      background: 'var(--color-surface-alt)',
      color: 'var(--color-text-tertiary)',
    }}>
      <Package size={20} />
    </div>
  );
}

function TypeBadge({ type }: { type: string }) {
  if (type === 'variable') {
    return (
      <span className="inline-flex items-center gap-1 px-2 py-1 text-xs font-medium rounded-full" style={{
        background: 'var(--color-info-light)',
        color: 'var(--color-info)',
      }}>
        <Layers size={12} />
        Variable
      </span>
    );
  }
  return (
    <span className="inline-flex items-center gap-1 px-2 py-1 text-xs font-medium rounded-full" style={{
      background: 'var(--color-surface-alt)',
      color: 'var(--color-text-tertiary)',
    }}>
      <Package size={12} />
      Simple
    </span>
  );
}

function PriceDisplay({ price, comparePrice }: { price: number; comparePrice: number | null }) {
  const formatAmount = useCurrencyStore((s) => s.formatAmount);

  if (comparePrice && comparePrice > price) {
    return (
      <div className="flex flex-col">
        <span className="text-sm font-medium" style={{ color: 'var(--color-text)' }}>
          {formatAmount(price)}
        </span>
        <span className="text-xs line-through" style={{ color: 'var(--color-text-tertiary)' }}>
          {formatAmount(comparePrice)}
        </span>
      </div>
    );
  }
  return (
    <span className="text-sm font-medium" style={{ color: 'var(--color-text)' }}>
      {formatAmount(price)}
    </span>
  );
}

// ─── Main Component ───────────────────────────────────────────────────────────

export default function ProductsTable({
  canEdit,
  canDelete,
  canBulkDelete,
  canViewDeleted,
  canPermanentDelete,
  canRestore,
  canBulkRestore,
  canViewTimeline,
  canActivateDeactivate,
  initialProducts,
  initialCounts,
  categories,
}: ProductsTableProps) {
  const router = useRouter();

  // ── Core state ────────────────────────────────────────────────────────────
  const [products, setProducts] = useState<Product[]>(initialProducts.products);
  const [pagination, setPagination] = useState<PaginationData>(initialProducts.pagination);
  const [counts, setCounts] = useState<TabCounts>(initialCounts);
  const [currentPage, setCurrentPage] = useState(1);
  const [loading, setLoading] = useState(false);
  const [activeTab, setActiveTab] = useState<TabType>('active');
  const [selectedIds, setSelectedIds] = useState<Set<string>>(new Set());
  const [showFilters, setShowFilters] = useState(false);
  const [isDeleting, setIsDeleting] = useState(false);
  const [modal, setModal] = useState<ModalConfig>(MODAL_CLOSED);

  // ── Timeline state ──────────────────────────────────────────────────────
  // ✅ Changed to match Categories pattern
  const [timelineModal, setTimelineModal] = useState<{
    isOpen: boolean;
    productId: string;
    productName: string;
  }>({
    isOpen: false,
    productId: '',
    productName: '',
  });

  // ── Committed filters ─────────────────────────────────────────────────────
  const [activeFilters, setActiveFilters] = useState<ActiveFilters>(EMPTY_ACTIVE_FILTERS);
  const [deletedFilters, setDeletedFilters] = useState<DeletedFilters>(EMPTY_DELETED_FILTERS);

  // ── Draft filters ─────────────────────────────────────────────────────────
  const [draftActive, setDraftActive] = useState<ActiveFilters>(EMPTY_ACTIVE_FILTERS);
  const [draftDeleted, setDraftDeleted] = useState<DeletedFilters>(EMPTY_DELETED_FILTERS);

  // ── Refs ──────────────────────────────────────────────────────────────────
  const abortRef = useRef<AbortController | null>(null);
  const productsRef = useRef(products);
  const selectedRef = useRef(selectedIds);

  useEffect(() => { productsRef.current = products; }, [products]);
  useEffect(() => { selectedRef.current = selectedIds; }, [selectedIds]);
  useEffect(() => () => abortRef.current?.abort(), []);

  // ── Category options for filter ──────────────────────────────────────────
  const categoryOptions = useMemo(() => {
    return [
      { value: '', label: 'All Categories' },
      ...categories.map(cat => ({
        value: cat.id,
        label: cat.default_name || 'Unnamed Category',
      })),
    ];
  }, [categories]);

  // ── Fetch functions ──────────────────────────────────────────────────────
  const fetchProducts = useCallback(async (
    page: number,
    tab: TabType,
    committed: { active: ActiveFilters; deleted: DeletedFilters },
  ) => {
    abortRef.current?.abort();
    const ctrl = new AbortController();
    abortRef.current = ctrl;

    setLoading(true);
    try {
      const json = await fetchProductsApi(page, tab, committed.active, committed.deleted, ctrl.signal);
      setProducts(json.data.products);
      setPagination(json.data.pagination);
      setCurrentPage(page);
      setSelectedIds(new Set());
    } catch (err) {
      if ((err as Error).name === 'AbortError') return;
      console.error('Failed to fetch products:', err);
      toast.error('Failed to load products');
    } finally {
      if (abortRef.current === ctrl) setLoading(false);
    }
  }, []);

  const refreshCounts = useCallback(async () => {
    try {
      const updated = await fetchCountsApi();
      setCounts(updated);
    } catch {
      console.warn('Could not refresh product counts');
    }
  }, []);

  const refreshAfterMutation = useCallback(async (
    tab: TabType,
    committed: { active: ActiveFilters; deleted: DeletedFilters },
    page: number,
  ) => {
    await Promise.all([
      fetchProducts(page, tab, committed),
      refreshCounts(),
    ]);
  }, [fetchProducts, refreshCounts]);

  // ── Modal helpers ─────────────────────────────────────────────────────────
  const closeModal = useCallback(() => {
    if (!isDeleting) setModal(MODAL_CLOSED);
  }, [isDeleting]);

  const openModal = useCallback((config: Omit<ModalConfig, 'isOpen'>) => {
    setModal({ isOpen: true, ...config });
  }, []);

  // ── Timeline handlers ─────────────────────────────────────────────────────
  // ✅ Simplified to match Categories pattern
  const handleTimelineClick = useCallback((product: Product) => {
    setTimelineModal({
      isOpen: true,
      productId: product.id,
      productName: product.default_name || 'Product',
    });
  }, []);

  // ── Status Change Handler ──────────────────────────────────────────────────
  const handleStatusChange = useCallback(async (id: string, action: 'activate' | 'deactivate') => {
    setIsDeleting(true);
    try {
      const newStatus = action === 'activate' ? 1 : 0;
      const res = await fetch(`/api/products/${id}/status`, {
        method: 'PATCH',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ is_active: newStatus })
      });
      
      if (res.ok) {
        setModal(MODAL_CLOSED);
        await refreshAfterMutation(activeTab, { active: activeFilters, deleted: deletedFilters }, currentPage);
        toast.success(`Product ${action}d successfully`);
      } else {
        const data = await res.json();
        toast.error(getApiErrorMessage(data, `Failed to ${action} product`));
      }
    } catch { toast.error('Network error — please try again'); }
    finally { setIsDeleting(false); }
  }, [refreshAfterMutation, activeTab, activeFilters, deletedFilters, currentPage]);

  // ── CRUD operations ───────────────────────────────────────────────────────

  const handleRestoreProduct = useCallback(async (id: string) => {
    setIsDeleting(true);
    try {
      const res = await fetch(`/api/products/${id}/restore`, { method: 'POST' });
      if (res.ok) {
        setModal(MODAL_CLOSED);
        await refreshAfterMutation(activeTab, { active: activeFilters, deleted: deletedFilters }, currentPage);
        toast.success('Product restored successfully');
      } else {
        toast.error((await res.json()).message || 'Failed to restore product');
      }
    } catch { toast.error('Network error — please try again'); }
    finally { setIsDeleting(false); }
  }, [refreshAfterMutation, activeTab, activeFilters, deletedFilters, currentPage]);

  const handleBulkRestore = useCallback(async () => {
    setIsDeleting(true);
    try {
      const res = await fetch('/api/products/bulk/restore', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ ids: Array.from(selectedRef.current) }),
      });
      if (res.ok) {
        setModal(MODAL_CLOSED);
        await refreshAfterMutation(activeTab, { active: activeFilters, deleted: deletedFilters }, currentPage);
        toast.success('Products restored successfully');
      } else {
        toast.error((await res.json()).message || 'Failed to restore products');
      }
    } catch { toast.error('Network error — please try again'); }
    finally { setIsDeleting(false); }
  }, [refreshAfterMutation, activeTab, activeFilters, deletedFilters, currentPage]);

  const handlePermanentDelete = useCallback(async (id: string) => {
    setIsDeleting(true);
    try {
      const res = await fetch(`/api/products/${id}/permanent`, { method: 'DELETE' });
      if (res.ok) {
        setModal(MODAL_CLOSED);
        await refreshAfterMutation(activeTab, { active: activeFilters, deleted: deletedFilters }, currentPage);
        toast.success('Product permanently deleted');
      } else {
        toast.error((await res.json()).message || 'Failed to delete product');
      }
    } catch { toast.error('Network error — please try again'); }
    finally { setIsDeleting(false); }
  }, [refreshAfterMutation, activeTab, activeFilters, deletedFilters, currentPage]);

  const handleBulkPermanentDelete = useCallback(async () => {
    setIsDeleting(true);
    try {
      const res = await fetch('/api/products/bulk/permanent', {
        method: 'DELETE',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ ids: Array.from(selectedRef.current) }),
      });
      if (res.ok) {
        setModal(MODAL_CLOSED);
        await refreshAfterMutation(activeTab, { active: activeFilters, deleted: deletedFilters }, currentPage);
        toast.success('Products permanently deleted');
      } else {
        toast.error((await res.json()).message || 'Failed to delete products');
      }
    } catch { toast.error('Network error — please try again'); }
    finally { setIsDeleting(false); }
  }, [refreshAfterMutation, activeTab, activeFilters, deletedFilters, currentPage]);

  const handleDeleteProduct = useCallback(async (id: string) => {
    setIsDeleting(true);
    try {
      const res = await fetch(`/api/products/${id}`, { method: 'DELETE' });
      if (res.ok) {
        setModal(MODAL_CLOSED);
        await refreshAfterMutation(activeTab, { active: activeFilters, deleted: deletedFilters }, currentPage);
        toast.success('Product deleted successfully');
      } else {
        const data = await res.json();
        toast.error(getApiErrorMessage(data, 'Failed to delete product'));
      }
    } catch { toast.error('Network error — please try again'); }
    finally { setIsDeleting(false); }
  }, [refreshAfterMutation, activeTab, activeFilters, deletedFilters, currentPage]);

  const handleBulkDelete = useCallback(async () => {
    setIsDeleting(true);
    try {
      const res = await fetch('/api/products/bulk', {
        method: 'DELETE',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ ids: Array.from(selectedRef.current) }),
      });
      if (res.ok) {
        setModal(MODAL_CLOSED);
        await refreshAfterMutation(activeTab, { active: activeFilters, deleted: deletedFilters }, currentPage);
        toast.success('Products deleted successfully');
      } else {
        toast.error((await res.json()).message || 'Failed to delete products');
      }
    } catch { toast.error('Network error — please try again'); }
    finally { setIsDeleting(false); }
  }, [refreshAfterMutation, activeTab, activeFilters, deletedFilters, currentPage]);

  // ── Action handlers ───────────────────────────────────────────────────────

  const handleEditClick = useCallback((id: string) => {
    router.push(`/admin/dashboard/products/edit/${id}`);
  }, [router]);

  const handleDeleteClick = useCallback((product: Product) => {
    if (activeTab === 'deleted') {
      openModal({
        type: 'danger',
        title: 'Permanent Delete Product',
        message: `Are you sure you want to permanently delete "${product.default_name}"? This cannot be undone.`,
        confirmText: 'Permanently Delete',
        cancelText: 'Cancel',
        onConfirm: () => handlePermanentDelete(product.id),
      });
      return;
    }

    openModal({
      type: 'danger',
      title: 'Delete Product',
      message: `Are you sure you want to delete "${product.default_name}"? It will move to deleted items.`,
      confirmText: 'Delete',
      cancelText: 'Cancel',
      onConfirm: () => handleDeleteProduct(product.id),
    });
  }, [activeTab, handleDeleteProduct, handlePermanentDelete, openModal]);

  const handleRestoreClick = useCallback((product: Product) => {
    openModal({
      type: 'info',
      title: 'Restore Product',
      message: `Restore "${product.default_name}"?`,
      confirmText: 'Restore',
      cancelText: 'Cancel',
      onConfirm: () => handleRestoreProduct(product.id),
    });
  }, [handleRestoreProduct, openModal]);

  const handleActivateClick = useCallback((product: Product) => {
    openModal({
      type: 'success',
      title: 'Activate Product',
      message: `Activate "${product.default_name}"?`,
      confirmText: 'Activate',
      cancelText: 'Cancel',
      onConfirm: () => handleStatusChange(product.id, 'activate'),
    });
  }, [handleStatusChange, openModal]);

  const handleDeactivateClick = useCallback((product: Product) => {
    openModal({
      type: 'warning',
      title: 'Deactivate Product',
      message: `Deactivate "${product.default_name}"?`,
      confirmText: 'Deactivate',
      cancelText: 'Cancel',
      onConfirm: () => handleStatusChange(product.id, 'deactivate'),
    });
  }, [handleStatusChange, openModal]);

  // ── Bulk actions ──────────────────────────────────────────────────────────

  const showBulkDeleteConfirmation = useCallback(() => {
    if (activeTab === 'deleted') {
      openModal({
        type: 'danger',
        title: 'Permanent Bulk Delete',
        message: `Permanently delete ${selectedRef.current.size} product(s)? This cannot be undone.`,
        confirmText: 'Permanently Delete All',
        cancelText: 'Cancel',
        onConfirm: handleBulkPermanentDelete,
      });
      return;
    }

    openModal({
      type: 'danger',
      title: 'Bulk Delete Products',
      message: `Delete ${selectedRef.current.size} product(s)? They will move to deleted items.`,
      confirmText: 'Delete All',
      cancelText: 'Cancel',
      onConfirm: handleBulkDelete,
    });
  }, [activeTab, handleBulkDelete, handleBulkPermanentDelete, openModal]);

  const showBulkRestoreConfirmation = useCallback(() => {
    openModal({
      type: 'info',
      title: 'Bulk Restore Products',
      message: `Restore ${selectedRef.current.size} product(s)?`,
      confirmText: 'Restore All',
      cancelText: 'Cancel',
      onConfirm: handleBulkRestore,
    });
  }, [handleBulkRestore, openModal]);

  // ── Tab change ────────────────────────────────────────────────────────────
  const handleTabChange = useCallback((tab: TabType) => {
    setActiveTab(tab);
    setShowFilters(false);
    const freshActive = EMPTY_ACTIVE_FILTERS;
    const freshDeleted = EMPTY_DELETED_FILTERS;
    setActiveFilters(freshActive);
    setDeletedFilters(freshDeleted);
    setDraftActive(freshActive);
    setDraftDeleted(freshDeleted);
    fetchProducts(1, tab, { active: freshActive, deleted: freshDeleted });
  }, [fetchProducts]);

  // ── Filter panel ──────────────────────────────────────────────────────────
  const handleToggleFilters = useCallback(() => {
    setShowFilters(prev => {
      if (!prev) {
        setDraftActive({ ...activeFilters });
        setDraftDeleted({ ...deletedFilters });
      }
      return !prev;
    });
  }, [activeFilters, deletedFilters]);

  const handleApplyFilters = useCallback(() => {
    if (activeTab === 'deleted') {
      setDeletedFilters(draftDeleted);
      fetchProducts(1, activeTab, { active: activeFilters, deleted: draftDeleted });
    } else {
      setActiveFilters(draftActive);
      fetchProducts(1, activeTab, { active: draftActive, deleted: deletedFilters });
    }
    setShowFilters(false);
  }, [activeTab, draftActive, draftDeleted, activeFilters, deletedFilters, fetchProducts]);

  const handleResetFilters = useCallback(() => {
    if (activeTab === 'deleted') {
      setDraftDeleted(EMPTY_DELETED_FILTERS);
      setDeletedFilters(EMPTY_DELETED_FILTERS);
      fetchProducts(1, activeTab, { active: activeFilters, deleted: EMPTY_DELETED_FILTERS });
    } else {
      setDraftActive(EMPTY_ACTIVE_FILTERS);
      setActiveFilters(EMPTY_ACTIVE_FILTERS);
      fetchProducts(1, activeTab, { active: EMPTY_ACTIVE_FILTERS, deleted: deletedFilters });
    }
    setShowFilters(false);
  }, [activeTab, activeFilters, deletedFilters, fetchProducts]);

  // ── Pagination ────────────────────────────────────────────────────────────
  const handlePageChange = useCallback((page: number) => {
    if (page < 1 || page > pagination.totalPages) return;
    fetchProducts(page, activeTab, { active: activeFilters, deleted: deletedFilters });
  }, [pagination.totalPages, fetchProducts, activeTab, activeFilters, deletedFilters]);

  // ── Selection ─────────────────────────────────────────────────────────────
  const handleSelectAll = useCallback(() => {
    setSelectedIds(prev =>
      prev.size === productsRef.current.length
        ? new Set()
        : new Set(productsRef.current.map(r => r.id)),
    );
  }, []);

  const handleSelectProduct = useCallback((id: string) => {
    setSelectedIds(prev => {
      const next = new Set(prev);
      if (next.has(id)) { next.delete(id); } else { next.add(id); }
      return next;
    });
  }, []);

  // ── Columns ───────────────────────────────────────────────────────────────
  const columns = useMemo<Column<Product>[]>(() => {
    const cols: Column<Product>[] = [
      {
        key: 'product',
        header: 'Product',
        render: (product) => (
          <div className="flex items-center gap-3">
            <ProductImage hasImage={product.has_image} />
            <div>
              <div className="font-medium" style={{ color: 'var(--color-text)' }}>
                {product.default_name}
              </div>
              <div className="text-xs flex items-center gap-2" style={{ color: 'var(--color-text-tertiary)' }}>
                <span>SKU: {product.sku}</span>
                <span>ID: {product.id.substring(0, 8)}...</span>
                {product.category_name && (
                  <span className="px-1.5 py-0.5 rounded" style={{
                    background: 'var(--color-surface-alt)',
                  }}>
                    {product.category_name}
                  </span>
                )}
              </div>
            </div>
          </div>
        ),
      },
      {
        key: 'type',
        header: 'Type',
        render: (product) => <TypeBadge type={product.type} />,
      },
      {
        key: 'price',
        header: 'Price',
        render: (product) => <PriceDisplay price={product.price} comparePrice={product.compare_price} />,
      },
      {
        key: 'stock',
        header: 'Stock',
        render: (product) => <StockBadge product={product} />,
      },
      {
        key: 'variations',
        header: 'Variations',
        render: (product) => (
          <span className="text-sm" style={{ color: 'var(--color-text-secondary)' }}>
            {product.variations_count || '-'}
          </span>
        ),
      },
      {
        key: 'status',
        header: 'Status',
        render: (product) => <StatusBadge product={product} />,
      },
    ];

    if (activeTab === 'deleted') {
      cols.push({
        key: 'deleted_at',
        header: 'Deleted At',
        render: (product) => (
          <span style={{ color: 'var(--color-text-tertiary)' }}>
            {product.deleted_at ? new Date(product.deleted_at).toLocaleDateString() : '-'}
          </span>
        ),
      });
    }

    cols.push({
      key: 'actions',
      header: 'Actions',
      className: 'text-right',
      render: (product) => {
        const actions: React.ReactNode[] = [];

        // Timeline button
        if (canViewTimeline) {
          actions.push(
            <button
              key="timeline"
              onClick={() => handleTimelineClick(product)}
              className="p-1 rounded hover:bg-surface-alt transition-colors"
              style={{ color: 'var(--color-text-secondary)' }}
              title="View Timeline"
            >
              <History size={16} />
            </button>,
          );
        }

        if (activeTab === 'deleted') {
          if (canRestore) actions.push(
            <button
              key="restore"
              onClick={() => handleRestoreClick(product)}
              className="p-1 rounded hover:bg-surface-alt transition-colors"
              style={{ color: 'var(--color-success)' }}
              title="Restore Product"
            >
              <ArchiveRestore size={16} />
            </button>,
          );
          if (canPermanentDelete) actions.push(
            <button
              key="perm-del"
              onClick={() => handleDeleteClick(product)}
              className="p-1 rounded hover:bg-surface-alt transition-colors"
              style={{ color: 'var(--color-danger)' }}
              title="Permanently Delete"
            >
              <Trash2 size={16} />
            </button>,
          );
        } else {
          // Activate/Deactivate buttons
          if (canActivateDeactivate) {
            if (product.is_active) {
              actions.push(
                <button
                  key="deactivate"
                  onClick={() => handleDeactivateClick(product)}
                  className="p-1 rounded hover:bg-surface-alt transition-colors"
                  style={{ color: 'var(--color-warning)' }}
                  title="Deactivate Product"
                >
                  <X size={16} />
                </button>
              );
            } else if (!product.deleted_at) {
              actions.push(
                <button
                  key="activate"
                  onClick={() => handleActivateClick(product)}
                  className="p-1 rounded hover:bg-surface-alt transition-colors"
                  style={{ color: 'var(--color-success)' }}
                  title="Activate Product"
                >
                  <Check size={16} />
                </button>
              );
            }
          }

          if (canEdit) actions.push(
            <button
              key="edit"
              onClick={() => handleEditClick(product.id)}
              className="p-1 rounded hover:bg-surface-alt transition-colors"
              style={{ color: 'var(--color-info)' }}
              title="Edit Product"
            >
              <SquarePen size={16} />
            </button>,
          );

          if (canDelete) {
            actions.push(
              <button
                key="delete"
                onClick={() => handleDeleteClick(product)}
                className="p-1 rounded hover:bg-surface-alt transition-colors"
                style={{ color: 'var(--color-danger)' }}
                title="Delete"
              >
                <Trash2 size={16} />
              </button>
            );
          }
        }

        return <div className="flex justify-end gap-2">{actions}</div>;
      },
    });

    return cols;
  }, [
    activeTab, canEdit, canDelete, canPermanentDelete, canRestore,
    canViewTimeline, canActivateDeactivate,
    handleEditClick, handleDeleteClick, handleRestoreClick,
    handleTimelineClick, handleActivateClick, handleDeactivateClick,
  ]);

  // ── Filter fields ─────────────────────────────────────────────────────────
  const filterFields = useMemo(() => {
    const baseFields = [
      {
        name: 'category_id',
        label: 'Category',
        type: 'select' as const,
        options: categoryOptions,
        value: activeTab === 'deleted' ? draftDeleted.category_id : draftActive.category_id,
        onChange: (v: string) => {
          if (activeTab === 'deleted') {
            setDraftDeleted(p => ({ ...p, category_id: v }));
          } else {
            setDraftActive(p => ({ ...p, category_id: v }));
          }
        },
      },
    ];

    if (activeTab === 'deleted') {
      return [
        ...baseFields,
        {
          name: 'deletedSearch',
          label: 'Search',
          type: 'text' as const,
          placeholder: 'Search by name or SKU...',
          value: draftDeleted.search,
          onChange: (v: string) => setDraftDeleted(p => ({ ...p, search: v })),
        },
        {
          name: 'deletedStartDate',
          label: 'Deleted From',
          type: 'date' as const,
          value: draftDeleted.startDate,
          onChange: (v: string) => setDraftDeleted(p => ({ ...p, startDate: v })),
        },
        {
          name: 'deletedEndDate',
          label: 'Deleted To',
          type: 'date' as const,
          value: draftDeleted.endDate,
          onChange: (v: string) => setDraftDeleted(p => ({ ...p, endDate: v })),
        },
      ];
    }
    
    return [
      ...baseFields,
      {
        name: 'search',
        label: 'Search',
        type: 'text' as const,
        placeholder: 'Search by name or SKU...',
        value: draftActive.search,
        onChange: (v: string) => setDraftActive(p => ({ ...p, search: v })),
      },
      {
        name: 'type',
        label: 'Product Type',
        type: 'select' as const,
        options: [
          { value: '', label: 'All Types' },
          { value: 'simple', label: 'Simple' },
          { value: 'variable', label: 'Variable' },
        ],
        value: draftActive.type,
        onChange: (v: string) => setDraftActive(p => ({ ...p, type: v })),
      },
      {
        name: 'status',
        label: 'Status',
        type: 'select' as const,
        options: [
          { value: '', label: 'All Status' },
          { value: 'active', label: 'Active' },
          { value: 'inactive', label: 'Inactive' },
        ],
        value: draftActive.status,
        onChange: (v: string) => setDraftActive(p => ({ ...p, status: v })),
      },
      {
        name: 'min_price',
        label: 'Min Price',
        type: 'number' as const,
        placeholder: '0.00',
        value: draftActive.min_price,
        onChange: (v: string) => setDraftActive(p => ({ ...p, min_price: v })),
      },
      {
        name: 'max_price',
        label: 'Max Price',
        type: 'number' as const,
        placeholder: '999.99',
        value: draftActive.max_price,
        onChange: (v: string) => setDraftActive(p => ({ ...p, max_price: v })),
      },
      {
        name: 'startDate',
        label: 'Created From',
        type: 'date' as const,
        value: draftActive.startDate,
        onChange: (v: string) => setDraftActive(p => ({ ...p, startDate: v })),
      },
      {
        name: 'endDate',
        label: 'Created To',
        type: 'date' as const,
        value: draftActive.endDate,
        onChange: (v: string) => setDraftActive(p => ({ ...p, endDate: v })),
      },
    ];
  }, [activeTab, draftActive, draftDeleted, categoryOptions]);

  // ── Bulk action bar ───────────────────────────────────────────────────────
  const bulkActionBar = useMemo(() => {
    if (selectedIds.size === 0) return null;

    if (activeTab === 'deleted') {
      return (
        <div className="flex gap-2">
          {canBulkRestore && (
            <button
              onClick={showBulkRestoreConfirmation}
              className="inline-flex items-center gap-2 px-4 py-2 rounded-lg text-sm font-medium"
              style={{ background: 'var(--color-success)', color: 'white' }}
            >
              <svg width="16" height="16" {...ICON_STROKE}>
                <path d="M3 12a9 9 0 1 0 9-9m0 0v6m0-6h-6"/><path d="M21 12a9 9 0 1 1-9-9"/>
              </svg>
              Restore ({selectedIds.size})
            </button>
          )}
          {canPermanentDelete && (
            <button
              onClick={showBulkDeleteConfirmation}
              className="inline-flex items-center gap-2 px-4 py-2 rounded-lg text-sm font-medium"
              style={{ background: 'var(--color-danger)', color: 'white' }}
            >
              <svg width="16" height="16" {...ICON_STROKE}>
                <path d="M3 6h18M19 6v14a2 2 0 0 1-2 2H7a2 2 0 0 1-2-2V6m3 0V4a2 2 0 0 1 2-2h4a2 2 0 0 1 2 2v2"/>
              </svg>
              Permanently Delete ({selectedIds.size})
            </button>
          )}
        </div>
      );
    }
    
    if (canBulkDelete) {
      return (
        <button
          onClick={showBulkDeleteConfirmation}
          className="inline-flex items-center gap-2 px-4 py-2 rounded-lg text-sm font-medium"
          style={{ background: 'var(--color-danger)', color: 'white' }}
        >
          <svg width="16" height="16" {...ICON_STROKE}>
            <path d="M3 6h18M19 6v14a2 2 0 0 1-2 2H7a2 2 0 0 1-2-2V6m3 0V4a2 2 0 0 1 2-2h4a2 2 0 0 1 2 2v2"/>
          </svg>
          Delete ({selectedIds.size})
        </button>
      );
    }
    return null;
  }, [
    selectedIds, activeTab,
    canBulkDelete, canBulkRestore, canPermanentDelete,
    showBulkDeleteConfirmation, showBulkRestoreConfirmation,
  ]);

  // ── Render ────────────────────────────────────────────────────────────────
  return (
    <div className="space-y-4">
      {canViewDeleted && (
        <div className="flex border-b overflow-x-auto whitespace-nowrap" style={{ borderColor: 'var(--color-border)' }}>
          <button
            onClick={() => handleTabChange('active')}
            className={`px-4 py-2 text-sm font-medium transition-all border-b-2 ${
              activeTab === 'active'
                ? 'border-blue-500 text-blue-600'
                : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
            }`}
          >
            Active Products ({counts.active})
          </button>
          <button
            onClick={() => handleTabChange('deleted')}
            className={`px-4 py-2 text-sm font-medium transition-all border-b-2 ${
              activeTab === 'deleted'
                ? 'border-red-500 text-red-600'
                : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
            }`}
          >
            Deleted Products ({counts.deleted})
          </button>
        </div>
      )}

      <Toolbar
        leftActions={
          <>
            <button
              onClick={handleToggleFilters}
              className="inline-flex items-center gap-2 px-4 py-2 rounded-lg text-sm font-medium transition-all border"
              style={{
                borderColor: 'var(--color-border)',
                color: 'var(--color-text)',
                background: 'var(--color-surface)'
              }}
            >
              <svg width="16" height="16" {...ICON_STROKE}>
                <path d="M3 6h18M6 12h12M10 18h4"/>
              </svg>
              {showFilters ? 'Hide Filters' : 'Show Filters'}
            </button>
            {bulkActionBar}
          </>
        }
      />

      {showFilters && (
        <FilterPanel
          fields={filterFields}
          onApply={handleApplyFilters}
          onReset={handleResetFilters}
          applyButtonText="Apply Filters"
          resetButtonText="Reset"
        />
      )}

      <DataTable
        columns={columns}
        data={products}
        loading={loading}
        selectedIds={selectedIds}
        onSelect={handleSelectProduct}
        onSelectAll={handleSelectAll}
        getRowId={(product) => product.id}
        showCheckbox={activeTab === 'deleted' ? (canPermanentDelete || canBulkRestore) : canBulkDelete}
        emptyMessage={activeTab === 'deleted' ? 'No deleted products found' : 'No products found'}
        skeletonRows={10}
      />

      {!loading && pagination.totalPages > 0 && (
        <Pagination
          currentPage={currentPage}
          totalPages={pagination.totalPages}
          totalItems={pagination.total}
          itemsPerPage={pagination.limit}
          onPageChange={handlePageChange}
          showItemsInfo
        />
      )}

      {/* Confirmation Modal */}
      <Modal
        isOpen={modal.isOpen}
        onClose={closeModal}
        onConfirm={modal.onConfirm}
        title={modal.title}
        message={modal.message}
        confirmText={modal.confirmText}
        cancelText={modal.cancelText}
        type={modal.type}
        isLoading={isDeleting}
      />

      {/* ✅ Timeline Modal - Using CommonTimelineModal like Categories */}
      <CommonTimelineModal
        isOpen={timelineModal.isOpen}
        onClose={() => setTimelineModal({ isOpen: false, productId: '', productName: '' })}
        entityType="product"
        entityId={timelineModal.productId}
        entityName={timelineModal.productName}
        title="Product Timeline"
      />
    </div>
  );
}