import fs from "fs";
import path from "path";
import axios from "axios";
import FormData from "form-data";
import { storage } from "../storage";
import { callPythonSync } from "../queue/processors/_shared";
import * as paymentService from "./paymentService";

const VOUCHER_DIR = path.join(__dirname, "..", "..", "uploads", "MHVoucher");
const IMPORTED_LOG = path.join(VOUCHER_DIR, "imported_vouchers.json");
const OCR_BASE_URL = process.env.OCR_SERVICE_BASE_URL || "http://localhost:5003";

function loadImportedVouchers(): Set<string> {
  try {
    if (!fs.existsSync(IMPORTED_LOG)) return new Set();
    const data = JSON.parse(fs.readFileSync(IMPORTED_LOG, "utf-8"));
    return new Set(data.imported ?? []);
  } catch {
    return new Set();
  }
}

function saveImportedVoucher(voucher: string) {
  const existing = loadImportedVouchers();
  existing.add(voucher);
  fs.writeFileSync(IMPORTED_LOG, JSON.stringify({ imported: [...existing].sort() }, null, 2));
}

async function extractAndImportVoucherPdf(filePath: string, userId: number): Promise<{ paymentIds: number[]; rowCount: number }> {
  const buffer = fs.readFileSync(filePath);
  const filename = path.basename(filePath);

  const form = new FormData();
  form.append("files", buffer, { filename, contentType: "application/pdf", knownLength: buffer.length });

  const resp = await axios.post<{ rows: any[] }>(
    `${OCR_BASE_URL}/extract/pdf/json`,
    form,
    { headers: form.getHeaders(), maxBodyLength: Infinity, maxContentLength: Infinity, timeout: 120_000 }
  );

  const rows = resp.data?.rows ?? [];
  console.log(`[mh-batch] Extracted ${rows.length} rows from ${filename}`);
  if (rows.length === 0) return { paymentIds: [], rowCount: 0 };

  const paymentIds = await paymentService.pdfImportService.importRows(rows, userId);
  return { paymentIds, rowCount: rows.length };
}

export interface MhBatchCheckResult {
  noResults?: boolean;
  message?: string;
  importSummary?: string;
  importResults?: { voucher: string; paymentIds: number[]; rowCount: number; error?: string }[];
}

export async function runMhBatchPaymentCheck(userId: number, fromDate: string, toDate: string): Promise<MhBatchCheckResult> {
  const credentials = await storage.getInsuranceCredentialByUserAndSiteKey(userId, "MH");
  if (!credentials) {
    throw new Error("No MassHealth credentials found. Please add them in Settings.");
  }

  const seleniumResult = await callPythonSync("/mh-batch-payment-check", {
    data: {
      massdhpUsername: credentials.username,
      massdhpPassword: credentials.password,
      fromDate,
      toDate,
    },
  });

  const alreadyImported = loadImportedVouchers();
  const allPdfs = fs.existsSync(VOUCHER_DIR)
    ? fs.readdirSync(VOUCHER_DIR).filter((f) => f.endsWith(".pdf") && !f.startsWith("remittance_search_"))
    : [];
  const newPdfs = allPdfs.filter((f) => !alreadyImported.has(f.replace(".pdf", "")));

  console.log(`[mh-batch] ${allPdfs.length} voucher PDFs total, ${newPdfs.length} new to import`);

  const importResults: { voucher: string; paymentIds: number[]; rowCount: number; error?: string }[] = [];

  for (const pdfFile of newPdfs) {
    const voucher = pdfFile.replace(".pdf", "");
    const filePath = path.join(VOUCHER_DIR, pdfFile);
    try {
      const { paymentIds, rowCount } = await extractAndImportVoucherPdf(filePath, userId);
      saveImportedVoucher(voucher);
      importResults.push({ voucher, paymentIds, rowCount });
      console.log(`[mh-batch] ✓ ${voucher}: ${rowCount} rows → ${paymentIds.length} payment(s)`);
    } catch (err: any) {
      const errMsg = err?.response?.data?.detail ?? err.message ?? "Unknown error";
      console.error(`[mh-batch] ✗ ${voucher}: ${errMsg}`);
      importResults.push({ voucher, paymentIds: [], rowCount: 0, error: errMsg });
    }
  }

  const succeeded = importResults.filter((r) => !r.error);
  const failed = importResults.filter((r) => r.error);

  return {
    ...seleniumResult,
    importResults,
    importSummary: newPdfs.length === 0
      ? "All PDFs already imported."
      : `${succeeded.length} of ${newPdfs.length} PDFs imported successfully${failed.length ? `, ${failed.length} failed` : ""}.`,
  };
}
