// =================================================================
// pw-screens-publisher.jsx — Publisher Admin §1–4
//   OverviewScreen · MyPlanScreen · ConsumerPlansScreen · SubscribersScreen
// =================================================================

// ---------- helper: KPI grid ----------
const KpiGrid = ({ children }) => (
  <div className="pw-kpi-grid">
    {children}
    <style>{`
      .pw-kpi-grid { display: grid; gap: var(--gap); grid-template-columns: repeat(5, 1fr); }
      .pw-kpi-grid > * { min-width: 0; }
      @media (max-width: 1180px) { .pw-kpi-grid { grid-template-columns: repeat(3, 1fr); } }
      @media (max-width: 720px)  { .pw-kpi-grid { grid-template-columns: repeat(2, 1fr); } }
    `}</style>
  </div>
);

// =================================================================
// §1 Overview
// =================================================================
const OverviewScreen = ({ data }) => {
  const pub = window.PAYWALL_CONFIG.publisherContext;
  const me = (data.publishers || []).find(p => p.id === pub.id) || (data.publishers || [])[0] || {};
  const activeSubs = me.subscribers || data.subscribers.filter(s => ["active", "trialing"].includes(s.status)).length;
  const coinsWeek = data.coinsByDay.slice(-7).reduce((a, b) => a + b, 0);
  const couponsRevealed = data.couponOffers.reduce((a, o) => a + o.claimed_count, 0);
  const brands = new Set(data.storeDiscountCodes.map(c => c.advertiser_id)).size;
  const tiersDefined = data.adTiers.filter(t => t.status === "active").length;

  const sub = data.publisherSubscription;
  const plan = data.platformPlans.find(p => p.plan_code === sub.plan_code);
  const cfg = data.adConfig;
  const tierName = (code) => (data.adTiers.find(t => t.tier_code === code) || {}).name || "—";

  return (
    <Screen>
      <PageHead icon={IconChart} title="Overview"
        subtitle={`${pub.name} · paywall, engagement and ad performance at a glance.`}
        actions={<Pill tone="accent" style={{ whiteSpace: "nowrap" }}>{plan ? plan.name : sub.plan_code} plan</Pill>}/>

      <KpiGrid>
        <StatCard label="Active subscribers" value={fmt.compact(activeSubs)} delta="+4.8%" deltaTone="good" sub="vs last week" icon={<IconUsers size={16}/>}/>
        <StatCard label="Coins granted (7d)" value={fmt.compact(coinsWeek)} delta="+12%" deltaTone="good" sub="this week" icon={<IconCoin size={16}/>}/>
        <StatCard label="Coupons revealed" value={fmt.number(couponsRevealed)} sub="all offers" icon={<IconGift size={16}/>}/>
        <StatCard label="Assigned brands" value={brands} sub="discount partners" icon={<IconTag size={16}/>}/>
        <StatCard label="Ad tiers" value={tiersDefined} sub="active levels" icon={<IconAd size={16}/>}/>
      </KpiGrid>

      <div className="pw-2col">
        <Card title="New subscribers" subtitle="Last 30 days" >
          <LineChart data={data.signupsByDay} height={240}
            formatValue={(v) => fmt.number(v)}
            axisLabels={["30d ago", "", "Today"]} showArea showGrid showYAxis curve="monotone"/>
        </Card>

        <Card title="Recent activity" padded={false}>
          <div className="pw-activity">
            {data.activity.map(a => {
              const I = window[a.icon] || IconInfo;
              return (
                <div key={a.id} className="pw-act-row">
                  <span className="pw-act-icon"><I size={15}/></span>
                  <div style={{ minWidth: 0, flex: 1 }}>
                    <div className="pw-act-title">{a.title}</div>
                    <div className="pw-act-body">{a.body}</div>
                  </div>
                  <span className="pw-act-time">{a.at}</span>
                </div>
              );
            })}
          </div>
        </Card>
      </div>

      <Card title="Effective ad policy" subtitle="Default tier applied to each access class (least-ads-wins resolves at decision time).">
        <div className="pw-adpolicy">
          {[
            ["Anonymous", cfg.anonymous_tier_code], ["Paid (single)", cfg.paid_tier_code],
            ["Day pass", cfg.day_pass_tier_code], ["Courtesy share", cfg.courtesy_tier_code],
            ["Subscription", cfg.subscription_tier_code],
          ].map(([label, code]) => (
            <div key={label} className="pw-adpolicy-cell">
              <span className="pw-adpolicy-class">{label}</span>
              <span className="pw-adpolicy-tier">{tierName(code)}</span>
              <AdLoadBar tier={data.adTiers.find(t => t.tier_code === code)} width="100%"/>
            </div>
          ))}
        </div>
      </Card>

      <style>{`
        .pw-2col { display: grid; grid-template-columns: 1.5fr 1fr; gap: var(--gap); }
        .pw-2col > * { min-width: 0; }
        @media (max-width: 1023px) { .pw-2col { grid-template-columns: 1fr; } }
        .pw-activity { display: flex; flex-direction: column; }
        .pw-act-row { display: flex; gap: 12px; align-items: flex-start; padding: 12px var(--pad); border-bottom: 1px solid var(--line-2); }
        .pw-act-row:last-child { border-bottom: none; }
        .pw-act-icon { width: 30px; height: 30px; border-radius: 8px; background: var(--accent-soft); color: var(--accent); display: inline-flex; align-items: center; justify-content: center; flex-shrink: 0; }
        .pw-act-title { font-size: 13.5px; font-weight: 500; color: var(--ink); }
        .pw-act-body { font-size: 12.5px; color: var(--muted); margin-top: 2px; }
        .pw-act-time { font-size: 11.5px; color: var(--muted-2); white-space: nowrap; }
        .pw-adpolicy { display: grid; grid-template-columns: repeat(5, 1fr); gap: 14px; }
        @media (max-width: 900px) { .pw-adpolicy { grid-template-columns: repeat(2, 1fr); } }
        .pw-adpolicy-cell { display: flex; flex-direction: column; gap: 8px; padding: 14px; border: 1px solid var(--line); border-radius: var(--r-md); background: var(--panel-2); }
        .pw-adpolicy-class { font-size: 12px; color: var(--muted); }
        .pw-adpolicy-tier { font-size: 15px; font-weight: 600; color: var(--ink); }
      `}</style>
    </Screen>
  );
};

