# `runs/` — Run-trace convention (Harness-10) > **Mục đích:** mỗi workflow fan-out (RUN-TRACE mode) ghi lại 1 dấu-vết hoàn-chỉnh trong `runs//` git **TRACKED** — plan + per-sub detail + harvest gom — cộng sổ `_ledger.md` 2-nhịp. TRACKED nghĩa là mọi write trong run-folder hiện trong `git diff` → **audit trực-tiếp**, không cần tin lời agent return. Adopt AI_INFRA Harness-10 (anh 06-18). Convention cha: `../README.md`. **run-id** = `YYYY-MM-DD-h-` (vd `2026-06-18-h10-invest`). Nhiều run cùng ngày → slug phân-biệt stage (`-invest` / `-implement` / `-review`). --- ## C1 — Cấu trúc 3 phần (mỗi `runs//`) ``` runs// ├── run.md ← (1) PLAN — em main @P1: meta + mục-tiêu + agents-table + guards + status OPEN→CLOSE ├── sub-md/ ← (2) PER-SUB — 1 file/sub/turn: -.md (vd investigator-codebase-0.md) │ └── .gitkeep (giữ folder rỗng trong git khi chưa có write-sub) └── harvest/ ← (3) HARVEST — em main: -synthesis.md gom kết-quả turn (C4 per-turn) └── .gitkeep ``` - **(1) `run.md`** — nguồn-sự-thật của run: workflow run-id (evidence B3 `wf_…`), adap/mandate, checkpoint, opened, input-spec (nếu nối stage trước), agents-table (`# · role · task`), guards áp cho sub, output-path. Mẫu: `2026-06-18-h10-invest/run.md`. - **(2) `sub-md/-.md`** — full working detail 1 sub. Write-sub (Write/Edit) tự ghi @P2; read-only sub (CHỈ Bash) → trả `findings`+`subMdPath`, **em main scribe @P3** (single-writer, tránh mojibake). **1 sub-MD / role / turn** (fan-out cùng-role → đánh số `-0`/`-1`). - **(3) `harvest/-synthesis.md`** — em main gom `sub-md/`+findings → 5-trục integrity → build-spec/synthesis. Mẫu: `2026-06-18-h10-invest/harvest/invest-synthesis.md`. --- ## C2 — Scaffold ở CẢ 3 đầu-run (em main @P1, TRƯỚC khi invoke Workflow) `hmw.js` chạy JS-sandbox **no-filesystem** → KHÔNG tự tạo folder/file. Em main PHẢI Write @P1, đủ **3 đầu**: 1. **Tạo run-folder:** `runs//run.md` (điền plan) + `sub-md/.gitkeep` + `harvest/.gitkeep`. 2. **Ghi OPEN-beat** vào `runs/_ledger.md` (1 dòng, `closed=⏳`). 3. **(nối stage)** trỏ `input spec:` trong `run.md` sang `harvest/` của run trước (vd implement đọc invest-synthesis). > 🔴 **C2 là fragile-point.** Quên bước scaffold = run chạy nhưng KHÔNG có dấu-vết = **lỗ-hổng âm-thầm** (không lỗi, không cảnh-báo — chỉ thiếu file). 3-layer (C5) là lưới giảm-thiểu, KHÔNG khoá-cứng. Xem C7. --- ## C3 — Ledger 2-nhịp (`_ledger.md`) Sổ tất-cả run, 1 bảng. Mỗi run **2 lần ghi**: - **OPEN-beat** (@P1, lúc scaffold): thêm dòng `| | | | ⏳ | | ⏳ | harvest/ |`. - **CLOSE-beat** (lúc đóng run): điền `closed` timestamp + `verdict` (PASS/FAIL + 1 dòng + `wf_…`) + `harvest` (path file synthesis ✓). `closed=⏳` = đang chạy (OPEN chưa CLOSE). --- ## C4 — Per-turn primary (harvest NGAY, không đợi session-end) Harvest là **việc của turn**, không defer. Sau MỖI fan-out turn → em main đọc `sub-md/`+findings → ghi `harvest/-synthesis.md` **liền trong turn đó** (chính file synthesis này là bằng-chứng). Lợi: detail tươi, không mất qua nén-context; session-end chỉ VERIFY (không tái-tạo). --- ## C5 — 3-layer anti-miss (lưới chống bỏ-sót, KHÔNG khoá-cứng-cùng-lúc-fire) | Layer | Khi | Làm gì | |---|---|---| | **L1 in-run reminder** | lúc mở run mới (em-main @P1, TRƯỚC scaffold) | em-main đọc `_ledger.md`: nếu run TRƯỚC còn `closed=⏳` (OPEN-beat chưa CLOSE / `harvest/` rỗng) → harvest + CLOSE nó TRƯỚC khi mở run mới. *(Engine no-fs → KHÔNG đọc được ledger → L1 là convention EM-MAIN, KHÔNG phải `hmw.js` prompt. hmw.js chỉ emit C4 per-turn return-instruction cho sub tại writeGuard.)* | | **L2 session-start rescan** | đầu session (`session-start.md` §2.1.1 H2) | scan `runs/*/` tìm **OPEN-beat (ledger `closed=⏳`) mà `harvest/` rỗng = orphan** → báo + giải-quyết. | | **L3 session-end close-gate** | cuối session (`session-end.md` §L.b(f) H2) | VERIFY per-turn harvest đã xong cho mọi `runs//` (**idempotent — KHÔNG re-APPEND**, chống DUPLICATE-HARVEST) + 5-trục GATE backstop trước khi commit. | > 3 layer **độc-lập, fire ở 3 thời-điểm khác nhau** — không layer nào enforce lúc-ghi. Bỏ-sót ở P1 (C2) chỉ bị bắt MUỘN (L2 session sau / L3 close-gate), không chặn tại-chỗ. --- ## C6 — Orphan resolution (OPEN không CLOSE) **Orphan** = dòng ledger `closed=⏳` nhưng run thực-tế đã xong/bỏ (vd session bị kill, agent die-0-byte, quên CLOSE-beat). - **Phát-hiện:** L2 session-start rescan (`closed=⏳` + `harvest/` trạng-thái) hoặc L3 close-gate. - **Giải-quyết-CỨNG** (không để treo): 1. **Điều-tra** đĩa THẬT: `run.md` status + `sub-md/` có detail? + `harvest/` có synthesis? + git-log workflow `wf_…`. 2. **Đóng tay** nếu run thật-sự xong: điền CLOSE-beat (timestamp + verdict + harvest path). 3. **Đánh-dấu aborted** nếu run bỏ-dở: verdict = `⚠️ ABORTED — `, ghi rõ phần nào hoàn-thành (recover qua git/disk/prod truth, KHÔNG tin agent return-message). --- ## C7 — 🔴 CAVEAT trung-thực (no-overclaim) - **Engine no-fs → scaffold KHÔNG tự-động.** `hmw.js` (`:4` no hot-reload, JS-sandbox no-filesystem) KHÔNG tạo được folder. Run-trace dựa **100% vào em-main Write @P1** (C2). Không có cơ-chế nào ép tạo folder. - **C2 = fragile-point.** Quên scaffold = lỗ-hổng âm-thầm (run chạy OK, chỉ mất dấu-vết). Không lỗi runtime để bắt. - **3-layer = LƯỚI, KHÔNG khoá-cứng-cùng-lúc-fire.** L1/L2/L3 fire ở 3 thời-điểm khác nhau (run-open @P1 / session-start / session-end), **cả 3 đều là convention em-main/H2 — KHÔNG layer nào do engine enforce** (hmw.js no-fs). → giảm xác-suất sót, KHÔNG triệt-tiêu. Sót P1 (C2) cùng blind-spot với L1 (đều @P1) → chỉ bắt MUỘN ở L2/L3. - **G-015 no-overclaim — TRACKED ≠ read-only-ENFORCED.** Run-folder git-tracked KHÔNG biến sub thành read-only: sub **vẫn giữ Bash** (write-channel mở — ghi-ngoài-repo git-diff mù / curl Qdrant). Containment THẬT (xem model dưới) = em-main single-writer + git-diff(in-repo) + chunk-count(RAG), defense-in-depth — KHÔNG sandbox cứng, KHÔNG claim "ENFORCED". --- ## Containment model (PHẢI khớp `_ledger.md:4` — đồng-bộ 3 chỗ: đây · `_ledger.md` · `../hmw.js:112`) > Run-folder `runs//` được git **TRACKED** → mọi write **HIỆN** trong git-diff = **audit trực-tiếp**. Containment: tracked-change **NGOÀI** `runs//` **VÀ NGOÀI** code-disjoint đã giao = **vi-phạm** (thay model Harness-2 B6 "mọi tracked-change = vi-phạm"). G-015 no-overclaim: TRACKED ≠ read-only-enforced — sub vẫn giữ Bash (write-channel mở), containment THẬT = em-main single-writer + git-diff(in-repo) + chunk-count(RAG). **Verify pattern:** `git check-ignore -v ` — bẫy exit-code (exit 0 cho CẢ negation `!.claude/**` lẫn ignore) → dùng `&& IGNORED || NOT` để đọc đúng. Run-folder match `:83 !.claude/**` = re-included = TRACKED (HIỆN trong diff).