@cyning/harness 2.9.0 → 2.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +19 -0
- package/docs/ONBOARDING.md +9 -2
- package/docs/USER_GUIDE_v1.0_zh.md +7 -2
- package/docs/rethink/2026-07-mechanization-rate/03_coverage_matrix.md +4 -2
- package/docs/rethink/2026-07-mechanization-rate/04_next_steps.md +4 -3
- package/docs/spec/SPEC-discipline-coverage-yaml_v1.md +204 -0
- package/docs/spec/SPEC-lifecycle-engine-min_v1.md +246 -0
- package/docs/spec/SPEC-post-g4-debt-retro_v1.md +237 -0
- package/docs/spec/SPEC-verify-full-reviews-gate_v1.md +1 -1
- package/harness/discipline-coverage.yaml +289 -0
- package/harness/lifecycle.yaml +4 -3
- package/lib/cli.js +84 -20
- package/lib/discipline-coverage.js +96 -0
- package/lib/lifecycle.js +222 -0
- package/package.json +1 -1
- package/schema/discipline-coverage.v1.schema.json +55 -0
- package/schema/lifecycle.v1.schema.json +1 -1
|
@@ -0,0 +1,237 @@
|
|
|
1
|
+
# SPEC:Post-G4 / N1–N4 欠账复盘与下一 Epic 点菜(v1)
|
|
2
|
+
|
|
3
|
+
> **状态**:`signed`(维护者签收 2026-07-25 · 对话「签收」)
|
|
4
|
+
> **track**:`docs`(评估轨 · 非改码 Epic)
|
|
5
|
+
> **关联图谱**:无(文档复盘;不改 `_tech_graph`)
|
|
6
|
+
> **上游**:[`PLAN_post_g4_next_mechanization_v1_zh.md`](../../../docs/harness/guides/PLAN_post_g4_next_mechanization_v1_zh.md)(**closed**)· rethink [`2026-07-mechanization-rate/`](../rethink/2026-07-mechanization-rate/)(01–04)
|
|
7
|
+
> **前置**:G1–G4 ✅ · N1–N4 `@cyning/harness@2.7.0–2.9.0` published · CLOSE ✅
|
|
8
|
+
> **下游**:00 已起草 task(HG-TASK-DRAFT pending)→ 20-task-audit → HG-AUDIT-R1 → 30 写复盘文;**不**直接发版
|
|
9
|
+
|
|
10
|
+
---
|
|
11
|
+
|
|
12
|
+
## Harness 元信息
|
|
13
|
+
|
|
14
|
+
| 字段 | 值 |
|
|
15
|
+
|------|-----|
|
|
16
|
+
| **spec_slug** | `post-g4-debt-retro` |
|
|
17
|
+
| **test_strategy** | `not_applicable` |
|
|
18
|
+
| **test_strategy_note** | 交付物为复盘文档 + 欠账表 + ≤3 条下一 Epic 点菜建议;不改引擎/CLI/包版本;无可失败自动化测试对象 |
|
|
19
|
+
| **entry_invoke_10_spec** | `Projects/docs/harness/invokes/by-task/cyning-harness-post-g4-debt-retro/invoke_20260725_10_spec_post_g4_debt_retro.md` |
|
|
20
|
+
| **entry_invoke_00_draft** | `Projects/docs/harness/invokes/by-task/cyning-harness-post-g4-debt-retro/invoke_20260725_00_draft_post_g4_debt_retro.md` |
|
|
21
|
+
|
|
22
|
+
---
|
|
23
|
+
|
|
24
|
+
## 1. 背景与目标
|
|
25
|
+
|
|
26
|
+
2026-07-24~25 完成文档层主链机械化收口:
|
|
27
|
+
|
|
28
|
+
| 波次 | 版本 | 要点 |
|
|
29
|
+
|------|------|------|
|
|
30
|
+
| G1+G3 | 2.3.0 | `task lint` 结构 / 绝对路径 |
|
|
31
|
+
| G2 | 2.5.0 | reviews 留档(`--task` / close) |
|
|
32
|
+
| G4 | 2.6.0 | 思考轮结构(条件触发) |
|
|
33
|
+
| N1+N2 | 2.7.0 | `lifecycle.yaml` + `verify --task` lint **WARN** |
|
|
34
|
+
| N3 | 2.8.0 | `verify --spec` |
|
|
35
|
+
| N4 | 2.9.0 | 裸 `verify` 全量 reviews + 双路径 active |
|
|
36
|
+
|
|
37
|
+
[`PLAN_post_g4_next_mechanization_v1_zh.md`](../../../docs/harness/guides/PLAN_post_g4_next_mechanization_v1_zh.md) 已 **closed**。维护者指令:**针对最近欠账与更新做复盘**;须 **多轮思考防遗漏**(禁止 early_stop)。
|
|
38
|
+
|
|
39
|
+
**问题(PLAN 关闭后真空)**:候选下一棒(方向二引擎 / 方向三 git·契约 / dogfood 修齐 / N2-C block)散落在 PLAN §1–§3、rethink 03–04、各 SPEC residual、dogfood 口头结论中,**无单一复盘真值** → 点菜易漏项或重复立项。
|
|
40
|
+
|
|
41
|
+
**目标**:产出一份可签收的复盘交付包,使维护者能在「不改码、不发版」前提下完成点菜决策;并显式点名全部已知欠账与双仓发布态。
|
|
42
|
+
|
|
43
|
+
---
|
|
44
|
+
|
|
45
|
+
## 2. 范围(R2 裁定后)
|
|
46
|
+
|
|
47
|
+
### D1 · 复盘文落盘
|
|
48
|
+
|
|
49
|
+
- 主文路径(二选一 · 实现 task 时定稿,本 SPEC 推荐见 R2):
|
|
50
|
+
- **推荐 A**:`docs/harness/guides/RETRO_post_g4_n1n4_debt_v1_zh.md`(工作区编排可见 · 与 PLAN 同层)
|
|
51
|
+
- **备选 B**:`cyning-harness/docs/rethink/2026-07-post-g4-debt-retro/`(产品仓 rethink 续篇)
|
|
52
|
+
- 正文须含:时间线摘要、机械化率叙事更新(Starter 文档闸主链已覆盖 vs 仍 prompt-only)、PLAN closed 后真空说明。
|
|
53
|
+
|
|
54
|
+
### D2 · 欠账清单表(强制四栏分类)
|
|
55
|
+
|
|
56
|
+
| 分类 | 必须点名的项(最低集 · 复盘可增「新发现」行) |
|
|
57
|
+
|------|-----------------------------------------------|
|
|
58
|
+
| **已关账** | G1–G4;N1–N4 `@2.7–2.9`;PLAN closed |
|
|
59
|
+
| **未修齐** | dogfood 缺审查文 **3**:`a5_cli_verify` · `hat_chain_pointer_sync` · `task_validate_human_gate_ci_gate`(闸可 30;N4 不强制修齐) |
|
|
60
|
+
| **暂缓** | N2-C(lint→block);G7 执行证据;G6 git 行为;HGM G2 查询;全量模式不跑 lint/D5(N2/N4 刻意非范围);20 帽内容质量 / 40「真跑过」prompt-only |
|
|
61
|
+
| **新发现 / 运维态** | 产品仓 tag/`main`/npm 时序核对;编排仓 Projects **ahead origin**(复盘时点名实测;本波不强制 push) |
|
|
62
|
+
|
|
63
|
+
### D3 · 下一 Epic 点菜建议(≤3 条)
|
|
64
|
+
|
|
65
|
+
- 每条:一句话目标 · 归属方向(一/二/三/运维)· 理由 · **不做清单**(防膨胀)
|
|
66
|
+
- 候选池(复盘文从中点菜,不必全开):方向二状态机引擎骨架;G7;N2-C;dogfood 3 文修齐;方向三契约/G6;`discipline-coverage.yaml` 资产化;Projects push 卫生
|
|
67
|
+
|
|
68
|
+
### D4 · 双仓与发布态核对(只读报告)
|
|
69
|
+
|
|
70
|
+
- 复盘文内一小节:`@cyning/harness` 当前 version / tag `v2.9.0` / npm 是否对齐;Projects `origin/main` ahead 计数(复盘执行时重测)
|
|
71
|
+
- **不**代推、不改 npm 脚本
|
|
72
|
+
|
|
73
|
+
### D5 · task 路径预告(仅指针)
|
|
74
|
+
|
|
75
|
+
- 建议 task_slug:`cyning-harness-post-g4-debt-retro`
|
|
76
|
+
- 建议 active 路径:`docs/harness/tasks/active/task_cyning_harness_post_g4_debt_retro_v1.md`(**正文由 00 起草**;本 SPEC 不写 §5)
|
|
77
|
+
|
|
78
|
+
---
|
|
79
|
+
|
|
80
|
+
## 3. 非范围
|
|
81
|
+
|
|
82
|
+
- 本波 **不**实现引擎 / 不改 `packages` 或产品仓 CLI 行为
|
|
83
|
+
- **不**强制修齐 3 个缺审查文 task(可列入点菜建议)
|
|
84
|
+
- **不**发版(无 2.9.x / 2.10.0)
|
|
85
|
+
- **不**把 lint 升 block(N2-C)、**不**做 G6/G7 实现、**不**开 HGM G2
|
|
86
|
+
- **不**代签 `HG-SPEC-SIGNOFF` / 任何人闸
|
|
87
|
+
- **不**更新 rethink 01–04 数字为「再审计」(可在复盘文注明「矩阵数字仍为 2026-07-24 快照,未重盘」)
|
|
88
|
+
|
|
89
|
+
---
|
|
90
|
+
|
|
91
|
+
## 4. 验收标准
|
|
92
|
+
|
|
93
|
+
- [ ] 复盘主文已落盘于 D1 裁定路径,简体中文,可独立阅读
|
|
94
|
+
- [ ] 欠账表含四栏:已关账 / 未修齐 / 暂缓 / 新发现;最低集(§2 D2)无遗漏行
|
|
95
|
+
- [ ] 明确写出 PLAN closed 后「点菜真空」与闭环方式(本复盘 + 点菜 ≤3)
|
|
96
|
+
- [ ] 下一 Epic 建议 **≤3** 条,每条含理由 + 不做清单
|
|
97
|
+
- [ ] dogfood 3 task basename 与双仓发布态(npm/tag/ahead)有专节或表行
|
|
98
|
+
- [ ] 机械化率叙事:主链已机械 vs 20 内容质量 / 40 真跑过仍 prompt-only
|
|
99
|
+
- [ ] `test_strategy: not_applicable` 理由在 task 元信息回填(与本 SPEC 一致)
|
|
100
|
+
- [ ] 无产品代码 diff;无新版本号声称
|
|
101
|
+
|
|
102
|
+
---
|
|
103
|
+
|
|
104
|
+
## 5. failure_paths
|
|
105
|
+
|
|
106
|
+
| 触发条件 | 系统行为 / 文档行为 | 可重试 |
|
|
107
|
+
|----------|---------------------|--------|
|
|
108
|
+
| 复盘文漏写某已知欠账 | 20-spec-audit / 维护者退回 · 补表行 | 是 |
|
|
109
|
+
| 点菜建议 >3 条 | 拒签收 · 合并或降为「观察项」附录 | 是 |
|
|
110
|
+
| 把实现/发版写进本波范围 | 00/30 拒开工 · 拆独立 SPEC | — |
|
|
111
|
+
| 双仓状态与复盘时实测不符 | 复盘文标注「时点快照」· 不阻断签收 | 重测更新表 |
|
|
112
|
+
| 误将 3 缺审 task 当作本波必做 | 对照 §3 非范围 · 仅建议栏 | — |
|
|
113
|
+
|
|
114
|
+
---
|
|
115
|
+
|
|
116
|
+
## 6. 依赖与引用
|
|
117
|
+
|
|
118
|
+
- PLAN(closed):`docs/harness/guides/PLAN_post_g4_next_mechanization_v1_zh.md`
|
|
119
|
+
- rethink:`cyning-harness/docs/rethink/2026-07-mechanization-rate/{01..04,README}.md`
|
|
120
|
+
- 最近 SPEC:`SPEC-verify-full-reviews-gate_v1.md`(N4 · dogfood 15/4/3)
|
|
121
|
+
- N2 residual:lint block(选项 C)须 FAIL 率下降
|
|
122
|
+
- dogfood active:
|
|
123
|
+
- `docs/harness/tasks/active/task_cyning_harness_a5_cli_verify_v101_v1.md`
|
|
124
|
+
- `docs/harness/tasks/active/task_harness_cyning_harness_hat_chain_pointer_sync_v1.md`
|
|
125
|
+
- `docs/harness/tasks/active/task_harness_task_validate_human_gate_ci_gate_v1.md`
|
|
126
|
+
- 产品仓 `@2.9.0` · 编排仓 Harness 落盘惯例
|
|
127
|
+
|
|
128
|
+
---
|
|
129
|
+
|
|
130
|
+
## 7. 思考轮(10-spec 回填 · R0–R5 · 形态 A · 禁止 early_stop)
|
|
131
|
+
|
|
132
|
+
### R0 · 读入与约束
|
|
133
|
+
|
|
134
|
+
**读入**:维护者「新建任务 · 欠账与更新复盘 · 多轮防遗漏」;PLAN closed(N1–N4 published);rethink 01(四方向排序)· 03(G7/G6 仍 P2/P3)· 04(lifecycle 文档先行已兑现;discipline YAML 仍建议);N4 SPEC dogfood 3 缺审;用户明示欠账清单 1–8。
|
|
135
|
+
|
|
136
|
+
**约束**:
|
|
137
|
+
|
|
138
|
+
1. 只 SPEC + invoke;不实现、不发版、不代签。
|
|
139
|
+
2. `early_stop=no` · 跑满 R5(防遗漏优先于省轮)。
|
|
140
|
+
3. track=`docs` · `test_strategy=not_applicable`。
|
|
141
|
+
4. 交付可观测:落盘路径 + 表 + ≤3 点菜,而非「聊过就算」。
|
|
142
|
+
|
|
143
|
+
**时点快照(10-spec 起草日 2026-07-25)**:产品仓 `main` 与 `origin/main` 对齐 · tag `v2.9.0` 存在 · npm `@cyning/harness@2.9.0`;编排仓 Projects **ahead origin 29**(含未追踪 interview/sim 文档等)——复盘执行须重测,防漂移。
|
|
144
|
+
|
|
145
|
+
### R1 · 范围 / 非范围 / 场景
|
|
146
|
+
|
|
147
|
+
**角色与场景**:
|
|
148
|
+
|
|
149
|
+
| 场景 | 谁 | 要什么 |
|
|
150
|
+
|------|-----|--------|
|
|
151
|
+
| S1 点菜 | 维护者 | 一张欠账全景 + ≤3 可开 Epic,避免 PLAN 关闭后口头漂移 |
|
|
152
|
+
| S2 考古 | 未来 10-spec / 面试叙事 | 「为何暂缓 G6/G7/N2-C」有单一出处 |
|
|
153
|
+
| S3 dogfood 卫生 | 编排 Agent | 知道 3 缺审是已知债非 N4 回归失败 |
|
|
154
|
+
| S4 发布卫生 | 维护者 | 双仓 tag/npm/ahead 是否再欠一刀 push |
|
|
155
|
+
|
|
156
|
+
**范围边界**:复盘 + 建议;**不**消化债本身。非范围见 §3——尤其「不修 3 文 / 不发版 / 不做引擎」防止复盘 task 膨胀成隐藏 30。
|
|
157
|
+
|
|
158
|
+
**遗漏扫描清单(R1 强制过一遍)**:
|
|
159
|
+
|
|
160
|
+
1. 发布流程:npm ↔ tag ↔ CHANGELOG ↔ 本地 vs origin
|
|
161
|
+
2. 双仓:产品仓已同步 vs Projects ahead
|
|
162
|
+
3. dogfood:3 缺审 + N4「不强制修齐」语义
|
|
163
|
+
4. 机械化率:主链 ✅ vs 20 质量 / 40 真跑过 / 全量 lint·D5
|
|
164
|
+
5. PLAN 真空:closed 后下一动作入口 = 本复盘
|
|
165
|
+
6. 方向二/三接口:lifecycle 文档先行已有 → 引擎仍空
|
|
166
|
+
7. HGM G2:无消费者暂缓(方向四)
|
|
167
|
+
8. N2-C:warn→block 前置条件(FAIL 率)
|
|
168
|
+
|
|
169
|
+
### R2 · 方案对比
|
|
170
|
+
|
|
171
|
+
| 决策点 | 选项 | 裁定 | 理由 |
|
|
172
|
+
|--------|------|------|------|
|
|
173
|
+
| 复盘主文落点 | A 工作区 `guides/` · B 产品仓 `rethink/` · C 两者镜像 | **推荐 A 为主**;B 可作「索引一小段」链回 A(task 阶段二选一,勿双真值) | PLAN/点菜消费者在 Projects;rethink 01–04 已声明「非 SPEC」;镜像易漂移 |
|
|
174
|
+
| 形态 | 仅聊天纪要 / 正式 SPEC+复盘文 / 直接开引擎 Epic | **SPEC(本文件)→ 签收 → 00 task → 复盘文** | 维护者要「新建任务」;防遗漏须可审计;引擎 Epic 须点菜后再独立 SPEC |
|
|
175
|
+
| 点菜条数 | 开放列表 / 硬顶 3 / 只排序不建议 | **硬顶 ≤3** + 附录「观察项」可选 | 防同时开多 Epic;与 PLAN「点菜」语气一致 |
|
|
176
|
+
| 3 缺审处理 | 本波必修 / 仅列表 / 忽略 | **仅列表 + 可进点菜候选** | N4 已裁定不强制;复盘职责是可见化 |
|
|
177
|
+
| 是否重跑机械化率盘点 | 全量重盘 02/03 / 叙事增量 | **叙事增量**(主链已覆盖陈述) | 全量重盘另 Epic;本波防遗漏靠清单非重审计 |
|
|
178
|
+
| test_strategy | recommended / N/A | **`not_applicable`** | 无改码;验收=文档勾选 |
|
|
179
|
+
|
|
180
|
+
**弃选**:C 双落盘镜像(维护成本);直接跳过 SPEC 开 30(违反帽链 · 且无范围闸)。
|
|
181
|
+
|
|
182
|
+
### R3 · 边界 / 失败语义 / 安全
|
|
183
|
+
|
|
184
|
+
- **边界**:复盘文不得声称「机械化率 XX%」新数字,除非附重盘方法;沿用 03 快照 +「主链已机械」定性即可。
|
|
185
|
+
- **失败**:漏项 → 书面审退回;把实现塞进范围 → 拒开工。
|
|
186
|
+
- **安全**:只读 git/npm 状态;不写密钥;不 push。
|
|
187
|
+
- **依赖**:签收本 SPEC 前,00 **不得**把复盘做成改 CLI 的 task。
|
|
188
|
+
- **误伤**:点菜若选「dogfood 修齐」勿与 N4 回归混淆——那是存量卫生,非 verify bug。
|
|
189
|
+
|
|
190
|
+
### R4 · 验收 / 可测性 / test_strategy
|
|
191
|
+
|
|
192
|
+
- 可测性 = **文档可勾选**(§4),非 pytest。
|
|
193
|
+
- `test_strategy: not_applicable` + note(元信息已填)。
|
|
194
|
+
- 建议 40 自检(task 阶段):对 §2 D2 最低集做 diff 核对;`git status -sb` / `npm view` 结果贴进复盘「时点」节。
|
|
195
|
+
- 不要求新建自动化测试文件。
|
|
196
|
+
|
|
197
|
+
### R5 · SPEC 签收就绪 · 是否可交 00 出 task
|
|
198
|
+
|
|
199
|
+
**自足性**:背景、范围/非范围、欠账最低集、落盘推荐、点菜硬顶、failure_paths、双仓注意均已写入。
|
|
200
|
+
|
|
201
|
+
**可交 00**:是。建议单 task:`cyning-harness-post-g4-debt-retro`(lightweight 文档 task · `test_strategy=not_applicable`)。图谱无需 bootstrap。
|
|
202
|
+
|
|
203
|
+
**签收后链路**:人签本 SPEC(或轻量 20-spec-audit)→ 00 起草 task → 10-task(可 early_stop 若仅投影本 §2)→ 20-task-audit → HG-AUDIT-R1 → 30 写复盘文。
|
|
204
|
+
|
|
205
|
+
**下一棒 Prompt 要点**:00 勿扩 scope 至 N2-C/G7 实现;点菜结论写进复盘文末「维护者待勾选」表即可。
|
|
206
|
+
|
|
207
|
+
### 思考轮控制
|
|
208
|
+
|
|
209
|
+
| 字段 | 值 |
|
|
210
|
+
|------|-----|
|
|
211
|
+
| `actual_last_round` | `R5` |
|
|
212
|
+
| `early_stop` | `no` |
|
|
213
|
+
| `early_stop_reason` | — |
|
|
214
|
+
| `residual_risks` | ① 复盘执行时双仓 ahead/npm 可能已变——须时点重测;② 点菜 ≤3 仍可能争议排序(方向二 vs dogfood 卫生)——留给维护者勾选非 Agent 代决;③ rethink 03 数字未重盘,对外叙事若引用百分比须标注快照日;④ Projects 未追踪文档与 ahead 29 混杂,复盘勿误判「全是 Harness 债」;⑤ 若维护者坚持复盘落产品仓 rethink,须避免与 guides 双真值 |
|
|
215
|
+
| `round_extension_note` | 维护者要求多轮防遗漏 · **禁止 early_stop** · 已跑满 R0–R5;未扩 R6 |
|
|
216
|
+
|
|
217
|
+
---
|
|
218
|
+
|
|
219
|
+
## 8. 建议点菜池(供复盘文精炼至 ≤3 · 非本波范围)
|
|
220
|
+
|
|
221
|
+
| ID | 候选 | 方向 | 一句话理由 | 典型不做 |
|
|
222
|
+
|----|------|------|------------|----------|
|
|
223
|
+
| P1 | 方向二:lifecycle **转移引擎**最小骨架 | 二 | YAML 已先行;挂点决策下一台阶 | 不做完整 runner / G7 同波硬塞 |
|
|
224
|
+
| P2 | dogfood:补齐 3 缺审查文 | 运维/卫生 | 裸 verify 工作区可绿;成本低 | 不改 verify 语义 |
|
|
225
|
+
| P3 | N2-C:`verify --task` lint **block** | 一 | WARN 债转真闸;须先证明 FAIL 率下降 | 不做全量 lint |
|
|
226
|
+
| P4 | G7 执行证据(`harness run`) | 二 | 40「真跑过」最大黑洞 | 不做 grep 伪证据 |
|
|
227
|
+
| P5 | 方向三:`--json` 契约收敛 / G6 调研 | 三 | Agent 消费者放大前置 | 不上 MCP |
|
|
228
|
+
| P6 | `discipline-coverage.yaml` 资产化 | 一 | 04 已建议;改进路线可版本化 | 不做重盘全量人工周 |
|
|
229
|
+
|
|
230
|
+
---
|
|
231
|
+
|
|
232
|
+
## 修订记录
|
|
233
|
+
|
|
234
|
+
| 日期 | 摘要 |
|
|
235
|
+
|------|------|
|
|
236
|
+
| 2026-07-25 | 10-spec R0–R5(形态 A · early_stop=no)· 维护者指令「欠账复盘 · 多轮防遗漏」 |
|
|
237
|
+
| 2026-07-25 | 维护者签收(对话「签收」)→ `signed` · 00 起草 task |
|
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
> **关联图谱**:无(纯 Harness 工具链)
|
|
6
6
|
> **上游**:[`PLAN_post_g4_next_mechanization_v1_zh.md`](../../../docs/harness/guides/PLAN_post_g4_next_mechanization_v1_zh.md) · N4 · G2 residual
|
|
7
7
|
> **前置**:G2 `@cyning/harness@2.5.0`(`--task` 已查 reviews)· N3 `@2.8.0`
|
|
8
|
-
> **下游**:
|
|
8
|
+
> **下游**:CLOSE ✅ · `@cyning/harness@2.9.0` published · 合入 `main` · tag `v2.9.0`
|
|
9
9
|
|
|
10
10
|
---
|
|
11
11
|
|
|
@@ -0,0 +1,289 @@
|
|
|
1
|
+
# Discipline coverage · Starter 子集机械化率资产(方向一)
|
|
2
|
+
#
|
|
3
|
+
# 运行时真值:本文件(随 npm 包分发)。
|
|
4
|
+
# 历史叙事:docs/rethink/2026-07-mechanization-rate/03_coverage_matrix.md
|
|
5
|
+
# 维护:新闸合入时更新 statements[].status / gaps[] / as_of_package_version
|
|
6
|
+
# 禁止:把本文件当「每周全量重盘」流程;不做 audit --discipline UI(本波)
|
|
7
|
+
|
|
8
|
+
version: "1"
|
|
9
|
+
as_of_package_version: "2.10.0"
|
|
10
|
+
scope: "Starter · harness/prompts (10/22/30/40 + FRAGMENT)+ TEMPLATE_invoke"
|
|
11
|
+
source_audit: "rethink/2026-07-mechanization-rate · 02 转录 + 03 聚合 · 状态已按 G1–G4/N1–N4 刷新(非第二轮通读盘点)"
|
|
12
|
+
|
|
13
|
+
gaps:
|
|
14
|
+
- id: G1
|
|
15
|
+
title: task md 结构 lint
|
|
16
|
+
status: closed
|
|
17
|
+
closed_in: "2.3.0"
|
|
18
|
+
note: "task lint E1–E7"
|
|
19
|
+
- id: G2
|
|
20
|
+
title: reviews 留档闸
|
|
21
|
+
status: closed
|
|
22
|
+
closed_in: "2.5.0"
|
|
23
|
+
note: "verify --task + close 检查 6;N4 全量 2.9.0"
|
|
24
|
+
- id: G3
|
|
25
|
+
title: 文本纪律(绝对路径)
|
|
26
|
+
status: closed
|
|
27
|
+
closed_in: "2.3.0"
|
|
28
|
+
note: "E6;invoke 预写 approved grep 仍缓做"
|
|
29
|
+
- id: G4
|
|
30
|
+
title: 思考轮结构
|
|
31
|
+
status: closed
|
|
32
|
+
closed_in: "2.6.0"
|
|
33
|
+
note: "task lint E8–E10 / W4–W5"
|
|
34
|
+
- id: G6
|
|
35
|
+
title: git 行为层
|
|
36
|
+
status: deferred
|
|
37
|
+
closed_in: null
|
|
38
|
+
note: "方向三"
|
|
39
|
+
- id: G7
|
|
40
|
+
title: 执行证据(真跑过)
|
|
41
|
+
status: deferred
|
|
42
|
+
closed_in: null
|
|
43
|
+
note: "方向二 runner;跟 lifecycle dry-run 之后"
|
|
44
|
+
- id: N2-C
|
|
45
|
+
title: verify --task lint → block
|
|
46
|
+
status: deferred
|
|
47
|
+
closed_in: null
|
|
48
|
+
note: "现 warn-only(2.7.0)· 须 FAIL 率下降"
|
|
49
|
+
- id: SPEC-reviews
|
|
50
|
+
title: SPEC 审查文闸
|
|
51
|
+
status: closed
|
|
52
|
+
closed_in: "2.8.0"
|
|
53
|
+
note: "verify --spec"
|
|
54
|
+
- id: FULL-reviews
|
|
55
|
+
title: 裸 verify 全量 reviews + 双路径
|
|
56
|
+
status: closed
|
|
57
|
+
closed_in: "2.9.0"
|
|
58
|
+
note: "N4"
|
|
59
|
+
- id: LIFECYCLE-ENGINE
|
|
60
|
+
title: lifecycle dry-run 最小引擎
|
|
61
|
+
status: closed
|
|
62
|
+
closed_in: "2.10.0"
|
|
63
|
+
note: "Epic T2 · 旁路报告"
|
|
64
|
+
|
|
65
|
+
statements:
|
|
66
|
+
- id: A1
|
|
67
|
+
source: 30-execute-code.md
|
|
68
|
+
summary: HG pending → 拒开工、禁改码
|
|
69
|
+
status: mechanical
|
|
70
|
+
mechanism: "M1 gate-check + M2 verify"
|
|
71
|
+
gap: null
|
|
72
|
+
notes: null
|
|
73
|
+
mechanism_quality: null
|
|
74
|
+
- id: A2
|
|
75
|
+
source: 30-execute-code.md
|
|
76
|
+
summary: 开工前首输出 GATE_VERIFY 闸扫描表
|
|
77
|
+
status: partial
|
|
78
|
+
mechanism: "M2 提供判定;Agent 是否先输出表无检查"
|
|
79
|
+
gap: null
|
|
80
|
+
notes: null
|
|
81
|
+
mechanism_quality: null
|
|
82
|
+
- id: A3
|
|
83
|
+
source: 30-execute-code.md
|
|
84
|
+
summary: 真值在 task 表;声称 vs 表 pending → STOP
|
|
85
|
+
status: partial
|
|
86
|
+
mechanism: "M1/M2 读表"
|
|
87
|
+
gap: null
|
|
88
|
+
notes: "用户声称侧不可机械"
|
|
89
|
+
mechanism_quality: null
|
|
90
|
+
- id: A4
|
|
91
|
+
source: 30-execute-code.md
|
|
92
|
+
summary: test_strategy required → 先可失败测试再改实现
|
|
93
|
+
status: partial
|
|
94
|
+
mechanism: "M3 D5 探测测试文件存在"
|
|
95
|
+
gap: null
|
|
96
|
+
notes: "先红后绿顺序无机制 · mechanism_quality 预留"
|
|
97
|
+
mechanism_quality: null
|
|
98
|
+
- id: A5
|
|
99
|
+
source: 30-execute-code.md
|
|
100
|
+
summary: 运行验证命令 + 回填自检结论
|
|
101
|
+
status: mechanical
|
|
102
|
+
mechanism: "M5 非占位符检查"
|
|
103
|
+
gap: G7
|
|
104
|
+
notes: "命令真跑过仍靠 40 诚实"
|
|
105
|
+
mechanism_quality: null
|
|
106
|
+
- id: A6
|
|
107
|
+
source: 30-execute-code.md
|
|
108
|
+
summary: invoke 快照落盘 by-task/<slug>/
|
|
109
|
+
status: mechanical
|
|
110
|
+
mechanism: "M5 close + M6 lint-done"
|
|
111
|
+
gap: null
|
|
112
|
+
notes: null
|
|
113
|
+
mechanism_quality: null
|
|
114
|
+
- id: A7
|
|
115
|
+
source: 30-execute-code.md
|
|
116
|
+
summary: 归档只能 task close PASS 后进行
|
|
117
|
+
status: mechanical
|
|
118
|
+
mechanism: "M5"
|
|
119
|
+
gap: null
|
|
120
|
+
notes: "手动 mv 旁路由 M6 兜底"
|
|
121
|
+
mechanism_quality: null
|
|
122
|
+
- id: A8
|
|
123
|
+
source: 30-execute-code.md
|
|
124
|
+
summary: HG-GRAPH-MODULES pending → 禁改码
|
|
125
|
+
status: mechanical
|
|
126
|
+
mechanism: "M1 gate-check --graph"
|
|
127
|
+
gap: null
|
|
128
|
+
notes: null
|
|
129
|
+
mechanism_quality: null
|
|
130
|
+
- id: A9
|
|
131
|
+
source: 30-execute-code.md
|
|
132
|
+
summary: 缺验收/failure_paths/必读 → 仅输出阻塞清单
|
|
133
|
+
status: mechanical
|
|
134
|
+
mechanism: "task lint E1–E7(G1 · v2.3.0)"
|
|
135
|
+
gap: G1
|
|
136
|
+
notes: "02 原 ❌ · 已刷新"
|
|
137
|
+
mechanism_quality: null
|
|
138
|
+
- id: A10
|
|
139
|
+
source: 30-execute-code.md
|
|
140
|
+
summary: 交接物 commit 仅本轮路径、禁 git add -A
|
|
141
|
+
status: prompt-only
|
|
142
|
+
mechanism: null
|
|
143
|
+
gap: G6
|
|
144
|
+
notes: null
|
|
145
|
+
mechanism_quality: null
|
|
146
|
+
- id: B1
|
|
147
|
+
source: 40-self-check.md
|
|
148
|
+
summary: 逐条对照验收标准标记 pass/fail
|
|
149
|
+
status: partial
|
|
150
|
+
mechanism: "M5 查无未勾选"
|
|
151
|
+
gap: null
|
|
152
|
+
notes: null
|
|
153
|
+
mechanism_quality: null
|
|
154
|
+
- id: B2
|
|
155
|
+
source: 40-self-check.md
|
|
156
|
+
summary: 必须运行验证命令并摘要退出码
|
|
157
|
+
status: prompt-only
|
|
158
|
+
mechanism: null
|
|
159
|
+
gap: G7
|
|
160
|
+
notes: "真跑过无证据"
|
|
161
|
+
mechanism_quality: null
|
|
162
|
+
- id: B3
|
|
163
|
+
source: 40-self-check.md
|
|
164
|
+
summary: 必须回填自检结论(执行者)
|
|
165
|
+
status: mechanical
|
|
166
|
+
mechanism: "M5"
|
|
167
|
+
gap: null
|
|
168
|
+
notes: null
|
|
169
|
+
mechanism_quality: null
|
|
170
|
+
- id: B4
|
|
171
|
+
source: 40-self-check.md
|
|
172
|
+
summary: 禁止改 tasks/reviews/invokes(S2)
|
|
173
|
+
status: prompt-only
|
|
174
|
+
mechanism: null
|
|
175
|
+
gap: G6
|
|
176
|
+
notes: null
|
|
177
|
+
mechanism_quality: null
|
|
178
|
+
- id: B5
|
|
179
|
+
source: 40-self-check.md
|
|
180
|
+
summary: 不凭记忆声称测过
|
|
181
|
+
status: prompt-only
|
|
182
|
+
mechanism: null
|
|
183
|
+
gap: null
|
|
184
|
+
notes: "诚实纪律 · 设计上留 Prompt"
|
|
185
|
+
mechanism_quality: null
|
|
186
|
+
- id: C1
|
|
187
|
+
source: 22-task-audit.md
|
|
188
|
+
summary: 必须落盘 reviews task_*_audit_R*
|
|
189
|
+
status: mechanical
|
|
190
|
+
mechanism: "findReview · verify/close(G2 · v2.5+;全量 v2.9)"
|
|
191
|
+
gap: G2
|
|
192
|
+
notes: "02 原 ❌ · 已刷新;内容质量仍 prompt-only"
|
|
193
|
+
mechanism_quality: null
|
|
194
|
+
- id: C2
|
|
195
|
+
source: 22-task-audit.md
|
|
196
|
+
summary: HG-AUDIT-R1 pending 时禁止附 30 Prompt
|
|
197
|
+
status: partial
|
|
198
|
+
mechanism: "存在性闸;审查文内容无检查"
|
|
199
|
+
gap: G2
|
|
200
|
+
notes: null
|
|
201
|
+
mechanism_quality: null
|
|
202
|
+
- id: C3
|
|
203
|
+
source: 22-task-audit.md
|
|
204
|
+
summary: 思考轮审查不通过 → 退回 10
|
|
205
|
+
status: prompt-only
|
|
206
|
+
mechanism: null
|
|
207
|
+
gap: null
|
|
208
|
+
notes: "流程纪律"
|
|
209
|
+
mechanism_quality: null
|
|
210
|
+
- id: C4
|
|
211
|
+
source: 22-task-audit.md
|
|
212
|
+
summary: 零阻塞写已核对项;终轮写签收
|
|
213
|
+
status: prompt-only
|
|
214
|
+
mechanism: null
|
|
215
|
+
gap: null
|
|
216
|
+
notes: "审查文结构无 lint"
|
|
217
|
+
mechanism_quality: null
|
|
218
|
+
- id: D1
|
|
219
|
+
source: 10-requirements.md
|
|
220
|
+
summary: task 必含验收/failure_paths/非范围/依赖
|
|
221
|
+
status: mechanical
|
|
222
|
+
mechanism: "task lint(G1)"
|
|
223
|
+
gap: G1
|
|
224
|
+
notes: "02 原 ❌ · 已刷新"
|
|
225
|
+
mechanism_quality: null
|
|
226
|
+
- id: D2
|
|
227
|
+
source: 10-requirements.md
|
|
228
|
+
summary: 不写绝对本机路径
|
|
229
|
+
status: mechanical
|
|
230
|
+
mechanism: "task lint E6(G3)"
|
|
231
|
+
gap: G3
|
|
232
|
+
notes: "02 原 ❌ · 已刷新"
|
|
233
|
+
mechanism_quality: null
|
|
234
|
+
- id: D3
|
|
235
|
+
source: 10-requirements.md
|
|
236
|
+
summary: 预置 R0–R5 + 思考轮控制表
|
|
237
|
+
status: mechanical
|
|
238
|
+
mechanism: "task lint E8–E10(G4 · 条件触发)"
|
|
239
|
+
gap: G4
|
|
240
|
+
notes: "02 原 ❌ · 已刷新;内容质量仍 20 帽"
|
|
241
|
+
mechanism_quality: null
|
|
242
|
+
- id: D4
|
|
243
|
+
source: 10-requirements.md
|
|
244
|
+
summary: 缺验收/failure_paths → 仅输出阻塞清单
|
|
245
|
+
status: mechanical
|
|
246
|
+
mechanism: "task lint(G1)"
|
|
247
|
+
gap: G1
|
|
248
|
+
notes: null
|
|
249
|
+
mechanism_quality: null
|
|
250
|
+
- id: E1
|
|
251
|
+
source: FRAGMENT_30
|
|
252
|
+
summary: invoke 中禁止预写 HG-AUDIT-R1 approved
|
|
253
|
+
status: prompt-only
|
|
254
|
+
mechanism: null
|
|
255
|
+
gap: G3
|
|
256
|
+
notes: "SPEC R2 缓做 · 误报风险"
|
|
257
|
+
mechanism_quality: null
|
|
258
|
+
- id: E2
|
|
259
|
+
source: FRAGMENT_30
|
|
260
|
+
summary: 用户确认 approved = 须核验非事实
|
|
261
|
+
status: partial
|
|
262
|
+
mechanism: "M2 读表"
|
|
263
|
+
gap: null
|
|
264
|
+
notes: null
|
|
265
|
+
mechanism_quality: null
|
|
266
|
+
- id: F1
|
|
267
|
+
source: TEMPLATE_invoke.md
|
|
268
|
+
summary: 落盘路径 by-task/<task_slug>/
|
|
269
|
+
status: mechanical
|
|
270
|
+
mechanism: "M5/M6"
|
|
271
|
+
gap: null
|
|
272
|
+
notes: null
|
|
273
|
+
mechanism_quality: null
|
|
274
|
+
- id: F2
|
|
275
|
+
source: TEMPLATE_invoke.md
|
|
276
|
+
summary: 同帽追问不新增 invoke;打回用 _r2
|
|
277
|
+
status: prompt-only
|
|
278
|
+
mechanism: null
|
|
279
|
+
gap: null
|
|
280
|
+
notes: "命名纪律 · 可留 prompt"
|
|
281
|
+
mechanism_quality: null
|
|
282
|
+
- id: F3
|
|
283
|
+
source: TEMPLATE_invoke.md
|
|
284
|
+
summary: 落盘 + task 回填后再 commit
|
|
285
|
+
status: prompt-only
|
|
286
|
+
mechanism: null
|
|
287
|
+
gap: G6
|
|
288
|
+
notes: null
|
|
289
|
+
mechanism_quality: null
|
package/harness/lifecycle.yaml
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
|
-
# Task lifecycle ·
|
|
1
|
+
# Task lifecycle · 最小真值(方向二 · v1)
|
|
2
2
|
#
|
|
3
|
-
#
|
|
4
|
-
#
|
|
3
|
+
# 登记真值:状态 / 转移 / 守卫。yaml 本身不是引擎。
|
|
4
|
+
# 由 `lifecycle dry-run` 引擎消费(v2.10+ · 资格判定旁路报告 · 不写盘)。
|
|
5
|
+
# 只读展示:npx @cyning/harness lifecycle show [--json]
|
|
5
6
|
# Schema:schema/lifecycle.v1.schema.json
|
|
6
7
|
|
|
7
8
|
version: "1"
|
package/lib/cli.js
CHANGED
|
@@ -505,34 +505,98 @@ async function cmdVerify(args) {
|
|
|
505
505
|
}
|
|
506
506
|
|
|
507
507
|
async function cmdLifecycle(args) {
|
|
508
|
-
const {
|
|
508
|
+
const {
|
|
509
|
+
loadLifecycle,
|
|
510
|
+
formatLifecycleShow,
|
|
511
|
+
dryRunTransition,
|
|
512
|
+
formatLifecycleDryRun,
|
|
513
|
+
} = await import('./lifecycle.js');
|
|
509
514
|
const [sub, ...rest] = args;
|
|
510
515
|
if (!sub || sub === '--help' || sub === '-h' || args.includes('--help') || args.includes('-h')) {
|
|
511
|
-
console.log(`用法:
|
|
516
|
+
console.log(`用法:
|
|
517
|
+
npx @cyning/harness lifecycle show [--json]
|
|
518
|
+
npx @cyning/harness lifecycle dry-run --transition ID --from STATE [--task PATH] [--json]
|
|
519
|
+
[--allow-no-review] [--allow-lint-fail] [--allow-no-spec-review]
|
|
512
520
|
|
|
513
|
-
|
|
514
|
-
|
|
521
|
+
show · 只读展示 harness/lifecycle.yaml(登记真值 · v2.7+)
|
|
522
|
+
dry-run · 转移资格判定(引擎消费 yaml · v2.10+ · 旁路报告 · 非 runner / 非 G7)
|
|
515
523
|
`);
|
|
516
524
|
return;
|
|
517
525
|
}
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
526
|
+
|
|
527
|
+
if (sub === 'show') {
|
|
528
|
+
const json = rest.includes('--json');
|
|
529
|
+
const unknown = rest.filter((a) => a !== '--json');
|
|
530
|
+
if (unknown.length > 0) {
|
|
531
|
+
const err = new Error(`lifecycle show 未知参数: ${unknown.join(' ')}`);
|
|
532
|
+
err.exitCode = 1;
|
|
533
|
+
throw err;
|
|
534
|
+
}
|
|
535
|
+
const { data } = loadLifecycle();
|
|
536
|
+
if (json) {
|
|
537
|
+
console.log(JSON.stringify(data, null, 2));
|
|
538
|
+
} else {
|
|
539
|
+
console.log(formatLifecycleShow(data));
|
|
540
|
+
}
|
|
541
|
+
return;
|
|
529
542
|
}
|
|
530
|
-
|
|
531
|
-
if (
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
543
|
+
|
|
544
|
+
if (sub === 'dry-run') {
|
|
545
|
+
let remaining = rest;
|
|
546
|
+
const { value: transitionId, rest: r1 } = takeOption(remaining, '--transition');
|
|
547
|
+
remaining = r1;
|
|
548
|
+
const { value: fromState, rest: r2 } = takeOption(remaining, '--from');
|
|
549
|
+
remaining = r2;
|
|
550
|
+
const { value: taskPath, rest: r3 } = takeOption(remaining, '--task');
|
|
551
|
+
remaining = r3;
|
|
552
|
+
const json = remaining.includes('--json');
|
|
553
|
+
const allowNoReview = remaining.includes('--allow-no-review');
|
|
554
|
+
const allowLintFail = remaining.includes('--allow-lint-fail');
|
|
555
|
+
const allowNoSpecReview = remaining.includes('--allow-no-spec-review');
|
|
556
|
+
remaining = remaining.filter(
|
|
557
|
+
(a) =>
|
|
558
|
+
a !== '--json' &&
|
|
559
|
+
a !== '--allow-no-review' &&
|
|
560
|
+
a !== '--allow-lint-fail' &&
|
|
561
|
+
a !== '--allow-no-spec-review',
|
|
562
|
+
);
|
|
563
|
+
if (remaining.length > 0) {
|
|
564
|
+
const err = new Error(`lifecycle dry-run 未知参数: ${remaining.join(' ')}`);
|
|
565
|
+
err.exitCode = 1;
|
|
566
|
+
throw err;
|
|
567
|
+
}
|
|
568
|
+
if (!transitionId || !fromState) {
|
|
569
|
+
const err = new Error(
|
|
570
|
+
'lifecycle dry-run 须 --transition <id> 与 --from <state>\n提示: lifecycle show',
|
|
571
|
+
);
|
|
572
|
+
err.exitCode = 1;
|
|
573
|
+
throw err;
|
|
574
|
+
}
|
|
575
|
+
|
|
576
|
+
const report = dryRunTransition({
|
|
577
|
+
transitionId,
|
|
578
|
+
fromState,
|
|
579
|
+
taskPath,
|
|
580
|
+
flags: { allowNoReview, allowLintFail, allowNoSpecReview },
|
|
581
|
+
cwd: process.cwd(),
|
|
582
|
+
});
|
|
583
|
+
|
|
584
|
+
if (json) {
|
|
585
|
+
console.log(JSON.stringify(report, null, 2));
|
|
586
|
+
} else {
|
|
587
|
+
console.log(formatLifecycleDryRun(report));
|
|
588
|
+
}
|
|
589
|
+
if (report.exitCode && report.exitCode !== 0) {
|
|
590
|
+
process.exitCode = report.exitCode;
|
|
591
|
+
}
|
|
592
|
+
return;
|
|
535
593
|
}
|
|
594
|
+
|
|
595
|
+
const err = new Error(
|
|
596
|
+
`lifecycle 子命令未知: ${sub}\n用法: lifecycle show [--json] · lifecycle dry-run --transition ID --from STATE`,
|
|
597
|
+
);
|
|
598
|
+
err.exitCode = 1;
|
|
599
|
+
throw err;
|
|
536
600
|
}
|
|
537
601
|
|
|
538
602
|
async function cmdSync(args) {
|