import * as React from "react";
import * as XLSX from "xlsx";
import { Card, CardContent, CardDescription, CardHeader, CardTitle, } from "@/components/ui/card";
import { Button } from "@/components/ui/button";
import { FileText, X, Download, DatabaseIcon } from "lucide-react";
import { useMutation } from "@tanstack/react-query";
import { apiRequest, queryClient } from "@/lib/queryClient";
import { toast } from "@/hooks/use-toast";
import { QK_PAYMENTS_RECENT_BASE } from "@/components/payments/payments-recent-table";
import { MultipleFileUploadZone, } from "../file-upload/multiple-file-upload-zone";
const COLUMNS = [
    { key: "Patient Name", label: "Patient Name" },
    { key: "Member #", label: "Member #" },
    { key: "ICN", label: "ICN" },
    { key: "Submitted Code", label: "Submitted Code" },
    { key: "Paid Code", label: "Paid Code" },
    { key: "Tooth", label: "Tooth" },
    { key: "Date of Service", label: "Date of Service" },
    { key: "Submitted Amount", label: "Submitted ($)" },
    { key: "Allowed Amount", label: "Allowed ($)" },
    { key: "Paid Amount", label: "Paid ($)" },
];
const SUMMARY_FIELDS = [
    "Source File",
    "Payee ID",
    "Business NPI",
    "Run #",
    "RA #",
    "RA Date",
    "Claim Detail Amount",
    "Claim Adjustment Amount",
    "Misc. Adjustment Amount",
    "Payment Amount",
];
// Convert a string value to a number if it looks numeric, otherwise keep as string.
// Handles: "36.00" → 36, "$14,369.00" → 14369, "($3,107.39)" → -3107.39
function toExcelValue(val) {
    if (!val)
        return "";
    const stripped = val
        .replace(/\$/g, "")
        .replace(/,/g, "")
        .replace(/^\((.+)\)$/, "-$1") // (3,107.39) → -3107.39
        .trim();
    const num = Number(stripped);
    return stripped !== "" && !isNaN(num) ? num : val;
}
function downloadExcel(rows, headers, sourceFileName) {
    const wb = XLSX.utils.book_new();
    // Sheet 1 — RA Summary (one row per uploaded PDF)
    if (headers.length > 0) {
        const summaryData = headers.map((h) => {
            const out = {};
            SUMMARY_FIELDS.forEach((f) => { out[f] = toExcelValue(h[f] ?? ""); });
            return out;
        });
        const wsSummary = XLSX.utils.json_to_sheet(summaryData, {
            header: SUMMARY_FIELDS,
        });
        XLSX.utils.book_append_sheet(wb, wsSummary, "RA Summary");
    }
    // Sheet 2 — Payment Data (one row per ICN)
    const data = rows.map((row) => {
        const out = {};
        COLUMNS.forEach(({ key, label }) => { out[label] = toExcelValue(row[key] ?? ""); });
        return out;
    });
    const wsData = XLSX.utils.json_to_sheet(data, {
        header: COLUMNS.map((c) => c.label),
    });
    XLSX.utils.book_append_sheet(wb, wsData, "Payment Data");
    const name = sourceFileName.replace(/\.pdf$/i, "") || "payment_extract";
    XLSX.writeFile(wb, `${name}.xlsx`);
}
export default function PaymentUploadDocumentsBlock() {
    const MAX_FILES = 10;
    const ACCEPTED_FILE_TYPES = "application/pdf";
    const uploadZoneRef = React.useRef(null);
    const [filesForUI, setFilesForUI] = React.useState([]);
    const [isUploading] = React.useState(false);
    const [error, setError] = React.useState(null);
    // ── shared extract helper ────────────────────────────────────────────────
    const extractData = async (files) => {
        const formData = new FormData();
        files.forEach((file) => formData.append("files", file, file.name));
        const res = await apiRequest("POST", "/api/payment-pdf/extract", formData);
        if (!res.ok) {
            const err = await res.json().catch(() => ({}));
            throw new Error(err?.error || "Failed to extract PDF data");
        }
        const data = (await res.json());
        return { rows: data.rows ?? [], headers: data.headers ?? [] };
    };
    const getFiles = () => {
        const files = uploadZoneRef.current?.getFiles() ?? [];
        if (!files.length) {
            setError("Please upload at least one PDF file.");
            return null;
        }
        setError(null);
        return files;
    };
    // ── Extract & Download ───────────────────────────────────────────────────
    const downloadMutation = useMutation({
        mutationFn: async (files) => {
            const { rows, headers } = await extractData(files);
            return { rows, headers, sourceName: files[0]?.name ?? "payment_extract" };
        },
        onSuccess: ({ rows, headers, sourceName }) => {
            if (rows.length === 0) {
                toast({ title: "No data", description: "No rows were extracted from the PDF.", variant: "destructive" });
                return;
            }
            downloadExcel(rows, headers, sourceName);
            toast({ title: "Downloaded", description: `${rows.length} rows exported to Excel.` });
        },
        onError: (err) => {
            toast({ title: "Error", description: err.message, variant: "destructive" });
        },
    });
    // ── Extract & Import ─────────────────────────────────────────────────────
    const importMutation = useMutation({
        mutationFn: async (files) => {
            const { rows } = await extractData(files);
            if (rows.length === 0)
                throw new Error("No rows extracted from the PDF.");
            const res = await apiRequest("POST", "/api/payment-pdf/import", { rows });
            if (!res.ok) {
                const err = await res.json().catch(() => ({}));
                throw new Error(err?.error || "Import failed");
            }
            return res.json();
        },
        onSuccess: async (data) => {
            toast({
                title: "Imported",
                description: `${data.paymentIds?.length ?? 0} payment(s) created successfully.`,
            });
            await queryClient.invalidateQueries({ queryKey: QK_PAYMENTS_RECENT_BASE });
        },
        onError: (err) => {
            toast({ title: "Error", description: err.message, variant: "destructive" });
        },
    });
    const handleZoneFilesChange = React.useCallback((files) => {
        setFilesForUI(files);
        setError(null);
    }, []);
    const removeUploadedFile = React.useCallback((index) => {
        uploadZoneRef.current?.removeFile(index);
    }, []);
    const busy = downloadMutation.isPending || importMutation.isPending;
    return (<div className="mb-8">
      <Card>
        <CardHeader>
          <CardTitle>Upload Payment Documents</CardTitle>
          <CardDescription>
            Upload up to 10 MassHealth remittance PDFs. Extract and download as
            Excel, or import directly into the database.
          </CardDescription>
        </CardHeader>

        <CardContent>
          <div className="bg-gray-100 p-4 rounded-md space-y-4">
            <MultipleFileUploadZone ref={uploadZoneRef} isUploading={isUploading} acceptedFileTypes={ACCEPTED_FILE_TYPES} maxFiles={MAX_FILES} onFilesChange={handleZoneFilesChange}/>

            {filesForUI.length > 0 && (<div>
                <p className="text-sm text-gray-600 mb-2">
                  Uploaded ({filesForUI.length}/{MAX_FILES})
                </p>
                <ul className="space-y-2 max-h-48 overflow-auto">
                  {filesForUI.map((file, idx) => (<li key={`${file.name}-${file.size}-${idx}`} className="flex items-center justify-between border rounded-md p-2 bg-white">
                      <div className="flex items-center gap-3">
                        <FileText className="h-6 w-6 text-blue-500"/>
                        <div className="text-left">
                          <p className="font-medium text-blue-700 truncate">{file.name}</p>
                          <p className="text-sm text-gray-500">
                            {(file.size / 1024 / 1024).toFixed(2)} MB
                          </p>
                        </div>
                      </div>
                      <Button variant="ghost" size="sm" onClick={() => removeUploadedFile(idx)}>
                        <X className="h-4 w-4"/>
                      </Button>
                    </li>))}
                </ul>
              </div>)}
          </div>

          <div className="mt-4 flex gap-3">
            {/* Extract & Download */}
            <Button className="flex-1 h-12 gap-2 bg-blue-600 hover:bg-blue-700 text-white" type="button" disabled={busy || !filesForUI.length} onClick={() => {
            const files = getFiles();
            if (files)
                downloadMutation.mutate(files);
        }}>
              <Download className="h-4 w-4"/>
              {downloadMutation.isPending ? "Extracting…" : "Extract & Download"}
            </Button>

            {/* Extract & Import */}
            <Button className="flex-1 h-12 gap-2 bg-teal-600 hover:bg-teal-700 text-white" type="button" disabled={busy || !filesForUI.length} onClick={() => {
            const files = getFiles();
            if (files)
                importMutation.mutate(files);
        }}>
              <DatabaseIcon className="h-4 w-4"/>
              {importMutation.isPending ? "Importing…" : "Extract & Import"}
            </Button>
          </div>

          {error && <p className="mt-3 text-sm text-red-600">{error}</p>}
        </CardContent>
      </Card>
    </div>);
}
