dsh-build-driver
DSH 插件:把 CMake + Ninja + MSVC 的配置 / 构建 / 后台任务 / 停止做成 4 个工具,供 agent 直接调用。 覆盖增量构建、MSVC 环境自动注入、编译诊断解析、长构建转后台。
插件 id:build-driver;包名:dsh-build-driver。
工具
| 工具 | 作用 |
|---|---|
build_configure |
配置工程(cmake -S <src> -B <build> -G Ninja -DCMAKE_C_COMPILER=cl ...),自动注入 MSVC 环境,并给 C/CXX 追加 /diagnostics:caret(让诊断带列号) |
build_run |
增量构建(cmake --build),前台等 foregroundWaitMs,未完成自动转后台并返回 backgroundJobId |
build_status |
查询后台构建(省略 jobId = 当前/最近一次),可短等 waitMs(上限 30s) |
build_stop |
停止本插件启动的构建(只终止自有进程树,不碰系统里的其他进程) |
ok 语义:完成且 exit 0 → true;完成非 0 → false;仍在后台运行 → null(成败看 status)。
status 取值:completed / failed / running / stopped / timed_out。
buildDir 解析规则:显式传 buildDir 时相对会话 cwd(旧行为不变);省略时与 build_configure 对齐——传了 sourceDir 就用 <sourceDir>/.build,否则用 <cwd>/.build。
诊断对象:{ file, line, col, severity, code, message }。支持 MSVC 编译/链接、clang/clang-cl、CMake Error/Warning 四类;
build_configure 默认注入 /diagnostics:caret,因此 MSVC 编译错误带列号(例如 main.cpp(1,20): error C2065 → col: 20);
errors 最多返回 maxDiagnostics 条,errorCount / warningCount 始终统计全部。
编码(中文诊断)
本机 cl.exe 按控制台代码页(GBK/936)输出中文;而 subprocess 的 collect 模式按 UTF-8 解码会得到乱码。
因此插件优先用 stdio: 'pipe' 拿原始字节,构建结束时整体用 UTF-8 严格解码、失败回退 gb18030,再写日志。
宿主不支持 pipe 时自动退回 collect 模式(构建本身不受影响,中文诊断可能乱码)。
配置
cordis.patch.yml 里的 config(全部可选):
| 键 | 默认 | 说明 |
|---|---|---|
toolchainPath |
自动发现 | toolchain.json 路径;顺序:包同级 → 包内 → 会话 cwd → cwd/mlir-lang |
cmakePath |
toolchain.json 的 cmake.path |
显式 cmake 路径优先 |
ninjaPath |
toolchain.json 的 ninja.path |
显式 ninja 路径优先 |
vcvarsPath |
toolchain.json 的 msvc.vcvars |
vcvars64.bat 路径 |
generator |
Ninja |
v1 只支持 Ninja |
foregroundWaitMs |
120000 |
前台最多等多久再转后台 |
defaultTimeoutMs |
900000 |
单次构建总预算 |
maxDiagnostics |
50 |
errors 最多返回条数(计数仍统计全部) |
maxOutputBytes |
1048576 |
内存里保留的输出上限(完整日志始终落盘) |
logKeep |
100 |
<buildDir>/.build-driver/ 下保留的日志份数 |
构建日志:<buildDir>/.build-driver/build-<时间>-<序号>.log(UTF-8)。
依赖
- Node.js
^22.19.0 || >=24.0.0 - DSH
>=0.2.1-rc.5 <0.3.0-0 - CMake ≥ 3.20、Ninja、MSVC(Visual Studio / Build Tools)
- 可选:
toolchain.json(P-01 同一份),没有时也可用显式cmakePath/ninjaPath/vcvarsPath
MSVC 环境解析顺序:vcvars64.bat dump → 失败时按目录布局兜底(MSVC Tools + Windows SDK,读 KitsRoot10 注册表)。
本机 vcvars64.bat 是精简 VS 的 shim(vcvarsall.bat 会失败),实际走的是目录布局兜底。
开发与测试
npm test
# 等价于 node --test --test-isolation=none test/*.test.mjs
必须带 --test-isolation=none:受限沙箱里 Node 的测试 runner 默认会为每个文件 fork 子进程,会得到 spawn EPERM。
改完 lib/*.js 后必须重载插件才会生效:profile 的 cordis.patch.yml 只承载配置,不会重新 import 模块代码。
在 DSH 里执行:
plugin_manager set_plugin target "include:build-driver" enabled:false
plugin_manager set_plugin target "include:build-driver" enabled:true
验收记录(需求 §5,本机 2026-11-04)
| # | 场景 | 结果 |
|---|---|---|
| ① | 最小工程 configure | ok:true,CMakeCache.txt 存在,generator Ninja,compiler cl.exe(14.51.36231),cmake 4.4.4 |
| ② | 构建 hello | ok:true、exitCode 0、错误 0;hello.exe 输出 hello from build-driver、退出码 0 |
| ③ | int main(){ return x; } |
ok:false,1 条 error C2065,file 指向 broken\main.cpp,col: 20(/diagnostics:caret),消息 “x”: 未声明的标识符(GBK 解码正确) |
| ④ | 修好后再构建 | ok:true、exitCode 0;broken.exe 退出码 0 |
| ⑤ | 立即再跑 | 主判据为 upToDate:true 且输出含 ninja: no work to do;不再用「耗时 < 首次 20%」这类噪声大的时间门槛(固定开销约 200ms) |
| ⑥ | 长构建(cmake -E sleep 240 / 125) |
120s 后返回 status:"running" + backgroundJobId;240s 工程 build_stop 返回 stopped:true、status:"stopped";125s 工程 build_status(waitMs:30000) 拿到完成态 completed、exitCode 0、125.3s(含 startedAt/finishedAt) |
| ⑦ | 错 vcvarsPath / cmakePath |
ok:false + 中文 hint(vcvars 脚本不存在… / cmake 路径不存在…),不抛 ENOENT、宿主不崩 |
| ⑧ | 构建失败但无诊断(cmake -E false) |
ok:false、errorCount 0、返回 logPath,hint 为「build 失败但未解析到诊断」 |
| ⑨ | build_run 省略 buildDir(只给 sourceDir) |
默认解析到 <sourceDir>/.build(与 build_configure 一致),构建成功;不给 sourceDir 时回退 <cwd>/.build |
手工验收夹具在本地 .acceptance/(hello、broken、caret、slow、slowdone、nodiag、bad-toolchain.json,含本机路径,不入库)。
单测:39 通过 / 1 跳过(真实 subprocess 冒烟默认 skip,BUILD_DRIVER_SPAWN_SMOKE=1 才跑)。
安装
从 GitHub clone 后装进 desktop profile:
git clone https://github.com/Rcyc-1025/dsh-build-driver
& 'D:\exe\DSH\resources\runtime\cli\bin\dsh.cmd' plugin --profile desktop add D:\path\to\dsh-build-driver
也可在 DSH 里用 plugin_manager install_bundle,target 传本目录绝对路径。
No comments yet. Be the first to write one.