// =================================================================
// §2 My Plan (platform subscription)
// =================================================================
const MyPlanScreen = ({ data, setData }) => {
  const sub = data.publisherSubscription;
  const current = data.platformPlans.find(p => p.plan_code === sub.plan_code);
  const [pending, setPending] = React.useState(null);

  const checkout = async (plan) => {
    setPending(plan.plan_code);
    window.__toast(`Opening ${sub.gateway} checkout for ${plan.name}…`);
    try {
      await window.__api.write("publisherCheckout",
        d => ({ ...d, publisherSubscription: { ...d.publisherSubscription, plan_code: plan.plan_code } }),
        { body: { plan_code: plan.plan_code, gateway: sub.gateway }, ok: `Subscribed to ${plan.name}`, err: "Checkout failed" });
    } catch (e) {}
    setPending(null);
  };

  const rank = (c) => ["starter", "growth", "scale", "enterprise"].indexOf(c);

  return (
    <Screen>
      <PageHead icon={IconReceipt} title="My Plan" subtitle="Your Krafts Paywall platform subscription." />

      <Card>
        <div className="pw-curplan">
          <div>
            <div style={{ display: "flex", alignItems: "center", gap: 10 }}>
              <h3 style={{ margin: 0, fontSize: 20, fontWeight: 600 }}>{current ? current.name : sub.plan_code}</h3>
              <StatusPill status={sub.status}/>
              {sub.cancel_at_period_end && <Pill tone="warn">Cancels {fmt.date(sub.current_period_end)}</Pill>}
            </div>
            <div style={{ color: "var(--muted)", fontSize: 13.5, marginTop: 8 }}>
              {pwMoney(current?.price_fiat)}{current?.price_fiat ? `/${current.interval}` : ""} · via {sub.gateway} ·
              renews {fmt.date(sub.current_period_end)}
            </div>
          </div>
          <KeyValueList items={[
            { k: "Subscription", v: <span style={{ fontFamily: "var(--mono)", fontSize: 12.5 }}>{sub.subscription_id}</span> },
            { k: "Period", v: `${fmt.date(sub.current_period_start)} → ${fmt.date(sub.current_period_end)}` },
            { k: "Gateway", v: <span style={{ textTransform: "capitalize" }}>{sub.gateway}</span> },
          ]}/>
        </div>
      </Card>

      <FormSection title="Available plans" description="Subscribe or upgrade. Checkout opens in your configured gateway." />
      <div className="pw-plan-grid">
        {data.platformPlans.map(p => {
          const isCurrent = p.plan_code === sub.plan_code;
          const isUpgrade = rank(p.plan_code) > rank(sub.plan_code);
          return (
            <div key={p.plan_code} className={`pw-plan-card ${isCurrent ? "on" : ""}`}>
              <div className="pw-plan-top">
                <div className="pw-plan-name">{p.name}</div>
                {isCurrent && <Pill tone="accent">Current</Pill>}
              </div>
              <div className="pw-plan-price">
                {pwMoney(p.price_fiat)}
                {p.price_fiat ? <span className="pw-plan-int">/{p.interval}</span> : null}
              </div>
              <ul className="pw-plan-feats">
                {p.features.map((f, i) => <li key={i}><IconCheck size={13}/> {f}</li>)}
              </ul>
              <div style={{ marginTop: "auto", paddingTop: 14 }}>
                {isCurrent
                  ? <Btn kind="secondary" disabled style={{ width: "100%", justifyContent: "center" }}>Current plan</Btn>
                  : p.price_fiat == null
                    ? <Btn kind="secondary" onClick={() => window.__toast("Contact sales — request sent")} style={{ width: "100%", justifyContent: "center" }}>Contact sales</Btn>
                    : <Btn kind="primary" disabled={pending === p.plan_code} onClick={() => checkout(p)} style={{ width: "100%", justifyContent: "center" }}>
                        {pending === p.plan_code ? "Redirecting…" : isUpgrade ? "Upgrade" : "Switch"}
                      </Btn>}
              </div>
            </div>
          );
        })}
      </div>

      <style>{`
        .pw-curplan { display: grid; grid-template-columns: 1.2fr 1fr; gap: 28px; align-items: center; }
        @media (max-width: 860px) { .pw-curplan { grid-template-columns: 1fr; gap: 18px; } }
        .pw-plan-grid { display: grid; grid-template-columns: repeat(4, 1fr); gap: var(--gap); }
        @media (max-width: 1100px) { .pw-plan-grid { grid-template-columns: repeat(2, 1fr); } }
        @media (max-width: 560px) { .pw-plan-grid { grid-template-columns: 1fr; } }
        .pw-plan-card { display: flex; flex-direction: column; border: 1px solid var(--line); border-radius: var(--r-md); padding: var(--pad); background: var(--panel); box-shadow: var(--shadow-1); }
        .pw-plan-card.on { border-color: var(--accent); box-shadow: 0 0 0 1px var(--accent); }
        .pw-plan-top { display: flex; justify-content: space-between; align-items: center; gap: 8px; }
        .pw-plan-name { font-size: 15px; font-weight: 600; }
        .pw-plan-price { font-size: 26px; font-weight: 600; letter-spacing: -.02em; margin: 10px 0 14px; }
        .pw-plan-int { font-size: 13px; color: var(--muted); font-weight: 400; }
        .pw-plan-feats { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 9px; }
        .pw-plan-feats li { display: flex; gap: 8px; align-items: flex-start; font-size: 13px; color: var(--ink-2); }
        .pw-plan-feats svg { color: var(--accent); flex-shrink: 0; margin-top: 2px; }
      `}</style>
    </Screen>
  );
};

