import React, { useState, useMemo } from 'react';
import clsx from 'clsx';
import { Loader2 } from 'lucide-react';

export interface TableColumn<T> {
  key: string;
  header: string;
  sortable?: boolean;
  render?: (row: T) => React.ReactNode;
  accessor?: (row: T) => string | number;
  width?: string;
}

export interface TableProps<T> {
  columns: TableColumn<T>[];
  data: T[];
  rowKey: (row: T) => string;
  onRowClick?: (row: T) => void;
  emptyMessage?: string;
  loading?: boolean;
}

type SortDirection = 'asc' | 'desc';

export function Table<T extends Record<string, any>>({
  columns,
  data,
  rowKey,
  onRowClick,
  emptyMessage = 'Keine Daten vorhanden',
  loading = false,
}: TableProps<T>) {
  const [sortColumn, setSortColumn] = useState<string | null>(null);
  const [sortDirection, setSortDirection] = useState<SortDirection>('asc');

  const sortedData = useMemo(() => {
    if (!sortColumn) return data;
    const column = columns.find((c) => c.key === sortColumn);
    if (!column?.sortable) return data;

    const accessor = column.accessor || ((row: T) => row[sortColumn]);
    return [...data].sort((a, b) => {
      const aVal = accessor(a);
      const bVal = accessor(b);
      if (aVal < bVal) return sortDirection === 'asc' ? -1 : 1;
      if (aVal > bVal) return sortDirection === 'asc' ? 1 : -1;
      return 0;
    });
  }, [data, sortColumn, sortDirection, columns]);

  const handleSort = (column: TableColumn<T>) => {
    if (!column.sortable) return;
    if (sortColumn === column.key) {
      setSortDirection((prev) => (prev === 'asc' ? 'desc' : 'asc'));
    } else {
      setSortColumn(column.key);
      setSortDirection('asc');
    }
  };

  return (
    <div className="overflow-x-auto" role="region" aria-label="Data table">
      <table className="min-w-full divide-y divide-secondary-200">
        <thead>
          <tr>
            {columns.map((col) => (
              <th
                key={col.key}
                scope="col"
                className={clsx(
                  'px-6 py-3 text-left text-xs font-semibold text-secondary-600 uppercase tracking-wider',
                  col.sortable && 'cursor-pointer select-none hover:bg-secondary-50 min-h-touch'
                )}
                style={col.width ? { width: col.width } : undefined}
                aria-sort={sortColumn === col.key ? (sortDirection === 'asc' ? 'ascending' : 'descending') : 'none'}
                onClick={() => handleSort(col)}
                onKeyDown={(e) => {
                  if (col.sortable && (e.key === 'Enter' || e.key === ' ')) {
                    e.preventDefault();
                    handleSort(col);
                  }
                }}
                tabIndex={col.sortable ? 0 : undefined}
                role={col.sortable ? 'button' : undefined}
                aria-label={col.sortable ? `${col.header}, sortierbar` : undefined}
              >
                <div className="flex items-center gap-1">
                  {col.header}
                  {col.sortable && (
                    <span aria-hidden="true">
                      {sortColumn === col.key ? (sortDirection === 'asc' ? '▲' : '▼') : '↕'}
                    </span>
                  )}
                </div>
              </th>
            ))}
          </tr>
        </thead>
        <tbody className="divide-y divide-secondary-100">
          {loading ? (
            <tr>
              <td colSpan={columns.length} className="px-6 py-8 text-center text-secondary-500">
                <span className="inline-flex items-center gap-2">
                  <Loader2 className="animate-spin motion-reduce:animate-none h-5 w-5" aria-hidden="true" />
                  Wird geladen...
                </span>
              </td>
            </tr>
          ) : sortedData.length === 0 ? (
            <tr>
              <td colSpan={columns.length} className="px-6 py-8 text-center text-secondary-500">
                {emptyMessage}
              </td>
            </tr>
          ) : (
            sortedData.map((row) => (
              <tr
                key={rowKey(row)}
                className={clsx(
                  'hover:bg-secondary-50 motion-safe:transition-colors',
                  onRowClick && 'cursor-pointer'
                )}
                onClick={onRowClick ? () => onRowClick(row) : undefined}
                tabIndex={onRowClick ? 0 : undefined}
                onKeyDown={onRowClick ? (e) => {
                  if (e.key === 'Enter') onRowClick(row);
                } : undefined}
              >
                {columns.map((col) => (
                  <td key={col.key} className="px-6 py-4 text-sm text-secondary-900">
                    {col.render ? col.render(row) : (row[col.key] ?? '—')}
                  </td>
                ))}
              </tr>
            ))
          )}
        </tbody>
      </table>
    </div>
  );
}
