// =================================================================
// pw-screens-leads.jsx — Publisher Admin · Content Leads
//
//   Readers who filled in a lead form on one of the publisher's own
//   content items. Distinct from ad-click lead brokering (Phase 8):
//   these are the publisher's own leads, not a third party's.
// =================================================================

const LEAD_STATUSES = [
  { label: "New", value: "new" },
  { label: "Contacted", value: "contacted" },
  { label: "Qualified", value: "qualified" },
  { label: "Archived", value: "archived" },
];
const LEAD_STATUS_TONE = { new: "info", contacted: "warn", qualified: "good", archived: "neutral" };

const csvCell = (value) => {
  const s = value == null ? "" : String(value);
  // Guard against a leading =/+/-/@ being executed when the export is opened in a spreadsheet.
  const safe = /^[=+\-@]/.test(s) ? `'${s}` : s;
  return `"${safe.replace(/"/g, '""')}"`;
};

const LeadDetail = ({ lead, onClose, onStatus }) => (
  <Drawer open={!!lead} onClose={onClose} width={480} title={lead ? (lead.full_name || lead.email || "Lead") : ""}>
    {lead && (
      <div style={{ display: "flex", flexDirection: "column", gap: 18 }}>
        <div style={{ display: "grid", gridTemplateColumns: "1fr 1fr", gap: 14 }}>
          <MiniStat label="Status" value={<Pill tone={LEAD_STATUS_TONE[lead.status] || "neutral"}>{lead.status}</Pill>}/>
          <MiniStat label="Received" value={fmt.date ? fmt.date(lead.created_at) : String(lead.created_at || "").slice(0, 10)}/>
          <MiniStat label="Content" value={lead.content_title || lead.content_id}/>
          <MiniStat label="Country" value={lead.country || "—"}/>
        </div>

        <div>
          <label className="pw-lbl">Submitted answers</label>
          <div className="pw-lead-fields">
            {Object.entries(lead.fields || {}).map(([key, value]) => (
              <div className="pw-lead-field" key={key}>
                <span className="pw-lead-key">{key}</span>
                <span className="pw-lead-val">{typeof value === "boolean" ? (value ? "Yes" : "No") : String(value)}</span>
              </div>
            ))}
            {Object.keys(lead.fields || {}).length === 0 && (
              <div style={{ fontSize: 13, color: "var(--muted)" }}>No answers recorded.</div>
            )}
          </div>
        </div>

        <div>
          <label className="pw-lbl">Move to</label>
          <div style={{ display: "flex", gap: 6, flexWrap: "wrap" }}>
            {LEAD_STATUSES.filter(s => s.value !== lead.status).map(s => (
              <Btn key={s.value} kind="secondary" size="sm" onClick={() => onStatus(lead, s.value)}>{s.label}</Btn>
            ))}
          </div>
        </div>
      </div>
    )}
    <style>{`
      .pw-lead-fields { display: flex; flex-direction: column; gap: 1px; background: var(--line-2); border: 1px solid var(--line); border-radius: var(--r-md); overflow: hidden; }
      .pw-lead-field { display: grid; grid-template-columns: 150px 1fr; gap: 12px; padding: 9px 12px; background: var(--panel); font-size: 13px; }
      .pw-lead-key { font-family: var(--mono); font-size: 11.5px; color: var(--muted); align-self: center; }
      .pw-lead-val { color: var(--ink); word-break: break-word; }
    `}</style>
  </Drawer>
);

