Repository navigation
Releases: yan-mc/dsh-normify
Release list
v0.5.4 · 修掉第二轮 A/B 实测暴露的 4 个工具缺陷
Normify v0.5.4 · 修掉第二轮 A/B 实测暴露的 4 个工具缺陷
第二轮对照实验换了题目:表格公式引擎 + CLI(同一份规范、隐藏黑盒 88 项,另加差分模糊测试)。
两组最终 B 88/88、A 87/88(唯一差异是一条 §5.2 语义,属被测实现问题而非插件)。
这一版修的是那一轮暴露的工具侧四个坑——都是"AI 真实踩到、并且为此绕路"的:
🎯 四处修复
① mode:"patch" 的静默 no-op(最危险的"假成功")
normify_module_batch { mode:"patch", items:[{ patch:{ id:"x", tags:[...] } }] }(少一层包装)会走
applyPatch(module, {}),返回 ok:true, count:1 而一个字段都没改。
- 现在内层
patch缺失 /null/ 非对象 / 空对象 →args/invalid-patch,evidence 带收到的键与正确形状。 - 单模块
normify_module_patch传空补丁(含"只给expect_updated_at")→args/empty-patch。
② normify_module_refresh 不再强依赖 git
repoRoot 不是 git 仓库时以前直接失败(实测中 AI 只能 git init 才能把 planned 模块激活)。
现在降级:指纹重算、activate 生效、revision 保持原值,并给出 refresh/git-unavailable 警告 + 修法。
③ change_open 的 acceptance 报错具体化
传 {zh,en} 时现在明确写出"第 N 条不是非空字符串"并说明"验收标准只接受纯字符串,双语请写 title/intent"。
④ normify_help 支持 tool:<工具名> 参数树
topic:"tools" 每个工具带 必填 / 可选 摘要;新增 topic:"tool:normify_module_batch" 打印完整参数树
(类型 / 描述 / 必填,注册表实时生成、与运行时校验同源)。实测里 AI 为确认 patch 嵌套形状去读了插件源码,
这条主题就是为了消灭这种绕路。
✅ 验证
| 项目 | 结果 |
|---|---|
tests/regression-0.5.4.mjs(新增) |
21 项断言全绿 |
tests/engine-e2e.mjs / companion-e2e.mjs / regression-0.5.2.mjs / regression-0.5.3.mjs |
全部 PASS |
ci-contract-check.cjs(31 个工具契约) |
ok |
tsc -p tsconfig.json(strict / declaration) |
0 error |
📦 安装
Invoke-WebRequest -Uri "https://github.com/yan-mc/dsh-normify/releases/download/v0.5.4/dsh-external-dsh-normify-0.5.4.tgz" -OutFile "dsh-external-dsh-normify-0.5.4.tgz"curl -L -o dsh-external-dsh-normify-0.5.4.tgz \
https://github.com/yan-mc/dsh-normify/releases/download/v0.5.4/dsh-external-dsh-normify-0.5.4.tgz📚 实验记录
- 报告:
test-results/2026-09-13-ab2-formula-engine/TEST-REPORT.md - 差分模糊结论:
check载荷 60/60 一致、eval无环子集 36/36 一致、有环子集差异只在order - 三处规范缺口(
IF短路语义、区域传标量函数、文件级错误载荷形状)已补进归档SPEC.md附录
📚 文档
v0.5.3 · 修掉伴随编程 A/B 实测暴露的 4 个摩擦点
Normify v0.5.3 · 把「伴随编程实测」暴露的 4 个摩擦点修掉
这一版没有新功能,只有四件事 —— 全部来自一次真实的 A/B 对照实验:同一份规范、同一类模型,两个 AI 写同一个
交互式白板后端,一个带 dsh-normify 走伴随流程,一个纯手写;用一套隐藏黑盒验收(42 项)打分,两组最终都是 42/42。
插件组额外交付了 41 模块 / 110 API / 10 层的架构数据,也把下面 4 个粗糙处暴露了出来。
🎯 四处修复
① normify_help 现在按主题返回(此前完全忽略入参)
0.5.2 的 normify_help 无论传什么都返回同一份字段速查。实验里 AI 为了拿到 change_open / layout_upsert /
change_close 的准确参数名,只能去读插件的 lib/tools.js,多花约 4 分钟。
- 主题:
fields(默认)/deps(箭头与 API 直连)/renders(渲染数据)/flow(伴随开发主流程)/
tools(工具清单,由注册表实时生成)/policy(架构规则)/errors(常见诊断码与修法)/all - 传错主题不再静默忽略:返回
args/invalid-topic并列出可用主题。
② 项目初始化通道(新增第 31 个工具)
实验里"第一次开项目"没有入口:change_open 要求项目目录已存在(project/no-modules),
normify_brief({id}) 要求模块已存在,AI 只能用 module_batch {items: [], dry_run: true} 去"建目录"。
- 新增
normify_project_init:建normify-<slug>/+ 安装默认架构规则;可选root一步创建"计划态根模块";幂等。 normify_change_open现在也会自动建项目目录(写工具语义)。normify_brief遇到不存在的模块,返回"先 init / 先建树 / 或改用task参数"的可执行提示。
③ 批量诊断补上因果链
实验里一条 structure/label-too-long 连带出 3 条 dep/target-missing(L1 失败的模块会被移出批次工作集),
报错完全不点明因果,AI 只能读源码才确认根因,白跑一轮。
- 连带错误改报
dep/target-dropped/structure/parent-dropped,message 与evidence.root_cause_code
直接写明"某模块因哪条 L1 诊断被移出批次"; - 失败响应新增
root_causes: [{module, code, message}]+hint,一眼看清"修哪几个"。
④ 「API 直连」引导
实验数据:结构数据里声明了 110 条 API、54 条箭头,其中 0 条用 from_api / to_api 锚定到具体 API ——
等于白丢渲染器最精细的一层(箭头只能落在框边,钉不到 API 行)。
normify_validate现在会给出聚合 warningdep/unanchored:条数 + 前 3 条示例 + 修法。- 引导不等于放宽:锚到不存在的 API 键仍然是 error(
dep/from-api-invalid)。
✅ 验证
| 项目 | 结果 |
|---|---|
tests/regression-0.5.3.mjs(新增,锁定四点) |
21 项断言全绿 |
tests/engine-e2e.mjs / tests/companion-e2e.mjs / tests/regression-0.5.2.mjs |
全部 PASS |
ci-contract-check.cjs |
工具数契约 30 → 31,并断言 3 个关键工具存在 |
tsc -p tsconfig.json(strict / declaration) |
0 error |
📦 安装
Invoke-WebRequest -Uri "https://github.com/yan-mc/dsh-normify/releases/download/v0.5.3/dsh-external-dsh-normify-0.5.3.tgz" -OutFile "dsh-external-dsh-normify-0.5.3.tgz"curl -L -o dsh-external-dsh-normify-0.5.3.tgz \
https://github.com/yan-mc/dsh-normify/releases/download/v0.5.3/dsh-external-dsh-normify-0.5.3.tgz然后按 README「安装」 把包登记进 profile 的 dependencies + dsh.profile.bundles,重启 DSH。
📚 实验记录(本版修复的依据)
- 报告:
test-results/2026-09-12-ab-companion/TEST-REPORT.md(A/B 交付物、隐藏黑盒 42 项、两份过程日志、证据清单) - 关键数字:A 组 41 模块 / 110 API / 54 箭头 / 10 层 /
validate0 error;两组端到端耗时 ≈8.4 min vs ≈22 min
📚 文档
v0.5.2 · 修掉三处写坏数据的真实缺陷 + API 默认全展开
Normify v0.5.2 · 修掉三处会写坏数据的真实缺陷
把整个项目描述成一棵"人机共读"的分形模块树:AI 分析与创作,确定性引擎校验、编译与渲染。
这一版没有新功能,只把三处会让工具自己产出非法数据的真实缺陷修掉 —— 都是 0.4.1 时代就存在、
在伴随开发里会真实踩到的坑。
🎯 三处修复
① normify_module_upsert 的必填表不再丢失(工具契约)
parameters.required 此前是 undefined,frontmatter 的 9 个必填字段(uid / id / parent / name / description /
source / revision / updated_at / fingerprint)在模型侧与运行时校验里全部消失,空参调用也不会被拦截。
根因是嵌套 schema 被二次编译:moduleParams() 返回已编译的 JSON Schema,再被
params({ frontmatter: moduleParams() }) 编译一次时,内层的对象级 required: [...] 被整段丢掉。
- 修复:
moduleParams()改为返回作者态 schema(required: true内联),由外层params()统一编译;
toJsonSchema()同时改成幂等(保留并合并对象级required数组),任何嵌套复用都不再丢约束。 - 实测:
parameters.required = ["frontmatter"]、frontmatter.required9 项齐全、空参调用返回args/missing。
② normify_module_move 迁移渲染数据时重写内容(不再"搬个坏文件过去")
迁移时按字节复制 renders/*.json,id / order / groups.children / edge_hints 还停在旧 id 世界,
旧父级的 order 也仍指向已迁出的子模块 —— move 一完成,normify_validate 立刻报
layout/id-mismatch、layout/order-child、layout/group-child、layout/groups-empty、layout/hint-endpoint。
- 修复:迁移时用新 id 重写渲染数据(
id/order/groups.children/edge_hints,并按新子模块集合过滤);
旧父级去掉已迁出子模块的引用(空组/空字段整体删除,mode: groups无组时一并摘除);
新父级把新 id 补进order;dry_run新增detail.layout_rewrites列出原地重写清单。 - 渲染数据本身解析失败时按原样搬运 + 回报
layout/unparsed-carried警告(不再静默吞掉)。 - 实测:move 前 0 error → 修复前 move 后 8–9 error → 修复后 0 error。
③ 叶子晋升为容器时,API 不再留在容器上
writeModuleFile() 的自动晋升与 promoteModule() 的显式晋升都只把 x.md 改成 x/index.md,
不清理 frontmatter 里的 apis,于是晋升后项目必然卡在 api/non-leaf(容器不允许声明 API)。
- 修复:两条晋升路径都会摘掉容器上的
apis(无 API 时仍走原来的"改名即晋升",字节不变),
并回报structure/api-dropped-on-promote警告,附丢失的 API 键清单与建议(写回合适的叶子)。
upsert/promote/move/batch/patch/refresh都会把该警告带回给调用方。
✨ 行为变更:API 默认全展开
渲染数据字段 max_api_rows 的缺省值由 6 改为 0 = 全部展开 —— 叶子上的 API 一行都不折叠,
箭头可以精确锚定到每一条 API 行。需要收窄时显式写 1..48。既有数据集不写该字段即等于"全展开",无需改动。
✅ 验证
| 项目 | 结果 |
|---|---|
tests/regression-0.5.2.mjs(新增,锁定三处缺陷) |
34 项断言全绿 |
tests/engine-e2e.mjs |
PASS |
tests/companion-e2e.mjs |
PASS(原"记录 0.4.1 缺陷"的断言反转为"必须重写内容 + move 后 L2 = 0 error") |
tsc -p tsconfig.json(strict / declaration) |
0 error |
📦 安装
Invoke-WebRequest -Uri "https://github.com/yan-mc/dsh-normify/releases/download/v0.5.2/dsh-external-dsh-normify-0.5.2.tgz" -OutFile "dsh-external-dsh-normify-0.5.2.tgz"curl -L -o dsh-external-dsh-normify-0.5.2.tgz \
https://github.com/yan-mc/dsh-normify/releases/download/v0.5.2/dsh-external-dsh-normify-0.5.2.tgz然后按 README「安装」 把包登记进 profile 的 dependencies + dsh.profile.bundles,重启 DSH。
📚 文档
v0.5.1 · 渲染器防重叠 + 更精细的结构数据
Normify v0.5.1 — 发布说明(可直接粘贴到 GitHub Release)
复制下面
---之间的内容到 https://github.com/yan-mc/dsh-normify/releases/new?tag=v0.5.1
Normify v0.5.1 · 渲染器防重叠 + 更精细的结构数据
把整个项目描述成一棵"人机共读"的分形模块树:AI 分析与创作,确定性引擎校验、编译与渲染。
🎯 本次重点
渲染器不再"线压线" —— 28 层全量几何自检:共线重叠 12 处 → 0 处。
四处根因(都在 src/engine/template.ts):
- 首选路由只判"不穿别人的框",从不检查是否压到已画线 → 改为只接受
violations === 0的候选(不穿框 / 不压已画线 / 不横穿自身框 / 端口法向正确),
没有完全干净的路径时才退化为"违规最少"。 - API 锚定端口没有端口分离(同一 API 行常被多条边共用)→ 按到达顺序在行内 ±5.5px 扇形分离,
仍钉在该 API 行(行高 13px)上。 - API 端口落在上下边时被放进框内部 → 上下边退回按边均匀分离。
segClear整块跳过源/目标框,连线可横穿自己的框 → 新增"进入自身框内部"检查(内缩 2px),
并把首/末段"沿节点边滑行"计入违规。
另将节点/分组间距 GX/GY 170 → 220,给密集层更多自由通道。
✨ 同期能力(v0.5.0)
- 取消模块数量上限:删除硬编码的
MAX_DEPTH = 12,树可以一直下钻到"单一功能单元";
需要限层时用policy.yml的max-depth规则显式声明(maxDepth1..64,可 scope)。 - API 行数可配:渲染数据新增
max_api_rows(0 = 全部展开,1..48,缺省 6),叶子 API 不再被硬截断。 - SKILL:目标深度改为"不设上限",单批上限 40 → 200,新增"每叶 API 尽量 3–5 条"的粒度指引。
📐 用自身做的验证
| 指标 | 值 |
|---|---|
| 结构规模 | 129 模块 / 101 叶子 / 214 API / 257 箭头(125 条 API 直连)/ 28 层渲染数据 |
| 校验 | normify_validate 0 error / 0 warning(含仓库证据校验) |
| 几何自检 | 28 层:线压线 0 处;27/28 层"越界/贴边/穿框/贴组框/线压线"五项全 0 |
| 工程 | tsc --noEmit 0 error;engine e2e + companion e2e 全绿;bundle + 30 工具命名契约通过 |
| 伴随开发 | 先建图后编程 12/12 + 伴随编程改图 10/10 PASS |
📦 安装
cd dsh-normify && npm install && npm run build && npm pack
# 解包到 <profile>/node_modules/@dsh-external/dsh-normify/
# profile 的 package.json:dependencies + dsh.profile.bundles 各加一行
# 重启 DSH 桌面端(工具列表在会话启动时快照)兼容 DSH 0.1.5-rc.2 / DSHEAC AIO 6.9.x(profile web-desktop)/ Node ≥ 18。
📚 文档
📦 安装:从本 Release 直接下载
# Windows(PowerShell)
Invoke-WebRequest -Uri "https://github.com/yan-mc/dsh-normify/releases/download/v0.5.1/dsh-external-dsh-normify-0.5.1.tgz" -OutFile "dsh-external-dsh-normify-0.5.1.tgz"# macOS / Linux
curl -L -o dsh-external-dsh-normify-0.5.1.tgz \
https://github.com/yan-mc/dsh-normify/releases/download/v0.5.1/dsh-external-dsh-normify-0.5.1.tgz| 项 | 值 |
|---|---|
| 附件 | dsh-external-dsh-normify-0.5.1.tgz |
| 体积 | 188 668 B(83 个文件) |
| SHA-256 | 5ef29340a751db9f0b0ac752114f52d3cceeb7a9a0716d2c64ac116d2db0c7bb |
装完之后的 profile 登记方式(dependencies + dsh.profile.bundles)见 README「安装」。