/* ZY console — 采购 → 入库 连贯流程（procure_to_intake_flow.v1）。
   动作/工作台（非只读日报）：一张采购单从创建 → 审核生效 → 到货 → 建入库单草稿 →
   人工盘点（硬门槛）→ 生效入库单（真正进库存）的全生命周期。
   四个门控写（▢①②③④）各自跑 dry-run → 老板审批(decision_ref) → 执行(写 JST) → 回滚，
   复用 KitGatedWrite。库存只在 ▢④ 动；▢④ 在盘点确认前不可点。read-model 待后端聚合。 */
const DSFLOW = window.ZYDesignSystem_d746df;

// 5 个里程碑节点（左→右）；▢ 标记节点间的门控动作
const FLOW_NODES = [
  { key: "po", label: "采购单", icon: "FileText" },
  { key: "confirmed", label: "已生效", icon: "BadgeCheck" },
  { key: "arrived", label: "到货", icon: "Truck" },
  { key: "in_draft", label: "入库草稿", icon: "ClipboardList" },
  { key: "activated", label: "库存到账", icon: "PackageCheck" },
];

// stage → { 当前所处节点 index, 状态标签/色, 该节点允许的唯一动作 }
const STAGE = {
  po_draft:                { node: 0, label: "采购单 · 待审核", tone: "warn",    action: "confirm" },
  po_confirmed:            { node: 1, label: "已生效 · 等待到货", tone: "accent", action: "arrive" },
  awaiting_goods:          { node: 2, label: "货已到 · 待建入库单", tone: "accent", action: "createIn" },
  in_draft_awaiting_count: { node: 3, label: "入库单草稿 · 待盘点", tone: "warn",  action: "activate" },
  activated:               { node: 4, label: "库存已到账", tone: "good",   action: "receipt" },
  voided:                  { node: -1, label: "已作废", tone: "neutral", action: null },
};
// JST purchase.query 不回 external_id（真机 0/146）——数据层诚实 null,展示/subject 用 PO-{po_id} 回退
const poLabel = (r) => r.po_external_id || ("PO-" + r.po_id);
const IN_STATUS_LABEL = { WaitConfirm: "待确认（is_confirm=false · 不动库存）", Confirmed: "已生效（已进库存）" };
const PO_STATUS_LABEL = { WaitConfirm: "WaitConfirm · 待审核", Confirmed: "Confirmed · 采购在途", Finished: "Finished · 已完成", Delete: "Delete · 已作废", Cancelled: "Cancelled · 已取消" };

function FlowPipe({ stage }) {
  const { Icon } = DSFLOW;
  const cur = STAGE[stage] ? STAGE[stage].node : -1;
  const voided = stage === "voided";
  return (
    <div className={"fpipe" + (voided ? " fpipe--void" : "")}>
      {FLOW_NODES.map((n, i) => (
        <React.Fragment key={n.key}>
          <span className={"fpipe__n" + (i < cur ? " is-done" : "") + (i === cur ? " is-cur" : "")} title={n.label}>
            <span className="fpipe__ic"><Icon name={i < cur ? "Check" : n.icon} size={12} /></span>
            <span className="fpipe__lab">{n.label}</span>
          </span>
          {i < FLOW_NODES.length - 1 && <span className={"fpipe__bar" + (i < cur ? " is-done" : "")}>{i === 2 && <span className="fpipe__gate" title="人工盘点硬门槛"><Icon name="ScanLine" size={9} /></span>}</span>}
        </React.Fragment>
      ))}
    </div>
  );
}

