dsh-vibe-math 2.3.1 → 2.3.2
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/AUDIT-CHECKLIST.md +45 -0
- package/README.md +16 -6
- package/RELEASE-NOTES-2.3.2.md +145 -0
- package/audit-formal-sensitivity.mjs +11 -2
- package/audit-prompt-invariants.mjs +414 -0
- package/audit-spec-traceability.mjs +173 -0
- package/docs/formal-verification.md +33 -10
- package/docs/generate_framework_diagram_v5.mjs +2 -1
- package/docs/test-timing.md +32 -10
- package/formal-verify-v2.test.mjs +242 -2
- package/formal-verify-v3.test.mjs +176 -4
- package/formal-verify-v4.test.mjs +184 -5
- package/formal-verify-v5.test.mjs +91 -4
- package/installer.js +3 -1
- package/package.json +5 -2
- package/prompt-corpus-persona/persona-corpus.json +2 -2
- package/prompt-corpus-persona/persona-corpus.md +6 -2
- package/prompt-corpus-v2/formal-verify-v2.json +134 -44
- package/prompt-corpus-v2/formal-verify-v2.md +1033 -44
- package/prompt-corpus-v3/formal-verify-v3.json +200 -128
- package/prompt-corpus-v3/formal-verify-v3.md +948 -243
- package/prompt-corpus-v4/formal-verify-v4.json +8 -3
- package/prompt-corpus-v4/formal-verify-v4.md +38 -10
- package/prompt-corpus-v5/prompt-corpus-v5.json +175 -246
- package/prompt-corpus-v5/prompt-corpus-v5.md +341 -781
- package/prompt-v5-integrity.test.mjs +136 -22
- package/run-tests.mjs +30 -11
- package/vibe-math-v2/vibe-math-v2.js +149 -35
- package/vibe-math-v2//345/256/236/347/216/260/346/226/271/346/241/210.md +53 -5
- package/vibe-math-v3/vibe-math-v3.js +88 -23
- package/vibe-math-v3//345/256/236/347/216/260/346/226/271/346/241/210.md +7 -6
- package/vibe-math-v4/vibe-math-v4.js +103 -24
- package/vibe-math-v4//345/256/236/347/216/260/346/226/271/346/241/210.md +34 -11
- package/vibe-math-v5/agent.cordis.yml +6 -2
- package/vibe-math-v5/vibe-math-v5.js +56 -10
- package/vibe-math-v5//345/256/236/347/216/260/346/226/271/346/241/210.md +40 -13
- package/vibe-math-v5//346/236/266/346/236/204/345/233/276.md +16 -2
- package//347/244/272/344/276/213/345/233/276//346/241/206/346/236/266/345/233/276-v5.svg +6 -5
package/AUDIT-CHECKLIST.md
CHANGED
|
@@ -119,6 +119,51 @@
|
|
|
119
119
|
- [ ] 每个档位(`off` / `encourage` / `require`)的注入文本是否**各自**被人读过?只读一个档位等于没读
|
|
120
120
|
——首版 `require` 档的门禁措辞从未进入任何语料。
|
|
121
121
|
|
|
122
|
+
### 1.8 四套同构:任何语义修正必须**四套同步**
|
|
123
|
+
|
|
124
|
+
v2/v3/v4/v5 是**同构实现**(同一份契约、四份独立代码,刻意零共享)。这带来一个特有的缺陷类别:
|
|
125
|
+
**修正只落到一套**。真实事故(2.3.1 → 2.3.2):
|
|
126
|
+
|
|
127
|
+
- `defect` 的"`encourage` 档不得声称框架会强制搁置"这条修正只改了 v5,另外三套仍无条件宣称
|
|
128
|
+
"本次裁定**不定论**"——承诺了 `encourage` 档根本无法强制的行为;
|
|
129
|
+
- "撤回归档证明"在 v5 是**删除 → 校验真的没了 → 否则覆盖撤回说明**,另外三套只做尽力删除
|
|
130
|
+
(两套静默吞掉失败、一套不校验)——宿主删不掉时,已撤回的证明仍留在 `Verified/Lean/<id>.lean`
|
|
131
|
+
这个"大家找证明"的位置;
|
|
132
|
+
- `formal` 回执通道在 v2/v3 有 `formalOn()` 守卫,v4/v5 没有——`off` 档可被残留回执写入状态。
|
|
133
|
+
|
|
134
|
+
所以:
|
|
135
|
+
|
|
136
|
+
- [ ] 任何语义/措辞修正,**逐一核对四套**(含各自的 `实现方案.md`、persona、语料与断言);
|
|
137
|
+
- [ ] 参数、工具名、字段名、路径、错误码这类**表面**已有静态守卫
|
|
138
|
+
(`audit-persona-surface` / `audit-spec-traceability` / `audit-prompt-invariants`);
|
|
139
|
+
但**语义**(承诺强度、失败回退、边界条件)没有静态守卫,必须靠"把四套**渲染后的提示词/行为**
|
|
140
|
+
并排对照"来查——随包语料就是为这个准备的;
|
|
141
|
+
- [ ] 用**同一份输入**驱动四套,比较**可观测结果**(记录落库、文件是否撤回、门禁是否放行),
|
|
142
|
+
而不是比较代码长得像不像。
|
|
143
|
+
|
|
144
|
+
### 1.9 工具参数 schema:文档写了 ≠ 工具收得下
|
|
145
|
+
|
|
146
|
+
§1.6 查的是"persona 里有没有写",这一节查**工具的参数 schema 收不收得下**。本仓库所有工具 schema 都由
|
|
147
|
+
`objParams` 收口,并以 `additionalProperties:false` **关闭**:schema 没列出的键会被任何遵守 schema 的
|
|
148
|
+
provider **直接拒绝**。于是"提示词/规格/状态表都写着这个参数"完全可以在**功能根本打不开**的同时全绿。
|
|
149
|
+
|
|
150
|
+
- [ ] 每个"可调参数"是否同时出现在:**设置工具的参数 schema**、发现面(`vibe_math_setup` 返回的
|
|
151
|
+
`PARAM_SCHEMA` / v4·v5 的 status 参数表)、`<vibe root>/*setting.json` 模板、以及 persona 参数表?
|
|
152
|
+
**真实事故(2.3.2 D1)**:v3 的四个 Lean 参数写进了 persona、规格与状态行,却**从未写进
|
|
153
|
+
`vibe_math_set_params` 的 schema**;所有套件全绿(套件直接调 handler、绕过 schema),而用户
|
|
154
|
+
**永远无法开启这个功能**。
|
|
155
|
+
- [ ] schema **声明的**每个键,参数层是否**真的接收**?(v2/v3 的闸门是 `DEFAULT_PARAMS` 的键集、
|
|
156
|
+
v4 是 `k in params`、v5 是 `normalizeParams` 的类型列表。)声明而不接收 = 调用返回 `{ok:true}`、
|
|
157
|
+
什么都不发生——最容易被读成"设置成功"的静默失效。
|
|
158
|
+
- [ ] 同一工具被**注册两次**(v2/v3 各有"会话 handler 表"与"真实 `tools.register`"两份定义)时,
|
|
159
|
+
两份 schema 是否**逐键一致**?漂移会让其中一条路径上的功能不可达。
|
|
160
|
+
- [ ] 新增/修改任何参数后,跑 `node audit-prompt-invariants.mjs`(I13/I14)与
|
|
161
|
+
`node audit-prompt-invariants.mjs --self-probe`(证明这两条不变式**真的会变红**)。
|
|
162
|
+
|
|
163
|
+
> **守卫为什么必须是"可被证伪的"**:I13/I14 用 `--self-probe` 在内存里注入真实缺陷形状
|
|
164
|
+
> (v3 少一个 Lean 参数 / v4 多一个参数层不接收的键 / v5 的 `normalizeParams` 少一项),
|
|
165
|
+
> 要求对应不变式**变红**,并要求**未变异的对照跑仍为绿**。没有对照的探针会把"脚本坏了"当成"守住了"。
|
|
166
|
+
|
|
122
167
|
---
|
|
123
168
|
|
|
124
169
|
### 2.1 逐条断言,而不是抽查
|
package/README.md
CHANGED
|
@@ -247,7 +247,7 @@ flowchart TB
|
|
|
247
247
|
|
|
248
248
|
| 取值 | 含义 |
|
|
249
249
|
|---|---|
|
|
250
|
-
| **`'off'`(默认)** | **不额外进行任何要求。**
|
|
250
|
+
| **`'off'`(默认)** | **不额外进行任何要求。** 成员提示词里不出现任何 Lean 内容,不写入任何形式化状态,验证流程与门禁完全不变(是**真正的无操作**,有断言与探针守着)。三个工具仍注册可用(主动调用照常工作);主代理的 persona **始终**写着这三个工具与四个参数——否则这个开关就不可发现、"off" 也就无从打开 |
|
|
251
251
|
| `'encourage'` | **鼓励但不强制**:验证时先判断该对象的**实现难度**,能在可接受工作量内形式化就优先做;一旦 Lean 通过,审查重心转为**忠实性**。平时工作也鼓励把常用/可能复用的对象、假设、新定义随手形式化归档。**不设门禁** |
|
|
252
252
|
| `'require'` | **强制**:真/假结论必须满足「**Lean 已通过**」或「**显式记录了阻塞原因**」,否则本次裁定**不生效**——记为未定论(原因 `formal-required`)、写入「形式化待办」、群聊公告,对象留库待形式化后重新提议 |
|
|
253
253
|
|
|
@@ -265,14 +265,22 @@ Lean 通过只保证"这段代码过了内核",**不保证它说的就是命
|
|
|
265
265
|
用来求真的机制反而**伪造出一个错误的否定结论**。
|
|
266
266
|
- 正确做法:给一个严格介于 0 与 1 之间的值(记为弃权)+ 用回执
|
|
267
267
|
`formal:{decision:'defect', note:'<具体偏差>'}` 记录偏差。框架随即**撤回这条证明的「已通过」状态**
|
|
268
|
-
(降级为 `attempted
|
|
269
|
-
|
|
268
|
+
(降级为 `attempted`;`Verified/Lean/<id>.lean` **删除**,宿主删不掉时改写为"已撤回"说明,
|
|
269
|
+
绝不把一个已撤回的证明留在大家找证明的位置;写入「形式化待办」),`require` 档下
|
|
270
|
+
**本次裁定不定论**(`encourage` 档没有门禁,不得声称框架会强制搁置——那里靠表决者弃权阻止定论);
|
|
271
|
+
修正形式化并重新跑通后再投票。
|
|
270
272
|
- 只有表决者**独立于这份 Lean 代码**也能确定命题为假(并能给出独立理由)时才投 0。
|
|
271
273
|
|
|
274
|
+
> **回执通道**(不调用 Lean 工具的成员也能留下判断,`require` 档下必须留):
|
|
275
|
+
> `"formal": {"target":"<对象id>", "decision":"used|blocked|defect", "file":"Formal/<对象id>.lean", "note":"难度判断/阻塞原因/具体偏差"}`。
|
|
276
|
+
> `decision='blocked'`/`'defect'` 时 **`note` 必填**(缺则整条拒绝);`used` 只把对象记为 `attempted`;
|
|
277
|
+
> `off` 档下这个通道**失效**(否则 `off` 就不是真正的无操作了)。
|
|
278
|
+
|
|
272
279
|
> 注入提示词的另外三条硬要求(契约 §6):工具名一律**全称**(`<prefix>lean_archive` 不是
|
|
273
280
|
> `lean_archive`——缩写不是注册名,代理照抄会调用一个不存在的工具);归档可复用定义/引理**前先跑通**,
|
|
274
|
-
> 跑不通不许进库;**工具链缺失**(`LEAN_NOT_FOUND
|
|
275
|
-
> "宿主无 Lean 工具链"
|
|
281
|
+
> 跑不通不许进库;**工具链缺失**(`LEAN_NOT_FOUND` 解析不到可执行文件 / `NO_SUBPROCESS` 宿主没有
|
|
282
|
+
> subprocess 服务)时把代码写下来归档并在 `note` 写明"宿主无 Lean 工具链"——这算显式阻塞原因,
|
|
283
|
+
> 门禁据此放行,不会因为装不了 Lean 而卡死。
|
|
276
284
|
|
|
277
285
|
### 归档:形式化代码放哪里
|
|
278
286
|
|
|
@@ -808,7 +816,9 @@ v5 的完整架构(含成员生命周期、一轮时序、共识状态机、
|
|
|
808
816
|
- **Lean 形式化验证(四架构共用契约)**:[`docs/formal-verification.md`](docs/formal-verification.md)
|
|
809
817
|
- **测试耗时基线与并行跑法**:[`docs/test-timing.md`](docs/test-timing.md)(`node run-tests.mjs` 并行跑全部套件 ≈1.9 min;探针脚本 ≈2.6 min;每个 runner 都会打印耗时/加速比供下次选策略)
|
|
810
818
|
- **静态提示词面一致性(persona ↔ 工具注册表 ↔ 斜杠命令 hint/usage)**:[`audit-persona-surface.test.mjs`](audit-persona-surface.test.mjs)(197 条断言,并生成 [`prompt-corpus-persona/persona-corpus.md`](prompt-corpus-persona/persona-corpus.md) 供人工复核)+ [`audit-persona-sensitivity.mjs`](audit-persona-sensitivity.mjs)(11 条灵敏度探针)——守"注册的工具必须在 persona 里出现 / persona 里的名字必须真的注册 / `prefix` 与 `text` 两块逐行一致 / hint、usage、实际分支三处必须一致"
|
|
811
|
-
- **全面检查必查清单**:[`AUDIT-CHECKLIST.md`](AUDIT-CHECKLIST.md)
|
|
819
|
+
- **全面检查必查清单**:[`AUDIT-CHECKLIST.md`](AUDIT-CHECKLIST.md)(本仓库的强制审计流程;§1.9 专门查"工具参数 schema 收不收得下")
|
|
820
|
+
- **提示词/交互不变式(四套一起,可一键复核)**:[`audit-prompt-invariants.mjs`](audit-prompt-invariants.mjs)(145 条断言)——把"历史上真实发生过的提示词/工具面缺陷类别"逐条编码成静态不变式(缩写工具名、把忠实性缺陷投成 0、`defect` 只写在提示词里没实现、回执契约缺 `defect`、无 note 放行、字段名错、`off` 档回执仍能写状态、语料不确定、探针缺失、**工具的封闭 schema 收不下它自己文档里的参数**、**schema 声明了参数层却静默丢弃的键**)。加 `--self-probe` 会在内存里注入这些缺陷形状,要求对应不变式**变红**、未变异的对照跑**仍为绿**(5/5)
|
|
821
|
+
- **规格 ↔ 代码可追溯(四套一起)**:[`audit-spec-traceability.mjs`](audit-spec-traceability.mjs)(91 条断言)——`实现方案.md`/README 里承诺的工具必须真的注册;四个 Lean 参数必须同时被文档与代码接受
|
|
812
822
|
|
|
813
823
|
---
|
|
814
824
|
|
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
# dsh-vibe-math 2.3.2 — 四套深度审计:三处高危门禁缺陷 + 撤回语义统一 + 语料确定性
|
|
2
|
+
|
|
3
|
+
> 上一版:2.3.1。本版是**审计驱动**的修复版:对 v2/v3/v4/v5 各做了一轮逐架构深度审计
|
|
4
|
+
> (插件 + 套件 + 实现方案 + persona + 语料),并做了四个架构之间的**横向对照**。
|
|
5
|
+
> 无破坏性变更,默认仍为 `formalVerify: 'off'`。
|
|
6
|
+
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
## 0. 三处高危缺陷(都会让"严格验证"失效或不可用)
|
|
10
|
+
|
|
11
|
+
| # | 架构 | 缺陷 | 后果 |
|
|
12
|
+
|---|---|---|---|
|
|
13
|
+
| 1 | **v3** | 四个 Lean 参数**根本没写进 `vibe_math_set_params` 的参数 schema**(该 schema 是 `additionalProperties:false`) | 遵守 schema 的 provider **拒绝这个调用** → 用户**永远无法开启**这个功能;而套件全绿,因为它直接调 handler、**绕过 schema** |
|
|
14
|
+
| 2 | **v2** | `require` 门禁**只读自己那一侧的 id**(`formalOf(rId)`),而代理用**对象 id** 归档、别名同步只更新**已存在**的键 | "归档了 passed、验证侧还没有记录"时门禁**永远搁置**;搁置本身又写下 `rId='none'`,于是**每轮重开一次辩论、对象永远无法定论**、其它对象被饿死 |
|
|
15
|
+
| 3 | **v4** | `formalSetRun` 硬编码 `status:'attempted'`,**把已验证对象的 `passed` 抹掉**(与自己的注释、规格、v2/v5 都矛盾) | 一次随手 `lean_run` 就让对象丢掉"已形式化":投票提示词**丢掉忠实性分支**,`require` 档对**已有绿色归档证明**的对象重新关门 |
|
|
16
|
+
|
|
17
|
+
另有一处**门禁旁路**(v2):`settleVerdict` 的「判断命题」转移在 v=0 时直接写
|
|
18
|
+
`布尔估计=0`/`已验证`/`优先级 never` 并压入 `正确概率:1` 条目,**完全不看门禁**——一个未形式化的
|
|
19
|
+
命题被侧面判为**假**且永久退出调度。已改为先过门禁。
|
|
20
|
+
|
|
21
|
+
---
|
|
22
|
+
|
|
23
|
+
## 1. 撤回语义统一:**删除 → 复核 → 覆盖撤回说明**
|
|
24
|
+
|
|
25
|
+
2.3.1 只在 v5 做对了。本轮把同一语义推广到四套:撤回归档证明时
|
|
26
|
+
|
|
27
|
+
1. 先删(`subprocess` 可用时);
|
|
28
|
+
2. **用 fs 复核文件真的没了**;
|
|
29
|
+
3. 仍在(宿主没有 `subprocess`、shell 静默失败、权限问题)→ **就地覆盖为撤回说明**
|
|
30
|
+
(`-- 已撤回(<时间>):该形式化被认定与命题原文不一致。` + 指向保留的工作文件);
|
|
31
|
+
4. 公告**如实说明**发生了哪一种(删除 / 覆盖 / ⚠ 两者都失败,请不要把它当作该对象的证明)。
|
|
32
|
+
|
|
33
|
+
此外修掉了两处静默漏洞:v2 只从两个 id 收集 `proof`(别名归档的证明留在盘上);v2/v3/v4 用
|
|
34
|
+
`removeFile` 尽力删除且吞掉结果。
|
|
35
|
+
|
|
36
|
+
**同一类问题还有一处**:`lean_archive kind='proof'` 在**这次跑红**时曾保留 `prev.proof`
|
|
37
|
+
(而工作文件已被新代码覆盖)→ `Formal/Index.md` 会同时显示"attempted/fail"与一条**不再成立的**
|
|
38
|
+
`Verified/Lean/…`,忠实性提示词还会打印这个路径。四套统一为"`proof` 只属于 `passed`",并在跑红时
|
|
39
|
+
撤回旧的归档证明(v4 另外把"随手 `lean_run` 不许降级 passed"补回)。
|
|
40
|
+
|
|
41
|
+
---
|
|
42
|
+
|
|
43
|
+
## 2. 提示词/交互修复(逐条都有断言与探针)
|
|
44
|
+
|
|
45
|
+
| 修复 | 说明 |
|
|
46
|
+
|---|---|
|
|
47
|
+
| **按档位承诺**(四套) | 忠实性分支曾**无条件**宣称"本次裁定**不定论**",而只有 `require` 有门禁。现在 require 保留该承诺,encourage 明确写"**本档没有门禁**:请务必给弃权值,以保证本轮无法得出一致结论";defect 公告、TODO/Index 措辞同样按档位分叉 |
|
|
48
|
+
| **无工具链出路点名两个错误码**(四套) | 只写 `LEAN_NOT_FOUND` 时,遇到 `NO_SUBPROCESS`(宿主没有 subprocess 服务)的代理会当成未知失败而重试;现在两个都点出 |
|
|
49
|
+
| **失败提示要可执行**(v3) | `LEAN_NOT_FOUND`/`NO_SUBPROCESS`/`LEAN_SPAWN_FAILED` 没有编译器输出,却提示"按上面的编译器输出修复" → 改为按失败码给不同的出路 |
|
|
50
|
+
| **活动日志里的工具名**(v4) | 代理可读的日志里写着缩写 `lean_run` → 改为注册名 `vibe_v4_lean_run`;注入文本扫描现在也覆盖 `State/session.json` 的 `activityLog` |
|
|
51
|
+
| **路径指向真实位置**(v2) | 工作轮把可复用引理指向项目内的 `Formal/Proved/`——那是**不存在**的路径(全局库在项目树之外)→ 改为 `<VibeMath 根>/Formal/Proved/` |
|
|
52
|
+
| **红灯不许声称可复用**(v2) | `kind='def'/'lemma'` 跑红时工具返回值仍写"已并入全局可复用库,可直接 import 复用" |
|
|
53
|
+
| **`vibe_math_setup` 重复参数**(v3) | `plannerPersona` 出现两行 |
|
|
54
|
+
| **规格里的幽灵工具**(v4,由我的新审计发现) | `实现方案.md` 把 `vibe_v4_propose_verify(targetId)` 写成工具,而 v4 **没有**这个工具(真机制是回执字段 `propose_verify`) |
|
|
55
|
+
|
|
56
|
+
---
|
|
57
|
+
|
|
58
|
+
## 3. 语料确定性(契约 §10 要求"逐字节可 diff")
|
|
59
|
+
|
|
60
|
+
- **v5**:语料每跑一次都变。根因有三层:心跳/会议唤醒依赖**真实时钟**与异步顺序;捕捉心跳时
|
|
61
|
+
"最闲成员"随时间抖动;写入端**只按 kind 排序**,同 kind 内仍随 drain 顺序变化。
|
|
62
|
+
修法:套件加**虚拟时钟**(`ctx.timeout` 接虚拟队列、`sleep(n)` 推进虚拟时间)+心跳在
|
|
63
|
+
**单成员研究所**内捕捉+写入端**全序排序**(kind → owner → prompt)。
|
|
64
|
+
结果:**连跑 6 次哈希全同**,且套件 **7–9 s → 1.7 s**。
|
|
65
|
+
- **v3**:20 条 `planner:*` 条目带随机 plan id 与 epoch 时间戳 → scrub 归一化 + 断言。
|
|
66
|
+
- **v2/v4**:本已稳定;v4 的语料在套件运行中重生成并验证两次哈希一致。
|
|
67
|
+
- 五份语料(四个预设 + persona)现在都通过我的确定性检查(无绝对路径、无时间戳、可重复)。
|
|
68
|
+
|
|
69
|
+
---
|
|
70
|
+
|
|
71
|
+
## 4. 新增的常驻守卫(随包发布,可一键复核)
|
|
72
|
+
|
|
73
|
+
| 脚本 | 作用 |
|
|
74
|
+
|---|---|
|
|
75
|
+
| `audit-prompt-invariants.mjs` | 把历次**真实发生过的提示词/工具面缺陷类别**编码成四套 × 31 条静态不变式(缩写工具名 / "偏离→0" / `defect` 规则缺失或未实现 / 回执契约缺 `defect` / 无 note 放行 / 字段名错 / `off` 档回执未被门禁 / 语料不确定或缺档位 / 探针缺失 / 按档位承诺 / **封闭的 schema 收不下自己文档里的参数** / **schema 声明了、参数层却静默丢弃的键**)。**当前 145/0**,并带 `--self-probe`:在内存里注入这些缺陷形状,要求对应不变式**变红**、未变异的对照跑**仍为绿**(5/5) |
|
|
76
|
+
| `audit-spec-traceability.mjs` | 规格/README 承诺的工具必须真的注册(**能识别"文档里说它不存在"的否定语境**);四个 Lean 参数必须同时被文档与代码接受;契约 §7 的 `terminate()`;契约 §8 的**门禁收口点无旁路**(调用图检查)。**当前 91/0** |
|
|
77
|
+
| `run-tests.mjs` | 并行跑全部套件,打印每项耗时/加速比/最慢几项(本轮又修了 `--only x` 空格形式被静默忽略、`--json` 混入人类输出两个 bug) |
|
|
78
|
+
| `docs/test-timing.md` | 耗时基线 + 并行安全规则 + 虚拟时钟的适用条件(若套件用 `Date.now()` 做超时判据又用 `setInterval` 轮询,冻结时钟会让判据永不超时,必须连轮询定时器一起虚拟化) |
|
|
79
|
+
|
|
80
|
+
### 4.1 新增「工具参数 schema」守卫:文档写了 ≠ 工具收得下
|
|
81
|
+
|
|
82
|
+
本轮最贵的一处缺陷(v3 开不了档)暴露出一整类**既有测试全都盲**的漏洞:四个预设的工具 schema 都由
|
|
83
|
+
`objParams` 以 `additionalProperties:false` **关闭**,因此 schema 没列出的键会被任何遵守 schema 的
|
|
84
|
+
provider **直接拒绝**——可提示词/规格/状态行可以全都在说这个参数,套件也可以全绿(套件直接调 handler、
|
|
85
|
+
绕过 schema)。现在这层有了三重守卫:
|
|
86
|
+
|
|
87
|
+
1. 四套各自的 `formal-verify-vN.test.mjs` 直接检查**真实注册的** schema 对象:schema 必须仍是封闭的、
|
|
88
|
+
必须声明 `formalVerify`/`leanCommand`/`leanArgs`/`leanTimeoutMs`、`formalVerify` 的 enum 必须恰好是
|
|
89
|
+
三档(**已用探针证明**:把 v3 真实注册那一份里的 `leanArgs` 去掉,套件立刻变红);
|
|
90
|
+
2. `audit-prompt-invariants.mjs` 的 I13:**每一处** set 工具定义(v2/v3 有"会话 handler 表"与
|
|
91
|
+
"真实注册"两份)都必须声明这四个参数,且每一份 `objParams` 都必须关闭 schema;
|
|
92
|
+
3. 同脚本的 I14:schema **声明的每个键**都必须被参数层真正接收(v2/v3 的闸门是 `DEFAULT_PARAMS` 键集、
|
|
93
|
+
v4 是 `k in params`、v5 是 `normalizeParams` 的类型列表)——声明而不接收 = 调用返回 `{ok:true}`
|
|
94
|
+
而什么都不发生,是最容易被读成"设置成功"的静默失效。
|
|
95
|
+
|
|
96
|
+
`AUDIT-CHECKLIST.md` 新增 **§1.8「四套同构:任何语义修正必须四套同步」**——本轮三处高危里有两处正是
|
|
97
|
+
"改了一套、另三套没改"或"四套共用同一写法而没人横向对照"造成的。
|
|
98
|
+
|
|
99
|
+
---
|
|
100
|
+
|
|
101
|
+
## 5. 测试与探针(实测)
|
|
102
|
+
|
|
103
|
+
| 套件 | 2.3.1 | 2.3.2 |
|
|
104
|
+
|---|---|---|
|
|
105
|
+
| `formal-verify-v2.test.mjs` | 261 | **319** |
|
|
106
|
+
| `formal-verify-v3.test.mjs` | 247 | **283** |
|
|
107
|
+
| `formal-verify-v4.test.mjs` | 226 | **269** |
|
|
108
|
+
| `formal-verify-v5.test.mjs` | 120 | **145** |
|
|
109
|
+
| `prompt-v5-integrity.test.mjs` | 588 | **506**(语料去重:心跳只记 1 条)+ 虚拟时钟 |
|
|
110
|
+
| `e2e-v4-fixes.test.mjs` | 120 | 120(**修掉并行下的抖动**:T21 的会议看门狗 80 ms 在 CPU 争用下提前放弃会议) |
|
|
111
|
+
|
|
112
|
+
- 全量回归:**连续 3 次并行跑,23/23 全绿**(wall ≈111 s,最新一次实测 wall 111.5 s / sum 221.5 s / x1.99,
|
|
113
|
+
关键路径 `e2e-v4-fixes` 98.1 s);
|
|
114
|
+
- `audit-formal-sensitivity.mjs`:**49 条探针全部按预期变红,0 问题**;
|
|
115
|
+
- `audit-prompt-invariants.mjs`:**145/0**,`--self-probe` **5/5**;`audit-spec-traceability.mjs` **91/0**;
|
|
116
|
+
- `audit-persona-sensitivity.mjs`:11/11 变红;`audit-persona-surface.test.mjs` 197/0;
|
|
117
|
+
- `audit-v5-integrity.mjs` clean;四套 `audit-registration.mjs` 无重复/无缺失;
|
|
118
|
+
- 新增两条 **schema 级探针**:把 v3 真实注册的 schema 里 `leanArgs` 去掉 → v3 套件变红(已实测);
|
|
119
|
+
在 v4/v5 里造一个"声明但不接收"的参数 → `audit-prompt-invariants.mjs` 变红(已实测)。
|
|
120
|
+
|
|
121
|
+
---
|
|
122
|
+
|
|
123
|
+
## 6. 仍然存疑、需要人决定的政策问题(不是 bug,故未擅自改)
|
|
124
|
+
|
|
125
|
+
1. **跑红的 `kind='proof'` 是否应撤销旧证明**:本轮按"`proof` 只属于 `passed`"(契约 §4)统一四套;
|
|
126
|
+
若你认为"随手一次失败不该抹掉已证结论",应改**契约**而不是改代码。
|
|
127
|
+
2. **`off` 档"主动调用工具"算不算无操作**:契约 §2 明确工具仍可用,但那会写 `Formal/Index.md`/状态/公告;
|
|
128
|
+
四个审计都把它记为 policy call,现已在规格里澄清"off 约束的是**框架自身**,主动调用是显式行为"。
|
|
129
|
+
3. **`used` 回执的语义**:契约状态表字面写"→ attempted",而四套实现都**保留** `passed`/`blocked`
|
|
130
|
+
(否则每条"我用了它"的回执都会把 passed 打回 attempted 并重新关门)。建议改契约字面。
|
|
131
|
+
4. **v2 的 id 解析歧义(真实可达)**:`formalObjectIdOf` 把"对象 id 本身以 `-sN/-pfN/-rfN` 结尾"的
|
|
132
|
+
rId 解析错(`r-p-s1 → p`):这类命题的提示词/卡片会引用**另一个对象**的证明、门禁会被那个对象的
|
|
133
|
+
`passed` 放行。正确修法是**在记录里落权威 `objectId`**,但这要先把契约定下来。
|
|
134
|
+
5. **只剩"被门禁搁置"的对象时**:调度器会空转(不会卡死、不会误判终止)——契约没写这种局面该终止还是空转。
|
|
135
|
+
|
|
136
|
+
---
|
|
137
|
+
|
|
138
|
+
## 7. 升级
|
|
139
|
+
|
|
140
|
+
```
|
|
141
|
+
npm i dsh-vibe-math@latest
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
无迁移:新参数默认 `off`,四套既有行为与 `off` 一致。升级后重启 DSH;未被手动改过的 preset 文件
|
|
145
|
+
会自动更新。
|
|
@@ -231,14 +231,23 @@ const CONCURRENCY = (() => {
|
|
|
231
231
|
return Math.max(1, Number.isFinite(v) ? v : 1)
|
|
232
232
|
})()
|
|
233
233
|
const ONLY = (() => {
|
|
234
|
-
const
|
|
235
|
-
|
|
234
|
+
const eq = process.argv.find((a) => a.startsWith('--only='))
|
|
235
|
+
if (eq) return eq.split('=')[1]
|
|
236
|
+
// also accept the space form (`--only v5`), which the usage line advertises
|
|
237
|
+
const i = process.argv.indexOf('--only')
|
|
238
|
+
return i >= 0 && process.argv[i + 1] && !process.argv[i + 1].startsWith('--') ? process.argv[i + 1] : ''
|
|
236
239
|
})()
|
|
237
240
|
const selected = probes.filter((p) => !ONLY || p.name.includes(ONLY) || p.preset === ONLY)
|
|
238
241
|
if (process.argv.includes('--list')) {
|
|
239
242
|
for (const p of selected) console.log(p.preset + ' ' + p.name)
|
|
240
243
|
process.exit(0)
|
|
241
244
|
}
|
|
245
|
+
// A filter that matches nothing must FAIL, not report success: with zero probes the summary below
|
|
246
|
+
// would say "0 problems / ALL PROBES RED" — a textbook false green (AUDIT-CHECKLIST §2.5).
|
|
247
|
+
if (selected.length === 0) {
|
|
248
|
+
console.error('no probes matched' + (ONLY ? ' --only=' + ONLY : '') + ' — refusing to report success on an empty run')
|
|
249
|
+
process.exit(2)
|
|
250
|
+
}
|
|
242
251
|
|
|
243
252
|
function runAsync(cmd, args, opts) {
|
|
244
253
|
return new Promise((resolve) => {
|