Tags: AnranS/botmux
Tags
canary: workflow runtime v0.1.4-a cancel responsiveness 新功能 - 用户从 IM/Dashboard 取消 workflow run 后,daemon 立刻向所有 in-flight subagent worker 发 SIGINT,5 秒优雅 grace,超时 SIGKILL 兜底 - orchestrator 看到 cancelRequested 后短路,不再派发新工作,避免 late activitySucceeded 把 run 推到错误终态 - cancel 真等 worker exit 才落 activityCanceled,terminal 事件不再超前于 worker 实际停止 - cancel 期间 quiesce 和 hardDeadline 自动 disarm,cancel-wins 语义闭环 - WorkerSpawnResult 新增 kind:'cancelled',带 cancelOriginEventId 链接原始 cancel 事件 兼容性 - WorkerSpawnInput 新增可选 cancelSignal: AbortSignal(向后兼容) - WorkerSpawnResult 新增 kind:'cancelled' (现有 success/failure 不变) - 事件 schema 不变,replay 不变 测试 - 181/181 通过(workflow-spawn-cancel 5 + responsiveness 6 + finalize-e2e 1 + 现有全套) - 5 个 codex review 轮回收住 dedup race / B1 worker exit / M1 cancel-wins 需要 dogfood 验真实 Claude/Codex CLI 子进程对 SIGINT 的现场响应。
v2.31.0:群内授权 + CoCo 接入稳定性 新功能 - 群内授权:群主可直接在群里用 /grant、/revoke 给成员开通或收回机器人使用权限,配授权卡片二次确认。内置防重放、拒绝冷却节流,并支持按邮箱反查成员。 修复与改进 - CoCo 消息偶发卡在输入框、表现为「回复上一条」的问题:粘贴改用 bracketed-paste 标记,确保整段内容一次性提交。 - CoCo「没能确认提交」误报:CoCo 新版本写入历史记录的时机变化,导致提交确认逻辑偶发漏判而错误告警;现已兼容,消息其实已送达且会正常回复。 - 完整解析飞书卡片消息:消息、历史、引用场景都能正确还原卡片内容。 - 建群时可绑定 oncall 工作目录。 - tmux 通道更稳健:send-keys 失败不再拖垮 worker,并补充 CLI 退出诊断信息。 - 兼容 Claude Code 自定义 Chat 快捷键。
canary: workflow runtime v0.1.3 (approve/reject + i18n + catalog + 并发) 新功能 - Dashboard 直接 approve/reject humanGate,无需回飞书卡片;失败 run 加摘要 + 移动端 UI - Workflow 页面 zh/en i18n,topbar 语言切换 + localStorage 持久化 - Workflow Catalog: GET /api/workflows/definitions[/:id] 公开读 + cookie 受限 POST .../run; 详情页展示 def + params schema + JSON,Run 后跳详情;invalid_params 结构化 issues - runLoop 并发 dispatch:同 tick 内 ready 节点 Promise.allSettled 并行,maxConcurrency 封顶(默认 4),per-bot tick 内串行;completeNode/Run 串行收尾 - pre-attempt dispatch 抛错直接 no-progress,避免无 attemptId 时重试到 maxTicks 文档/示例 - 内置 parallel-fanout-demo workflow 兼容性 - WorkflowDefinitionSchema.defaults.maxConcurrency 新增可选字段(向后兼容) - 事件 schema 不变,replay 不变 已知限制(v0.1.4 单独切刀做) - cancel 在 in-flight 并行期间不主动打断 worker - 没有可插拔 cancelPolicy / 注入 prompt 软取消
canary: params 类型校验/默认值深化 — CLI 拉齐 IM 严格 + --param-json + skill 同步
亮点
- 共享 coerceWorkflowParams 模块 (src/workflows/params.ts): 单一来源,IM
/workflow run 和 CLI botmux workflow run 走同一条严格校验链。
- CLI 拉齐 IM 严格度: 之前 CLI 只 check required, type 全不校验,默认值不
materialize, 未知 param 静默通过。canary.6 起所有 param 入参一致行为:
未知 param reject、type 严格(string/number/boolean/object/array)、optional
默认值 materialize、错误聚合一次给全 issue。
- --param-json key=<json>: CLI 新入口,thread object/array(或想保留 JSON
类型的标量)直接传 JSON 字面值,例如 --param-json tags='["x","y"]' 或
--param-json config='{"mode":"safe"}'。--param 标量、--param-json
结构化、两个都接 --flag value 和 --flag=value 两种 syntax。
- workflow-create skill 文档同步: Schema 速查补全 params 五字段
(type/required/default/description/format),明确 CLI/IM 启动差异+
object/array 限制,补 5 条错误样例(未知参数/缺少必填参数/必须是 number/
必须是 boolean/object array 用 --param-json),LLM 不会再编错指令。
builtin-skills 锁断言 +8 条,防文档漂移。
测试
- 16 case 共享模块单测 (test/workflow-params.test.ts): 字符串 channel
七条 + RawParamInput 混 channel 七条 + 错误聚合 + 默认值 verbatim。
- 4 case CLI integration (test/workflow-cli.test.ts): 未知 param reject,
type=number 严格,--param-json object/array,坏 JSON 报错。
- builtin-skills 5 case + 8 锁断言: workflow-create skill 关键词全覆盖。
- IM 端 13 case 零回归。
升级影响
- npm i botmux@canary 即可装到 v2.31.0-canary.6。
- 老 CLI 用户的 \`--param key=value\` 流程不变;新增 \`--param-json\` 入口
完全 additive。
- 严格校验是 CLI 行为收紧: 之前 \`--param days=abc\` 当 type=number 能跑
现在 fail-fast 报 "参数 days 必须是 number"。IM 端这条一直是这么做的,
CLI 现在对齐。
- 共享模块抽出后 IM workflow-slash-command.ts re-export coerceWorkflowParams
保持原签名,IM 端调用方零侵入。
dogfood 重点
- 跑现有 weather-trip-plan 等 workflow,验证 --param key=value 行为不变
- 试 \`--param-json\` 传 object/array 参数
- 故意写错 param name / type 看错误提示是否清晰
- workflow-create skill 重新生成一个 workflow,看 LLM 是否按新文档教 --param-json
canary: step detail v2 收口 + promptRef + dashboard auth refactor + rou… …te smoke 亮点 - promptRef 三刀(4b80db8 schema + efc1e5a runtime spill + a44ac62 卡片 与 dashboard): ≥1 KiB 的 humanGate prompt 自动落 blob,事件内只携带 OutputRef-shaped promptRef + ≤800B 短 promptPreview。飞书审批卡片 始终用 preview + "完整内容见 Web 详情" 引导,绝不读 blob。dashboard Node I/O 新增 Wait prompt 块按 64 KiB ladder 读完整文本。互斥 invariant 在 parseEvent / safeParseEvent / EventLog.append 三路都 拦得住坏 draft;历史 2-3 KiB inline prompt 兼容性保留(schema 不加 max, 1024 阈值是 producer 策略不是 wire format 约束)。 - 86fc623 step detail v2 收口: renderAttemptDetail 一直只显 errorCode, 现在补上 errorMessage 一行 pre-wrap 渲染,operator 能直接看到 "humanGate.prompt too large 4950 bytes" 这种诊断;加 ops-projection 单测锁住 previewAttemptLog 是 tail 语义(70 KiB filler + 头/尾 sentinel,以后误改回 head-window 即挂)。 - 759f3e6 dashboard auth refactor: 抽 decideDashboardAuth 纯函数挂在 src/dashboard/auth.ts,把 canary.3 加的 public-read 决策(workflow GET / 静态 shell 免 cookie,其它 401)从 dashboard.ts 内联 24 行抽出来, 附 15 个矩阵单测覆盖 public 三条 / protected 七条 / ?t= cookie set 五条 + 边界。 - c36b64d HTTP route smoke (codex): 真 createServer + handleWorkflowApi e2e,覆盖 GET workflows runs/snapshot 无 cookie 200, POST cancel 无 cookie 401 且不 proxy, GET sessions 无 cookie 401, /__health 200, / 200, /assets/missing 404 (boundary 不挡), /?t=correct 302+Set-Cookie, /?t=wrong 在 public 路径 200 不 mint 错 cookie / 在 protected 路径 401, cookie 携带 correct token 访问 protected 200。 升级影响 - npm i botmux@canary 即可装到 v2.31.0-canary.5。 - 老 daemon 进程对 promptRef 字段走 strip mode silent degrade(读不到 promptRef → AttemptState.wait.prompt 落空,卡片显空),建议整批升级。 - decideDashboardAuth 是纯重构、行为零变化,dashboard cookie / public-read / set-cookie redirect 跟 canary.4 完全一致,30/30 e2e + 单测验证过。 dogfood 重点(codex 划) - weather-trip-plan 大 humanGate prompt 自动 spill,卡片只显 preview, dashboard 能看完整 Wait prompt - dashboard public-read / cancel write-protect 没被 refactor 影响 - Node I/O 的展开、滚动、errorMessage、terminal log tail 都稳定
canary: humanGate 大 prompt 自动 spill 到 promptRef + promptPreview 亮点 - waitCreated.payload 字段级 blob spill:> 1KiB 的 humanGate prompt 自动 落 <runDir>/blobs/<hash> blob 文件,事件内只携带 OutputRef-shaped promptRef + 短 promptPreview。weather-trip-plan 等大 markdown 工作流不再被 4KiB EventLog inline cap 卡死。 - 历史 / 小 prompt 100% 兼容:schema 上 prompt 仍是 z.string().optional() 不加 max,1024B 阈值只是 producer 策略;老版本 2-3KiB inline prompt 不 受影响。 - 互斥 invariant:prompt 和 promptRef 同存 / promptRef 缺 promptPreview 都会在 parseEvent / safeParseEvent / EventLog.append 三条路径上抛 ZodError,producer 写坏 draft 也能被拦下。 - 飞书审批卡边界明确:卡片永远只用 promptPreview,不读 blob 文件—— 否则 EventLog 4KiB 问题只是搬到飞书消息体积 / payload 上限。promptRef 存在时卡片自动加 "完整内容见 Web 详情" 引导。 - dashboard Node I/O 新增 Wait prompt 块,有 promptRef 时按 64KiB BlobPreview ladder 读完整文本,跟 input / output / log 同构。 - replay 严格不读 blob:promptRef / promptPreview 字段原样落到 AttemptState.wait,消费端(card-builder / dashboard)按需读。 测试 165/165 绿,跨 events 模式 / append 路径 / replay / runtime / 卡片 / dashboard ops-projection 六文件。 升级影响 - npm i botmux@canary 即可装到。老 daemon 进程读新 events 时 strip mode 自动丢 promptRef 字段(silent degrade,不 crash),建议整批升级再验证大 prompt workflow。
canary: workflow runtime 字符串模板 + OOM 根因修复 + dashboard public-read
亮点
- $ref 之外补一套字符串内 ${...} 内嵌(仅标量),允许在 prompt 里直接
拼 params.city / fetchWeather.output.summary,不再被迫加上游 planRequest
wrapper 字段。
- workflow worker OOM 根因定位并修复:cwd 上的 ~ 没展开导致 fork ENOENT,
错误路径无 settle guard 反复 reject 把 event loop 塞满。fork cwd 统一
expandWorkflowWorkingDir + 单次 settle guard + spawn-mem 面包屑(事后
可在 attempt log 看到逐段耗时和 worker pid)。
- humanGate 大 prompt 不再让 EventLog.append 硬抛:dispatchGate 估算
waitCreated payload 大小,超阈值直接 activityFailed(InputBindingFailed,
userFault) 并提示用 summary 字段。
- 跨 daemon bot 解析回退共享 bots.json:多 daemon 各自只装载自己那只
bot,workflow subagent 指向兄弟 bot 时不再 "bot not found"。
- dashboard /api/workflows/* GET 和 SPA shell 放开免 token,写操作仍校验
cookie;run 详情页新增 Node I/O 面板,每个 attempt 把 input /
resolvedInput / output / 终端 log 折叠成可读 BlobPreview。
- 顺手修审批卡片里 workflowRunDetailUrl 的 /#workflow/<id> → /#/workflows/<id>,
老链接点开是空白页。
- daemon-0 默认 5s 打 [memdiag] 内存快照,--max-old-space-size 提到 8GB;
worker.ts 在 BOTMUX_WORKFLOW=1 时跳过 web 终端 + 截图 + 分析器,
PTY 转写到内存里只在见到 </WORKFLOW_OUTPUT> 时 emit final_output。
- workflow-create SKILL.md 同步双语法 + weather-city 范例 C,下次新建
workflow 时 LLM 会直接用 ${...},不再发明 planRequest wrapper。
dogfood
weather-trip-plan 三节点(coco fetch / aiden plan / feishu-send + humanGate)
端到端跑通:summary/plan 拆分 + ${...} 注入 params.city + humanGate 卡片
点通后发完整 markdown 到群。
v2.31.0-canary.2 — Workflow Runtime(dogfood 修复轮) 基于 v2.31.0-canary.1,按真实 dogfood 反馈修两个 workflow 设计阶段的常见坑: dogfood 撞到:LLM 老实按 `botmux bots list` 输出的 `name` 字段填 subagent.bot, 但 name 来自 Lark `listChatBotMembers.displayName`(admin 可改),而 runtime `resolveBotSnapshot` 严格匹配 `config.name / botName / larkAppId`。跨 daemon 时 botName 拿不到、`config.name` 经常 unset,唯一可靠的全局 ID 是 larkAppId。 - `botmux bots list` 两条输出路径都加 `larkAppId` 字段 + `workflowBot` alias (本地配置 bot = larkAppId;外部 introduce bot = null),让 LLM 明确知道 workflow.subagent.bot 应填哪个值 - `createRun()` 找不到 subagent bot 时错误信息升级:明确"用 botmux bots list、 填 larkAppId 不是 display name",并附上 available larkAppIds 让 LLM self-correct - `botmux-workflow-create` skill 硬规则 2 改成强制填 larkAppId,三个范例的 bot 字段从具名(如 "claude-loopy")换成占位符 "cli_xxxxxxxxxxxxxxxx" - 常见错误新增 sharp negative example: "subagent.bot 填了 displayName (如 claude-loopy 或 aiden-oncall(d2)) 而不是 larkAppId:跨 daemon 必 fail" dogfood 撞到:LLM 把文件写到自己 cwd 的 `./workflows/`,daemon 进程 cwd 不 一致就找不到。runtime search path 是 \$CWD/workflows/ + \$HOME/.botmux/workflows/, 后者作为全局位置最稳。 - SKILL.md 硬规则 3 改为绝对路径:\$HOME/.botmux/workflows/<id>.workflow.json - Step 4 / Step 5 全程换成绝对路径口径 - 常见错误新增:写到 ./workflows/ 而不是 \$HOME/.botmux/workflows/,daemon 找不到 - 38 测试文件 / 499 用例全绿(含新的 bots-list-output / workflow-run-init 测试) - targeted: 21/21(builtin-skills + bots-list-output + workflow-run-init + workflow-cli) npm i -g botmux@canary botmux restart # 或 pm2 restart all npm i -g botmux@latest
v2.31.0-canary.1 — Workflow Runtime(事件驱动流程编排) 引入 botmux 流程编排能力。事件驱动 workflow runtime,支持三类节点 + DAG 依赖 + 数据流 + 重试/超时/审批 + 故障恢复 + 四入口 cancel。 - 流程定义:`workflows/*.workflow.json`,三种节点类型(subagent / hostExecutor / humanGate) - 启动:`botmux workflow run <id>` 或 IM `/workflow run <id>` - 数据流:`$ref: "<nodeId>.output.<path>"` 引上游节点输出 + `$ref: "params.<path>"` 引启动入参(支持嵌套) - 审批:飞书卡片 Approve / Reject / 取消 Run,humanGate.approvers 白名单 enforce - Cancel chain 四入口 + e2e 全部锁定:CLI / IM slash / IM card / Dashboard - Dashboard Workflows 标签页:Run List(5s 刷新) + Run Detail(2s 刷新,timeline + dangling + cancel) - 故障恢复:daemon 重启自动 cold-attach owned runs,dangling effect 通过 provider reconciler 收敛,worker crash 标 WorkerCrashed retryable - 新内置 skill botmux-workflow-create:根据自然语言描述生成 workflow.json,6 步流程(复述拆分 → bots list → 设计稿 → 写文件 → validate → 启动) - 新 CLI 子命令:botmux workflow validate / ls / tail / show - 37 测试文件 / 495 用例全绿 npm i -g botmux@canary botmux restart # or pm2 restart all 不会污染 latest(默认 npm i 仍拿 stable)。 npm i -g botmux@latest
PreviousNext