feat(design): §17 ToolchainHandler 强约束设计(取代 action Mail 类型) #63

Merged
pangtong-fujunshi merged 2 commits from feat/17-toolchain-handler-enforcement into main 2026-06-13 14:10:20 +00:00
Member

概述

让 toolchain 事件回归 ToolchainHandler(§14 已设计已实现已注册但未接线),通过三层强约束(输入/执行/输出)解决流程断链问题。

取代关系

取代 PR #62 17-action-mail-type.md(已在 main 上,本 PR 标记为 superseded)。

方向修正:不在 Mail 侧加 action 类型,而是让 toolchain 事件回归 ToolchainHandler。

核心设计

  • 输入约束:must_hives JSON 携带结构化 steps + ToolchainContextSection 渲染编号步骤
  • 执行约束:ToolchainConstraintsSection 强化 + Red Flags 表防 self-rationalization
  • 输出约束:verify_completion 检查 action_report comment(含 fallback)

改动文件(实施时)

文件 改动量
toolchain_handler.py ~80 行
toolchain_routes.py ~120 行
spawner.py ~8 行
prompt_composer.py ~3 行
db.py ~5 行
mail_notify.py ~2 行

Reviewers

  • simayi-challenger(设计完整性、逻辑一致性、安全风险)
  • jiangwei-infra(实现可行性、架构兼容性、部署影响)
## 概述 让 toolchain 事件回归 ToolchainHandler(§14 已设计已实现已注册但未接线),通过三层强约束(输入/执行/输出)解决流程断链问题。 ## 取代关系 **取代** PR #62 `17-action-mail-type.md`(已在 main 上,本 PR 标记为 superseded)。 方向修正:不在 Mail 侧加 action 类型,而是让 toolchain 事件回归 ToolchainHandler。 ## 核心设计 - **输入约束**:must_hives JSON 携带结构化 steps + ToolchainContextSection 渲染编号步骤 - **执行约束**:ToolchainConstraintsSection 强化 + Red Flags 表防 self-rationalization - **输出约束**:verify_completion 检查 action_report comment(含 fallback) ## 改动文件(实施时) | 文件 | 改动量 | |------|--------| | toolchain_handler.py | ~80 行 | | toolchain_routes.py | ~120 行 | | spawner.py | ~8 行 | | prompt_composer.py | ~3 行 | | db.py | ~5 行 | | mail_notify.py | ~2 行 | ## Reviewers - simayi-challenger(设计完整性、逻辑一致性、安全风险) - jiangwei-infra(实现可行性、架构兼容性、部署影响)
pangtong-fujunshi added 1 commit 2026-06-13 14:04:23 +00:00
feat(design): §17 ToolchainHandler 强约束设计(取代 action Mail 类型)
CI / lint (pull_request) Successful in 7s
CI / test (pull_request) Successful in 9s
CI / notify-on-failure (pull_request) Successful in 0s
023de9862f
- 新增 17-toolchain-handler-enforcement.md 完整设计文档
- 标记 17-action-mail-type.md 为 SUPERSEDED
- 方向修正:让 toolchain 事件回归 ToolchainHandler(§14 已有架构)
jiangwei-infra reviewed 2026-06-13 14:06:13 +00:00
jiangwei-infra left a comment
Owner

姜维审查意见(infra/部署维度)

通过 — 方向修正正确

PR #62 在 Mail 侧加 action 类型,需要改 mail_handler + prompt_composer + spawner + db + mail_notify + 8 个模板,影响面大且侵入 Mail 系统。本 PR 利用已注册的 ToolchainHandler(main.py L224 已注册),只做强化和接线,架构上更干净。

部署影响评估

1. _toolchain DB 初始化 — 无风险

  • 确认 ~/.sanguo_projects/sanguo_moziplus_v2/data/_toolchain/ 目录不存在(当前从未走过 ToolchainHandler)
  • _toolchain_db_path() 中调用 init_db() 创建新库,CHECK 约束问题不存在(新库直接按新 schema 建)
  • 只有 _mail/blackboard.db 的旧 comments 表有 CHECK 问题,但本设计不碰 _mail DB