// =================================================================
// §2b Integration Kits
// =================================================================
const IntegrationKitsScreen = ({ data }) => {
  const pub = window.PAYWALL_CONFIG.publisherContext;
  const apiBase = (window.__api.getConfig().baseUrl || "https://api.example.com").replace(/\/+$/, "");
  const publisherId = pub.id || "pub_we72";
  const snippet = `<script src="${apiBase}/sdk/paywall-ads.js" async></script>
<script>
  window.DropcapPaywall = {
    publisherId: "${publisherId}",
    apiBaseUrl: "${apiBase}"
  };
</script>`;

  const kits = [
    {
      id: "web",
      title: "Website JavaScript",
      file: "paywall-ads.js",
      href: "sdk/paywall-ads.js",
      meta: "Browser snippet for CMS templates and article pages.",
    },
    {
      id: "android",
      title: "Android SDK",
      file: "PaywallAds.kt",
      href: "sdk/PaywallAds.kt",
      meta: "Kotlin reference SDK for native Android apps.",
    },
    {
      id: "ios",
      title: "iOS SDK",
      file: "PaywallAds.swift",
      href: "sdk/PaywallAds.swift",
      meta: "Swift reference SDK for native iOS apps.",
    },
    {
      id: "flutter",
      title: "Flutter SDK",
      file: "paywall_ads.dart",
      href: "sdk/paywall_ads.dart",
      meta: "Dart reference SDK for Flutter apps.",
    },
  ];

  const downloadKit = (kit) => {
    const a = document.createElement("a");
    a.href = kit.href;
    a.download = kit.file;
    document.body.appendChild(a);
    a.click();
    a.remove();
    window.__toast(`Downloaded ${kit.file}`);
  };

  return (
    <Screen>
      <PageHead icon={IconDownload} title="Integration Kits" subtitle="Download the web script and native app SDK starters for this publisher." />

      <div className="pw-kit-grid">
        {kits.map(k => (
          <Card key={k.id}>
            <div className="pw-kit-head">
              <span className="pw-kit-icon"><IconDownload size={16}/></span>
              <div>
                <div className="pw-kit-title">{k.title}</div>
                <div className="pw-kit-meta">{k.meta}</div>
              </div>
            </div>
            <div className="pw-kit-file">{k.file}</div>
            <Btn kind="primary" icon={<IconDownload size={14}/>} onClick={() => downloadKit(k)} style={{ width: "100%", justifyContent: "center" }}>Download</Btn>
          </Card>
        ))}
      </div>

      <Card title="Website install snippet" subtitle={`${pub.name} · publisher_id ${publisherId}`}>
        <pre className="pw-snippet"><code>{snippet}</code></pre>
        <Btn kind="secondary" icon={<IconCopy size={14}/>} onClick={() => { navigator.clipboard?.writeText(snippet); window.__toast("Snippet copied"); }}>Copy snippet</Btn>
      </Card>

      <style>{`
        .pw-kit-grid { display: grid; grid-template-columns: repeat(4, 1fr); gap: var(--gap); }
        .pw-kit-grid > * { min-width: 0; }
        @media (max-width: 1120px) { .pw-kit-grid { grid-template-columns: repeat(2, 1fr); } }
        @media (max-width: 640px) { .pw-kit-grid { grid-template-columns: 1fr; } }
        .pw-kit-head { display: flex; align-items: flex-start; gap: 12px; min-height: 76px; }
        .pw-kit-icon { width: 34px; height: 34px; border-radius: 8px; background: var(--accent-soft); color: var(--accent); display: inline-flex; align-items: center; justify-content: center; flex-shrink: 0; }
        .pw-kit-title { font-size: 15px; font-weight: 600; color: var(--ink); }
        .pw-kit-meta { font-size: 12.5px; color: var(--muted); line-height: 1.45; margin-top: 4px; }
        .pw-kit-file { font-family: var(--mono); font-size: 12px; color: var(--ink-2); background: var(--panel-2); border: 1px solid var(--line); border-radius: var(--r-sm); padding: 10px 12px; margin: 14px 0; overflow-wrap: anywhere; }
        .pw-snippet { margin: 0 0 14px; white-space: pre-wrap; word-break: break-word; background: var(--panel-2); border: 1px solid var(--line); border-radius: var(--r-md); padding: 14px; color: var(--ink-2); font-size: 12.5px; line-height: 1.5; }
      `}</style>
    </Screen>
  );
};

