'use client';

import { useState, useMemo } from 'react';
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
import {
  Card, CardContent, Button, Input, Label,
  Dialog, DialogContent, DialogHeader, DialogTitle, DialogFooter,
  cn,
} from '@horux/shared-ui';
import { apiClient } from '@/lib/api/client';
import { useAuthStore } from '@/stores/auth-store';
import { useContribuyenteStore } from '@/stores/contribuyente-store';
import { Upload, Download, Trash2, CheckCircle2, XCircle, Clock, AlertTriangle, MessageSquare } from 'lucide-react';

const MESES = ['Enero','Febrero','Marzo','Abril','Mayo','Junio','Julio','Agosto','Septiembre','Octubre','Noviembre','Diciembre'];
const ALLOWED_MIMES = [
  'application/pdf',
  'application/msword',
  'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
  'application/vnd.ms-excel',
  'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
];
const ALLOWED_EXT = '.pdf,.doc,.docx,.xls,.xlsx';
const MAX_SIZE = 5 * 1024 * 1024;
const ROLES_APROBADOR = new Set(['owner', 'cfo', 'supervisor']);

interface Papeleria {
  id: number;
  contribuyenteId: string;
  nombre: string;
  descripcion: string | null;
  archivoFilename: string;
  archivoMime: string;
  archivoSize: number;
  anio: number;
  mes: number;
  requiereAprobacion: boolean;
  estado: 'pendiente' | 'aprobado' | 'rechazado' | null;
  comentarioRechazo: string | null;
  subidoPor: string;
  createdAt: string;
}

function fileToBase64(file: File): Promise<string> {
  return new Promise((resolve, reject) => {
    const r = new FileReader();
    r.onload = () => {
      const result = String(r.result);
      const i = result.indexOf(',');
      resolve(i >= 0 ? result.substring(i + 1) : result);
    };
    r.onerror = reject;
    r.readAsDataURL(file);
  });
}

function EstadoBadge({ estado, requiereAprobacion }: { estado: string | null; requiereAprobacion: boolean }) {
  if (!requiereAprobacion) {
    return <span className="inline-flex items-center gap-1 px-2 py-0.5 rounded-full text-xs bg-muted text-muted-foreground">Sin aprobación</span>;
  }
  if (estado === 'aprobado') {
    return <span className="inline-flex items-center gap-1 px-2 py-0.5 rounded-full text-xs bg-green-100 text-green-800 dark:bg-green-900/30 dark:text-green-400"><CheckCircle2 className="h-3 w-3" /> Aprobado</span>;
  }
  if (estado === 'rechazado') {
    return <span className="inline-flex items-center gap-1 px-2 py-0.5 rounded-full text-xs bg-red-100 text-red-800 dark:bg-red-900/30 dark:text-red-400"><XCircle className="h-3 w-3" /> Rechazado</span>;
  }
  return <span className="inline-flex items-center gap-1 px-2 py-0.5 rounded-full text-xs bg-yellow-100 text-yellow-800 dark:bg-yellow-900/30 dark:text-yellow-400"><Clock className="h-3 w-3" /> Pendiente</span>;
}

