'use client';

import { useState, useMemo } from 'react';
import { useQuery } from '@tanstack/react-query';
import {
  AlertTriangle, Train, Download, Search, X,
  ChevronDown, ChevronUp, Loader2, ChevronLeft, ChevronRight,
} from 'lucide-react';
import { apiClient } from '@/lib/api-client';

// ── Types ─────────────────────────────────────────────────────────────────────

interface ScheduleOption { id: string; label: string; departureAt: string; isPackage: boolean; }

interface PassengerBreakdown {
  passengerName: string;
  seatClass: string;
  coachNumber: string | null;
  seatNumber: string | null;
  fareMinor: number;
}

interface DiscrepancyRow {
  bookingRef: string;
  isPackage: boolean;
  seatClass: string;
  coachNumber: string | null;
  seatNumber: string | null;
  origin: string;
  destination: string;
  phone: string;
  actualMinor: number;
  paidMinor: number;
  varianceMinor: number;
  breakdown: PassengerBreakdown[];
}

interface DiscrepancyReport { total: number; rows: DiscrepancyRow[]; }

// ── Pagination ────────────────────────────────────────────────────────────────

const PAGE_SIZE = 20;

function usePagination<T>(items: T[], resetKey?: unknown) {
  const [page, setPage] = useState(1);
  useMemo(() => { setPage(1); }, [resetKey]); // eslint-disable-line react-hooks/exhaustive-deps
  const totalPages = Math.max(1, Math.ceil(items.length / PAGE_SIZE));
  const safePage = Math.min(page, totalPages);
  const slice = items.slice((safePage - 1) * PAGE_SIZE, safePage * PAGE_SIZE);
  return { page: safePage, setPage, totalPages, slice };
}

function Pagination({ page, totalPages, setPage, total }: {
  page: number; totalPages: number; setPage: (p: number) => void; total: number;
}) {
  if (totalPages <= 1) return null;
  const from = (page - 1) * PAGE_SIZE + 1;
  const to = Math.min(page * PAGE_SIZE, total);
  return (
    <div className="flex items-center justify-between px-1 pt-3 border-t border-border text-xs text-muted-foreground">
      <span>{from}–{to} of {total}</span>
      <div className="flex items-center gap-1">
        <button
          onClick={() => setPage(page - 1)}
          disabled={page === 1}
          className="p-1 rounded hover:bg-muted disabled:opacity-30 disabled:cursor-not-allowed transition-colors"
        >
          <ChevronLeft className="w-4 h-4" />
        </button>
        <span className="px-2">Page {page} of {totalPages}</span>
        <button
          onClick={() => setPage(page + 1)}
          disabled={page === totalPages}
          className="p-1 rounded hover:bg-muted disabled:opacity-30 disabled:cursor-not-allowed transition-colors"
        >
          <ChevronRight className="w-4 h-4" />
        </button>
      </div>
    </div>
  );
}

// ── Helpers ───────────────────────────────────────────────────────────────────

function fmtMinor(minor: number) {
  return `ETB ${(minor / 100).toLocaleString('en-US', { minimumFractionDigits: 2 })}`;
}

// paidMinor from PaymentIntent.amountMinor is converted to cents server-side before being returned
function fmtPaid(amount: number) {
  return `ETB ${(amount / 100).toLocaleString('en-US', { minimumFractionDigits: 2 })}`;
}

function downloadCsv(csv: string, filename: string) {
  const blob = new Blob([csv], { type: 'text/csv' });
  const url = URL.createObjectURL(blob);
  const a = document.createElement('a');
  a.href = url; a.download = filename; a.click();
  URL.revokeObjectURL(url);
}

// ── Discrepancy page ──────────────────────────────────────────────────────────

