import { useEffect, useState } from "react";
import { useMutation } from "@tanstack/react-query";
import { useServerFn } from "@tanstack/react-start";
import { toast } from "sonner";
import { verifyTransactionPin } from "@/lib/transaction-pin.functions";
import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogDescription } from "@/components/ui/dialog";
import { InputOTP, InputOTPGroup, InputOTPSlot } from "@/components/ui/input-otp";
import { Button } from "@/components/ui/button";
import { ShieldCheck, Receipt } from "lucide-react";
import { formatNaira } from "@/lib/format";

export type PinSummaryItem = { label: string; value: string };

type Props = {
  open: boolean;
  onOpenChange: (v: boolean) => void;
  /** Called after the PIN is verified server-side. */
  onVerified: (pin: string) => void;
  title?: string;
  description?: string;
  /** Line items shown on the review step before PIN entry. */
  summary?: PinSummaryItem[];
  /** Total charged to the wallet — shown as the hero amount on review. */
  amount?: number | string;
};

/**
 * Two-step confirmation: the customer first reviews exactly what they are about
 * to pay for, then enters the 4-digit PIN. Verification runs server-side via
 * `verifyTransactionPin`; the parent re-sends the PIN with its purchase call so
 * the backend validates it again.
 */
export function PinPromptDialog({
  open, onOpenChange, onVerified, title, description, summary, amount,
}: Props) {
  const hasReview = !!(summary?.length || amount != null);
  const [step, setStep] = useState<"review" | "pin">(hasReview ? "review" : "pin");
  const [pin, setPin] = useState("");
  const verify = useServerFn(verifyTransactionPin);

  useEffect(() => {
    if (open) { setStep(hasReview ? "review" : "pin"); setPin(""); }
  }, [open, hasReview]);

  const m = useMutation({
    mutationFn: () => verify({ data: { pin } }),
    onSuccess: () => {
      const p = pin;
      setPin("");
      onOpenChange(false);
      onVerified(p);
    },
    onError: (e: Error) => toast.error(e.message),
  });

  return (
    <Dialog open={open} onOpenChange={(v) => { if (!v) setPin(""); onOpenChange(v); }}>
      <DialogContent className="sm:max-w-sm">
        <DialogHeader>
          <div className="mx-auto mb-2 flex h-12 w-12 items-center justify-center rounded-full bg-primary/10">
            {step === "review" ? <Receipt className="h-6 w-6 text-primary" /> : <ShieldCheck className="h-6 w-6 text-primary" />}
          </div>
          <DialogTitle className="text-center">
            {step === "review" ? "Review your transaction" : (title ?? "Confirm with PIN")}
          </DialogTitle>
          <DialogDescription className="text-center">
            {step === "review"
              ? "Please confirm these details are correct before you authorize."
              : (description ?? "Enter your 4-digit transaction PIN to authorize this payment.")}
          </DialogDescription>
        </DialogHeader>

        {step === "review" ? (
          <div className="space-y-3 pt-1">
            {amount != null && (
              <div className="rounded-2xl bg-muted/60 p-4 text-center">
                <p className="text-[11px] uppercase tracking-wide text-muted-foreground">You are paying</p>
                <p className="text-3xl font-extrabold tracking-tight">{formatNaira(amount)}</p>
              </div>
            )}
            {!!summary?.length && (
              <dl className="rounded-2xl border border-border/60 p-3 text-sm">
                {summary.map((s) => (
                  <div key={s.label} className="flex items-start justify-between gap-4 py-1.5">
                    <dt className="shrink-0 text-muted-foreground">{s.label}</dt>
                    <dd className="break-all text-right font-medium">{s.value}</dd>
                  </div>
                ))}
              </dl>
            )}
            <div className="flex gap-2">
              <Button variant="secondary" className="flex-1" onClick={() => onOpenChange(false)}>Cancel</Button>
              <Button className="flex-1 bg-gradient-primary" onClick={() => setStep("pin")}>Continue</Button>
            </div>
          </div>
        ) : (
          <div className="flex flex-col items-center gap-4 pt-2">
            {amount != null && (
              <p className="text-sm text-muted-foreground">
                Authorizing <span className="font-bold text-foreground">{formatNaira(amount)}</span>
              </p>
            )}
            <InputOTP maxLength={4} value={pin} onChange={setPin} autoFocus>
              <InputOTPGroup>
                <InputOTPSlot index={0} />
                <InputOTPSlot index={1} />
                <InputOTPSlot index={2} />
                <InputOTPSlot index={3} />
              </InputOTPGroup>
            </InputOTP>
            <Button
              className="w-full bg-gradient-primary"
              disabled={pin.length < 4 || m.isPending}
              onClick={() => m.mutate()}
            >
              {m.isPending ? "Verifying…" : "Authorize"}
            </Button>
            {hasReview && (
              <button type="button" onClick={() => setStep("review")} className="text-xs text-muted-foreground underline">
                Back to summary
              </button>
            )}
          </div>
        )}
      </DialogContent>
    </Dialog>
  );
}
