# Night Gym DAG Review Loop
## Before: 当前 MVP
| 环节 | 当前行为 | 缺口 |
|---|---|---|
| 发现问题 | master 读 input.json,抽候选主题 | 候选生成依赖一次性 prompt,状态不可恢复 |
| 子分析 | `spawn_subagent.sh` 并发生成 `out/sub/*.json` | 只有分析,没有执行验证 |
| 产物 | `manifest.json`、`MORNING_REVIEW.md`、`approve.sh` | `approve.sh` 只改状态,不证明方案真的能跑 |
| 早上 review | 人看候选和 evidence | 缺少 demo diff、测试日志、reviewer verdict |
## After: 显式 DAG + 可运行 demo
| DAG 节点 | 输入 | 输出 | 验收 |
|---|---|---|---|
| `ingest_sessions` | Codex session logs | `input.json` | 脱敏、路径压缩、session 数可统计 |
| `propose_candidates` | `input.json` | `out/candidates.json` | 1-5 个候选,含片段和初始价值判断 |
| `spawn_analyzers` | 候选片段 | `out/sub/*.json` | 每个候选有 valid/evidence/proposed_changes |
| `route_candidates` | 子分析结果 | `out/routed.json` | 只把 high value 且 medium 以下风险候选送 demo |
| `build_demo` | 候选 + 临时 workspace | `demo_results/<id>/` | worker 产出 diff、命令日志、最小可运行例子 |
| `review_demo` | demo diff + logs | reviewer verdict | pass/block/needs-human,明确阻塞理由 |
| `package_writer` | routed + verdict | morning review package | 早上看到的是“候选 + 证据 + demo 结果” |
## 一个具体结果
Before 的 morning review 只能说:`建议把 Night Gym 升级成 DAG`。
After 的 morning review 可以说:`night-gym-dag-review-loop` 已在临时 demo workspace 跑过:DAG state 写入正常,失败节点可 resume,3 个 unittest 通过;reviewer verdict 为 `pass`,建议人工批准后合入 `tools/night-gym/night_gym/dag.py` 和相关 prompt。