"use client";

import React, { useCallback, useEffect, useRef, useState } from "react";
import Select from "react-select";
import AsyncSelect from "react-select/async";
import toast from "react-hot-toast";
import ui from "./BatchForm.module.css";
import { fetchApi } from "@/lib/api/http";
import { getClientsPagedAll } from "@/lib/api/clients.api";
import { mapClientsToSearchRows } from "@/lib/api/mappers/clients.mappers";
import { createInquiry, INQUIRIES_API_BASE } from "@/lib/api/inquiry.api";

type StdOption = { value: number; label: string };
type SelectOption = { value: number | string; label: string; raw?: any };

const TYPE_OPTIONS = [
  { value: "SURVEILLANCE", label: "Surveillance" },
  { value: "RE_CERTIFICATION", label: "Re-Certification" },
  { value: "INITIAL", label: "New Client" },
];
const STAGE_OPTIONS = [
  { value: "Stage 1", label: "Stage 1" },
  { value: "Stage 2", label: "Stage 2" },
  { value: "Surveillance", label: "Surveillance" },
  { value: "Recertification", label: "Recertification" },
];
const DOC_TYPE_OPTIONS = [
  { value: "trade_license", label: "Trade License" },
  { value: "previous_certificate", label: "Previous Certificate" },
  { value: "audit_report", label: "Audit Report" },
  { value: "scope_letter", label: "Scope Letter" },
  { value: "other", label: "Other" },
];
const CERT_BODIES = ["QRS", "TQS"];

type PendingFile = { file: File; type: string };

type InquiryCard = {
  _key: string;
  _companyLabel: string;
  company_name: string;
  inquiry_type: string;
  audit_stage: string;
  audit_date: string;
  auditor_name: string;
  previous_cert_no: string;
  surveillance_audit_due: string;   // ✅ full field set
  recertification_due: string;      // ✅ full field set
  notes: string;
  standard_ids: number[];
  _files: PendingFile[];
};

const emptyCard = (): InquiryCard => ({
  _key: Math.random().toString(36).slice(2),
  _companyLabel: "",
  company_name: "",
  inquiry_type: "SURVEILLANCE",
  audit_stage: "",
  audit_date: "",
  auditor_name: "",
  previous_cert_no: "",
  surveillance_audit_due: "",
  recertification_due: "",
  notes: "",
  standard_ids: [],
  _files: [],
});

const uploadWithProgress = (
  inquiryId: number,
  files: PendingFile[],
  onProgress: (pct: number) => void,
): Promise<void> =>
  new Promise((resolve, reject) => {
    if (!files.length) return (onProgress(100), resolve());
    const fd = new FormData();
    files.forEach((pf) => fd.append("files", pf.file));
    fd.append("types", JSON.stringify(files.map((p) => p.type)));
    const token = localStorage.getItem("access_token");
    const xhr = new XMLHttpRequest();
    xhr.open("POST", `${INQUIRIES_API_BASE}/inquiries/${inquiryId}/upload-documents`);
    if (token) xhr.setRequestHeader("Authorization", `Bearer ${token}`);
    xhr.upload.onprogress = (e) =>
      e.lengthComputable && onProgress(Math.round((e.loaded / e.total) * 100));
    xhr.onload = () =>
      xhr.status >= 200 && xhr.status < 300
        ? (onProgress(100), resolve())
        : reject(new Error(`Upload failed (${xhr.status})`));
    xhr.onerror = () => reject(new Error("Upload failed (network error)"));
    xhr.send(fd);
  });

const selectPortal = {
  menuPortalTarget: typeof document !== "undefined" ? document.body : undefined,
  styles: { menuPortal: (b: any) => ({ ...b, zIndex: 3000 }) },
};

