import { useState, useRef } from 'react';
import { ArrowDown, ArrowUp, GripVertical, Pencil } from 'lucide-react';
import { toast } from 'sonner';
import { api } from '@/api.js';
import { cn, fmt, fmtDate } from '@/lib/utils';
import { Button } from '@/components/ui/button';
import { Input } from '@/components/ui/input';
import {
  AlertDialog, AlertDialogContent, AlertDialogHeader, AlertDialogTitle,
  AlertDialogDescription, AlertDialogFooter, AlertDialogCancel, AlertDialogAction,
} from '@/components/ui/alert-dialog';
import MonthlyStateDialog from '@/components/tracker/MonthlyStateDialog';
import PaymentModal from '@/components/tracker/PaymentModal';
import { paymentDateForTrackerMonth, paymentSummary, ROW_STATUS_CLS } from '@/lib/trackerUtils';
import { StatusBadge } from '@/components/tracker/StatusBadge';
import { PaymentProgress } from '@/components/tracker/PaymentProgress';
import { LowerThisMonthButton } from '@/components/tracker/LowerThisMonthButton';
import { PaymentLedgerDialog } from '@/components/tracker/PaymentLedgerDialog';
import { NotesCell } from '@/components/tracker/NotesCell';
import { AutopaySuggestionActions } from '@/components/tracker/AutopaySuggestionActions';