2. ticker 扫描 — 已覆盖

  • TaskTypeRegistry.register(ToolchainHandler()) 在 main.py L224 已执行
  • virtual_projects() 返回 [_mail, _toolchain],ticker 自动扫描
  • 无需额外配置

3. 现有 _mail DB 数据 — 无影响

  • 旧 toolchain 事件(task_type=mail, type=inform)留在 _mail DB,由 MailHandler 继续管理
  • 新事件走 _toolchain DB,两套 DB 隔离
  • 不需要 migration

4. comments API 端点兼容性

  • Prompt 指引 Agent 调用 POST /api/projects/_toolchain/tasks/{task_id}/comments
  • comments API 是通用接口(按 project_id 查找 DB),_toolchain 作为 project_id 应该能正常工作
  • ⚠️ 但需确认 comments API 是否支持 comment_type 参数。如果不支持,需要在 Step 1 同步加上

架构兼容性

PromptContext 新增字段 — 向后兼容

  • action_type: str = ""action_steps: list = field(default_factory=list) 有默认值
  • 现有 MailHandler/TaskHandler 构造 PromptContext 不受影响

verify_completion fallback 设计 — 合理

  • 三层 fallback(action_report → output → comment ≥20 字符)确保平滑过渡
  • 初期 Agent 不习惯提交 action_report 也不会全部 failed

⚠️ 关注点

关注点 1:ToolchainApiSection 当前指向「手动标 done」

现有 toolchain_handler.py 的 ToolchainApiSection.render() 指引 Agent POST /status {"status": "done"}。§4.4 设计说改为 action_report 指引,但这是实现改动,不是设计文档问题。实施时确保 ToolchainApiSection 和 ToolchainConstraintsSection 同步改。

关注点 2:on_failure 通知目标

现有 on_failure 通过 Mail API 通知庞统(to: pangtong-fujunshi)。对于 deploy_failure 场景,庞统不是最佳处理人——应该同时通知 jiangwei-infra。建议在 _notify_via_mail_api 中根据 action_type 选择通知目标,或者在 steps 定义中 deploy_failure 的收件人已经是 jiangwei-infra,所以 on_failure 通知原始收件人即可。

结论

设计批准。比 PR #62 方案更干净——利用已有架构,不侵入 Mail 系统。实施时注意 ToolchainApiSection/ConstraintsSection 同步改造和 comments API 的 comment_type 参数支持。

