import { ReactNode, useEffect, useMemo, useState } from "react";
import { Head, Link } from "@inertiajs/react";
import { useQuery, useMutation, useQueryClient } from "@tanstack/react-query";
import AdminLayout from "@/layouts/AdminLayout";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Badge } from "@/components/ui/badge";
import {
  Select, SelectContent, SelectItem, SelectTrigger, SelectValue,
} from "@/components/ui/select";
import {
  Dialog, DialogContent, DialogHeader, DialogTitle,
} from "@/components/ui/dialog";
import {
  AlertDialog, AlertDialogAction, AlertDialogCancel, AlertDialogContent,
  AlertDialogDescription, AlertDialogFooter, AlertDialogHeader, AlertDialogTitle,
} from "@/components/ui/alert-dialog";
import {
  Table, TableBody, TableCell, TableHead, TableHeader, TableRow,
} from "@/components/ui/table";
import { ScrollText, Search, Wallet, FileText, Building2, User, X, ExternalLink } from "lucide-react";
import { format } from "date-fns";
import { toast } from "sonner";

const csrfToken = () =>
  (document.querySelector('meta[name="csrf-token"]') as HTMLMetaElement | null)?.content ?? "";

const fmtMoney = (cents: number) =>
  `£${(cents / 100).toLocaleString("en-GB", { minimumFractionDigits: 2, maximumFractionDigits: 2 })}`;

interface CreditNoteRow {
  id: string;
  reference: string;
  company_id: string | null;
  user_id: string | null;
  source_order_id: string | null;
  amount_cents: number;
  balance_cents: number;
  status: "active" | "spent" | "cancelled" | "expired";
  reason: string | null;
  issued_at: string;
  expires_at: string | null;
  company: { id: string; name: string } | null;
  user: { id: string; name: string; email: string } | null;
  source_order: { id: string; course_title: string | null; start_date: string | null } | null;
}

interface IndexResponse {
  credit_notes: CreditNoteRow[];
  totals: {
    count: number;
    active_count: number;
    active_balance_cents: number;
    issued_total_cents: number;
    redeemed_total_cents: number;
  };
}

const statusVariant = (s: string): "default" | "secondary" | "destructive" | "outline" => {
  switch (s) {
    case "active": return "default";
    case "spent": return "secondary";
    case "cancelled": return "destructive";
    case "expired": return "outline";
    default: return "outline";
  }
};