function KitFlow() {
  const { Card, SectionHead, Pill, Button, Icon } = DSFLOW;
  const K = window.KIT, S = window.KitStrip, Kp = window.KitKpi;
  const M = K.flowMeta;
  const [rows, setRows] = React.useState(() => K.flowRows.map(r => ({ ...r })));
  const [modal, setModal] = React.useState(null);   // { kind, po_id }
  const [countId, setCountId] = React.useState(null); // row in count checkpoint
  const [countBy, setCountBy] = React.useState("余丽");
  const [filter, setFilter] = React.useState("active");

  const patch = (po_id, ch) => setRows(rs => rs.map(r => r.po_id === po_id ? { ...r, ...ch } : r));
  const rowOf = (po_id) => rows.find(r => r.po_id === po_id);

  const unix = () => Math.floor(Date.now() / 1000);

  // ── 计数 ─────────────────────────────────────────────
  const byStage = (s) => rows.filter(r => r.stage === s).length;
  const pendCount = byStage("in_draft_awaiting_count");
  const inTransit = byStage("po_confirmed") + byStage("awaiting_goods");
  const toConfirm = byStage("po_draft");
  const activated = byStage("activated");

  const ACTIVE = ["po_draft", "po_confirmed", "awaiting_goods", "in_draft_awaiting_count"];
  const visible = rows.filter(r => filter === "all" ? true : filter === "done" ? (r.stage === "activated" || r.stage === "voided") : ACTIVE.includes(r.stage));

  // ── 四个门控写 flow（绑定契约真实 dryRun/execute 投影）──────────────
  // ▢① 创建采购单 — procurement_purchase_order_creation.v1
  const SUPPLIERS = window.KIT.suppliers || [];
  const createPoFlow = () => {
    const supOpts = [{ value: "", label: "— 选择供应商 —" }, ...SUPPLIERS.map(s => ({ value: s.ref, label: s.name + " · " + s.ref }))];
    return {
      icon: "FilePlus2", title: "① 创建采购单", subject: "新建采购单 · 本仓 / 工厂代发采购范围",
      steps: ["预览 dry-run", "老板审批", "回执"],
      fields: [
        { key: "supplierRef", label: "供应商", type: "select", options: supOpts, value: "" },
        { key: "scope", label: "采购范围 scope", type: "select", options: [{ value: "owned_warehouse_procurement", label: "本仓采购 owned_warehouse_procurement" }, { value: "factory_direct_ship_procurement_order", label: "工厂代发 factory_direct_ship_procurement_order" }], value: "owned_warehouse_procurement" },
        { key: "externalId", label: "外部采购单号 externalId", hint: "正式采购单号(purchase_order_ref)由 JST 创建时自动生成;此处仅为可选外部编号,已自动填充。", type: "text", value: "ZY-PO-" + new Date().toISOString().slice(0, 10).replace(/-/g, "") + "-" + String(unix()).slice(-3) },
      ],
      lines: {
        label: "采购明细 lines[]·一单可多款",
        initial: [{ sku: "", qty: 100, unit_cost: "" }],
        blank: { sku: "", qty: 0, unit_cost: "" },
        columns: [
          { key: "sku", label: "SKU", type: "text", placeholder: "如 LF-1180" },
          { key: "qty", label: "数量", type: "number", unit: "件" },
          { key: "unit_cost", label: "采购价", type: "number", unit: "元/件" },
        ],
      },
      blocked: (v, f, lines) => !(f.supplierRef && f.supplierRef.toString().trim()) || (f.externalId || "").length > 32 || !(lines || []).some(l => l.sku && Number(l.qty) > 0) || (lines || []).some(l => l.sku && !(Number(l.qty) > 0)),
      blockedReason: (v, f, lines) => (f.externalId || "").length > 32 ? "externalId 超过 32 字符（JST 限制）。" : !f.supplierRef ? "未选择供应商。写采购单必须有供应商映射。" : !(lines || []).some(l => l.sku && Number(l.qty) > 0) ? "至少填一款 SKU 且数量大于 0。" : "有已填 SKU 的明细数量为 0，请补全或删除该行。",
      previewBanner: "预览 · 未创建（dry-run，不写 JST）",
      previewRows: (v, f, lines) => {
        const sup = SUPPLIERS.find(s => s.ref === f.supplierRef);
        const valid = (lines || []).filter(l => l.sku && Number(l.qty) > 0);
        const totalQty = valid.reduce((s, l) => s + (Number(l.qty) || 0), 0);
        const costKnown = valid.length > 0 && valid.every(l => l.unit_cost !== "" && l.unit_cost != null);
        const est = costKnown ? valid.reduce((s, l) => s + (Number(l.qty) || 0) * (Number(l.unit_cost) || 0), 0) : null;
        return [
          { k: "supplier_ref", v: (sup ? sup.name : "—") + " · " + (f.supplierRef || "未配") },
          { k: "procurement_scope", v: f.scope },
          { k: "line_count", v: valid.length + " 款" },
          { k: "明细", v: valid.length ? valid.map(l => l.sku + "×" + (Number(l.qty) || 0)).join("、") : "—" },
          { k: "total_qty", v: totalQty + " 件" },
          { k: "est_total_cost", v: est != null ? window.yuan(est) : "待核价（部分采购价未填）", tone: est == null ? "warn" : "" },
          { k: "would_write", v: "true" },
        ];
      },
      payload: (v, f, lines) => ({ action: "create_purchase_order", supplierRef: f.supplierRef, procurementScope: f.scope, externalId: f.externalId,
        lines: (lines || []).filter(l => l.sku && Number(l.qty) > 0).map(l => ({ sku: l.sku, qty: Number(l.qty) || 0, unit_cost: l.unit_cost === "" ? null : Number(l.unit_cost) })) }),
      approveNote: "引擎在缺少 decision_ref 时拒绝执行；下方为本次审批的决策引用。",
      refPrefix: "PO", decisionPrefix: "DEC", executeLabel: "创建采购单（写 JST · jst_write_count=1）",
      receiptRows: (ref, v, f, lines) => {
        const sup = SUPPLIERS.find(s => s.ref === f.supplierRef);
        const valid = (lines || []).filter(l => l.sku && Number(l.qty) > 0);
        return [
          { k: "purchase_order_ref", v: ref },
          { k: "supplier_ref", v: (sup ? sup.name : "—") + " · " + (f.supplierRef || "—") },
          { k: "procurement_scope", v: f.scope },
          { k: "line_count", v: valid.length + " 款" },
          { k: "total_qty", v: valid.reduce((s, l) => s + (Number(l.qty) || 0), 0) + " 件" },
          { k: "readback_status", v: "confirmed", tone: "good" },
          { k: "jst_write_count", v: "1" },
        ];
      },
      voidLabel: "作废采购单",
    };
  };

  // ▢② 审核生效采购单 — procurement_purchase_order_confirmation.v1
  const confirmFlow = (r) => ({
    icon: "BadgeCheck", title: "② 审核生效采购单", subject: poLabel(r) + " · po_id " + r.po_id,
    steps: ["预览 dry-run", "老板审批", "回执"],
    previewBanner: "预览 · 未写入（dry-run，不写 JST）",
    previewRows: () => [
      { k: "purchase_order_ref", v: "po_id " + r.po_id + " · " + poLabel(r) },
      { k: "供应商", v: r.supplier_name + " · " + r.supplier_ref },
      { k: "明细", v: r.sku_id + " × " + r.total_qty + " 件" },
      { k: "action", v: "审核生效 (change/status option 1)" },
      { k: "would_write", v: "true" },
    ],
    payload: () => ({ action: "confirm_purchase_order", poId: r.po_id }),
    approveNote: "引擎在缺少 decision_ref 时拒绝执行；生效后进入 JST 采购在途（Confirmed）。",
    refPrefix: "PO", decisionPrefix: "DEC", executeLabel: "审核生效采购单（写 JST · 进采购在途）",
    receiptRows: () => [
      { k: "purchase_order_ref", v: poLabel(r) },
      { k: "confirmed", v: "true", tone: "good" },
      { k: "readback_status", v: "confirmed", tone: "good" },
      { k: "jst_write_count", v: "1" },
    ],
    voidLabel: "作废采购单",
  });

  // ▢③ 创建入库单(草稿) — warehouse_purchase_in_creation.v1
  const createInFlow = (r) => ({
    icon: "ClipboardList", title: "③ 创建入库单（草稿）", subject: poLabel(r) + " · po_id " + r.po_id,
    steps: ["预览 dry-run", "老板审批", "回执"],
    fields: [
      { key: "externalId", label: "外部入库单号 externalId", hint: "正式入库单号(io_id)由 JST 创建时自动生成;此处为可选外部编号,已自动填充。", type: "text", value: "OPENCLAW-HERMES-IN-" + unix() },
    ],
    blocked: (v, f) => (f.externalId || "").length > 32,
    blockedReason: () => "externalId 超过 32 字符（JST 限制）。",
    previewBanner: "预览 · 未写入；本步创建待确认草稿，不动库存（dry-run）",
    previewRows: () => [
      { k: "purchase_order_ref", v: "po_id " + r.po_id + " · " + poLabel(r) },
      { k: "供应商（取自关联 PO）", v: r.supplier_name + " · " + r.supplier_ref },
      { k: "line_count", v: r.line_count + " 款" },
      { k: "明细（整单入库）", v: linesOf(r).map(l => l.sku + "×" + l.qty).join("、") },
      { k: "total_qty", v: r.total_qty + " 件" },
      { k: "库存影响", v: "无 · 创建 is_confirm=false 草稿", tone: "good" },
      { k: "would_write", v: "true" },
    ],
    payload: (v, f) => ({ action: "create_purchase_in", purchaseOrderRef: r.po_id, lines: linesOf(r).map(l => ({ sku: l.sku, qty: l.qty })), externalId: f.externalId }),
    approveNote: "引擎在缺少 decision_ref 时拒绝执行；本步写入草稿单，不移动任何库存。",
    refPrefix: "IN", decisionPrefix: "DEC", executeLabel: "创建入库单草稿（写 JST · 不动库存）",
    receiptRows: (ref) => [
      { k: "purchase_in_ref", v: ref },
      { k: "purchase_order_ref", v: poLabel(r) },
      { k: "in_status", v: "待确认（is_confirm=false）", tone: "warn" },
      { k: "库存变动", v: "0 · 库存未动", tone: "good" },
      { k: "readback_status", v: "confirmed", tone: "good" },
      { k: "jst_write_count", v: "1" },
    ],
    voidLabel: "取消入库单",
  });

  // ▢④ 生效入库单 — warehouse_purchase_in_confirmation.v1 — 盘点硬门槛
  const activateFlow = (r) => ({
    icon: "PackageCheck", title: "④ 生效入库单 · 真正进库存", subject: "io_id " + r.io_id + " · " + poLabel(r),
    steps: ["预览 dry-run", "老板审批", "回执"],
    blocked: () => !r.count_verified,
    blockedReason: () => "物理盘点未确认 — 无法生效入库单（count_verified ≠ true）。请先完成左侧「人工盘点」硬门槛。",
    previewBanner: "预览 · 未写入；这是唯一真正移动库存的一步（dry-run）",
    previewRows: () => [
      { k: "purchase_in_ref", v: "io_id " + r.io_id },
      { k: "count_verified", v: r.count_verified ? "true ✓" : "false", tone: r.count_verified ? "good" : "danger" },
      { k: "counted_by", v: r.counted_by || "—（未盘点）" },
      { k: "action", v: "入库单确认/生效 (received/upload)" },
      { k: "库存影响", v: "⚠ 本步真正把 " + r.total_qty + " 件加进 JST 库存", tone: "warn" },
      { k: "would_write", v: "true" },
    ],
    payload: () => ({ action: "confirm_purchase_in", purchaseInRef: r.io_id, countVerified: r.count_verified, countedBy: r.counted_by }),
    approveNote: "引擎在缺少 decision_ref 时拒绝执行；执行后 JST 真正加库存。",
    refPrefix: "IN", decisionPrefix: "DEC", executeLabel: "生效入库单（写 JST · 真正进库存）",
    receiptRows: () => [
      { k: "purchase_in_ref", v: "io_id " + r.io_id },
      { k: "confirmed", v: "true", tone: "good" },
      { k: "库存到账", v: "+" + r.total_qty + " 件 已写入 JST", tone: "good" },
      { k: "counted_by", v: r.counted_by },
      { k: "readback_status", v: "confirmed", tone: "good" },
      { k: "jst_write_count", v: "1" },
    ],
    voidLabel: "取消入库单（回滚库存）",
  });

  const flowFor = (kind, r) => kind === "createPo" ? createPoFlow() : kind === "confirm" ? confirmFlow(r) : kind === "createIn" ? createInFlow(r) : activateFlow(r);

  // execute 后推进 stage（无后端，前端模拟状态机）
  const onExec = (kind, po_id) => (ref, val, form, lines) => {
    if (kind === "createPo") {
      const sup = SUPPLIERS.find(s => s.ref === (form && form.supplierRef));
      const valid = (lines || []).filter(l => l.sku && Number(l.qty) > 0).map(l => ({ sku: l.sku, qty: Number(l.qty) || 0, unit_cost: l.unit_cost === "" ? null : Number(l.unit_cost) }));
      const totalQty = valid.reduce((s, l) => s + l.qty, 0);
      const newRow = {
        po_id: Number(String(Date.now()).slice(-6)), po_external_id: (form && form.externalId) || ref,
        supplier_ref: (form && form.supplierRef) || "", supplier_name: sup ? sup.name : "—",
        sku_id: valid.length === 1 ? valid[0].sku : valid.length + " 款 SKU", sku_name: valid.length ? (valid[0].sku + (valid.length > 1 ? " 等 " + valid.length + " 款" : "")) : "—",
        procurement_scope: (form && form.scope) || "owned_warehouse_procurement",
        po_status: "WaitConfirm", line_count: valid.length, total_qty: totalQty, lines: valid,
        io_id: null, in_status: null, count_verified: false, counted_by: null, stage: "po_draft", _poRef: ref,
      };
      setRows(rs => [newRow, ...rs]);
      return;
    }
    if (kind === "confirm") patch(po_id, { stage: "po_confirmed", po_status: "Confirmed", _poRef: ref });
    if (kind === "createIn") patch(po_id, { stage: "in_draft_awaiting_count", io_id: Number(String(Date.now()).slice(-6)), in_status: "WaitConfirm", _inRef: ref });
    if (kind === "activate") patch(po_id, { stage: "activated", po_status: "Finished", in_status: "Confirmed", _inRef: ref });
  };
  const onVoid = (kind, po_id) => () => {
    if (kind === "confirm") patch(po_id, { stage: "po_draft", po_status: "WaitConfirm" });
    if (kind === "createIn") patch(po_id, { stage: "awaiting_goods", io_id: null, in_status: null });
    if (kind === "activate") patch(po_id, { stage: "in_draft_awaiting_count", po_status: "Confirmed", in_status: "WaitConfirm" });
    setModal(null);
  };

  const markArrived = (po_id) => patch(po_id, { stage: "awaiting_goods" });
  // 一单多款明细（回退：单款从 sku_id/total_qty 推导）
  const linesOf = (r) => (r.lines && r.lines.length) ? r.lines : [{ sku: r.sku_id, qty: r.total_qty, unit_cost: r.unit_cost }];
  const skuLabel = (r) => r.line_count > 1 ? (r.line_count + " 款 SKU · 共 " + r.total_qty + " 件") : (r.sku_id + " × " + r.total_qty + " 件");
  const confirmCount = (po_id) => { patch(po_id, { count_verified: true, counted_by: countBy.trim() || "盘点员" }); setCountId(null); };
  const undoCount = (po_id) => patch(po_id, { count_verified: false, counted_by: null });

  const ACT_LABEL = { confirm: "② 审核生效", createIn: "③ 建入库单草稿", activate: "④ 生效入库单" };

  return (
    <div className="view viewfade">
      <S icon="GitBranch" title="采购 → 入库流程" mode="采购 × 仓储 · 受控写动作台"
        judge="一张采购单的全生命周期：创建 → 审核生效 → 到货 → 建入库单草稿 → 人工盘点(硬门槛) → 生效入库单。每个节点只给一个门控动作，库存只在最后一步动。"
        src="采购入库全流程读模型" tone="warn" toneLabel="待后端聚合" />

      {!M.served && (
        <div className="flowbanner">
          <Icon name="Workflow" size={15} />
          <span><b>read-model 待后端聚合</b> · 单一生命周期读模型尚未服务，字段仅源于采购单查询 + 入库单查询 + ▢④ 任务盘点态，UI 先绑此形状。</span>
        </div>
      )}

      {/* 状态机图例 */}
      <Card>
        <SectionHead title="生命周期状态机" icon="GitBranch" sub="左→右单向推进 · ▢ 为门控写动作（dry-run → 审批 → 写 → 回滚），· 为真实世界事件" />
        <div className="fmachine">
          <span className="fm__node fm__node--start"><span className="fm__ic"><Icon name="FileText" size={15} /></span>采购单<br />草稿/待审核</span>
          <span className="fm__edge"><span className="fm__gact">▢① 创建</span><span className="fm__line" /></span>
          <span className="fm__node"><span className="fm__ic"><Icon name="BadgeCheck" size={15} /></span>已审核生效<br />Confirmed</span>
          <span className="fm__edge"><span className="fm__gact">▢② 审核生效</span><span className="fm__line" /></span>
          <span className="fm__node fm__node--evt"><span className="fm__ic"><Icon name="Truck" size={15} /></span>货到仓库<br />· 事件</span>
          <span className="fm__edge"><span className="fm__gact">▢③ 建入库草稿</span><span className="fm__line" /></span>
          <span className="fm__node fm__node--gate"><span className="fm__ic"><Icon name="ScanLine" size={15} /></span>人工盘点<br />硬门槛 count_verified</span>
          <span className="fm__edge"><span className="fm__gact">▢④ 生效入库</span><span className="fm__line" /></span>
          <span className="fm__node fm__node--end"><span className="fm__ic"><Icon name="PackageCheck" size={15} /></span>库存到账<br />JST 真正加库存</span>
        </div>
        <div className="fmnote"><Icon name="Info" size={13} />库存<b>只在 ▢④</b> 移动；▢③ 仅建草稿(is_confirm=false)不动库存。一 IN ↔ 一 PO 整单入库，无分批/按行入库。</div>
      </Card>

      <div className="kpigrid">
        <Kp label="待审核采购单" value={toConfirm} hint="▢② 审核生效" pill={toConfirm ? "待处理" : "无"} pillTone={toConfirm ? "warn" : "good"} feat valTone={toConfirm ? "ovstat--warn" : ""} />
        <Kp label="采购在途 / 待入库" value={inTransit} hint="等待到货 + 待建入库单" icon="Truck" />
        <Kp label="待人工盘点" value={pendCount} hint="▢④ 生效前的硬门槛" pill={pendCount ? "硬门槛" : "无"} pillTone={pendCount ? "danger" : "good"} valTone={pendCount ? "ovstat--danger" : ""} />
        <Kp label="本期已到账" value={activated} hint="库存已写入 JST" icon="PackageCheck" valTone="good" />
      </div>

      <Card>
        <SectionHead title="入库工作台" icon="ListTree" sub="每行一张采购单 · 当前节点只给一个门控动作 · 盘点未确认时 ▢④ 不可点"
          right={<div style={{ display: "flex", gap: 10, alignItems: "center", flexWrap: "wrap" }}>
            <div className="fchips">
              {[["active", "进行中"], ["done", "已完结"], ["all", "全部"]].map(([k, l]) => (
                <button key={k} className={"fchip" + (filter === k ? " is-on" : "")} onClick={() => setFilter(k)}>{l}</button>
              ))}
            </div>
            <Button variant="solid" size="sm" onClick={() => setModal({ kind: "createPo" })}><Icon name="Plus" size={14} />创建采购单</Button>
          </div>} />

        <div className="flowlist">
          {visible.length === 0 && <div className="emptyrow"><Icon name="Inbox" size={14} />无{filter === "active" ? "进行中" : filter === "done" ? "已完结" : ""}的采购单</div>}
          {visible.map(r => {
            const st = STAGE[r.stage] || {};
            const inCount = countId === r.po_id;
            return (
              <div className={"flowrow flowrow--" + r.stage} key={r.po_id}>
                <div className="flowrow__head">
                  <div className="flowrow__id">
                    <span className="flowrow__po num">{poLabel(r)}</span>
                    <span className="flowrow__meta">po_id {r.po_id} · {r.supplier_name} · {skuLabel(r)}{r.io_id ? " · io_id " + r.io_id : ""}</span>
                  </div>
                  <Pill tone={st.tone} soft>{st.label}</Pill>
                </div>

                <FlowPipe stage={r.stage} />

                <div className="flowrow__foot">
                  <span className="flowrow__status num">
                    <span className="flowrow__sk">PO</span> {PO_STATUS_LABEL[r.po_status] || r.po_status}
                    {r.in_status && <><span className="flowrow__sk" style={{ marginLeft: 10 }}>IN</span> {IN_STATUS_LABEL[r.in_status] || r.in_status}</>}
                  </span>
                  <span className="flowrow__act">
                    {st.action === "confirm" && <Button variant="solid" size="sm" onClick={() => setModal({ kind: "confirm", po_id: r.po_id })}>{ACT_LABEL.confirm}<Icon name="ArrowRight" size={13} /></Button>}
                    {st.action === "arrive" && <Button variant="solid" size="sm" onClick={() => markArrived(r.po_id)}><Icon name="Truck" size={13} />标记到货</Button>}
                    {st.action === "createIn" && <Button variant="solid" size="sm" onClick={() => setModal({ kind: "createIn", po_id: r.po_id })}>{ACT_LABEL.createIn}<Icon name="ArrowRight" size={13} /></Button>}
                    {st.action === "activate" && (r.count_verified
                      ? <Button variant="solid" size="sm" onClick={() => setModal({ kind: "activate", po_id: r.po_id })}>{ACT_LABEL.activate}<Icon name="ArrowRight" size={13} /></Button>
                      : <span className="flowrow__locked"><Icon name="Lock" size={13} />④ 待盘点解锁</span>)}
                    {st.action === "receipt" && <Button variant="ghost" size="sm" onClick={() => setModal({ kind: "activate", po_id: r.po_id })}>查看回执 / 回滚</Button>}
                    {r.stage === "voided" && <span className="flowrow__locked"><Icon name="Ban" size={13} />已作废 · 终态</span>}
                  </span>
                </div>

                {/* 人工盘点硬门槛 —— 仅 in_draft_awaiting_count 显示 */}
                {r.stage === "in_draft_awaiting_count" && (
                  <div className={"countgate" + (r.count_verified ? " is-done" : "")}>
                    <div className="countgate__l">
                      <span className="countgate__ic"><Icon name={r.count_verified ? "ShieldCheck" : "ScanLine"} size={16} /></span>
                      <div>
                        <div className="countgate__t">人工盘点 · 硬门槛 {r.count_verified ? "· 已确认" : ""}</div>
                        <div className="countgate__d">{r.count_verified
                          ? <>已实物点验 {r.total_qty} 件 · 盘点人 <b>{r.counted_by}</b> · ▢④ 已解锁</>
                          : <>实物到仓须人工点数后才能生效入库；这是两步入库的全部意义，不可跳过。</>}</div>
                      </div>
                    </div>
                    <div className="countgate__r">
                      {r.count_verified
                        ? <Button variant="ghost" size="sm" onClick={() => undoCount(r.po_id)}>撤销盘点</Button>
                        : inCount
                          ? <span className="countgate__form">
                              <span className="countgate__field"><span className="countgate__fl">盘点人</span><input className="countgate__in" value={countBy} onChange={e => setCountBy(e.target.value)} placeholder="如 余丽" /></span>
                              <Button variant="ghost" size="sm" onClick={() => setCountId(null)}>取消</Button>
                              <Button variant="solid" size="sm" onClick={() => confirmCount(r.po_id)}><Icon name="Check" size={13} />确认已实物盘点 {r.total_qty} 件</Button>
                            </span>
                          : <Button variant="solid" size="sm" onClick={() => { setCountBy(r.counted_by || "余丽"); setCountId(r.po_id); }}><Icon name="ScanLine" size={14} />开始人工盘点</Button>}
                    </div>
                  </div>
                )}
              </div>
            );
          })}
        </div>
        <div className="pqfoot"><span className="pqfoot__l"><Icon name="ShieldCheck" size={13} />JST 为唯一事实源 · 每个写都走 dry-run → 老板审批(decision_ref) → 单次写 + 回读 → 可回滚 · 库存只在 ▢④ 动</span></div>
      </Card>

      {modal && <window.KitGatedWrite
        flow={flowFor(modal.kind, modal.po_id ? rowOf(modal.po_id) : null)}
        existingRef={modal.kind === "activate" && rowOf(modal.po_id) && rowOf(modal.po_id).stage === "activated" ? rowOf(modal.po_id)._inRef : null}
        onClose={() => setModal(null)}
        onExecuted={onExec(modal.kind, modal.po_id)}
        onVoided={onVoid(modal.kind, modal.po_id)} />}
    </div>
  );
}

Object.assign(window, { KitFlow });