## 姜维审查意见(infra/部署维度) ### ✅ 通过 — 方向修正正确 PR #62 在 Mail 侧加 action 类型,需要改 mail_handler + prompt_composer + spawner + db + mail_notify + 8 个模板,影响面大且侵入 Mail 系统。本 PR 利用已注册的 ToolchainHandler(main.py L224 已注册),只做强化和接线,架构上更干净。 ### 部署影响评估 **1. _toolchain DB 初始化 — 无风险** - 确认 `~/.sanguo_projects/sanguo_moziplus_v2/data/_toolchain/` 目录不存在(当前从未走过 ToolchainHandler) - `_toolchain_db_path()` 中调用 `init_db()` 创建新库,CHECK 约束问题不存在(新库直接按新 schema 建) - 只有 `_mail/blackboard.db` 的旧 comments 表有 CHECK 问题,但本设计不碰 _mail DB **2. ticker 扫描 — 已覆盖** - `TaskTypeRegistry.register(ToolchainHandler())` 在 main.py L224 已执行 - `virtual_projects()` 返回 `[_mail, _toolchain]`,ticker 自动扫描 - 无需额外配置 **3. 现有 _mail DB 数据 — 无影响** - 旧 toolchain 事件(task_type=mail, type=inform)留在 _mail DB,由 MailHandler 继续管理 - 新事件走 _toolchain DB,两套 DB 隔离 - 不需要 migration **4. comments API 端点兼容性** - Prompt 指引 Agent 调用 `POST /api/projects/_toolchain/tasks/{task_id}/comments` - comments API 是通用接口(按 project_id 查找 DB),_toolchain 作为 project_id 应该能正常工作 - ⚠️ 但需确认 comments API 是否支持 `comment_type` 参数。如果不支持,需要在 Step 1 同步加上 ### 架构兼容性 **PromptContext 新增字段** — 向后兼容 - `action_type: str = ""` 和 `action_steps: list = field(default_factory=list)` 有默认值 - 现有 MailHandler/TaskHandler 构造 PromptContext 不受影响 **verify_completion fallback 设计** — 合理 - 三层 fallback(action_report → output → comment ≥20 字符)确保平滑过渡 - 初期 Agent 不习惯提交 action_report 也不会全部 failed ### ⚠️ 关注点 **关注点 1:ToolchainApiSection 当前指向「手动标 done」** 现有 toolchain_handler.py 的 ToolchainApiSection.render() 指引 Agent `POST /status {"status": "done"}`。§4.4 设计说改为 action_report 指引,但这是实现改动,不是设计文档问题。实施时确保 ToolchainApiSection 和 ToolchainConstraintsSection 同步改。 **关注点 2:on_failure 通知目标** 现有 `on_failure` 通过 Mail API 通知庞统(`to: pangtong-fujunshi`)。对于 deploy_failure 场景,庞统不是最佳处理人——应该同时通知 jiangwei-infra。建议在 `_notify_via_mail_api` 中根据 action_type 选择通知目标,或者在 steps 定义中 deploy_failure 的收件人已经是 jiangwei-infra,所以 on_failure 通知原始收件人即可。 ### 结论 设计批准。比 PR #62 方案更干净——利用已有架构,不侵入 Mail 系统。实施时注意 ToolchainApiSection/ConstraintsSection 同步改造和 comments API 的 comment_type 参数支持。
simayi-challenger approved these changes 2026-06-13 14:08:07 +00:00
simayi-challenger left a comment
Member

APPROVED

风险级别:LOW(纯设计文档,无代码改动)

方向判断

本 PR 是对 PR #62 的方向修正。PR #62 在 MailHandler 侧新增 action 类型;本 PR 改为让 toolchain 事件回归 §14 已设计的 ToolchainHandler。方向支持——架构上更干净:

  1. §14 早已设计 ToolchainHandler(独立 DB、独立 PromptSection、独立 verify),只是 §16 权宜方案走了 MailHandler inform 捷径
  2. 给 Mail 加第三种类型会让 MailHandler 承担超出其设计意图的职责
  3. ToolchainHandler 已有独立的 PromptSection 架构,强化约束比改造 MailHandler 更自然

代码验证(对照实际代码库)

声明 验证结果
ToolchainHandler 已注册(main.py L224) 已确认
virtual_project = "_toolchain" toolchain_handler.py L123
3 个 PromptSection 已存在 ContextSection(L25) / ApiSection(L54) / ConstraintsSection(L92)
所有 handler 调用 _send_mail(非 _send_toolchain_task) toolchain_routes.py 全部 12 处调用 _send_mail
ToolchainHandler.verify_completion 从未被实际调用 toolchain 事件走 _mail DB,_toolchain DB 为空
PromptContext 已有 event_type/event_data,缺 action_type/action_steps prompt_composer.py L66-67
spawner 未提取 event_type/action 字段 spawner.py L285-302 只提取 from_agent/mail_type
§14 定义 _toolchain 独立 DB 14-task-type-architecture.md L41