const CreditNotesPage = () => {
  const qc = useQueryClient();
  const [statusFilter, setStatusFilter] = useState("all");
  const [search, setSearch] = useState("");
  const [selected, setSelected] = useState<CreditNoteRow | null>(null);
  const [cancelTarget, setCancelTarget] = useState<CreditNoteRow | null>(null);

  const { data, isLoading } = useQuery<IndexResponse>({
    queryKey: ["admin-credit-notes", statusFilter, search],
    queryFn: async () => {
      const p = new URLSearchParams();
      if (statusFilter !== "all") p.set("status", statusFilter);
      if (search.trim()) p.set("search", search.trim());
      const res = await fetch(`/api/admin/credit-notes?${p.toString()}`);
      if (!res.ok) throw new Error("Failed to load credit notes");
      return res.json();
    },
  });

  const cancelMutation = useMutation({
    mutationFn: async (id: string) => {
      const res = await fetch(`/api/admin/credit-notes/${id}/cancel`, {
        method: "POST",
        headers: { "X-CSRF-TOKEN": csrfToken() },
      });
      if (!res.ok) {
        const err = await res.json().catch(() => ({ error: "Failed" }));
        throw new Error(err.error || "Failed");
      }
      return res.json();
    },
    onSuccess: () => {
      toast.success("Credit note cancelled");
      qc.invalidateQueries({ queryKey: ["admin-credit-notes"] });
      setCancelTarget(null);
      setSelected(null);
    },
    onError: (e: Error) => toast.error(e.message),
  });

  const totals = data?.totals;
  const rows = useMemo(() => data?.credit_notes ?? [], [data]);

  // Auto-open a note from a `?id=...` deep link — used by the "View Credit Note"
  // link on a cancelled order's details. Strip the param after consuming it so
  // closing the dialog doesn't immediately re-open it.
  useEffect(() => {
    if (!rows.length || selected) return;
    if (typeof window === "undefined") return;
    const url = new URL(window.location.href);
    const wantedId = url.searchParams.get("id");
    if (!wantedId) return;
    const match = rows.find((n) => n.id === wantedId);
    if (match) {
      setSelected(match);
      url.searchParams.delete("id");
      window.history.replaceState(null, "", url.toString());
    }
  }, [rows, selected]);

  return (
    <>
      <Head title="Credit Notes" />
      <div>
        <div className="flex items-center justify-between mb-6">
          <div>
            <h1 className="text-2xl font-bold text-foreground flex items-center gap-2">
              <ScrollText className="w-5 h-5 text-primary" /> Credit Notes
            </h1>
            <p className="text-sm text-muted-foreground mt-1">
              Refund-derived store credit. Issued automatically when an order is refunded — usable at checkout for future bookings.
            </p>
          </div>
        </div>

        {/* KPIs */}
        <div className="grid grid-cols-2 md:grid-cols-4 gap-4 mb-6">
          <div className="bg-card border border-border rounded-xl p-4">
            <div className="flex items-center gap-2 text-muted-foreground text-xs mb-1">
              <ScrollText className="w-3.5 h-3.5" /> Total Issued
            </div>
            <p className="text-2xl font-bold text-foreground">{fmtMoney(totals?.issued_total_cents ?? 0)}</p>
            <p className="text-xs text-muted-foreground mt-1">{totals?.count ?? 0} note{(totals?.count ?? 0) === 1 ? "" : "s"}</p>
          </div>
          <div className="bg-card border border-border rounded-xl p-4">
            <div className="flex items-center gap-2 text-muted-foreground text-xs mb-1">
              <Wallet className="w-3.5 h-3.5" /> Active Balance
            </div>
            <p className="text-2xl font-bold text-foreground">{fmtMoney(totals?.active_balance_cents ?? 0)}</p>
            <p className="text-xs text-muted-foreground mt-1">{totals?.active_count ?? 0} active</p>
          </div>
          <div className="bg-card border border-border rounded-xl p-4">
            <div className="flex items-center gap-2 text-muted-foreground text-xs mb-1">
              <FileText className="w-3.5 h-3.5" /> Redeemed
            </div>
            <p className="text-2xl font-bold text-foreground">{fmtMoney(totals?.redeemed_total_cents ?? 0)}</p>
          </div>
        </div>

        {/* Filters */}
        <div className="flex flex-col sm:flex-row gap-3 mb-4">
          <div className="relative flex-1 max-w-md">
            <Search className="absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-muted-foreground" />
            <Input
              placeholder="Reference, company, or user…"
              value={search}
              onChange={(e) => setSearch(e.target.value)}
              className="pl-9"
            />
          </div>
          <Select value={statusFilter} onValueChange={setStatusFilter}>
            <SelectTrigger className="w-[180px]">
              <SelectValue />
            </SelectTrigger>
            <SelectContent>
              <SelectItem value="all">All Statuses</SelectItem>
              <SelectItem value="active">Active</SelectItem>
              <SelectItem value="spent">Spent</SelectItem>
              <SelectItem value="cancelled">Cancelled</SelectItem>
              <SelectItem value="expired">Expired</SelectItem>
            </SelectContent>
          </Select>
        </div>

        {/* Table */}
        <div className="bg-card border border-border rounded-xl overflow-x-auto">
          <Table className="text-sm">
            <TableHeader>
              <TableRow>
                <TableHead>Reference</TableHead>
                <TableHead>Issued</TableHead>
                <TableHead>Holder</TableHead>
                <TableHead>Source</TableHead>
                <TableHead className="text-right">Amount</TableHead>
                <TableHead className="text-right">Balance</TableHead>
                <TableHead>Status</TableHead>
                <TableHead className="text-right">Actions</TableHead>
              </TableRow>
            </TableHeader>
            <TableBody>
              {isLoading ? (
                <TableRow>
                  <TableCell colSpan={8} className="text-center text-muted-foreground py-12">Loading…</TableCell>
                </TableRow>
              ) : rows.length === 0 ? (
                <TableRow>
                  <TableCell colSpan={8} className="text-center text-muted-foreground py-12">No credit notes found.</TableCell>
                </TableRow>
              ) : (
                rows.map((n) => (
                  <TableRow key={n.id} className="cursor-pointer hover:bg-muted/30" onClick={() => setSelected(n)}>
                    <TableCell className="font-mono text-xs">{n.reference}</TableCell>
                    <TableCell className="text-xs whitespace-nowrap">{format(new Date(n.issued_at), "dd MMM yy")}</TableCell>
                    <TableCell>
                      {n.company ? (
                        <span className="inline-flex items-center gap-1.5">
                          <Building2 className="w-3.5 h-3.5 text-muted-foreground" /> {n.company.name}
                        </span>
                      ) : n.user ? (
                        <span className="inline-flex items-center gap-1.5">
                          <User className="w-3.5 h-3.5 text-muted-foreground" />
                          <span className="truncate max-w-[200px]">{n.user.name || n.user.email}</span>
                        </span>
                      ) : (
                        <span className="text-muted-foreground">—</span>
                      )}
                    </TableCell>
                    <TableCell className="text-xs" onClick={(e) => e.stopPropagation()}>
                      {n.source_order ? (
                        <Link
                          href={`/admin/orders?id=${encodeURIComponent(n.source_order.id)}`}
                          className="text-primary hover:underline inline-flex items-center gap-1"
                        >
                          {n.source_order.course_title || "View order"}
                          <ExternalLink className="w-3 h-3" />
                        </Link>
                      ) : (
                        <span className="text-muted-foreground">—</span>
                      )}
                    </TableCell>
                    <TableCell className="text-right whitespace-nowrap">{fmtMoney(n.amount_cents)}</TableCell>
                    <TableCell className="text-right whitespace-nowrap font-semibold">{fmtMoney(n.balance_cents)}</TableCell>
                    <TableCell><Badge variant={statusVariant(n.status)} className="capitalize">{n.status}</Badge></TableCell>
                    <TableCell className="text-right" onClick={(e) => e.stopPropagation()}>
                      {n.status === "active" && (
                        <Button
                          size="sm"
                          variant="outline"
                          className="h-7 text-xs text-destructive hover:text-destructive"
                          onClick={() => setCancelTarget(n)}
                        >
                          <X className="w-3.5 h-3.5 mr-1" /> Cancel
                        </Button>
                      )}
                    </TableCell>
                  </TableRow>
                ))
              )}
            </TableBody>
          </Table>
        </div>
      </div>

      {/* Detail dialog */}
      <Dialog open={!!selected} onOpenChange={(open) => !open && setSelected(null)}>
        <DialogContent className="sm:max-w-lg">
          <DialogHeader>
            <DialogTitle className="flex items-center gap-2">
              <ScrollText className="w-5 h-5 text-primary" />
              {selected?.reference}
            </DialogTitle>
          </DialogHeader>
          {selected && (
            <div className="space-y-4 text-sm">
              <div className="bg-muted/50 rounded-lg p-4 grid grid-cols-2 gap-3">
                <div>
                  <p className="text-xs text-muted-foreground">Amount</p>
                  <p className="font-semibold">{fmtMoney(selected.amount_cents)}</p>
                </div>
                <div>
                  <p className="text-xs text-muted-foreground">Balance</p>
                  <p className="font-semibold">{fmtMoney(selected.balance_cents)}</p>
                </div>
                <div>
                  <p className="text-xs text-muted-foreground">Status</p>
                  <Badge variant={statusVariant(selected.status)} className="capitalize">{selected.status}</Badge>
                </div>
                <div>
                  <p className="text-xs text-muted-foreground">Issued</p>
                  <p>{format(new Date(selected.issued_at), "dd MMM yyyy 'at' HH:mm")}</p>
                </div>
                {selected.expires_at && (
                  <div className="col-span-2">
                    <p className="text-xs text-muted-foreground">Expires</p>
                    <p>{format(new Date(selected.expires_at), "dd MMM yyyy")}</p>
                  </div>
                )}
              </div>

              <div className="bg-secondary/30 rounded-lg p-4 space-y-2">
                <p className="text-xs font-semibold text-muted-foreground uppercase">Holder</p>
                {selected.company ? (
                  <Link href={`/admin/companies/${selected.company.id}`} className="text-primary hover:underline inline-flex items-center gap-1">
                    <Building2 className="w-4 h-4" /> {selected.company.name} <ExternalLink className="w-3 h-3" />
                  </Link>
                ) : selected.user ? (
                  <div className="inline-flex items-center gap-1">
                    <User className="w-4 h-4" />
                    <span className="font-medium">{selected.user.name}</span>
                    <span className="text-muted-foreground">· {selected.user.email}</span>
                  </div>
                ) : (
                  <p className="text-muted-foreground italic">No holder</p>
                )}
              </div>

              {selected.source_order && (
                <div className="bg-secondary/30 rounded-lg p-4 space-y-1">
                  <p className="text-xs font-semibold text-muted-foreground uppercase">Source Booking</p>
                  <Link
                    href={`/admin/orders?id=${encodeURIComponent(selected.source_order.id)}`}
                    className="font-medium text-primary hover:underline inline-flex items-center gap-1"
                  >
                    {selected.source_order.course_title || "View order"}
                    <ExternalLink className="w-3 h-3" />
                  </Link>
                  {selected.source_order.start_date && (
                    <p className="text-xs text-muted-foreground">
                      Started {format(new Date(selected.source_order.start_date + "T00:00:00"), "dd MMM yyyy")}
                    </p>
                  )}
                </div>
              )}

              {selected.reason && (
                <div className="bg-secondary/30 rounded-lg p-4">
                  <p className="text-xs font-semibold text-muted-foreground uppercase mb-1">Reason</p>
                  <p>{selected.reason}</p>
                </div>
              )}

              {selected.status === "active" && (
                <div className="border-t border-border pt-4 flex justify-end">
                  <Button variant="outline" className="text-destructive hover:text-destructive" onClick={() => setCancelTarget(selected)}>
                    <X className="w-4 h-4 mr-1.5" /> Cancel Credit Note
                  </Button>
                </div>
              )}
            </div>
          )}
        </DialogContent>
      </Dialog>

      {/* Cancel confirmation */}
      <AlertDialog open={!!cancelTarget} onOpenChange={(open) => !open && setCancelTarget(null)}>
        <AlertDialogContent>
          <AlertDialogHeader>
            <AlertDialogTitle>Cancel this credit note?</AlertDialogTitle>
            <AlertDialogDescription>
              {cancelTarget && (
                <>
                  {cancelTarget.reference} · {fmtMoney(cancelTarget.balance_cents)} balance.
                  Once cancelled, the holder cannot redeem any remaining balance.
                </>
              )}
            </AlertDialogDescription>
          </AlertDialogHeader>
          <AlertDialogFooter>
            <AlertDialogCancel>Keep Active</AlertDialogCancel>
            <AlertDialogAction
              className="bg-destructive text-destructive-foreground hover:bg-destructive/90"
              disabled={cancelMutation.isPending}
              onClick={() => cancelTarget && cancelMutation.mutate(cancelTarget.id)}
            >
              {cancelMutation.isPending ? "Cancelling…" : "Cancel Credit Note"}
            </AlertDialogAction>
          </AlertDialogFooter>
        </AlertDialogContent>
      </AlertDialog>
    </>
  );
};

CreditNotesPage.layout = (page: ReactNode) => <AdminLayout>{page}</AdminLayout>;

export default CreditNotesPage;