export function MobileTrackerRow({ row, year, month, refresh, index, onEditBill, moveControls, dragProps }) {
  const amountRef                     = useRef(null);
  const [editPayment, setEditPayment] = useState(null);
  const [paymentLedgerOpen, setPaymentLedgerOpen] = useState(false);
  const [showMbs,     setShowMbs]     = useState(false);
  const [confirmUnpay, setConfirmUnpay] = useState(false);
  const [suggestionLoading, setSuggestionLoading] = useState(false);

  const threshold = row.actual_amount != null ? row.actual_amount : row.expected_amount;
  const defaultPaymentDate = paymentDateForTrackerMonth(year, month, row.due_day);
  const isSkipped = !!row.is_skipped;
  const hasAutopaySuggestion = !!row.autopay_suggestion && !isSkipped;
  const isPaidByThreshold = row.total_paid > 0 && row.total_paid >= threshold;
  const isPaid = row.status === 'paid' || (row.status === 'autodraft' && !hasAutopaySuggestion) || isPaidByThreshold;
  const effectiveStatus = isSkipped
    ? 'skipped'
    : (isPaidByThreshold && row.status !== 'paid' && row.status !== 'autodraft')
      ? 'paid'
      : row.status;
  const rowBg = isSkipped ? '' : (ROW_STATUS_CLS[effectiveStatus] || '');
  const remaining = Math.max((threshold || 0) - (row.total_paid || 0), 0);
  const summary = paymentSummary(row, threshold);

  async function handleQuickPay() {
    const val = parseFloat(amountRef.current?.value);
    if (!val || val <= 0) { toast.error('Enter a payment amount'); return; }
    try {
      await api.quickPay({ bill_id: row.id, amount: val, paid_date: defaultPaymentDate });
      toast.success('Payment added');
      refresh();
    } catch (err) {
      toast.error(err.message);
    }
  }

  async function performTogglePaid() {
    try {
      const result = await api.togglePaid(row.id, {
        amount: isPaid ? undefined : threshold,
        year: year,
        month: month,
      });
      if (isPaid && result.paymentId) {
        toast.success('Payment moved to recovery', {
          action: {
            label: 'Undo',
            onClick: async () => {
              try {
                await api.restorePayment(result.paymentId);
                toast.success('Payment restored');
                refresh();
              } catch (err) {
                toast.error(err.message || 'Failed to restore payment');
              }
            },
          },
        });
      } else {
        toast.success('Payment recorded');
      }
      refresh();
    } catch (err) {
      toast.error(err.message || 'Failed to toggle payment status');
    }
  }

  function handleTogglePaid() {
    if (isPaid) {
      setConfirmUnpay(true);
      return;
    }
    performTogglePaid();
  }

  async function handleConfirmSuggestion() {
    setSuggestionLoading(true);
    try {
      const result = await api.confirmAutopaySuggestion(row.id, { year, month });
      toast.success(result.created ? 'Autopay payment confirmed' : 'Autopay already recorded');
      refresh();
    } catch (err) {
      toast.error(err.message || 'Failed to confirm autopay suggestion');
    } finally {
      setSuggestionLoading(false);
    }
  }

  async function handleDismissSuggestion() {
    setSuggestionLoading(true);
    try {
      await api.dismissAutopaySuggestion(row.id, { year, month });
      toast.success('Autopay suggestion dismissed');
      refresh();
    } catch (err) {
      toast.error(err.message || 'Failed to dismiss autopay suggestion');
    } finally {
      setSuggestionLoading(false);
    }
  }

  return (
    <>
      <div
        draggable={dragProps?.draggable}
        onDragStart={dragProps?.onDragStart}
        onDragEnter={dragProps?.onDragEnter}
        onDragOver={dragProps?.onDragOver}
        onDragEnd={dragProps?.onDragEnd}
        onDrop={dragProps?.onDrop}
        className={cn(
          'rounded-lg border border-border/60 bg-background/60 p-3 shadow-sm',
          'space-y-3 transition-colors',
          isSkipped ? 'opacity-55' : rowBg,
          dragProps?.isDragging && 'opacity-45',
          dragProps?.isDropTarget && 'ring-2 ring-primary/40',
        )}
        style={{ animationDelay: `${index * 40}ms` }}
      >
        <div className="flex min-w-0 items-start justify-between gap-3">
          <div className="flex min-w-0 gap-2">
            <div className="flex shrink-0 items-center gap-0.5 pt-0.5">
              <GripVertical
                className={cn(
                  'h-4 w-4 text-muted-foreground/55',
                  moveControls?.enabled && 'cursor-grab',
                  !moveControls?.enabled && 'opacity-30',
                )}
                aria-hidden="true"
              />
              <button
                type="button"
                onClick={moveControls?.onMoveUp}
                disabled={!moveControls?.enabled || !moveControls?.canMoveUp || moveControls?.moving}
                className="rounded text-muted-foreground transition-colors hover:bg-accent hover:text-foreground disabled:pointer-events-none disabled:opacity-25"
                title="Move bill up"
                aria-label={`Move ${row.name} up`}
              >
                <ArrowUp className="h-3 w-3" />
              </button>
              <button
                type="button"
                onClick={moveControls?.onMoveDown}
                disabled={!moveControls?.enabled || !moveControls?.canMoveDown || moveControls?.moving}
                className="rounded text-muted-foreground transition-colors hover:bg-accent hover:text-foreground disabled:pointer-events-none disabled:opacity-25"
                title="Move bill down"
                aria-label={`Move ${row.name} down`}
              >
                <ArrowDown className="h-3 w-3" />
              </button>
            </div>
            <div className="min-w-0">
            <div className="flex min-w-0 items-center gap-2">
              {row.website ? (
                <a
                  href={row.website}
                  target="_blank"
                  rel="noreferrer"
                  className={cn(
                    'min-w-0 truncate text-[15px] font-semibold leading-tight text-foreground',
                    'underline-offset-2 transition-colors hover:text-primary hover:underline',
                    isSkipped && 'line-through',
                  )}
                >
                  {row.name}
                </a>
              ) : (
                <span className={cn('min-w-0 truncate text-[15px] font-semibold leading-tight text-foreground', isSkipped && 'line-through')}>
                  {row.name}
                </span>
              )}
              {row.autopay_enabled && (
                <span
                  className="inline-flex shrink-0 rounded border border-sky-500/25 bg-sky-500/10 px-1.5 py-0.5 text-[10px] font-bold leading-none text-sky-600 dark:text-sky-300"
                  title="Autopay"
                >
                  AP
                </span>
              )}
              {(row.has_merchant_rule || row.has_linked_transactions) && (
                <span
                  className="inline-flex shrink-0 rounded border border-emerald-500/25 bg-emerald-500/10 px-1.5 py-0.5 text-[10px] font-bold leading-none text-emerald-600 dark:text-emerald-400"
                  title="Linked to bank transactions"
                >
                  L
                </span>
              )}
              {row.is_subscription && (
                <span
                  className="inline-flex shrink-0 rounded border border-indigo-500/25 bg-indigo-500/10 px-1.5 py-0.5 text-[10px] font-bold leading-none text-indigo-600 dark:text-indigo-300"
                  title="Subscription"
                >
                  S
                </span>
              )}
              <Button
                size="icon" variant="ghost"
                className="h-7 w-7 opacity-100 transition-opacity text-muted-foreground hover:text-foreground hover:bg-accent lg:opacity-0 lg:group-hover:opacity-100"
                title="Edit bill"
                onClick={() => onEditBill?.(row)}
              >
                <Pencil className="h-3 w-3" />
              </Button>
            </div>
            {row.monthly_notes && (
              <p className="mt-1 line-clamp-2 text-xs italic text-amber-500/80" title={row.monthly_notes}>
                {row.monthly_notes}
              </p>
            )}
            </div>
          </div>
          <StatusBadge status={effectiveStatus} clickable={!isSkipped} onClick={handleTogglePaid} />
        </div>

        <div className="grid grid-cols-2 gap-x-3 gap-y-2 text-xs text-muted-foreground sm:grid-cols-4">
          <div>
            <p className="uppercase tracking-wide text-muted-foreground/60">Due</p>
            <p className="tracker-number mt-0.5 text-sm font-medium text-foreground/90">{fmtDate(row.due_date)}</p>
          </div>
          <div>
            <p className="uppercase tracking-wide text-muted-foreground/60">Category</p>
            <p className="mt-0.5 truncate text-sm text-foreground">{row.category_name || 'Uncategorized'}</p>
          </div>
          <div>
            <p className="uppercase tracking-wide text-muted-foreground/60">Expected</p>
            <p className={cn('tracker-number mt-0.5 text-sm font-semibold', row.actual_amount != null ? 'text-amber-300' : 'text-foreground')}>
              {fmt(threshold)}
            </p>
          </div>
          <div>
            <p className="uppercase tracking-wide text-muted-foreground/60">Last Month</p>
            <p className="tracker-number mt-0.5 text-sm font-medium text-muted-foreground/80">
              {fmt(row.previous_month_paid)}
            </p>
          </div>
          <div>
            <p className="uppercase tracking-wide text-muted-foreground/60">Remaining</p>
            <p className={cn('tracker-number mt-0.5 text-sm font-semibold', remaining > 0 ? 'text-foreground' : 'text-emerald-300')}>
              {fmt(remaining)}
            </p>
          </div>
        </div>

        <div className="rounded-md border border-border/50 bg-muted/20">
          <PaymentProgress row={row} threshold={threshold} onOpen={() => setPaymentLedgerOpen(true)} compact />
        </div>

        <div className="flex flex-col gap-2 sm:flex-row sm:items-center sm:justify-between">
          <div className="grid grid-cols-2 gap-2 text-xs sm:flex sm:items-center">
            <div className="rounded-md bg-muted/45 px-2 py-1.5">
              <span className="text-muted-foreground">Paid </span>
              <span className="tracker-number font-semibold text-emerald-300">{row.total_paid > 0 ? fmt(row.total_paid) : '—'}</span>
            </div>
            <div className="rounded-md bg-muted/45 px-2 py-1.5">
              <span className="text-muted-foreground">Date </span>
              <button
                type="button"
                onClick={() => setPaymentLedgerOpen(true)}
                className="tracker-number rounded font-medium text-foreground underline-offset-2 hover:underline"
              >
                {row.last_paid_date ? fmtDate(row.last_paid_date) : '—'}
                {summary.count > 1 && <span className="ml-1 text-[10px] text-muted-foreground">({summary.count})</span>}
              </button>
            </div>
          </div>

          <div className="flex flex-wrap items-center justify-end gap-1.5">
            {hasAutopaySuggestion && (
              <AutopaySuggestionActions
                row={row}
                loading={suggestionLoading}
                onConfirm={handleConfirmSuggestion}
                onDismiss={handleDismissSuggestion}
                compact
              />
            )}
            {!isPaid && !isSkipped && !hasAutopaySuggestion && (
              <div className="flex items-center gap-1.5">
                <Input
                  ref={amountRef}
                  type="number" min="0" step="0.01"
                  defaultValue={summary.remaining || threshold}
                  className="tracker-number h-8 w-24 text-right text-sm font-medium bg-background/70 border-border/60"
                  title="Payment amount"
                  aria-label={`${row.name} payment amount`}
                />
                <Button
                  size="sm" variant="default"
                  onClick={handleQuickPay}
                  className="h-8 px-3 text-xs font-semibold"
                >
                  Add
                </Button>
              </div>
            )}
            <LowerThisMonthButton
              row={row}
              year={year}
              month={month}
              refresh={refresh}
              compact
            />

          </div>
        </div>

        <div className="rounded-md border border-border/50 bg-muted/25 px-2 py-1.5">
          <NotesCell row={{ ...row, year, month }} refresh={refresh} />
        </div>
      </div>

      {editPayment && (
        <PaymentModal
          payment={editPayment}
          onClose={() => setEditPayment(null)}
          onSave={refresh}
        />
      )}

      {paymentLedgerOpen && (
        <PaymentLedgerDialog
          row={row}
          year={year}
          month={month}
          threshold={threshold}
          defaultPaymentDate={defaultPaymentDate}
          onClose={() => setPaymentLedgerOpen(false)}
          onSaved={refresh}
        />
      )}

      {showMbs && (
        <MonthlyStateDialog
          row={row}
          year={year}
          month={month}
          open={showMbs}
          onOpenChange={setShowMbs}
          onSaved={refresh}
        />
      )}

      <AlertDialog open={confirmUnpay} onOpenChange={setConfirmUnpay}>
        <AlertDialogContent>
          <AlertDialogHeader>
            <AlertDialogTitle>Mark this bill unpaid?</AlertDialogTitle>
            <AlertDialogDescription>
              This removes the current payment record for this month and moves it into recovery.
            </AlertDialogDescription>
          </AlertDialogHeader>
          <AlertDialogFooter>
            <AlertDialogCancel>Cancel</AlertDialogCancel>
            <AlertDialogAction
              className="bg-destructive text-destructive-foreground hover:bg-destructive/90"
              onClick={performTogglePaid}
            >
              Remove Payment
            </AlertDialogAction>
          </AlertDialogFooter>
        </AlertDialogContent>
      </AlertDialog>
    </>
  );
}