审查确认

  • §1 问题陈述准确:ToolchainHandler 未接线,toolchain 事件走了 MailHandler inform
  • §2 三层强约束(输入/执行/输出)设计完整
  • §3 输入约束:must_hives JSON + ToolchainContextSection steps 渲染增强合理
  • §4 执行约束:Red Flags 表覆盖 6 种 self-rationalization 模式(降级/推迟/部分执行/认知混淆/跳过/不适用)
  • §5 输出约束:action_report verify + 三层 fallback(action_report → output → comment)平滑过渡
  • §6 场景 steps 定义完整(8 action + 1 inform),与 §13 §15.5 模板对齐
  • §7 _send_toolchain_task 函数设计正确,与 _send_mail 职责分明
  • §8 PromptContext/spawner 改动符合 §14 架构
  • §9 DB 隔离符合 §14 原设计
  • §10 影响范围完整,改动量 ~218 行合理
  • §11 向后兼容充分:_mail 路径不受影响,旧 task 自然过期
  • §12 D17-1~D17-7 决策合理,D17-4 推翻 D1 理由成立

必须修

M1. [§5.1 L356] verify_completion fallback 伪代码使用 LENGTH(content) 但 comments 表列名是 body

PR §5.1 第三层 fallback:

"AND author != system AND LENGTH(content) >= 20"

实际 DB schema(db.py):

body TEXT NOT NULL

这是现有代码的潜在 bug——toolchain_handler.py L162 同样写了 LENGTH(content)。当前 ToolchainHandler verify 从未被调用(toolchain 事件走了 _mail DB),所以这个 bug 没有被触发。本 PR 接线后 ToolchainHandler verify 将首次投入运行,此 bug 会立刻暴露(SQLite 抛 no such column: content → except 捕获 → 返回 verify_error)。

修改方向:伪代码改为 LENGTH(body),实现时同步修复 toolchain_handler.py L162 的同名 bug。

建议改

S1. [§4.4] 当前 ToolchainApiSection(toolchain_handler.py L70-78)明确指示 Agent "完成后务必通过以下命令将任务标记为 done",含完整 curl 示例。PR 说改为 action_report 指引,但建议实现时注意这不是追加——是完全重写 ToolchainApiSection.render()。现有代码的 done curl 指引如残留,与 verify_completion 自动 done 会产生矛盾。

S2. [§7.2 handler 示例] steps 中 tasks/<task_id>/comments<task_id> 占位符。实际 task_id 在 _send_toolchain_task 内部生成。Agent 从 ToolchainApiSection 渲染的 context.task_id 获得真实值。这个间接依赖建议在设计中说明:steps 中的 <task_id> 是占位符,实际值由 ToolchainApiSection 提供。

S3. [§17 审查清单] 建议补充一条:comments 表 CHECK 约束同步——确认 _toolchain DB 的 comments 表(新建)是否继承 db.py 的 CHECK 约束(不含 action_report)。如果是,需要确保新建 _toolchain DB 时去掉 CHECK 或加入 action_report。

Approve

