'use client'

import { useCallback, useEffect, useState } from 'react'
import {
  getInvoices,
  setInvoicePaymentStatus,
  getIntegrationsStatus,
  IntegrationsStatus,
  AdminInvoiceRecord,
  PaymentTarget,
} from '@/lib/api/agent'
import { Card, CardContent } from '@/components/ui/Card'
import { Badge } from '@/components/ui/Badge'
import { Button } from '@/components/ui/Button'
import { Skeleton } from '@/components/ui/Skeleton'
import { EmptyState } from '@/components/ui/EmptyState'
import { ErrorState } from '@/components/ui/ErrorState'
import { formatCurrency, formatRelativeTime } from '@/lib/types'
import { useToast } from '@/components/ui/Toast'
import { CreditCard, RefreshCw } from 'lucide-react'

const FILTERS = ['all', 'initiated', 'confirmed', 'failed', 'refunded'] as const

const STATUS_BADGE: Record<string, 'default' | 'secondary' | 'success' | 'warning' | 'danger' | 'info'> = {
  pending: 'secondary',
  initiated: 'info',
  confirmed: 'success',
  failed: 'danger',
  refunded: 'warning',
  expired: 'secondary',
}

function nextActions(status: string): Array<{ target: PaymentTarget; label: string; variant: 'primary' | 'outline' }> {
  switch (status) {
    case 'initiated':
      return [
        { target: 'confirmed', label: 'Confirm', variant: 'primary' },
        { target: 'failed', label: 'Mark failed', variant: 'outline' },
      ]
    case 'failed':
      return [{ target: 'initiated', label: 'Re-initiate', variant: 'outline' }]
    case 'confirmed':
      return [{ target: 'refunded', label: 'Refund', variant: 'outline' }]
    default:
      return []
  }
}

export default function PaymentsPage() {
  const { toast } = useToast()
  const [invoices, setInvoices] = useState<AdminInvoiceRecord[]>([])
  const [filter, setFilter] = useState<(typeof FILTERS)[number]>('all')
  const [loading, setLoading] = useState(true)
  const [error, setError] = useState<string | null>(null)
  const [acting, setActing] = useState<string | null>(null)
  const [integrations, setIntegrations] = useState<IntegrationsStatus | null>(null)

  useEffect(() => {
    getIntegrationsStatus().then(r => { if (r.success) setIntegrations(r.data) }).catch(() => undefined)
  }, [])

  const load = useCallback(
    async (activeFilter: string) => {
      const res = await getInvoices({
        payment_status: activeFilter === 'all' ? undefined : activeFilter,
        limit: 100,
      })
      if (!res.success) throw new Error(res.message)
      setInvoices(res.data.invoices)
    },
    []
  )

  useEffect(() => {
    let mounted = true
    setLoading(true)
    load(filter)
      .catch(err => {
        if (mounted) setError(err instanceof Error ? err.message : 'Failed to load invoices')
      })
      .finally(() => {
        if (mounted) setLoading(false)
      })
    return () => {
      mounted = false
    }
  }, [filter, load])

  async function act(invoice: AdminInvoiceRecord, target: PaymentTarget) {
    if (
      target === 'refunded' &&
      !window.confirm(`Refund ${invoice.invoice_number} (${formatCurrency(invoice.total, invoice.currency)})?`)
    ) {
      return
    }
    setActing(invoice.id)
    const res = await setInvoicePaymentStatus(invoice.id, target)
    setActing(null)
    if (!res.success) {
      toast({ title: 'Update rejected', description: res.message, variant: 'destructive' })
    } else {
      toast({
        title: `Payment ${res.data.payment_status}`,
        description: `${invoice.invoice_number}: ${res.data.previous} → ${res.data.payment_status}`,
        variant: 'success',
      })
      try {
        await load(filter)
      } catch {
        /* keep current list */
      }
    }
  }

  return (
    <div className="space-y-6">
      <div className="flex flex-col sm:flex-row sm:items-center sm:justify-between gap-3">
        <div>
          <h1 className="text-2xl font-bold text-gray-900 dark:text-white">Payments</h1>
          <p className="text-gray-500 dark:text-gray-400">
            Reconcile payments manually — every change is audited and state-machine enforced
          </p>
        </div>
        <Button variant="outline" size="sm" onClick={() => load(filter).catch(() => undefined)}>
          <RefreshCw className="mr-2 h-4 w-4" /> Refresh
        </Button>
      </div>

      {integrations && !integrations.payments_configured && (
        <div className="rounded-lg border border-amber-200 bg-amber-50 px-4 py-3 text-sm text-amber-800 dark:border-amber-900/50 dark:bg-amber-950/30 dark:text-amber-300">
          Mobile-money payments are not configured (Paypack credentials missing).
          Customers see a honest “payment unavailable” notice, and staff can
          still reconcile payments manually below.
        </div>
      )}

      <div className="flex flex-wrap gap-2" role="tablist" aria-label="Payment status filter">
        {FILTERS.map(f => (
          <Button
            key={f}
            size="sm"
            role="tab"
            aria-selected={filter === f}
            variant={filter === f ? 'primary' : 'outline'}
            onClick={() => setFilter(f)}
          >
            {f.charAt(0).toUpperCase() + f.slice(1)}
          </Button>
        ))}
      </div>

      {loading ? (
        <Card>
          <CardContent className="space-y-3 p-6">
            {Array.from({ length: 5 }).map((_, i) => (
              <Skeleton key={i} className="h-12 w-full rounded-lg" />
            ))}
          </CardContent>
        </Card>
      ) : error ? (
        <ErrorState message={error} onRetry={() => load(filter).catch(() => undefined)} />
      ) : invoices.length === 0 ? (
        <EmptyState icon={CreditCard} title="No invoices" description={`No ${filter === 'all' ? '' : filter + ' '}invoices found.`} />
      ) : (
        <Card>
          <CardContent className="p-0">
            <ul className="divide-y divide-gray-100 dark:divide-gray-800">
              {invoices.map(inv => (
                <li key={inv.id} className="flex flex-col gap-3 px-4 py-3 sm:flex-row sm:items-center sm:justify-between">
                  <div className="min-w-0">
                    <div className="flex items-center gap-2">
                      <span className="text-sm font-semibold text-gray-900 dark:text-white">
                        {inv.invoice_number}
                      </span>
                      <Badge variant={STATUS_BADGE[inv.payment_status] ?? 'secondary'}>
                        {inv.payment_status}
                      </Badge>
                    </div>
                    <p className="mt-0.5 truncate text-xs text-gray-500 dark:text-gray-400">
                      Order {inv.orders?.order_number ?? inv.order_id} · issued{' '}
                      {formatRelativeTime(inv.issued_at)}
                    </p>
                  </div>
                  <div className="flex items-center gap-2 sm:flex-shrink-0">
                    <span className="mr-2 text-sm font-bold text-gray-900 dark:text-white">
                      {formatCurrency(inv.total, inv.currency)}
                    </span>
                    {nextActions(inv.payment_status).map(action => (
                      <Button
                        key={action.target}
                        size="sm"
                        variant={action.variant}
                        disabled={acting === inv.id}
                        onClick={() => act(inv, action.target)}
                      >
                        {acting === inv.id ? '…' : action.label}
                      </Button>
                    ))}
                  </div>
                </li>
              ))}
            </ul>
          </CardContent>
        </Card>
      )}
    </div>
  )
}