// =================================================================
// §3 Consumer Plans
// =================================================================
const PlanFormDrawer = ({ open, onClose, plan, adTiers, onSave }) => {
  const blank = { name: "", price_fiat: 4.99, currency: "USD", interval: "month", scope: { all_access: true }, ad_tier_code: null, status: "active" };
  const [f, setF] = React.useState(blank);
  React.useEffect(() => { if (open) setF(plan ? JSON.parse(JSON.stringify(plan)) : blank); }, [open, plan]);
  const set = (patch) => setF(prev => ({ ...prev, ...patch }));
  const scopeMode = f.scope?.all_access ? "all" : "specific";
  const contentIds = (f.scope?.content_ids || []).join(", ");

  const tierOpts = [{ label: "Use class default", value: "" }, ...adTiers.filter(t => t.status === "active").map(t => ({ label: `${t.name} (${t.tier_code})`, value: t.tier_code }))];

  return (
    <Drawer open={open} onClose={onClose} title={plan ? "Edit consumer plan" : "New consumer plan"} width={520}
      footer={<>
        <Btn kind="secondary" onClick={onClose}>Cancel</Btn>
        <Btn kind="primary" disabled={!f.name} onClick={() => { onSave(f); onClose(); }}>{plan ? "Save changes" : "Create plan"}</Btn>
      </>}>
      <div style={{ display: "flex", flexDirection: "column", gap: 4 }}>
        <FieldRow label="Plan name" layout="stacked">
          <Input value={f.name} onChange={e => set({ name: e.target.value })} placeholder="Digital Monthly"/>
        </FieldRow>
        <FieldRow label="Price & billing" layout="stacked">
          <FieldGroup cols={3}>
            <Input prefix="$" type="number" value={f.price_fiat} onChange={e => set({ price_fiat: Number(e.target.value) || 0 })}/>
            <Select value={f.currency} onChange={v => set({ currency: v })} options={["USD", "EUR", "GBP", "INR"]}/>
            <SegmentedControl value={f.interval} onChange={v => set({ interval: v })} options={[{ label: "Monthly", value: "month" }, { label: "Yearly", value: "year" }]}/>
          </FieldGroup>
        </FieldRow>

        <FieldRow label="Access scope" hint="What this plan unlocks." layout="stacked">
          <SegmentedControl value={scopeMode} onChange={(v) => set({ scope: v === "all" ? { all_access: true } : { content_ids: f.scope?.content_ids || [] } })}
            options={[{ label: "All access", value: "all" }, { label: "Specific content IDs", value: "specific" }]}/>
          {scopeMode === "specific" && (
            <div style={{ marginTop: 10 }}>
              <Textarea rows={2} value={contentIds} placeholder="investigations, longform, data-desk"
                onChange={e => set({ scope: { content_ids: e.target.value.split(",").map(s => s.trim()).filter(Boolean) } })}/>
              <InlineHelp icon={<IconInfo size={13}/>}>Comma-separated content IDs.</InlineHelp>
            </div>
          )}
        </FieldRow>

        <FieldRow label="Ad tier" hint="Overrides the access-class default for buyers of this plan." layout="stacked">
          <Select value={f.ad_tier_code || ""} onChange={v => set({ ad_tier_code: v || null })} options={tierOpts}/>
          {f.ad_tier_code && (
            <InlineHelp icon={<IconAd size={13}/>}>{adTierSummary(adTiers.find(t => t.tier_code === f.ad_tier_code))}</InlineHelp>
          )}
        </FieldRow>

        <FieldRow label="Status" layout="stacked">
          <SegmentedControl value={f.status} onChange={v => set({ status: v })} options={[{ label: "Active", value: "active" }, { label: "Draft", value: "draft" }, { label: "Retired", value: "retired" }]}/>
        </FieldRow>
      </div>
    </Drawer>
  );
};