export default function BatchInquiryForm({
  onClose,
  onSuccess,
}: {
  onClose: () => void;
  onSuccess: () => void;
}) {
  const [certBody, setCertBody] = useState("QRS");
  const [cards, setCards] = useState<InquiryCard[]>([emptyCard()]);
  const [standards, setStandards] = useState<StdOption[]>([]);
  const [submitting, setSubmitting] = useState(false);
  const [phase, setPhase] = useState<"idle" | "creating" | "uploading">("idle");
  const [progress, setProgress] = useState<Record<string, number>>({});
  const fileInputs = useRef<Record<string, HTMLInputElement | null>>({});

  useEffect(() => {
    fetchApi<any[]>(`${INQUIRIES_API_BASE}/standards`)
      .then((s) =>
        setStandards(
          (s ?? []).map((x: any) => ({ value: x.id, label: `${x.name} — ${x.title}` })),
        ),
      )
      .catch(() => toast.error("Failed to load standards"));
  }, []);

  const setCard = (key: string, patch: Partial<InquiryCard>) =>
    setCards((prev) => prev.map((c) => (c._key === key ? { ...c, ...patch } : c)));

  const addCard = () => setCards((p) => [...p, emptyCard()]);

  const removeCard = (key: string) =>
    setCards((p) => (p.length > 1 ? p.filter((c) => c._key !== key) : p));

  // ✅ DUPLICATE — copies everything from the card (incl. files) into a new card below it
  const duplicateCard = (key: string) =>
    setCards((prev) => {
      const idx = prev.findIndex((c) => c._key === key);
      if (idx === -1) return prev;
      const src = prev[idx];
      const copy: InquiryCard = {
        ...src,
        _key: Math.random().toString(36).slice(2),
        standard_ids: [...src.standard_ids],
        _files: [...src._files],
      };
      const next = [...prev];
      next.splice(idx + 1, 0, copy);
      return next;
    });

  // ✅ CLIENT API search — identical to audit-request batch form
  const searchClients = useCallback(async (input: string): Promise<SelectOption[]> => {
    const q = input.trim();
    if (q.length < 10) return [];
    try {
      const res = await getClientsPagedAll({ search: q, limit: 20 });
      const rows = mapClientsToSearchRows(res.rows ?? []);
      const qLower = q.toLowerCase();
      const exact = rows.filter((c) => c.company_name.trim().toLowerCase() === qLower);
      const pool = exact.length
        ? exact
        : rows.filter((c) => c.company_name.toLowerCase().startsWith(qLower));
      return pool.slice(0, 5).map((c) => ({
        value: c.id,
        label:
          c.company_name +
          (c.Address ? ` — ${c.Address}` : "") +
          `  ·  ${c.client_type}`,
        raw: c,
      }));
    } catch {
      return [];
    }
  }, []);

  const validate = (): string | null => {
    for (let i = 0; i < cards.length; i++) {
      const c = cards[i], n = i + 1;
      if (!c.company_name.trim()) return `Inquiry ${n}: select a client.`;
      if (!c.audit_date) return `Inquiry ${n}: audit date is required.`;
      if (!c.auditor_name.trim()) return `Inquiry ${n}: auditor name is required.`;
    }
    return null;
  };

  const handleSubmit = async (e?: React.FormEvent) => {
    e?.preventDefault();
    const v = validate();
    if (v) return toast.error(v);

    let userId: number | undefined;
    try {
      const token = localStorage.getItem("access_token");
      if (token) {
        const p = JSON.parse(atob(token.split(".")[1]));
        userId = Number(p?.sub ?? p?.id ?? p?.userId) || undefined;
      }
    } catch {}

    setSubmitting(true);
    setPhase("creating");
    setProgress({});
    let created = 0, failed = 0, uploadFailed = false;

    for (const c of cards) {
      try {
        const inq: any = await createInquiry({
          inquiry_type: c.inquiry_type,
          company_name: c.company_name.trim(),
          cert_body: certBody,
          audit_stage: c.audit_stage || undefined,
          audit_date: c.audit_date,
          auditor_name: c.auditor_name.trim(),
          previous_cert_no: c.previous_cert_no || undefined,
          surveillance_audit_due: c.surveillance_audit_due || undefined, // ✅
          recertification_due: c.recertification_due || undefined,       // ✅
          notes: c.notes || undefined,
          standards: c.standard_ids,
          submitted_by_id: userId,
        } as any);
        created++;
        setPhase("uploading");
        if (c._files.length && inq?.id) {
          await uploadWithProgress(inq.id, c._files, (pct) =>
            setProgress((p) => ({ ...p, [c._key]: pct })),
          ).catch(() => {
            uploadFailed = true;
            setProgress((p) => ({ ...p, [c._key]: -1 }));
          });
        }
      } catch (err: any) {
        failed++;
        toast.error(`${c.company_name || "Inquiry"}: ${err?.message || "failed"}`);
      }
      setPhase("creating");
    }

    setSubmitting(false);
    setPhase("idle");
    if (created) {
      toast.success(
        `${created} inquir${created > 1 ? "ies" : "y"} submitted${failed ? `, ${failed} failed` : ""}.`,
      );
      if (uploadFailed) toast("Some documents failed — re-attach via Edit.", { icon: "⚠️" });
      onSuccess();
      onClose();
    }
  };

  return (
    <div className={ui.page}>
      <div className={ui.topbar}>
        <div className={ui.topbarLeft}>
          <button type="button" className={ui.backBtn} onClick={onClose} disabled={submitting}>←</button>
          <div>
            <h1 className={ui.pageTitle}>New Batch Inquiry</h1>
            <p className={ui.pageSub}>One inquiry per client · {cards.length} added</p>
          </div>
        </div>
        <div className={ui.topbarActions}>
          <button type="button" className={ui.btnGhost} onClick={onClose} disabled={submitting}>Cancel</button>
          <button type="button" className={ui.btnPrimary} onClick={() => handleSubmit()} disabled={submitting}>
            {submitting
              ? phase === "creating" ? "Creating…" : "Uploading…"
              : `Submit ${cards.length} Inquir${cards.length > 1 ? "ies" : "y"}`}
          </button>
        </div>
      </div>

      <div className={ui.content}>
        <form onSubmit={handleSubmit}>
          {/* Shared: Group */}
          <div className={ui.card}>
            <div className={ui.cardHead}>
              <div className={ui.cardHeadLeft}>
                <span className={ui.stepBadge}>1</span>
                <div>
                  <p className={ui.cardTitle}>Shared Scope</p>
                  <p className={ui.cardHint}>Applies to every inquiry in this batch</p>
                </div>
              </div>
            </div>
            <div className={ui.cardBody}>
              <label className={ui.req}>Group</label>
              <div className={ui.groupToggle}>
                {CERT_BODIES.map((g) => (
                  <button key={g} type="button"
                    className={`${ui.groupBtn} ${certBody === g ? ui.groupBtnActive : ""}`}
                    onClick={() => setCertBody(g)}>
                    {g}{certBody === g && <span className={ui.groupCheck}>✓</span>}
                  </button>
                ))}
              </div>
            </div>
          </div>

          {cards.map((c, i) => (
            <div key={c._key} className={ui.card}>
              <div className={ui.cardHead}>
                <div className={ui.cardHeadLeft}>
                  <span className={`${ui.stepBadge} ${ui.clientBadge}`}>{i + 1}</span>
                  <div>
                    <p className={ui.cardTitle}>{c.company_name || `Inquiry ${i + 1}`}</p>
                    <p className={ui.cardHint}>
                      {c.standard_ids.length} standard{c.standard_ids.length !== 1 ? "s" : ""} · {c._files.length} doc{c._files.length !== 1 ? "s" : ""}
                    </p>
                  </div>
                </div>
                <div style={{ display: "flex", gap: 8 }}>
                  {/* ✅ DUPLICATE BUTTON */}
                  <button type="button" className={ui.btnGhost}
                    style={{ padding: "6px 12px", fontSize: 12 }}
                    onClick={() => duplicateCard(c._key)} disabled={submitting}>
                    ⧉ Duplicate
                  </button>
                  {cards.length > 1 && (
                    <button type="button" className={ui.removeClientBtn}
                      onClick={() => removeCard(c._key)} disabled={submitting}>
                      Remove
                    </button>
                  )}
                </div>
              </div>

              <div className={ui.cardBody}>
                <div className={ui.grid}>
                  <div className={ui.full}>
                    <label className={`${ui.label} ${ui.req}`}>Client</label>
                    <AsyncSelect<SelectOption>
                      classNamePrefix="rselect" cacheOptions defaultOptions={false}
                      loadOptions={searchClients}
                      value={c._companyLabel ? { value: -1, label: c._companyLabel } : null}
                      onChange={(opt: any) =>
                        setCard(c._key, {
                          _companyLabel: opt?.label ?? "",
                          company_name: opt?.raw?.company_name ?? "",
                        })
                      }
                      placeholder="Type the full company name (min 10 chars)…"
                      noOptionsMessage={({ inputValue }) =>
                        inputValue.length < 10
                          ? `Type the full company name (${10 - inputValue.length} more chars needed)`
                          : `No client found matching "${inputValue}"`}
                      loadingMessage={() => "Searching…"} isClearable {...selectPortal}
                    />
                  </div>

                  <div className={`${ui.field} ${ui.half}`}>
                    <label className={ui.req}>Inquiry Type</label>
                    <Select classNamePrefix="rselect" options={TYPE_OPTIONS}
                      value={TYPE_OPTIONS.find((o) => o.value === c.inquiry_type)}
                      onChange={(o: any) => o && setCard(c._key, { inquiry_type: o.value })}
                      isSearchable={false} {...selectPortal} />
                  </div>

                  <div className={`${ui.field} ${ui.half}`}>
                    <label className={ui.label}>Audit Stage</label>
                    <Select classNamePrefix="rselect" options={STAGE_OPTIONS}
                      value={STAGE_OPTIONS.find((o) => o.value === c.audit_stage) || null}
                      onChange={(o: any) => setCard(c._key, { audit_stage: o?.value ?? "" })}
                      isClearable isSearchable={false} placeholder="Select stage…" {...selectPortal} />
                  </div>

                  <div className={ui.full}>
                    <label className={`${ui.label} ${ui.req}`}>Standards</label>
                    <Select classNamePrefix="rselect" isMulti options={standards}
                      value={standards.filter((o) => c.standard_ids.includes(o.value))}
                      onChange={(opts: any) =>
                        setCard(c._key, { standard_ids: (opts ?? []).map((o: any) => o.value) })}
                      placeholder="Pick standards…" {...selectPortal} />
                  </div>

                  <div className={`${ui.field} ${ui.half}`}>
                    <label className={ui.req}>Audit Date</label>
                    <input type="date" className={ui.input} value={c.audit_date}
                      onChange={(e) => setCard(c._key, { audit_date: e.target.value })} />
                  </div>

                  <div className={`${ui.field} ${ui.half}`}>
                    <label className={ui.req}>Auditor Name</label>
                    <input type="text" className={ui.input} value={c.auditor_name}
                      placeholder="e.g. MR. HASSAN AL MALIK"
                      onChange={(e) => setCard(c._key, { auditor_name: e.target.value })} />
                  </div>

                  <div className={`${ui.field} ${ui.half}`}>
                    <label className={ui.label}>Previous Cert No.</label>
                    <input type="text" className={ui.input} value={c.previous_cert_no}
                      onChange={(e) => setCard(c._key, { previous_cert_no: e.target.value })} />
                  </div>

                  {/* ✅ Due dates — same fields as single InquiryForm */}
                  <div className={`${ui.field} ${ui.half}`}>
                    <label className={ui.label}>Surveillance Audit Due</label>
                    <input type="date" className={ui.input} value={c.surveillance_audit_due}
                      onChange={(e) => setCard(c._key, { surveillance_audit_due: e.target.value })} />
                  </div>

                  <div className={`${ui.field} ${ui.half}`}>
                    <label className={ui.label}>Recertification Due</label>
                    <input type="date" className={ui.input} value={c.recertification_due}
                      onChange={(e) => setCard(c._key, { recertification_due: e.target.value })} />
                  </div>

                  <div className={ui.full}>
                    <label className={ui.label}>Notes</label>
                    <textarea className={ui.textarea} rows={2} value={c.notes}
                      onChange={(e) => setCard(c._key, { notes: e.target.value })}
                      placeholder="Additional info from the client email…" />
                  </div>

                  {/* Documents */}
                  <div className={ui.full}>
                    <label className={ui.label}>Supporting Documents</label>
                    <div className={ui.dropzone}
                      onClick={() => !submitting && fileInputs.current[c._key]?.click()}
                      onDragOver={(e) => e.preventDefault()}
                      onDrop={(e) => {
                        e.preventDefault();
                        if (submitting) return;
                        const picked = Array.from(e.dataTransfer.files ?? []);
                        setCard(c._key, {
                          _files: [...c._files, ...picked.map((f) => ({ file: f, type: "trade_license" }))],
                        });
                      }}>
                      <div className={ui.dropzoneIcon}>📎</div>
                      <div>
                        <div className={ui.dropzoneText}>Drag &amp; drop, or <span>click to browse</span></div>
                        <div className={ui.dropzoneHint}>PDF, JPG, PNG, DOC — new picks are added</div>
                      </div>
                    </div>
                    <input ref={(el) => { fileInputs.current[c._key] = el; }} type="file" multiple
                      className={ui.hiddenInput}
                      onChange={(e) => {
                        const picked = Array.from(e.target.files ?? []);
                        setCard(c._key, {
                          _files: [...c._files, ...picked.map((f) => ({ file: f, type: "trade_license" }))],
                        });
                        e.target.value = "";
                      }} />

                    {c._files.length > 0 && (
                      <div className={ui.fileList}>
                        {c._files.map((pf, fi) => (
                          <div key={fi} className={ui.fileItem}>
                            <span>📄</span>
                            <span className={ui.fileName}>{pf.file.name}</span>
                            <select value={pf.type}
                              onChange={(e) =>
                                setCard(c._key, {
                                  _files: c._files.map((p, j) => (j === fi ? { ...p, type: e.target.value } : p)),
                                })}
                              style={{ fontSize: 12, padding: "3px 6px", borderRadius: 6, border: "1px solid #d1d5db" }}>
                              {DOC_TYPE_OPTIONS.map((t) => (
                                <option key={t.value} value={t.value}>{t.label}</option>
                              ))}
                            </select>
                            <span className={ui.fileSize}>{(pf.file.size / 1024).toFixed(0)} KB</span>
                            {!submitting && (
                              <button type="button" className={ui.fileRemove}
                                onClick={() =>
                                  setCard(c._key, { _files: c._files.filter((_, j) => j !== fi) })}>
                                ✕
                              </button>
                            )}
                          </div>
                        ))}
                      </div>
                    )}

                    {phase === "uploading" && progress[c._key] !== undefined && (
                      <div className={ui.progressWrap}>
                        <div className={ui.progressTrack}>
                          <div
                            className={`${ui.progressFill} ${progress[c._key] < 0 ? ui.progressFillError : progress[c._key] >= 100 ? ui.progressFillDone : ""}`}
                            style={{ width: `${progress[c._key] < 0 ? 100 : progress[c._key]}%` }} />
                        </div>
                        <span className={ui.progressLabel}>
                          {progress[c._key] < 0 ? "Failed" : progress[c._key] >= 100 ? "✓ Done" : `${progress[c._key]}%`}
                        </span>
                      </div>
                    )}
                  </div>
                </div>
              </div>
            </div>
          ))}

          <button type="button" className={ui.addClientBtn} onClick={addCard} disabled={submitting}>
            + Add Another Client
          </button>
        </form>
      </div>
    </div>
  );
}