export function PapeleriaTab() {
  const user = useAuthStore(s => s.user);
  const { selectedContribuyenteId } = useContribuyenteStore();
  const queryClient = useQueryClient();
  const canApprove = user?.role ? ROLES_APROBADOR.has(user.role) : false;

  const [showUpload, setShowUpload] = useState(false);
  const [rechazoFor, setRechazoFor] = useState<Papeleria | null>(null);
  const [comentarioRechazo, setComentarioRechazo] = useState('');

  // Filtros
  const currentYear = new Date().getFullYear();
  const [filterAnio, setFilterAnio] = useState<number | ''>('');
  const [filterMes, setFilterMes] = useState<number | ''>('');
  const [filterEstado, setFilterEstado] = useState<string>('');

  const query = useQuery<Papeleria[]>({
    queryKey: ['papeleria', selectedContribuyenteId, filterAnio, filterMes, filterEstado],
    queryFn: async () => {
      const p = new URLSearchParams({ contribuyenteId: selectedContribuyenteId! });
      if (filterAnio) p.set('anio', String(filterAnio));
      if (filterMes) p.set('mes', String(filterMes));
      if (filterEstado) p.set('estado', filterEstado);
      const { data } = await apiClient.get<Papeleria[]>(`/papeleria?${p}`);
      return data;
    },
    enabled: !!selectedContribuyenteId,
  });

  const invalidate = () => queryClient.invalidateQueries({ queryKey: ['papeleria'] });

  // Upload form state
  const [file, setFile] = useState<File | null>(null);
  const [nombre, setNombre] = useState('');
  const [descripcion, setDescripcion] = useState('');
  const [anio, setAnio] = useState(currentYear);
  const [mes, setMes] = useState(new Date().getMonth() + 1);
  const [requiereAprobacion, setRequiereAprobacion] = useState(false);
  const [uploadError, setUploadError] = useState<string | null>(null);

  const resetUpload = () => {
    setFile(null);
    setNombre('');
    setDescripcion('');
    setAnio(currentYear);
    setMes(new Date().getMonth() + 1);
    setRequiereAprobacion(false);
    setUploadError(null);
  };

  const uploadMutation = useMutation({
    mutationFn: async () => {
      if (!file) throw new Error('Selecciona un archivo');
      if (!ALLOWED_MIMES.includes(file.type)) throw new Error('Formato no permitido. Usa PDF, Word o Excel.');
      if (file.size > MAX_SIZE) throw new Error('El archivo excede 5 MB.');
      const base64 = await fileToBase64(file);
      await apiClient.post('/papeleria', {
        contribuyenteId: selectedContribuyenteId,
        nombre: nombre || file.name,
        descripcion: descripcion || null,
        anio,
        mes,
        requiereAprobacion,
        archivoBase64: base64,
        archivoFilename: file.name,
        archivoMime: file.type,
      });
    },
    onError: (err: any) => {
      setUploadError(err?.response?.data?.message || err.message || 'Error al subir');
    },
    onSuccess: () => {
      setShowUpload(false);
      resetUpload();
      invalidate();
    },
  });

  const downloadMutation = useMutation({
    mutationFn: async (item: Papeleria) => {
      const res = await apiClient.get(`/papeleria/${item.id}/download`, { responseType: 'blob' });
      const url = URL.createObjectURL(res.data);
      const a = document.createElement('a');
      a.href = url;
      a.download = item.archivoFilename;
      a.click();
      URL.revokeObjectURL(url);
    },
  });

  const aprobarMutation = useMutation({
    mutationFn: async (id: number) => apiClient.post(`/papeleria/${id}/aprobar`),
    onSuccess: invalidate,
  });

  const rechazarMutation = useMutation({
    mutationFn: async ({ id, comentario }: { id: number; comentario: string | null }) =>
      apiClient.post(`/papeleria/${id}/rechazar`, { comentario }),
    onSuccess: () => {
      setRechazoFor(null);
      setComentarioRechazo('');
      invalidate();
    },
  });

  const eliminarMutation = useMutation({
    mutationFn: async (id: number) => apiClient.delete(`/papeleria/${id}`),
    onSuccess: invalidate,
  });

  if (!selectedContribuyenteId) {
    return (
      <Card>
        <CardContent className="py-8 text-center text-muted-foreground">
          Selecciona un contribuyente para ver su papelería.
        </CardContent>
      </Card>
    );
  }

  const items = query.data ?? [];
  const años = useMemo(() => {
    const set = new Set<number>([currentYear]);
    items.forEach(i => set.add(i.anio));
    return [...set].sort((a, b) => b - a);
  }, [items, currentYear]);

  return (
    <div className="space-y-4">
      {/* Filtros + upload */}
      <div className="flex items-end justify-between gap-3 flex-wrap">
        <div className="flex items-end gap-2">
          <div>
            <Label className="text-xs">Año</Label>
            <select
              value={filterAnio}
              onChange={e => setFilterAnio(e.target.value ? parseInt(e.target.value, 10) : '')}
              className="h-9 rounded-md border bg-background px-2 text-sm"
            >
              <option value="">Todos</option>
              {años.map(a => <option key={a} value={a}>{a}</option>)}
            </select>
          </div>
          <div>
            <Label className="text-xs">Mes</Label>
            <select
              value={filterMes}
              onChange={e => setFilterMes(e.target.value ? parseInt(e.target.value, 10) : '')}
              className="h-9 rounded-md border bg-background px-2 text-sm"
            >
              <option value="">Todos</option>
              {MESES.map((m, i) => <option key={i + 1} value={i + 1}>{m}</option>)}
            </select>
          </div>
          <div>
            <Label className="text-xs">Estado</Label>
            <select
              value={filterEstado}
              onChange={e => setFilterEstado(e.target.value)}
              className="h-9 rounded-md border bg-background px-2 text-sm"
            >
              <option value="">Todos</option>
              <option value="pendiente">Pendiente</option>
              <option value="aprobado">Aprobado</option>
              <option value="rechazado">Rechazado</option>
              <option value="sin_aprobacion">Sin aprobación</option>
            </select>
          </div>
        </div>
        <Button onClick={() => setShowUpload(true)}>
          <Upload className="h-4 w-4 mr-2" /> Subir documento
        </Button>
      </div>

      {/* Listado */}
      {query.isLoading ? (
        <p className="text-sm text-muted-foreground">Cargando...</p>
      ) : items.length === 0 ? (
        <Card>
          <CardContent className="py-8 text-center text-muted-foreground">
            No hay documentos en papelería con los filtros seleccionados.
          </CardContent>
        </Card>
      ) : (
        <div className="space-y-2">
          {items.map(it => (
            <Card key={it.id}>
              <CardContent className="py-3 flex items-center gap-3">
                <div className="flex-1 min-w-0">
                  <div className="flex items-center gap-2 flex-wrap">
                    <span className="text-sm font-medium">{it.nombre}</span>
                    <EstadoBadge estado={it.estado} requiereAprobacion={it.requiereAprobacion} />
                    <span className="text-xs text-muted-foreground">
                      {MESES[it.mes - 1]} {it.anio}
                    </span>
                  </div>
                  {it.descripcion && (
                    <p className="text-xs text-muted-foreground mt-0.5">{it.descripcion}</p>
                  )}
                  <p className="text-xs text-muted-foreground mt-0.5">
                    {it.archivoFilename} · {(it.archivoSize / 1024).toFixed(0)} KB
                    · subido {new Date(it.createdAt).toLocaleDateString('es-MX')}
                  </p>
                  {it.estado === 'rechazado' && it.comentarioRechazo && (
                    <p className="text-xs mt-1 flex items-start gap-1 text-red-700 dark:text-red-400">
                      <MessageSquare className="h-3 w-3 mt-0.5 flex-shrink-0" />
                      <span>{it.comentarioRechazo}</span>
                    </p>
                  )}
                </div>
                <div className="flex items-center gap-1 flex-shrink-0">
                  <Button variant="ghost" size="icon" onClick={() => downloadMutation.mutate(it)} title="Descargar">
                    <Download className="h-4 w-4" />
                  </Button>
                  {canApprove && it.requiereAprobacion && it.estado === 'pendiente' && (
                    <>
                      <Button
                        variant="ghost" size="icon"
                        onClick={() => aprobarMutation.mutate(it.id)}
                        title="Aprobar"
                      >
                        <CheckCircle2 className="h-4 w-4 text-green-600" />
                      </Button>
                      <Button
                        variant="ghost" size="icon"
                        onClick={() => setRechazoFor(it)}
                        title="Rechazar"
                      >
                        <XCircle className="h-4 w-4 text-red-600" />
                      </Button>
                    </>
                  )}
                  <Button
                    variant="ghost" size="icon"
                    onClick={() => confirm(`¿Eliminar "${it.nombre}"?`) && eliminarMutation.mutate(it.id)}
                    title="Eliminar"
                  >
                    <Trash2 className="h-4 w-4 text-destructive" />
                  </Button>
                </div>
              </CardContent>
            </Card>
          ))}
        </div>
      )}

      {/* Modal Upload */}
      <Dialog open={showUpload} onOpenChange={(o) => { setShowUpload(o); if (!o) resetUpload(); }}>
        <DialogContent>
          <DialogHeader>
            <DialogTitle>Subir documento de papelería</DialogTitle>
          </DialogHeader>
          <div className="space-y-3">
            <div>
              <Label>Archivo (PDF, Word o Excel · máx 5 MB)</Label>
              <input
                type="file"
                accept={ALLOWED_EXT}
                onChange={e => {
                  const f = e.target.files?.[0] ?? null;
                  setFile(f);
                  if (f && !nombre) setNombre(f.name.replace(/\.[^.]+$/, ''));
                  setUploadError(null);
                }}
                className="block w-full text-sm border rounded-md px-3 py-2"
              />
              {file && (
                <p className="text-xs text-muted-foreground mt-1">
                  {file.name} · {(file.size / 1024).toFixed(0)} KB
                </p>
              )}
            </div>
            <div>
              <Label>Nombre</Label>
              <Input value={nombre} onChange={e => setNombre(e.target.value)} placeholder="Ej. Reporte de cuentas" />
            </div>
            <div>
              <Label>Descripción (opcional)</Label>
              <Input value={descripcion} onChange={e => setDescripcion(e.target.value)} />
            </div>
            <div className="grid grid-cols-2 gap-3">
              <div>
                <Label>Mes</Label>
                <select
                  value={mes}
                  onChange={e => setMes(parseInt(e.target.value, 10))}
                  className="w-full h-10 rounded-md border bg-background px-3 text-sm"
                >
                  {MESES.map((m, i) => <option key={i + 1} value={i + 1}>{m}</option>)}
                </select>
              </div>
              <div>
                <Label>Año</Label>
                <Input
                  type="number" min={2020} max={2100}
                  value={anio}
                  onChange={e => setAnio(parseInt(e.target.value, 10) || currentYear)}
                />
              </div>
            </div>
            <label className="flex items-center gap-2 text-sm cursor-pointer">
              <input
                type="checkbox"
                checked={requiereAprobacion}
                onChange={e => setRequiereAprobacion(e.target.checked)}
              />
              Este documento requiere aprobación de owner/supervisor
            </label>
            {uploadError && (
              <p className="text-xs text-destructive flex items-start gap-1">
                <AlertTriangle className="h-3 w-3 mt-0.5 flex-shrink-0" />
                <span>{uploadError}</span>
              </p>
            )}
          </div>
          <DialogFooter>
            <Button variant="outline" onClick={() => setShowUpload(false)}>Cancelar</Button>
            <Button
              onClick={() => uploadMutation.mutate()}
              disabled={!file || uploadMutation.isPending}
            >
              {uploadMutation.isPending ? 'Subiendo...' : 'Subir'}
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>

      {/* Modal Rechazo */}
      <Dialog open={!!rechazoFor} onOpenChange={(o) => { if (!o) { setRechazoFor(null); setComentarioRechazo(''); } }}>
        <DialogContent>
          <DialogHeader>
            <DialogTitle>Rechazar documento</DialogTitle>
          </DialogHeader>
          <div className="space-y-3">
            <p className="text-sm">
              Vas a rechazar <strong>{rechazoFor?.nombre}</strong>. El comentario es opcional.
            </p>
            <div>
              <Label>Comentario (opcional)</Label>
              <Input
                value={comentarioRechazo}
                onChange={e => setComentarioRechazo(e.target.value)}
                placeholder="Motivo del rechazo..."
              />
            </div>
          </div>
          <DialogFooter>
            <Button variant="outline" onClick={() => { setRechazoFor(null); setComentarioRechazo(''); }}>
              Cancelar
            </Button>
            <Button
              onClick={() => rechazoFor && rechazarMutation.mutate({ id: rechazoFor.id, comentario: comentarioRechazo || null })}
              className={cn('bg-destructive hover:bg-destructive/90 text-destructive-foreground')}
            >
              Rechazar
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>
    </div>
  );
}