const ConsumerPlansScreen = ({ data, setData }) => {
  const [drawer, setDrawer] = React.useState(false);
  const [editing, setEditing] = React.useState(null);
  const [q, setQ] = React.useState("");

  const tierName = (code) => code ? ((data.adTiers.find(t => t.tier_code === code) || {}).name || code) : "Class default";

  const save = (f) => {
    if (editing) {
      window.__api.write("updatePlan",
        d => ({ ...d, consumerPlans: d.consumerPlans.map(p => p.plan_id === editing.plan_id ? { ...p, ...f } : p) }),
        { params: { plan_id: editing.plan_id }, body: f, ok: `Updated “${f.name}”`, err: "Couldn’t update plan" });
    } else {
      const plan_id = "pl_" + Math.random().toString(36).slice(2, 7);
      window.__api.write("createPlan",
        d => ({ ...d, consumerPlans: [{ ...f, plan_id }, ...d.consumerPlans] }),
        { body: { ...f, plan_id }, ok: `Created “${f.name}”`, err: "Couldn’t create plan" });
    }
  };

  const rows = data.consumerPlans.filter(p => p.name.toLowerCase().includes(q.toLowerCase()));

  return (
    <Screen>
      <PageHead icon={IconList} title="Consumer Plans" subtitle="Subscription plans you sell to your readers."
        actions={<Btn kind="primary" icon={<IconPlus size={15}/>} onClick={() => { setEditing(null); setDrawer(true); }}>New plan</Btn>}/>

      <Toolbar search={q} onSearchChange={setQ} searchPlaceholder="Search plans"/>

      <DataTable rows={rows} keyField="plan_id" rowsPerPage={8}
        onRowClick={(r) => { setEditing(r); setDrawer(true); }}
        empty={<EmptyState icon={<IconList size={30}/>} title="No plans yet" description="Create the first plan you sell to readers." action={<Btn kind="primary" onClick={() => { setEditing(null); setDrawer(true); }}>New plan</Btn>}/>}
        columns={[
          { key: "name", label: "Plan", render: r => <strong style={{ color: "var(--ink)" }}>{r.name}</strong> },
          { key: "price_fiat", label: "Price", align: "right", accessor: r => r.price_fiat,
            render: r => <span style={{ fontFamily: "var(--mono)", fontSize: 12.5 }}>{pwMoney(r.price_fiat, r.currency)}<span style={{ color: "var(--muted)" }}>{r.price_fiat ? `/${r.interval === "year" ? "yr" : "mo"}` : ""}</span></span> },
          { key: "scope", label: "Scope", sortable: false, render: r => r.scope?.all_access ? <Pill tone="info">All access</Pill> : <span style={{ fontSize: 12.5, color: "var(--muted)" }}>{(r.scope?.content_ids || []).length} sections</span> },
          { key: "ad_tier_code", label: "Ad tier", render: r => <span style={{ fontSize: 13 }}>{tierName(r.ad_tier_code)}</span> },
          { key: "status", label: "Status", render: r => <StatusPill status={r.status}/> },
          { key: "_e", label: "", sortable: false, align: "right", render: r => <Btn kind="ghost" size="sm" icon={<IconPencil size={14}/>} onClick={() => { setEditing(r); setDrawer(true); }}>Edit</Btn> },
        ]}/>

      <PlanFormDrawer open={drawer} onClose={() => setDrawer(false)} plan={editing} adTiers={data.adTiers} onSave={save}/>
    </Screen>
  );
};

