跳到主要内容
阅读约 4 分钟

产物与质量门禁

节点之间如何交接、产物身份如何构成、质量门禁如何判断,以及为什么产物不能被下游修改。

产物是数据面

节点之间不通过对话交接,而通过产物。这是产品设计的核心选择:对话无法被校验、无法被稳定引用、也无法被下游安全消费。

每个成功执行都会冻结自己的产物,形成不可变版本。下游读取的永远是冻结版本,不是运行时目录中的临时文件。

产物身份

产物身份由四部分构成:节点标识、输出名称、执行尝试标识与内容摘要。

这意味着同一节点在不同执行中产出的同名产物是不同的产物,而不是同一个产物的两次写入。下游无法修改上游版本,因为它们引用的是一个具体的、已经冻结的组合。

流程的输出声明是必需契约,产物清单报告实际结果。运行时额外产物可以满足已声明的可选或集合输入,但不能新增依赖边。

完成协议

一个节点成功的核心条件是:

  • 流程声明的所有必需业务产物均已生成;
  • 产物清单存在、非空且能枚举实际产物;
  • 结果摘要存在且包含有效内容;
  • 质量门禁全部通过。

运行器校验路径、文件存在性、大小、格式与摘要后冻结该次执行。

产物校验发生在只读冻结之前,且摘要格式校验是强制的。因此每次成功执行的证据是完整且自洽的。

质量门禁

质量门禁是你声明的 Shell 命令。确定性构建、测试、静态检查与扫描都通过它承担,运行器只在本次执行的工作树中执行,并按退出码判断结果。

运行器镜像同时提供 Go、Node 与 Python 工具链,使这些仓库可以在沙箱内执行原生验证。

门禁失败时,监督器先把命令、退出码与受控输出送回当前 Agent 会话,在同一执行内执行有限次数的修复重跑。次数由流程显式冻结,节点不能覆盖。

这是重要的设计细节:门禁失败不是立即失败,而是先给 Agent 一次修复机会,因为这正是人类开发者会做的事。但次数有上限,避免无限循环。

代码证据与产物证据

节点完成协议同时冻结两类可审查证据。

代码证据绑定任务、节点、执行与代码修订。调用方只能提交规范化相对路径;提供方从冻结引用解析对象,不允许提交修订号、对象标识或物理仓库路径,也不能用最终任务分支冒充历史状态。

产物证据仅包含产物清单、结果摘要与契约声明的输出。监督器在产物契约校验后把它们原子复制到位于 Agent 可写目录之外的只读快照。后续节点修改运行目录不会改变已冻结内容,未声明的临时文件不可通过接口读取。

列表只返回路径、大小、媒体类型与摘要元数据。正文使用字节分页,每页有明确上限,支持任意大小的文本或二进制文件,不依赖扩大连接消息大小。

执行树结构

每次执行使用独立、不可变的目录:

.fusion/
  state.db
  stages/<stage-id>/attempt-<n>/
    artifacts.json
    result.md
    outputs/
  worktrees/

产物清单的规范格式是包含 artifacts 数组的对象。运行器同时兼容历史 Agent 可能生成的顶层数组,但两种格式进入同一套字段、路径、文件存在性与摘要校验,不把兼容解析降级为宽松验收。

数据生命周期

节点文件与快照属于沙箱生命周期数据,不进入控制面数据库。沙箱消失后,历史归档由独立的产物归档机制负责。

任务结束时,系统级知识归并钩子从任务输入、产物、代码变更、验证结果与有权限的交互中产生知识增量。成功任务归档每个成功执行的产物清单、结果摘要、所有声明产物,以及最终的图与版本清单;不归档源码工作区和未声明临时文件。

失败或取消且沙箱仍可访问时,归档已完成节点的声明产物、最后一次失败执行、失败报告和诊断清单。沙箱已消失时接受材料无法补传,只依赖已经进入遥测系统的链路数据和控制面任务级失败记录。

归档的最终清单是只读执行报告,不是可恢复的检查点。任务结束后界面可以读取该报告展示历史,但不能据此恢复原沙箱执行。