export default function PaymentsReportPage() {
  const [scheduleId, setScheduleId] = useState('');
  const [search, setSearch] = useState('');
  const [seatClass, setSeatClass] = useState('');
  const [sort, setSort] = useState<'desc' | 'asc'>('desc');
  const [expandedRef, setExpandedRef] = useState<string | null>(null);

  const { data: schedulesRaw, isLoading: loadingSchedules } = useQuery<ScheduleOption[]>({
    queryKey: ['report-schedules'],
    queryFn: () => apiClient.get('/reports/schedules'),
  });

  const now = new Date();
  const schedules = (schedulesRaw ?? []).filter(
    s => new Date(s.departureAt) >= now,
  );

  const { data, isLoading, isError } = useQuery<DiscrepancyReport>({
    queryKey: ['payments-discrepancy', scheduleId, search, seatClass, sort],
    queryFn: () => apiClient.get('/reports/payments/discrepancy', {
      params: { scheduleId, search: search || undefined, seatClass: seatClass || undefined, sort },
    }),
    enabled: !!scheduleId,
  });

  const pg = usePagination(data?.rows ?? [], `${scheduleId}-${search}-${seatClass}-${sort}`);

  const seatClassOptions = useMemo(() => {
    if (!data) return [];
    return [...new Set(data.rows.flatMap(r => r.breakdown.map(b => b.seatClass)))].sort();
  }, [data]);

  const doExport = () => {
    if (!data) return;
    const headers = ['Booking Ref', 'Route', 'Seat Class', 'Coach', 'Seat', 'Phone', 'Actual (ETB)', 'Paid (ETB)', 'Variance (ETB)'];
    const rows = data.rows.map(r => [
      r.bookingRef,
      `${r.origin} → ${r.destination}`,
      r.seatClass,
      r.coachNumber ?? '—',
      r.seatNumber ?? '—',
      r.phone,
      (r.actualMinor / 100).toFixed(2),
      (r.paidMinor / 100).toFixed(2),
      (r.varianceMinor / 100).toFixed(2),
    ].map(v => `"${String(v).replace(/"/g, '""')}"`).join(','));
    downloadCsv([headers.join(','), ...rows].join('\n'), `discrepancy-${scheduleId}.csv`);
  };

  return (
    <div className="space-y-6">
      <div>
        <h1 className="text-3xl font-bold text-foreground">Payments Report</h1>
        <p className="text-muted-foreground mt-1">Payment discrepancies for upcoming schedules</p>
      </div>

      {/* Schedule selector */}
      <div className="card">
        <div className="flex items-end gap-4 flex-wrap">
          <div className="flex-1 min-w-72">
            <label className="label">Schedule</label>
            <select
              className="input"
              value={scheduleId}
              onChange={e => { setScheduleId(e.target.value); setSeatClass(''); setSearch(''); }}
              disabled={loadingSchedules}
            >
              <option value="">{loadingSchedules ? 'Loading schedules…' : 'Select a schedule…'}</option>
              {schedules.map(s => <option key={s.id} value={s.id}>{s.label}</option>)}
            </select>
          </div>
        </div>
      </div>

      {scheduleId ? (
        <>
          {/* Schedule info banner */}
          <div className="card flex items-center gap-4">
            <div className="rounded-lg bg-emerald-100 dark:bg-emerald-900/30 p-2.5">
              <Train className="h-5 w-5 text-emerald-600 dark:text-emerald-400" />
            </div>
            <p className="font-semibold">{schedules.find(s => s.id === scheduleId)?.label ?? scheduleId}</p>
          </div>

          {/* Filters */}
          <div className="flex items-center gap-2 flex-wrap">
            <div className="relative flex-1 min-w-48">
              <Search className="absolute left-3 top-1/2 -translate-y-1/2 w-3.5 h-3.5 text-muted-foreground pointer-events-none" />
              <input
                type="text"
                value={search}
                onChange={e => setSearch(e.target.value.toUpperCase())}
                placeholder="Booking ref…"
                className="input pl-8 pr-7 font-mono text-sm w-full"
              />
              {search && (
                <button onClick={() => setSearch('')} className="absolute right-2.5 top-1/2 -translate-y-1/2 text-muted-foreground hover:text-foreground">
                  <X className="w-3.5 h-3.5" />
                </button>
              )}
            </div>
            <select
              value={seatClass}
              onChange={e => setSeatClass(e.target.value)}
              className="input w-48 text-sm"
            >
              <option value="">All seat classes</option>
              {seatClassOptions.map(sc => <option key={sc} value={sc}>{sc}</option>)}
            </select>
            <select
              value={sort}
              onChange={e => setSort(e.target.value as 'desc' | 'asc')}
              className="input w-48 text-sm"
            >
              <option value="desc">Variance: High → Low</option>
              <option value="asc">Variance: Low → High</option>
            </select>
            {data && data.rows.length > 0 && (
              <button
                onClick={doExport}
                className="flex items-center gap-1.5 text-xs font-medium text-muted-foreground hover:text-foreground border border-border rounded-lg px-3 py-1.5 transition-colors"
              >
                <Download className="w-3.5 h-3.5" /> Export CSV
              </button>
            )}
          </div>

          {isLoading && (
            <div className="flex items-center gap-2 text-sm text-muted-foreground py-8">
              <Loader2 className="w-4 h-4 animate-spin" />Loading…
            </div>
          )}
          {isError && <p className="text-sm text-red-500 py-4">Failed to load discrepancy data.</p>}

          {data && (
            <div className="card overflow-x-auto">
              <div className="mb-4">
                <h3 className="text-sm font-semibold uppercase tracking-wider text-muted-foreground">
                  {data.total} discrepanc{data.total !== 1 ? 'ies' : 'y'} found
                </h3>
              </div>
              <table className="w-full text-sm">
                <thead>
                  <tr className="border-b border-border text-left text-xs text-muted-foreground uppercase tracking-wider">
                    <th className="pb-2 pr-4 w-4" />
                    <th className="pb-2 pr-4 whitespace-nowrap">Booking Ref</th>
                    <th className="pb-2 pr-4 whitespace-nowrap">Seat Class · Coach · Seat</th>
                    <th className="pb-2 pr-4 whitespace-nowrap">Route</th>
                    <th className="pb-2 pr-4 text-right whitespace-nowrap">Actual</th>
                    <th className="pb-2 pr-4 text-right whitespace-nowrap">Paid</th>
                    <th className="pb-2 pr-4 text-right whitespace-nowrap">Variance</th>
                    <th className="pb-2 whitespace-nowrap">Phone</th>
                  </tr>
                </thead>
                <tbody className="divide-y divide-border">
                  {pg.slice.map(r => {
                    const isExpanded = expandedRef === r.bookingRef;
                    return (
                      <>
                        <tr
                          key={r.bookingRef}
                          className="hover:bg-muted/30 cursor-pointer"
                          onClick={() => setExpandedRef(isExpanded ? null : r.bookingRef)}
                        >
                          <td className="py-2 pr-2 text-muted-foreground">
                            {isExpanded ? <ChevronUp className="w-3.5 h-3.5" /> : <ChevronDown className="w-3.5 h-3.5" />}
                          </td>
                          <td className="py-2 pr-4 font-mono text-xs font-semibold">
                              {r.bookingRef}
                              {r.isPackage && (
                                <span className="ml-1.5 text-[10px] font-semibold bg-purple-100 dark:bg-purple-950/40 text-purple-700 dark:text-purple-300 border border-purple-200 dark:border-purple-800 px-1.5 py-0.5 rounded">
                                  package
                                </span>
                              )}
                            </td>
                          <td className="py-2 pr-4 text-xs">
                            <span className="font-medium">{r.seatClass}</span>
                            {r.coachNumber && <span className="text-muted-foreground"> · {r.coachNumber}</span>}
                            {r.seatNumber && <span className="text-muted-foreground"> · #{r.seatNumber}</span>}
                          </td>
                          <td className="py-2 pr-4 text-xs text-muted-foreground whitespace-nowrap">
                            {r.origin} → {r.destination}
                          </td>
                          <td className="py-2 pr-4 text-right tabular-nums text-xs">{fmtMinor(r.actualMinor)}</td>
                          <td className="py-2 pr-4 text-right tabular-nums text-xs">{fmtPaid(r.paidMinor)}</td>
                          <td className="py-2 pr-4 text-right">
                            <span className="inline-flex items-center gap-1 text-xs font-bold px-2 py-0.5 rounded-md bg-red-50 dark:bg-red-950/30 text-red-600 dark:text-red-400 border border-red-200 dark:border-red-800">
                              <AlertTriangle className="w-3 h-3" />
                              {fmtMinor(r.varianceMinor)}
                            </span>
                          </td>
                          <td className="py-2 text-xs text-muted-foreground">{r.phone}</td>
                        </tr>

                        {/* Fare breakdown */}
                        {isExpanded && (
                          <tr key={`${r.bookingRef}-breakdown`} className="bg-muted/20">
                            <td colSpan={8} className="px-6 py-3">
                              <p className="text-xs font-semibold uppercase tracking-wide text-muted-foreground mb-2">
                                Fare breakdown
                              </p>
                              <table className="w-full text-xs">
                                <thead>
                                  <tr className="text-left text-muted-foreground border-b border-border/50">
                                    <th className="pb-1.5 pr-4 font-semibold uppercase tracking-wide">Passenger</th>
                                    <th className="pb-1.5 pr-4 font-semibold uppercase tracking-wide">Seat Class</th>
                                    <th className="pb-1.5 pr-4 font-semibold uppercase tracking-wide">Coach</th>
                                    <th className="pb-1.5 pr-4 font-semibold uppercase tracking-wide">Seat</th>
                                    <th className="pb-1.5 font-semibold uppercase tracking-wide text-right">Actual Fare</th>
                                  </tr>
                                </thead>
                                <tbody className="divide-y divide-border/50">
                                  {r.breakdown.map((b, bi) => (
                                    <tr key={bi} className="text-foreground">
                                      <td className="py-1.5 pr-4 font-medium whitespace-nowrap">{b.passengerName}</td>
                                      <td className="py-1.5 pr-4">{b.seatClass}</td>
                                      <td className="py-1.5 pr-4 font-mono">{b.coachNumber ?? '—'}</td>
                                      <td className="py-1.5 pr-4 font-mono">{b.seatNumber ?? '—'}</td>
                                      <td className="py-1.5 text-right tabular-nums font-semibold">{fmtMinor(b.fareMinor)}</td>
                                    </tr>
                                  ))}
                                  <tr className="border-t border-border font-semibold">
                                    <td colSpan={4} className="pt-2 text-muted-foreground">Total actual vs paid</td>
                                    <td className="pt-2 text-right tabular-nums">
                                      {fmtMinor(r.actualMinor)} / {fmtPaid(r.paidMinor)}
                                      <span className="ml-2 text-red-500">(+{fmtMinor(r.varianceMinor)})</span>
                                    </td>
                                  </tr>
                                </tbody>
                              </table>
                            </td>
                          </tr>
                        )}
                      </>
                    );
                  })}
                  {data.rows.length === 0 && (
                    <tr><td colSpan={8} className="py-8 text-center text-sm text-muted-foreground">No discrepancies found.</td></tr>
                  )}
                </tbody>
              </table>
              <Pagination page={pg.page} totalPages={pg.totalPages} setPage={pg.setPage} total={data.rows.length} />
            </div>
          )}
        </>
      ) : (
        <div className="card py-16 text-center text-muted-foreground">
          <AlertTriangle className="h-10 w-10 mx-auto mb-3 opacity-30" />
          <p>Select a schedule above to load the discrepancy report</p>
        </div>
      )}
    </div>
  );
}
