'use client'

import { useState, useEffect, useCallback } from 'react'
import { useMutation, useQuery, useQueryClient } from '@tanstack/react-query'
import axios from 'axios'
import { toast } from 'sonner'
import { formatCurrency } from '@/lib/utils'
import { RotateCw, AlertCircle, CheckCircle2 } from 'lucide-react'
import { Modal, Button, Alert, Badge, Amount, LoadingSpinner } from '@/components/ui/components'

interface ExcessReconcileModalProps {
  open: boolean
  onClose: () => void
}

export default function ExcessReconcileModal({ open, onClose }: ExcessReconcileModalProps) {
  const qc = useQueryClient()
  const [allocations, setAllocations] = useState<Record<string, string>>({})
  const [results, setResults] = useState<{ reconciled: number; errors: string[] } | null>(null)

  const { data, isLoading, refetch } = useQuery({
    queryKey: ['reconcile-excess-list'],
    queryFn: () => axios.get('/api/savings/reconcile-excess').then(r => r.data),
    enabled: open,
  })

  useEffect(() => {
    if (open) {
      setAllocations({})
      setResults(null)
      refetch()
    }
  }, [open, refetch])

  const handleAccountChange = useCallback((repaymentId: string, savingsAccountId: string) => {
    setAllocations(prev => ({ ...prev, [repaymentId]: savingsAccountId }))
  }, [])

  const autoAssignAll = useCallback(() => {
    if (!data?.data) return
    const auto: Record<string, string> = {}
    for (const r of data.data) {
      const accounts = r.loan?.member?.savingsAccounts ?? []
      if (accounts.length > 0) {
        auto[r.id] = accounts[0].id
      }
    }
    setAllocations(auto)
  }, [data])

  const reconcileMutation = useMutation({
    mutationFn: (payload: any) => axios.post('/api/savings/reconcile-excess', payload),
    onSuccess: (r: any) => {
      const result = r.data?.data ?? { reconciled: 0, errors: [] }
      setResults(result)
      if (result.reconciled > 0) {
        toast.success(r.data?.message ?? `${result.reconciled} excess payment(s) reconciled`)
        qc.invalidateQueries({ queryKey: ['fosa'] })
        qc.invalidateQueries({ queryKey: ['bosa'] })
      }
      if (result.errors?.length > 0) {
        toast.error(`${result.errors.length} error(s) during reconciliation`)
      }
    },
    onError: (e: any) => toast.error(e.response?.data?.error ?? 'Reconciliation failed'),
  })

  const handleReconcileSelected = () => {
    const selected = Object.entries(allocations).filter(([, accountId]) => accountId)
    if (selected.length === 0) {
      toast.error('Select at least one savings account to reconcile')
      return
    }
    reconcileMutation.mutate({
      allocations: selected.map(([repaymentId, savingsAccountId]) => ({ repaymentId, savingsAccountId })),
    })
  }

  const handleAutoReconcile = () => {
    reconcileMutation.mutate({})
  }

  const allSelected = data?.data?.every((r: any) => {
    const accounts = r.loan?.member?.savingsAccounts ?? []
    return accounts.length === 0 || allocations[r.id]
  })

  const totalExcess = data?.totalExcessAmount ?? 0
  const unallocated = data?.data ?? []

  return (
    <Modal open={open} onClose={onClose} title="Reconcile Excess Payments to Savings" size="2xl"
      footer={
        results ? (
          <Button size="sm" onClick={() => { setResults(null); onClose() }}>Close</Button>
        ) : (
          <>
            <Button variant="outline" size="sm" onClick={onClose}>Cancel</Button>
            <Button variant="outline" size="sm" loading={reconcileMutation.isPending}
              onClick={handleAutoReconcile} icon={<RotateCw className="w-4 h-4"/>}>
              Auto-Reconcile All
            </Button>
            <Button size="sm" loading={reconcileMutation.isPending}
              disabled={!allSelected}
              onClick={handleReconcileSelected}>
              Reconcile Selected ({Object.values(allocations).filter(Boolean).length})
            </Button>
          </>
        )
      }
    >
      {isLoading ? (
        <LoadingSpinner message="Loading unallocated excess payments…" />
      ) : results ? (
        <div className="space-y-4">
          <Alert variant={results.errors.length === 0 ? 'success' : 'warning'}>
            <p className="font-medium">{results.reconciled} repayment(s) reconciled successfully</p>
            {results.errors.length > 0 && (
              <ul className="mt-2 space-y-1">
                {results.errors.map((err, i) => (
                  <li key={i} className="text-sm flex items-start gap-2">
                    <AlertCircle className="w-4 h-4 shrink-0 mt-0.5" />
                    <span>{err}</span>
                  </li>
                ))}
              </ul>
            )}
          </Alert>
          {results.reconciled > 0 && (
            <div className="flex items-center gap-2 text-sm text-green-700 bg-green-50 rounded-lg p-3 border border-green-200">
              <CheckCircle2 className="w-5 h-5" />
              Journal entries and savings deposits posted automatically.
            </div>
          )}
        </div>
      ) : unallocated.length === 0 ? (
        <div className="text-center py-8 text-muted-foreground">
          <CheckCircle2 className="w-12 h-12 mx-auto mb-3 text-green-500" />
          <p className="font-medium text-lg">All caught up!</p>
          <p className="text-sm mt-1">No unallocated excess payments found.</p>
        </div>
      ) : (
        <div className="space-y-4">
          <Alert variant="info">
            <strong>{unallocated.length} repayment(s)</strong> with unallocated excess totaling{' '}
            <strong>{formatCurrency(totalExcess)}</strong>. Select a savings account for each member below, then click Reconcile.
          </Alert>

          {Object.values(allocations).filter(Boolean).length < unallocated.length && (
            <button onClick={autoAssignAll} className="text-xs text-primary hover:underline">
              Auto-assign first available account for all
            </button>
          )}

          <div className="divide-y max-h-96 overflow-y-auto border rounded-xl">
            {unallocated.map((r: any) => {
              const member = r.loan?.member
              const accounts = member?.savingsAccounts ?? []
              const selectedAccount = allocations[r.id] ?? ''

              return (
                <div key={r.id} className="p-4 space-y-2">
                  <div className="flex items-center justify-between">
                    <div>
                      <p className="text-sm font-medium">{member?.fullName ?? 'Unknown'} <span className="text-muted-foreground text-xs">({member?.memberNo})</span></p>
                      <p className="text-xs text-muted-foreground">Loan: {r.loan?.loanRef} · {formatCurrency(r.excessAmount)} excess</p>
                    </div>
                    <Badge variant="warning">Unallocated</Badge>
                  </div>
                  {accounts.length === 0 ? (
                    <p className="text-xs text-red-600 flex items-center gap-1">
                      <AlertCircle className="w-3 h-3" />
                      No active FOSA/BOSA account — cannot reconcile
                    </p>
                  ) : (
                    <select
                      value={selectedAccount}
                      onChange={e => handleAccountChange(r.id, e.target.value)}
                      className="w-full rounded-lg border bg-background px-3 py-2 text-sm focus:outline-none focus:ring-2 focus:ring-primary/30"
                    >
                      <option value="">— Select savings account —</option>
                      {accounts.map((a: any) => (
                        <option key={a.id} value={a.id}>
                          {a.accountNo} ({a.accountType?.replace(/_/g, ' ')} — {formatCurrency(a.balance)})
                        </option>
                      ))}
                    </select>
                  )}
                </div>
              )
            })}
          </div>
        </div>
      )}
    </Modal>
  )
}
