import { useState } from 'react';
import { Loader2, LockOpen } from 'lucide-react';
import { Button } from '@/components/ui/button';
import {
  Dialog,
  DialogContent,
  DialogDescription,
  DialogFooter,
  DialogHeader,
  DialogTitle,
} from '@/components/ui/dialog';
import { Input } from '@/components/ui/input';
import { Label } from '@/components/ui/label';
import { useLockActions } from '../useWalletData';

// Unlock, and nothing else. The wallet spends most of its life locked and that is the intended state —
// this dialog exists for the moment before a signature, not as a gate on the app.
//
// The unlock window is capped by the deployment's unlockTtlSec; a caller may ask for less but never more,
// so the shorter options here are real and the longest is simply "whatever the sidecar allows".

type UnlockDialogProps = {
  open: boolean;
  onOpenChange: (open: boolean) => void;
  walletId: number;
  walletName: string;
  maxTtlSec: number;
};

/** Offered windows, filtered to those the deployment actually permits. */
const TTL_CHOICES = [
  { sec: 60, label: '1 minute' },
  { sec: 300, label: '5 minutes' },
  { sec: 900, label: '15 minutes' },
  { sec: 3600, label: '1 hour' },
];

export const UnlockDialog = ({ open, onOpenChange, walletId, walletName, maxTtlSec }: UnlockDialogProps) => {
  const { unlock } = useLockActions(walletId);
  // The passphrase lives HERE and nowhere else: no localStorage, no sessionStorage, no React Query
  // cache, no URL. It goes straight into the POST body and this state is cleared the moment the request
  // settles, on success and on failure alike.
  const [passphrase, setPassphrase] = useState('');
  const [ttlSec, setTtlSec] = useState<number>(() => Math.min(300, maxTtlSec));

  const choices = TTL_CHOICES.filter((c) => c.sec <= maxTtlSec);

  const close = () => {
    setPassphrase('');
    onOpenChange(false);
  };

  const submit = async (ev: React.FormEvent) => {
    ev.preventDefault();
    if (!passphrase) return;
    try {
      await unlock.mutateAsync({ passphrase, ttlSec });
      close();
    } finally {
      // Cleared even when the unlock failed — a wrong passphrase left sitting in an input is still a
      // passphrase sitting in memory attached to a mounted component.
      setPassphrase('');
    }
  };

  return (
    <Dialog open={open} onOpenChange={(next) => (next ? onOpenChange(true) : close())}>
      <DialogContent className="max-w-md">
        <form onSubmit={submit}>
          <DialogHeader>
            <DialogTitle>Unlock {walletName}</DialogTitle>
            <DialogDescription>
              The seed is decrypted in the wallet sidecar for the window you choose, then wiped. Balances and history do
              not need this — only signing does.
            </DialogDescription>
          </DialogHeader>

          <div className="mt-4 space-y-4">
            <div className="space-y-1.5">
              <Label htmlFor="wallet-unlock-pass">Passphrase</Label>
              {/* Controlled input → request body → cleared. Never written to any store. */}
              <Input
                id="wallet-unlock-pass"
                type="password"
                autoFocus
                autoComplete="off"
                value={passphrase}
                onChange={(ev) => setPassphrase(ev.target.value)}
              />
            </div>

            {choices.length > 0 && (
              <div className="space-y-1.5">
                <Label>Keep unlocked for</Label>
                <div className="flex flex-wrap gap-1.5">
                  {choices.map(({ sec, label }) => (
                    <button
                      key={sec}
                      type="button"
                      onClick={() => setTtlSec(sec)}
                      className={`rounded-md px-2.5 py-1 text-xs transition-colors ${
                        ttlSec === sec
                          ? 'bg-primary text-primary-foreground'
                          : 'bg-muted text-muted-foreground hover:bg-muted/70'
                      }`}
                    >
                      {label}
                    </button>
                  ))}
                </div>
              </div>
            )}
          </div>

          <DialogFooter className="mt-6">
            <Button type="button" variant="ghost" onClick={close}>
              Cancel
            </Button>
            <Button type="submit" disabled={!passphrase || unlock.isPending}>
              {unlock.isPending ? (
                <Loader2 className="mr-2 h-4 w-4 animate-spin" />
              ) : (
                <LockOpen className="mr-2 h-4 w-4" />
              )}
              Unlock
            </Button>
          </DialogFooter>
        </form>
      </DialogContent>
    </Dialog>
  );
};