// =================================================================
// §4 Subscribers
// =================================================================
const SubscribersScreen = ({ data, setData }) => {
  const [tab, setTab] = React.useState("all");
  const [q, setQ] = React.useState("");
  const [detail, setDetail] = React.useState(null);

  const counts = {
    all: data.subscribers.length,
    active: data.subscribers.filter(s => s.status === "active").length,
    trialing: data.subscribers.filter(s => s.status === "trialing").length,
    past_due: data.subscribers.filter(s => s.status === "past_due").length,
    canceled: data.subscribers.filter(s => s.status === "canceled").length,
  };

  const rows = data.subscribers
    .filter(s => tab === "all" ? true : s.status === tab)
    .filter(s => (s.user + s.plan).toLowerCase().includes(q.toLowerCase()));

  const cancel = (s) => {
    window.__api.write("cancelSubscription",
      d => ({ ...d, subscribers: d.subscribers.map(x => x.id === s.id ? { ...x, cancel_at_period_end: true } : x) }),
      { params: { id: s.id }, ok: `${s.user} set to cancel at period end`, err: "Couldn’t cancel" });
    setDetail(prev => prev ? { ...prev, cancel_at_period_end: true } : prev);
  };

  return (
    <Screen>
      <PageHead icon={IconUsers} title="Subscribers" subtitle="Readers subscribed to your consumer plans." />

      <Tabs value={tab} onChange={setTab} items={[
        { label: "All", value: "all", count: counts.all },
        { label: "Active", value: "active", count: counts.active },
        { label: "Trialing", value: "trialing", count: counts.trialing },
        { label: "Past due", value: "past_due", count: counts.past_due },
        { label: "Canceled", value: "canceled", count: counts.canceled },
      ]}/>

      <Toolbar search={q} onSearchChange={setQ} searchPlaceholder="Search by email or plan"/>

      <DataTable rows={rows} keyField="id" rowsPerPage={8} onRowClick={setDetail}
        defaultSort={{ key: "current_period_end", dir: "asc" }}
        empty={<EmptyState icon={<IconUsers size={30}/>} title="No subscribers here" description="No subscriptions match this filter."/>}
        columns={[
          { key: "user", label: "Subscriber", render: r => (
            <span style={{ display: "inline-flex", alignItems: "center", gap: 10 }}>
              <Avatar name={r.user} size={26}/><span style={{ color: "var(--ink)" }}>{r.user}</span>
            </span>) },
          { key: "plan", label: "Plan" },
          { key: "status", label: "Status", render: r => <StatusPill status={r.status}/> },
          { key: "current_period_end", label: "Renews / ends", align: "right", render: r => <span style={{ fontFamily: "var(--mono)", fontSize: 12.5 }}>{fmt.date(r.current_period_end)}</span> },
          { key: "cancel_at_period_end", label: "Cancel at end", sortable: false, render: r => r.cancel_at_period_end ? <Pill tone="warn">Yes</Pill> : <span style={{ color: "var(--muted-2)" }}>—</span> },
        ]}/>

      <Drawer open={!!detail} onClose={() => setDetail(null)} title="Subscriber" width={460}
        footer={detail && (detail.status === "active" || detail.status === "trialing") && !detail.cancel_at_period_end
          ? <><Btn kind="secondary" onClick={() => setDetail(null)}>Close</Btn><Btn kind="danger" onClick={() => cancel(detail)}>Cancel at period end</Btn></>
          : <Btn kind="secondary" onClick={() => setDetail(null)}>Close</Btn>}>
        {detail && (
          <div style={{ display: "flex", flexDirection: "column", gap: 18 }}>
            <div style={{ display: "flex", alignItems: "center", gap: 12 }}>
              <Avatar name={detail.user} size={44}/>
              <div>
                <div style={{ fontWeight: 600 }}>{detail.user}</div>
                <div style={{ marginTop: 4 }}><StatusPill status={detail.status}/></div>
              </div>
            </div>
            <KeyValueList items={[
              { k: "Subscription", v: <span style={{ fontFamily: "var(--mono)", fontSize: 12 }}>{detail.id}</span> },
              { k: "Plan", v: detail.plan },
              { k: "Period end", v: fmt.date(detail.current_period_end) },
              { k: "Cancel at end", v: detail.cancel_at_period_end ? "Yes" : "No" },
            ]}/>
            <InlineHelp icon={<IconInfo size={13}/>}>Cancellation is user-initiated and takes effect at the end of the current billing period.</InlineHelp>
          </div>
        )}
      </Drawer>
    </Screen>
  );
};

Object.assign(window, { OverviewScreen, MyPlanScreen, IntegrationKitsScreen, ConsumerPlansScreen, SubscribersScreen, KpiGrid, PlanFormDrawer });