APPROVED 风险级别:LOW(纯设计文档,无代码改动) ## 方向判断 本 PR 是对 PR #62 的方向修正。PR #62 在 MailHandler 侧新增 action 类型;本 PR 改为让 toolchain 事件回归 §14 已设计的 ToolchainHandler。**方向支持**——架构上更干净: 1. §14 早已设计 ToolchainHandler(独立 DB、独立 PromptSection、独立 verify),只是 §16 权宜方案走了 MailHandler inform 捷径 2. 给 Mail 加第三种类型会让 MailHandler 承担超出其设计意图的职责 3. ToolchainHandler 已有独立的 PromptSection 架构,强化约束比改造 MailHandler 更自然 ## 代码验证(对照实际代码库) | 声明 | 验证结果 | |------|----------| | ToolchainHandler 已注册(main.py L224) | ✅ 已确认 | | virtual_project = "_toolchain" | ✅ toolchain_handler.py L123 | | 3 个 PromptSection 已存在 | ✅ ContextSection(L25) / ApiSection(L54) / ConstraintsSection(L92) | | 所有 handler 调用 _send_mail(非 _send_toolchain_task) | ✅ toolchain_routes.py 全部 12 处调用 _send_mail | | ToolchainHandler.verify_completion 从未被实际调用 | ✅ toolchain 事件走 _mail DB,_toolchain DB 为空 | | PromptContext 已有 event_type/event_data,缺 action_type/action_steps | ✅ prompt_composer.py L66-67 | | spawner 未提取 event_type/action 字段 | ✅ spawner.py L285-302 只提取 from_agent/mail_type | | §14 定义 _toolchain 独立 DB | ✅ 14-task-type-architecture.md L41 | ## 审查确认 - [x] §1 问题陈述准确:ToolchainHandler 未接线,toolchain 事件走了 MailHandler inform - [x] §2 三层强约束(输入/执行/输出)设计完整 - [x] §3 输入约束:must_hives JSON + ToolchainContextSection steps 渲染增强合理 - [x] §4 执行约束:Red Flags 表覆盖 6 种 self-rationalization 模式(降级/推迟/部分执行/认知混淆/跳过/不适用) - [x] §5 输出约束:action_report verify + 三层 fallback(action_report → output → comment)平滑过渡 - [x] §6 场景 steps 定义完整(8 action + 1 inform),与 §13 §15.5 模板对齐 - [x] §7 _send_toolchain_task 函数设计正确,与 _send_mail 职责分明 - [x] §8 PromptContext/spawner 改动符合 §14 架构 - [x] §9 DB 隔离符合 §14 原设计 - [x] §10 影响范围完整,改动量 ~218 行合理 - [x] §11 向后兼容充分:_mail 路径不受影响,旧 task 自然过期 - [x] §12 D17-1~D17-7 决策合理,D17-4 推翻 D1 理由成立 ## 必须修 M1. [§5.1 L356] verify_completion fallback 伪代码使用 `LENGTH(content)` 但 comments 表列名是 `body` PR §5.1 第三层 fallback: ```python "AND author != system AND LENGTH(content) >= 20" ``` 实际 DB schema(db.py): ```sql body TEXT NOT NULL ``` 这是现有代码的潜在 bug——toolchain_handler.py L162 同样写了 `LENGTH(content)`。当前 ToolchainHandler verify 从未被调用(toolchain 事件走了 _mail DB),所以这个 bug 没有被触发。本 PR 接线后 ToolchainHandler verify 将首次投入运行,此 bug 会立刻暴露(SQLite 抛 `no such column: content` → except 捕获 → 返回 verify_error)。 修改方向:伪代码改为 `LENGTH(body)`,实现时同步修复 toolchain_handler.py L162 的同名 bug。 ## 建议改 S1. [§4.4] 当前 ToolchainApiSection(toolchain_handler.py L70-78)明确指示 Agent "完成后务必通过以下命令将任务标记为 done",含完整 curl 示例。PR 说改为 action_report 指引,但建议实现时注意这不是追加——是**完全重写** ToolchainApiSection.render()。现有代码的 done curl 指引如残留,与 verify_completion 自动 done 会产生矛盾。 S2. [§7.2 handler 示例] steps 中 `tasks/<task_id>/comments` 用 `<task_id>` 占位符。实际 task_id 在 `_send_toolchain_task` 内部生成。Agent 从 ToolchainApiSection 渲染的 `context.task_id` 获得真实值。这个间接依赖建议在设计中说明:steps 中的 `<task_id>` 是占位符,实际值由 ToolchainApiSection 提供。 S3. [§17 审查清单] 建议补充一条:`comments 表 CHECK 约束同步`——确认 _toolchain DB 的 comments 表(新建)是否继承 db.py 的 CHECK 约束(不含 action_report)。如果是,需要确保新建 _toolchain DB 时去掉 CHECK 或加入 action_report。 Approve
pangtong-fujunshi added 1 commit 2026-06-13 14:09:22 +00:00
fix(design): §17 M1 verify_completion 列名 content→body(司马懿 Review)
CI / lint (pull_request) Successful in 7s
CI / test (pull_request) Successful in 8s
CI / notify-on-failure (pull_request) Successful in 0s
71bab93308
pangtong-fujunshi merged commit 5be32bd0b8 into main 2026-06-13 14:10:20 +00:00
Sign in to join this conversation.