'use client'

import { useState } from 'react'
import { useQuery, useMutation, useQueryClient, keepPreviousData } from '@tanstack/react-query'
import axios from 'axios'
import { toast } from 'sonner'
import { useRouter } from 'next/navigation'
import { formatCurrency, fmtDate, cn } from '@/lib/utils'
import { Briefcase, Plus, Play, CheckCircle2, Download, FileText, Loader2, ExternalLink } from 'lucide-react'
import { StatCard, Card, CardHeader, CardTitle, CardContent, Badge, Button, Modal, Input, Select, PageHeader, Pagination, Amount, Alert } from '@/components/ui/components'

export default function PayrollPage() {
  const qc = useQueryClient()
  const router = useRouter()
  const [newModal, setNewModal] = useState(false)
  const [runForm, setRunForm]   = useState({ month: new Date().getMonth() + 1, year: new Date().getFullYear(), paymentDate: '' })
  const [page, setPage]         = useState(1)
  const [payslipRun, setPayslipRun] = useState<any>(null)
  const [omitAdvanceIds, setOmitAdvanceIds] = useState<string[]>([])

  const { data, isLoading } = useQuery({
    queryKey: ['payroll-runs', page],
    queryFn: () => axios.get(`/api/payroll?page=${page}&pageSize=20`).then(r => r.data),
    placeholderData: keepPreviousData,
  })

  const { data: staffData } = useQuery({
    queryKey: ['payroll-staff-all'],
    queryFn: () => axios.get('/api/payroll?sub=staff&pageSize=200').then(r => r.data.data),
    enabled: newModal,
  })

  const createRun = useMutation({
    mutationFn: (payload: any) => axios.post('/api/payroll', payload),
    onSuccess: () => { toast.success('Payroll run initiated'); qc.invalidateQueries({queryKey:['payroll-runs']}); setNewModal(false); setOmitAdvanceIds([]) },
    onError: (e: any) => toast.error(e.response?.data?.error ?? 'Failed to create payroll run'),
  })

  const actionRun = useMutation({
    mutationFn: ({id, action}: any) => axios.patch(`/api/payroll/${id}`, { action }),
    onSuccess: () => { toast.success('Payroll updated'); qc.invalidateQueries({queryKey:['payroll-runs']}) },
    onError: (e: any) => toast.error(e.response?.data?.error ?? 'Failed'),
  })

  const { data: payslipItems, isLoading: payslipLoading } = useQuery({
    queryKey: ['payroll-items', payslipRun?.id],
    queryFn: () => axios.get(`/api/payroll/${payslipRun!.id}/items`).then(r => r.data.data),
    enabled: !!payslipRun,
  })

  const downloadPayslip = (runId: string, staffId?: string) => {
    const url = `/api/payroll/${runId}/payslip${staffId ? `?staffId=${staffId}` : ''}`
    window.open(url, '_blank')
  }

  const handleCreate = () => {
    const overrides: Record<string, any> = {}
    omitAdvanceIds.forEach(sid => { overrides[sid] = { omitAdvance: true } })
    createRun.mutate({ action: 'run', ...runForm, overrides })
  }

  const runs    = data?.data ?? []
  const total   = data?.total ?? 0
  const summary = data?.summary ?? {}

  const MONTHS = ['January','February','March','April','May','June','July','August','September','October','November','December']

  const toggleOmit = (staffId: string) => {
    setOmitAdvanceIds(prev => prev.includes(staffId) ? prev.filter(x => x !== staffId) : [...prev, staffId])
  }

  return (
    <div className="p-6 space-y-5 max-w-screen-xl mx-auto">
      <PageHeader title="Payroll" description="Monthly payroll runs and payslips" icon={<Briefcase className="w-6 h-6"/>}
        actions={<Button size="sm" icon={<Plus className="w-4 h-4"/>} onClick={() => { setOmitAdvanceIds([]); setNewModal(true) }}>New Payroll Run</Button>}
      />

      <div className="grid grid-cols-2 sm:grid-cols-4 gap-4">
        <StatCard label="Staff Count"         value={(summary.staffCount ?? 0).toLocaleString()}   icon={<Briefcase className="w-5 h-5"/>} color="blue"/>
        <StatCard label="Gross Pay (MTD)"     value={formatCurrency(summary.grossPayMtd)}          icon={<Briefcase className="w-5 h-5"/>} color="green"/>
        <StatCard label="PAYE (MTD)"          value={formatCurrency(summary.payeMtd)}              icon={<Briefcase className="w-5 h-5"/>} color="amber"/>
        <StatCard label="Net Pay (MTD)"       value={formatCurrency(summary.netPayMtd)}            icon={<Briefcase className="w-5 h-5"/>} color="teal"/>
      </div>

      <Card>
        <CardHeader><CardTitle>Payroll Runs</CardTitle></CardHeader>
        <div className="overflow-x-auto">
          <table className="table-lms w-full">
            <thead><tr><th>Run Ref</th><th>Period</th><th>Staff</th><th>Gross Pay</th><th>Deductions</th><th>Net Pay</th><th>Status</th><th>Payment Date</th><th>Actions</th></tr></thead>
            <tbody>
              {isLoading ? Array.from({length:6}).map((_,i)=><tr key={i}>{Array.from({length:9}).map((_,j)=><td key={j}><div className="h-4 bg-muted rounded animate-pulse"/></td>)}</tr>)
              : runs.length === 0 ? <tr><td colSpan={9} className="text-center py-8 text-muted-foreground">No payroll runs found</td></tr>
              : runs.map((r: any) => (
                <tr key={r.id}>
                  <td className="font-mono text-xs">
                    <button className="hover:text-primary hover:underline cursor-pointer text-left" onClick={() => router.push(`/payroll/${r.id}`)}>{r.payrollRef}</button>
                  </td>
                  <td className="text-sm font-medium">{MONTHS[r.payMonth-1]} {r.payYear}</td>
                  <td className="text-center text-sm">{r._count?.items ?? r.employeeCount}</td>
                  <td><Amount value={r.totalGross}/></td>
                  <td><Amount value={r.totalDeductions}/></td>
                  <td className="font-bold text-green-600"><Amount value={r.totalNet}/></td>
                  <td><Badge variant={r.status==='PAID'?'success':r.status==='APPROVED'?'info':r.status==='CANCELLED'?'danger':'warning'}>{r.status}</Badge></td>
                  <td className="text-xs">{fmtDate(r.paymentDate)}</td>
                  <td>
                    <div className="flex items-center gap-1">
                      {r.status === 'DRAFT' && <Button size="xs" variant="outline" onClick={() => actionRun.mutate({id:r.id, action:'SUBMIT'})}>Submit</Button>}
                      {r.status === 'PENDING_APPROVAL' && <Button size="xs" onClick={() => actionRun.mutate({id:r.id, action:'APPROVE'})}>Approve</Button>}
                      {r.status === 'APPROVED' && <Button size="xs" variant="success" icon={<Play className="w-3 h-3"/>} onClick={() => actionRun.mutate({id:r.id, action:'PAY'})}>Mark Paid</Button>}
                      {r.status === 'PAID' && <Button size="xs" variant="success" icon={<Download className="w-3 h-3"/>} onClick={() => downloadPayslip(r.id)}>Download All</Button>}
                      <Button size="xs" variant="ghost" icon={<FileText className="w-3 h-3"/>} onClick={() => setPayslipRun(r)} disabled={r.status !== 'PAID'}>Payslips</Button>
                    </div>
                  </td>
                </tr>
              ))}
            </tbody>
          </table>
        </div>
        <Pagination page={page} pages={Math.ceil(total/20)} total={total} pageSize={20} onPage={setPage}/>
      </Card>

      {/* Payslip modal */}
      <Modal open={!!payslipRun} onClose={() => setPayslipRun(null)} title={`Payslips — ${payslipRun?.payrollRef ?? ''}`} size="lg"
        footer={<>
          <Button variant="outline" size="sm" onClick={() => setPayslipRun(null)}>Close</Button>
          {payslipRun && <Button size="sm" icon={<Download className="w-4 h-4"/>} onClick={() => downloadPayslip(payslipRun.id)}>Download All</Button>}
        </>}
      >
        {payslipLoading ? <div className="flex items-center justify-center py-12"><Loader2 className="w-6 h-6 animate-spin text-primary"/></div>
        : !payslipItems?.length ? <p className="text-center py-8 text-muted-foreground">No payslip items found</p>
        : <div className="space-y-1">
            {payslipItems.map((pi: any) => (
              <div key={pi.id} className="flex items-center justify-between py-2.5 px-3 rounded-lg hover:bg-accent/50 transition-colors border-b last:border-0">
                <div className="flex items-center gap-3 min-w-0">
                  <div className="w-8 h-8 rounded-full bg-primary/10 flex items-center justify-center text-xs font-bold text-primary shrink-0">
                    {pi.fullName.split(' ').map((s: string) => s[0]).join('').slice(0, 2).toUpperCase()}
                  </div>
                  <div className="min-w-0">
                    <p className="text-sm font-medium truncate">{pi.fullName}</p>
                    <p className="text-xs text-muted-foreground">{pi.staffNo} {pi.designation ? `· ${pi.designation}` : ''}</p>
                  </div>
                </div>
                <div className="flex items-center gap-3 shrink-0">
                  <span className="text-sm font-semibold text-green-600">KES {pi.netPay.toLocaleString('en-KE', {minimumFractionDigits:2})}</span>
                  <Button size="xs" variant="outline" icon={<Download className="w-3 h-3"/>} onClick={() => downloadPayslip(payslipRun.id, pi.staffId)}>Download</Button>
                </div>
              </div>
            ))}
          </div>
        }
      </Modal>

      {/* New run modal */}
      <Modal open={newModal} onClose={() => setNewModal(false)} title="Create Payroll Run" size="lg"
        footer={<><Button variant="outline" size="sm" onClick={() => setNewModal(false)}>Cancel</Button><Button size="sm" loading={createRun.isPending} onClick={handleCreate}>Create Run</Button></>}
      >
        <div className="space-y-4">
          <Alert variant="info">This will compute payroll for all active staff for the selected period based on their salary, allowances, and deductions.</Alert>
          <div className="grid grid-cols-2 gap-4">
            <Select label="Month" required value={String(runForm.month)} onChange={e=>setRunForm(f=>({...f,month:parseInt(e.target.value)}))}
              options={MONTHS.map((m,i)=>({value:String(i+1),label:m}))}
            />
            <Select label="Year" required value={String(runForm.year)} onChange={e=>setRunForm(f=>({...f,year:parseInt(e.target.value)}))}
              options={[2024,2025,2026,2027].map(y=>({value:String(y),label:String(y)}))}
            />
          </div>
          <Input label="Payment Date" type="date" value={runForm.paymentDate} onChange={e=>setRunForm(f=>({...f,paymentDate:e.target.value}))} hint="Date when salaries will be paid out"/>

          {/* Advance deduction exclusion */}
          <div>
            <p className="text-sm font-medium mb-2">Skip Advance Deductions for:</p>
            <p className="text-xs text-muted-foreground mb-2">Toggle staff you want to exclude from advance/loan deductions this run.</p>
            <div className="max-h-48 overflow-y-auto border rounded-lg divide-y">
              {!staffData ? (
                <div className="p-4 text-center text-sm text-muted-foreground">Loading staff...</div>
              ) : staffData.length === 0 ? (
                <div className="p-4 text-center text-sm text-muted-foreground">No active staff found</div>
              ) : staffData.map((s: any) => (
                <label key={s.id} className="flex items-center justify-between px-3 py-2 hover:bg-accent/50 cursor-pointer">
                  <div className="flex items-center gap-2 min-w-0">
                    <span className="text-sm font-medium truncate">{s.fullName}</span>
                    <span className="text-xs text-muted-foreground shrink-0">{s.staffNo}</span>
                    {s.cashAdvances?.length > 0 && (
                      <span className="text-xs text-amber-600 shrink-0">(has advance)</span>
                    )}
                  </div>
                  <button
                    type="button"
                    onClick={(e) => { e.preventDefault(); toggleOmit(s.id) }}
                    className={cn(
                      'relative inline-flex h-5 w-9 shrink-0 cursor-pointer rounded-full border-2 border-transparent transition-colors',
                      omitAdvanceIds.includes(s.id) ? 'bg-amber-500' : 'bg-muted'
                    )}
                  >
                    <span className={cn(
                      'inline-block h-4 w-4 rounded-full bg-white shadow-sm transition-transform',
                      omitAdvanceIds.includes(s.id) ? 'translate-x-4' : 'translate-x-0'
                    )}/>
                  </button>
                </label>
              ))}
            </div>
            {omitAdvanceIds.length > 0 && (
              <p className="text-xs text-amber-600 mt-1">{omitAdvanceIds.length} staff excluded from advance deductions</p>
            )}
          </div>
        </div>
      </Modal>
    </div>
  )
}