const ContentLeadsScreen = () => {
  const [leads, setLeads] = React.useState([]);
  const [loading, setLoading] = React.useState(true);
  const [statusFilter, setStatusFilter] = React.useState("all");
  const [search, setSearch] = React.useState("");
  const [selected, setSelected] = React.useState(null);
  const [toast, setToast] = React.useState(null);

  const notify = (message, tone = "good") => {
    setToast({ message, tone });
    setTimeout(() => setToast(null), 4000);
  };

  const load = React.useCallback(async () => {
    setLoading(true);
    try {
      const res = await window.__api.read("listContentLeads");
      setLeads(res?.leads || (Array.isArray(res) ? res : []));
    } catch (e) {
      notify(e.message || "Could not load leads.", "bad");
    } finally {
      setLoading(false);
    }
  }, []);

  React.useEffect(() => { load(); }, [load]);

  const setStatus = async (lead, status) => {
    try {
      await window.__api.write("setContentLeadStatus", null, {
        params: { submission_id: lead.submission_id },
        body: { status },
      });
      setLeads(prev => prev.map(l => (l.submission_id === lead.submission_id ? { ...l, status } : l)));
      setSelected(prev => (prev && prev.submission_id === lead.submission_id ? { ...prev, status } : prev));
      notify(`Moved to ${status}.`);
    } catch (e) {
      notify(e.message || "Could not update the lead.", "bad");
    }
  };

  const filtered = leads.filter(l => {
    if (statusFilter !== "all" && l.status !== statusFilter) return false;
    const q = search.trim().toLowerCase();
    if (!q) return true;
    return [l.email, l.full_name, l.content_title, l.content_id].some(v => String(v || "").toLowerCase().includes(q));
  });

  const exportCsv = () => {
    // Union of every answer key present, so a form that gained a field still exports cleanly.
    const keys = [...new Set(filtered.flatMap(l => Object.keys(l.fields || {})))];
    const header = ["received", "status", "content", "name", "email", ...keys];
    const rows = filtered.map(l => [
      l.created_at, l.status, l.content_title || l.content_id, l.full_name, l.email,
      ...keys.map(k => l.fields?.[k]),
    ]);
    const csv = [header, ...rows].map(r => r.map(csvCell).join(",")).join("\n");
    const url = URL.createObjectURL(new Blob([csv], { type: "text/csv;charset=utf-8" }));
    const a = document.createElement("a");
    a.href = url;
    a.download = `content-leads-${new Date().toISOString().slice(0, 10)}.csv`;
    a.click();
    URL.revokeObjectURL(url);
  };

  const countBy = (status) => leads.filter(l => l.status === status).length;

  return (
    <Screen>
      <PageHead icon={IconUsers} title="Leads"
        subtitle="Readers who filled in a lead form on your content. Only the fields you declared on each item are captured."
        actions={<Btn kind="secondary" icon={<IconDownload size={14}/>} onClick={exportCsv} disabled={!filtered.length}>Export CSV</Btn>}/>

      <KpiGrid>
        <StatCard label="New" value={fmt.number(countBy("new"))} sub="Awaiting follow-up"/>
        <StatCard label="Contacted" value={fmt.number(countBy("contacted"))}/>
        <StatCard label="Qualified" value={fmt.number(countBy("qualified"))} sub="Worth passing on"/>
        <StatCard label="Total" value={fmt.number(leads.length)}/>
      </KpiGrid>

      <Card padded={false}>
        <div style={{ padding: "14px var(--pad)" }}>
          <Toolbar search={search} onSearchChange={setSearch} searchPlaceholder="Search name, email or content">
            <Select value={statusFilter} onChange={setStatusFilter} style={{ minWidth: 160 }}
              options={[{ label: "All statuses", value: "all" }, ...LEAD_STATUSES]}/>
          </Toolbar>
        </div>

        {loading ? (
          <div style={{ padding: 32, textAlign: "center", color: "var(--muted)" }}>Loading…</div>
        ) : filtered.length === 0 ? (
          <EmptyState icon={<IconUsers size={26}/>}
            title={leads.length ? "Nothing matches that filter" : "No leads yet"}
            description={leads.length
              ? "Try a different search or status."
              : "Add a lead form CTA to a content item and submissions will land here."}/>
        ) : (
          <div className="pw-lead-list">
            <div className="pw-lead-row head">
              <span>Received</span><span>Name</span><span>Email</span><span>Content</span><span>Status</span>
            </div>
            {filtered.map(lead => (
              <button className="pw-lead-row" key={lead.submission_id} onClick={() => setSelected(lead)}>
                <span className="pw-lead-when">{String(lead.created_at || "").slice(0, 10)}</span>
                <span>{lead.full_name || "—"}</span>
                <span className="pw-lead-email">{lead.email || "—"}</span>
                <span className="pw-lead-content">{lead.content_title || lead.content_id}</span>
                <span><Pill tone={LEAD_STATUS_TONE[lead.status] || "neutral"}>{lead.status}</Pill></span>
              </button>
            ))}
          </div>
        )}
      </Card>

      <LeadDetail lead={selected} onClose={() => setSelected(null)} onStatus={setStatus}/>

      {toast && <div className={`pw-toast ${toast.tone}`} role="status">{toast.message}</div>}

      <style>{`
        .pw-lead-list { display: flex; flex-direction: column; }
        .pw-lead-row { display: grid; grid-template-columns: 110px 1fr 1.3fr 1.3fr 110px; gap: 12px; align-items: center;
          padding: 11px var(--pad); border-top: 1px solid var(--line-2); background: transparent; border-left: 0;
          border-right: 0; border-bottom: 0; width: 100%; text-align: left; font: inherit; color: var(--ink); cursor: pointer; }
        .pw-lead-row:hover:not(.head) { background: var(--hover); }
        .pw-lead-row.head { cursor: default; font-size: 11.5px; text-transform: uppercase; letter-spacing: .05em;
          color: var(--muted); font-weight: 600; border-top: 0; }
        .pw-lead-row > span { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; font-size: 13px; }
        .pw-lead-when, .pw-lead-email { font-family: var(--mono); font-size: 12px; }
        .pw-lead-content { color: var(--muted); }
        @media (max-width: 900px) {
          .pw-lead-row { grid-template-columns: 1fr 1fr; }
          .pw-lead-row.head { display: none; }
        }
      `}</style>
    </Screen>
  );
};

Object.assign(window, { ContentLeadsScreen, LEAD_STATUSES });
