首页
社区
课程
招聘
AI Agent 工程化原理与工作流插件套件实现
发表于: 1天前 559

AI Agent 工程化原理与工作流插件套件实现

1天前
559

AI Agent 工程化原理与工作流插件套件实现


第一部分:原理


一、AI 编码的工程瓶颈转移

软件工程数十年来围绕一个核心约束运转——编码成本高昂。瀑布模型的需求规格化、敏捷迭代的 Sprint 规划、代码评审制度、架构决策流程,本质上都在管理"工程师时间"这一稀缺资源。

AI Agent 时代改变了这一前提。编码执行不再是成本瓶颈,瓶颈转移至验证(代码是否正确)、治理(是否符合架构约束)、可续接性(跨会话、跨模型、跨设备如何保持工程连续性)。

这一变化影响五个维度:规划方式(产出速率数量级提升)、代码所有权(生成者归属模糊化)、代码评审(规模与工具的根本变化)、团队构成(技能组合重新定义)、知识共享(文档不再是唯一知识载体)。


二、上下文质量决定输出质量

2.1 信噪比决定输出质量

LLM 的输出质量与输入上下文的信噪比强相关。无关信息占据 token 预算,会降低模型对关键信息的注意力。实践中应遵循:

  • 项目文件精简:清除编译缓存、构建产物、无关文档;引用文件时使用绝对路径而非让 Agent 自行搜索。
  • 输入去噪:去除修饰词和语气词;将富文本转换为纯文本(Markdown/TXT),减少非语义标记干扰。
  • 无倾向性输入:提问时避免引导性表述,让模型独立判断而非拟合用户预期。

2.2 上下文污染与上下文腐烂

在 Agent 工作流中,有两个核心上下文退化机制:

上下文污染(Context Pollution):不相关的信息进入模型的可见上下文,干扰当前任务的推理。典型场景——3 个并行任务共享同一个上下文窗口时,任务 A 的代码搜索结果会占据任务 B 的注意力。

上下文腐烂(Context Decay):随着对话增长,模型对早期信息的回忆准确度下降。一个 200K token 的对话在第 150K token 时,对第 10K token 处的架构决策的引用可能出现幻觉。

这两个问题要求对上下文进行主动的边界管理——不是让上下文自由增长,而是在多个尺度上持续控制其质量和规模。

2.3 三层上下文边界模型

有效的上下文管理需要在三个尺度上同时建立边界:

层级 边界定义 解决的问题
会话级 压缩旧对话,保留摘要 + 近期消息 上下文腐烂——长对话中早期信息被遗忘
任务级 每个任务使用独立上下文,不继承调度器历史 上下文污染——并行任务之间互相干扰
项目级 结构化文档(AGENTS.md、ADR、C4)作为跨会话认知载体 认知断裂——换会话/换模型/换设备后丢失项目理解

三层边界的协同效果:会话级保证单次对话的质量,任务级保证并行执行的质量,项目级保证跨时间跨空间的连续性。

2.4 上下文压缩的信息保留策略

上下文压缩不应该是简单的截断,而是分层的信息保留策略:

  • 永久保留层:最近 N 条消息逐字保留,不送入压缩模型——这是当前工作状态的"工作记忆"
  • 高优先级保留层:文件路径、架构决策、未解决的 TODO、用户目标——这些是不可推导的项目事实
  • 低优先级丢弃层:探索性搜索结果、已覆盖的文件内容、重复搜索、"looks good" 式中间确认——这些是一次性消费品

这一分层策略的目标是:用远小于原始上下文的 token 数,保留恢复工作所需的全部关键信息。

V2 进一步引入压缩质量校验——压缩后自动验证关键模式(文件路径、ADR 引用、TODO/FIXME、不变量引用)的保留率是否 ≥ 70%。校验失败时触发三级降级:重试(换 prompt)→ 换模型 → 截断(保留原始上下文并通知用户),保证坏摘要不会静默损坏上下文。

2.5 上下文隔离与并行效率的关系

上下文隔离通常被视为质量保障手段,但它同时也是并行调度的效率前提

共享上下文下的并行:每个 worker 的工具调用结果都进入共享上下文 → 并发数越高,上下文膨胀越快 → 更快触发上下文窗口限制 → 更频繁的压缩 → 输出质量下降。

隔离上下文下的并行:每个 worker 的上下文独立增长 → 并发数不受上下文窗口约束 → 每个 worker 的上下文保持稳定规模 → 输出质量恒定。

这意味着:没有上下文隔离,并行度越高,质量衰减越快。隔离使并行加速比可以线性扩展而非在并发数增加时边际递减。


三、并行调度原理

3.1 依赖感知调度

朴素并行(所有任务同时启动)在有文件写集冲突时会导致并发任务互相覆盖,产出的代码需要大量人工修复,实际效率反而低于串行。有效的并行调度必须:

  1. 分析依赖关系:识别任务之间的前置依赖(任务 B 依赖任务 A 的产出)
  2. 检测写集冲突:识别哪些任务会修改相同文件
  3. 波次分组:将无依赖、无冲突的任务组织为可并行执行的波次
  4. 序列化冲突点:对有冲突的任务强制串行执行

3.2 并行加速比模型

设 N 个任务,平均执行时间 T,依赖深度 D:

调度策略 总时间 加速比 结果可靠性
串行执行 N × T 1x 可靠
朴素并行(无冲突分析) ~N/C × T ~C x 不可靠——写集冲突导致覆盖
依赖感知波次调度 D × T N/D x 可靠——冲突已消除

关键洞察:加速比的上限取决于依赖深度 D(关键路径长度),而非并发数 C。依赖越浅、独立任务越多,加速比越高。

3.3 调度器的可交互性

调度器在并行执行期间应始终保持可交互状态——用户可以随时查询进度、修改需求、取消任务。这要求:

  • 调度器与 worker 运行在不同的上下文/进程中
  • 调度器的状态通过持久化文件(而非内存)暴露
  • 轮询间隔是无人值守时的巡检节奏,用户主动查询时同步响应

V2 进一步引入 ScheduleWakeup 机制——调度器不自行循环轮询,而是通过系统的定时唤醒功能(每 5 分钟)被唤醒执行检查。这消除了"Agent 忘记轮询"的风险,将轮询从 Agent 的自觉行为升级为系统级保障。后台 Worker 完成时系统还会主动推送通知,调度器可以立即处理而不必等到下一个 5 分钟窗口。


四、证据驱动原理

4.1 AI Agent 的虚假验证问题

AI Agent 在验证自身产出时存在系统性偏差:倾向于以"命令返回 0"、"进程存在"、"日志无异常"等间接指标判定通过,而这些指标与实际功能正确性之间没有必然关系。尤其在 GUI 场景中,窗口拉起 ≠ 界面渲染正确,端口监听 ≠ 业务逻辑正确。

4.2 证据先于修复

正确的调试流程必须强制要求直接证据先于任何修复行为:

  • GUI 问题需要截图/图像证据
  • 网络问题需要抓包/pcap 证据
  • 代码质量问题需要静态分析报告

修复后必须用同类证据再次验证。不能以"代码改了"代替"问题验证了"。

4.3 闭环自动修复

执行 → 失败 → 收集证据 → 诊断 → 修复 → 重新执行,形成自动化循环。设置干预预算(如最多 2 次自动重试),耗尽后升级到人工决策。这避免了无限循环,也避免了过早打扰用户。

4.4 任务类型感知的证据门控(V2 新增)

V1 的证据门控是无差别触发——所有任务完成后都尝试触发 AirXDB 截图,导致非 GUI 任务(如纯后端逻辑修改)产生 11+ 次假阳性阻塞,每次都需要人工覆盖。

V2 引入 EvidenceGatePolicy——基于任务特征的差异化证据分类:

证据类别 触发条件(关键词匹配) 要求的证据类型
GUI_REQUIRED gui, ui, render, layout, dialog, widget, canvas, 界面, 按钮… 截图 + GUI 操作验证
NETWORK_REQUIRED network, rtsp, http, tcp, socket, stream, 网络, 抓包… 抓包 + 连通性验证
STATIC_ANALYSIS cppcheck, clang-tidy, mypy, lint, static analysis… 静态分析报告
CODE_ONLY 不匹配以上任何关键词 代码审查 + 测试结果

关键词匹配而非 LLM 分类的设计决策:

  • 确定性:相同输入总是产生相同输出,可测试
  • 零成本:不需要额外 API 调用
  • 可解释:用户可以理解为什么某个任务被分类为 GUI 任务
  • 可覆盖:用户可在 todo.md 中用 [no-xdb]/[no-ndb]/[no-sdb] 标记显式跳过

五、多模型交叉审计原理

5.1 单模型审计的系统性盲区

每个 LLM 有其固有的偏见和遗漏模式:某些模型倾向于关注文件完整性而忽视语义正确性,某些模型对安全问题的敏感度高于其他模型,某些模型在特定领域的推理深度更强。单模型审计无法识别这些盲区——你无法用同一个模型来验证它自己的遗漏。

5.2 交叉确认与置信度分级

多个独立模型对同一制品进行审计后,通过交叉确认矩阵对发现进行置信度分级:

独立确认的模型数 置信度 处置策略
≥ 3 高置信 必须立即修复,不复核
2 中置信 应当修复,可快速复核
1 低置信 需人工复核确认

核心逻辑:如果 3 个独立模型都发现了同一个问题,这个问题几乎一定是真实的。如果只有 1 个模型发现,可能是该模型的特有视角,也可能是误报。

5.3 评级不一致也是一种信息

当不同模型对同一制品给出显著不同的评级时,分歧本身就是有价值的信息——它揭示了不同模型的评价维度差异。例如:一个模型以"文件创建完成度"为主轴给出高评价,而另一个模型以"与规范的语义一致性"为主轴给出低评价。这种分歧恰恰指向了"文件存在 ≠ 语义正确"这一深层问题。

5.4 三种交叉审计模式

模式 结构 适用场景
并行审计 N 个模型同时独立审计,结果汇总 开发阶段审计、代码质量评估
递进审计 N 轮串行,每轮读取前轮发现并深挖 详细设计审查、根因分析
多视角审计 扮演不同角色(架构师/开发者/用户) 需求覆盖性检查、UX 缺口发现

六、架构状态持久化原理

6.1 架构即项目认知骨架

软件项目的架构知识通常存在于架构师脑中。AI Agent 时代,执行者每次可能是不同的模型实例——架构认知必须外化为结构化文档,成为任何执行者都能加载的项目认知。

两类核心文档承担这一角色:

  • C4 模块文档:定义模块边界、职责、公共接口、依赖关系、数据所有权。模块边界直接影响调试时的范围判定和并行调度的写集冲突分析
  • ADR(架构决策记录):记录每条架构决策的上下文(为什么)、决策(选了什么)、后果(正反面影响)和被拒绝的替代方案

6.2 C4 与 ADR 的联动:决策图谱

C4 定义了系统的静态边界——哪些模块存在、边界在哪、接口是什么。ADR 记录了边界的演化历史——为什么这样划分、拒绝了哪些替代方案、已知哪些代价。

两者构成决策图谱:C4 回答"现在是什么",ADR 回答"为什么是这样"。当新任务到来时,执行者加载决策图谱即可理解项目全貌,而不需要与前任执行者对话。

6.3 ADR 后果分析作为影响面定位工具

每条 ADR 的 Consequences 段落列出正面和负面影响——这些影响本质上定义了该决策的作用面。当出现问题时:

  1. 从问题症状出发,定位涉及的模块(C4)
  2. 从模块关联的 ADR 后果中,快速收窄根因搜索范围
  3. 如果修复与某条 ADR 的后果冲突,要么创建新 ADR 覆盖旧决策,要么放弃修复方向

这形成不可绕过的决策审计链——每次架构变更都有理由记录,每个理由都可追溯。

6.4 架构状态不丢失的保证(原理)

架构文档与代码同步的核心原则:不更新架构文档的任务无法标记为完成

这意味着每次任务合并时,系统必须强制验证 Worker 是否提交了所要求的架构文档更新——缺失则拒绝合并。架构文档因此成为代码合并的门控条件,而不是"事后补写"的附属物。

具体的标记块命名空间、6 阶段合并流水线、合并去重等实现细节,见第二十章 § 20.1。

6.5 ADR 变更级联失效(原理,V2 新增)

V1 暴露的深层问题:当架构方案变更(如 ffmpeg → gstreamer)时,基于旧 ADR 已完成的任务不会自动失效,旧代码残留与新方案冲突,下游任务基于过期产出继续执行。

原理层面的要求:架构决策一旦变更,所有引用该决策的已完成任务必须自动失效、进行中任务必须自动中止、下游依赖必须级联失效、基于旧决策的代码必须回滚、受影响的任务必须局部重规划。这五个动作构成一个架构变更的闭环——缺少任何一环,都会留下"幽灵代码"。

具体的 10 步级联闭环(ADRWatcher hash 对比 → TaskGraph.invalidate_by_adr → 调度冻结 → git revert → PartialReplanner 局部重规划 → 解冻)见第二十章 § 20.2。

6.6 认知卸载:从"记在脑中"到"写在文件中"

传统工程依赖架构师的持续在场来维护架构一致性。AI 工程将架构认知卸载到文件:

  • AGENTS.md:项目级指令与工作流规则——任何 AI 加载即获项目上下文
  • ADR:架构决策的永久记录——新模型或新设备上的新会话也能理解历史决策
  • C4:模块边界的权威定义——约束任务写集和调试范围
  • debug-log.md:问题生命周期的完整记录——从引入到解决的全链路可追溯

这些文件的集合构成项目的认知基础设施——不依赖任何特定人或特定 AI 会话。


七、范围约束降本原理

7.1 规划-执行分离与智能放大

传统开发中规划和执行混杂在同一上下文:开发者同时理解需求、设计架构、编写代码。范围约束将规划与执行分离:

  • 规划阶段(高能力模型):定义范围、验收标准、验证命令、依赖关系、写集冲突分析
  • 执行阶段(任意模型):在预定义的窄化切片内执行,不需要理解全局

关键洞察:当执行者的上下文被精确约束到6 个文件 + 1 个任务切片 + 预声明的写集时,执行者不需要"理解整个项目"——只需要在预先确定的范围内执行。

7.2 上下文约束使廉价模型可用

当任务上下文被约束在有限文件和结构化模板中时,执行者面对的是一个高度简化的问题空间

  • 不需要仓库探索(写集已预声明)
  • 不需要架构决策(ADR/C4 已作为必读文件提供)
  • 不需要任务规划(只有一个任务切片)
  • 不需要结果格式化(结构化模板已预填充)

执行者只需要:在预声明的文件中编写片段代码 → 按模板填入结果 → 运行预声明的验证。这个能力门槛远低于"理解一个项目并规划开发"——廉价模型完全可以胜任。

7.3 弱模型安全保障(V2 新增)

廉价模型的固有限制是字面理解、无推断能力。V2 在 AirArc 规划阶段引入 INV-16 弱模型安全约束,从四个维度保障任务描述的精确性:

约束维度 具体要求 防止的问题
禁止歧义词 不用"清理"、"重构"、"优化"等宽泛动词,指明具体改什么 Worker 误解任务意图
否定约束显式化 写明不做什么(如"不删除 src/ 下现有模块") Worker 过度执行
文件范围精确化 files_dirs 精确到文件级,不写 src/ 目录级 Worker 越界修改
完成标准可验证 done_when 能用 grep/diff/cmake --build 客观验证 Worker 无法判定完成

AirArc 在生成 execution-plan.json 时自动扫描所有 TODO 任务,检测危险词("清理"、"删除所有"、"重构整个"等)和目录级文件范围,产出 safetyWarnings 列表。

7.4 成本结构的反转

传统模式下,规划和执行都由同一高能力模型完成:

传统: 每个任务都需要昂贵模型(因为需要完整项目上下文 + 探索 + 规划 + 执行)
      成本 = N × 昂贵模型单价

范围约束: 规划一次(昂贵模型),执行 N 次(廉价模型)
          成本 = 规划费用 + N × 廉价模型单价

当 N 较大且廉价模型单价为昂贵模型的 1/10 时,边际成本降低约一个数量级。

7.5 约束边界与质量的关系

约束越严格,执行者的搜索空间越小,偏离预期的可能性越低:

约束类型 约束内容 防止的问题
写集约束 只能修改预声明的文件 越界修改导致回归
验收约束 必须满足 Done When 条件 不完整交付
验证约束 必须运行预声明的验证命令 遗漏测试
文档约束 必须更新预声明的架构文档 架构腐化

这些约束将执行者的行动空间从"修改仓库中的任何文件"收窄到"修改这 3 个文件并满足这 2 个条件"——搜索空间缩小约两个数量级。


八、长期工程迭代管理原理

8.1 状态持久化与会话连续性

AI Agent 时代,执行者每次可能是不同的模型实例。项目状态不能依赖会话内存——必须外化到磁盘文件

  • 项目目录包含完整状态:规划文档、架构记录、执行状态、调试历史、修复记录
  • 任何新会话从磁盘文件恢复,获得与上一会话完全一致的项目认知
  • 会话中断不丢失任何进度——所有状态变更即时写入磁盘

8.2 波次递进与增量交付

任务按依赖关系组织为波次(wave)。每个波次完成后自动触发下一波次。已完成任务的文档更新在合并时即时应用到项目文档——后续波次的执行者看到的是包含所有前序成果的最新上下文

增量交付的保证:第 N 波次的所有产出在第 N+1 波次启动前已合并到项目文档和架构记录中。

8.3 动态图调度替代静态表格(原理,V2 新增)

V1 的调度基于静态 todo.md 表格——AirArc 产出表格,AirEng 基于表格调度。当需求变更时 Arc 重新生成表格,Eng 无法增量吸收差异,需多轮 AI 迭代才能恢复调度。

原理层面的要求:调度结构必须是一个活的有向无环图(DAG),而非静态表格。它需要具备四项核心能力:

  • 增量吸收:重规划只更新变化的部分,已调度任务不受影响
  • 全量替换时保留完成态:避免已完成任务被重新调度
  • 图差异计算:新旧 DAG 对比产出精确的变更集(PlanDelta)
  • 就绪计算:返回入度为 0 且未开始的节点,调度冻结时返回空

这四项能力共同支撑**"需求变更是非破坏性的"**这一工程承诺——用户在执行中途修改任务表,系统能够增量吸收而非推倒重来。

TaskGraph 的具体数据结构(TaskNode 含 adr_refs/test_required/write_set)、PlanDelta 的 added/removed/modified 结构、apply_delta 的实现细节见第二十章 § 20.3。

8.4 范围变更的非破坏性

用户可以在执行中途修改任务表(添加、修改、取消任务)。V2 的 TaskGraph 使这一过程变为增量操作:

  1. 用户修改 todo.md
  2. AirEng 检测到 todo.md mtime > task-graph.json mtime
  3. 自动触发 incremental_replan:全量重建新 DAG → diff 旧 DAG → 产出 PlanDelta
  4. apply_delta() 增量更新,保留已调度任务的 DISPATCHED/DONE 状态
  5. 新任务自动进入后续波次调度

8.5 回归防护机制

  • 状态过滤:已完成任务不参与重新调度(ready_tasks() 只返回 status == "TODO"
  • 分组追踪:已完成的波次不会被重复派发
  • 合并验证:结果必须包含实质产出才能标记为完成
  • 文档强制:涉及全局文档的任务必须提交架构文档更新
  • 证据强制:GUI 任务必须有截图证据才能关闭
  • TaskGraph 状态同步(V2):merge 后 Phase 6.5 自动同步 task-graph.json 节点 status,防止重复派发已完成任务

8.6 跨模型、跨设备、跨时间的连续性

所有状态都是纯文件(JSON、Markdown),可通过版本控制或文件同步在多个维度实现连续性:

  • 跨模型:不同模型实例读取同一套制品,获得一致的项目认知
  • 跨设备:不同物理设备通过远程访问同一状态目录
  • 跨时间:任意时间点中断,从文件恢复完整执行历史

九、工具扩展与自动化原理

9.1 从语言模型到工程平台

LLM 本身不具备工具能力,但通过 CLI 工具注册、MCP 协议桥接、Skill 封装等机制,可以将其扩展为具备完整工程能力的平台。关键设计原则:

  • 工具注册与路径声明:显式注册工具路径,避免 Agent 在执行时重复发现或误用
  • 持久记忆:通过结构化文档(AGENTS.md、ADR、plan.md)为 Agent 提供跨会话记忆

9.2 重复的事情应该被自动化

如果一件事要重复五次,那么它应该被自动化

在以前,自动化涉及开发,是一件成本很高的事情,但 AI 发展后的现在,自动化的难度已经被极大的降低了,如果一件事你至少要重复五次,那为什么不拿出 2-3 次的时间把它自动化,然后省下几次的时间去做其他更重要的事?

AI 工程迭代路径恰好与以前工业时代的一句话对应:

复杂的事情简单化
简单的事情标准化
标准的事情自动化
自动的事情智能化


十、L1 代码级保障原理(V2 新增)

10.1 从"建议性"到"强制性"的范式跃迁

V1 的许多关键约束(证据先于修复、AirDbg 路由、AirArc 只读)仅通过 SKILL.md 的自然语言指令传达——本质上是建议性约束,依赖 LLM 的"自觉"遵守。V1 真实项目数据证明了这一范式的失效:

约束 V1 表达方式 实际违规率 根因
AirDo 调用 AirDbg SKILL.md 建议 频繁跳过 Worker 倾向直接返回
AirArc 不写代码 SKILL.md 声明 被 plan mode 劫持 Agent 框架覆盖
AirEng 自主推进 SKILL.md 期望 反复询问用户 无强制决策指令
AirDbg 先取证 7 步工作流 不取证就改代码 步骤可跳过

V2 的核心设计原则:凡是造成过实际损失的约束,必须从自然语言建议升级为 L1 代码级保障——即通过 Python 代码的门控逻辑、工具白名单、数据结构约束来硬性执行。

10.2 五种 L1 保障机制(原理层枚举)

L1 代码级保障体系在五个层面叠加防御,每一层针对不同类型的违规模式:

层面 针对的违规模式 硬化方式
① 工具白名单 Agent 越权操作(如 AirArc 写代码) 命令文件 frontmatter 声明
② Python 门控函数 跳步执行(如未取证就改代码) 运行时返回值强制
③ 数据结构约束 数据不合法(如 task_id 路径注入) 契约层校验
④ 强制路由链 跳过协作环节(如 AirDo 不调 AirDbg) finish_worker 强制派发
⑤ 原子操作 + 并发控制 状态损坏(如并发写竞态) 基础设施层保证

五层叠加后,任何一层失守都不会直接造成事故——其余层仍能阻断违规。这是纵深防御在 AI 工程中的体现。

每一层的具体代码实现(allowed-tools frontmatter、ArcPhaseGate/EvidenceFirstGate、WorkerResult.validate_for_finalize、finish_worker 6 级路由链、atomic_json_write + FileLock)见第二十章 § 20.4。

10.3 指令操作化:消除 Agent 推理歧义(原理)

V1 的命令文件使用意图描述(如"读取派发清单,为每个任务 spawn 隔离的 Worker 子代理"),Agent 需要多轮推理才能翻译成具体操作:用什么工具?参数格式?task-text 从哪取?猜错就多一轮,猜不出来就回退自己执行。

原理层面的要求:关键操作路径必须从意图描述升级为可执行伪代码——给出确切的工具名、参数结构、执行顺序、并发约束。Agent 不再需要推理,只需要按步骤执行

这背后的原则是:人类读意图,机器读指令。SKILL.md 同时服务于人类理解("为什么要派发子代理")和 Agent 执行("用什么工具、什么参数派发子代理"),但这两个目标对表达精度的要求完全不同。V2 的做法是在人类可读的意图描述之后,紧跟一份机器可执行的操作步骤——两套表达服务于两类读者,互不替代。

具体操作化示例(如 AirEng 派发 Worker 的 Agent 工具调用步骤、AirDo 路由链的 finish_worker 伪代码)见第二十章 § 20.5。

10.4 前置条件注入:在派发点强制补齐缺失制品(原理)

很多工作流约束失败,不是因为下游 Agent 不够聪明,而是因为上游在错误的前提条件下启动了它。例如:Scheduler 的运行前提本应是 plan.mdtask-graph.json 已存在;如果这个前提只靠 Main Agent "记得先做架构设计",那么一旦它漏掉一步,整个后续调度都会在错误世界里开始。

原理层面的要求:关键前置条件不能只写在文档里,而要在派发点由系统主动检查和补齐。

  • 当上游试图直接派发 Scheduler 时,运行时先检查 .air/shared/plan/plan.mdtask-graph.json 是否存在
  • 如果缺失,不是让 Scheduler 自己"发现后再说",而是系统在派发前直接改写/注入指令,强制先派发 Architect 生成规划
  • 下游 Agent 看到的永远是"前置条件已满足"的世界,而不是带缺口的半成品上下文

这条原则很重要,因为它把"先做架构设计"从流程约定升级成了入口门控。约束不再依赖 Agent 的记忆,而是依赖系统在工作流接缝处的主动校验。

10.5 自由文本也必须进入协议:把 Agent 输出转化为可审计信号(原理)

结构化字段(如 status=completed)只能表达"Agent 自称完成",却不能表达它是如何完成的。真实工程里,很多违规恰恰藏在自由文本里:例如 Worker 一边写着 completed,一边说"for now 先这样";Reviewer 一边给 PASS,一边整份报告都只在说"build 通过、测试通过、函数存在"。

原理层面的要求:凡是会参与关闭任务、放行结果的自由文本,都必须被视作协议的一部分,进入机器可检查的门控链路。

  • Worker 输出不仅要有状态字段,还必须包含编译 / 测试 / cppcheck 证据,且不得出现降级关键词
  • Reviewer 报告不仅要给 verdict,还必须包含 Code-to-Design 逐行对照表,不能只凭"表面证据"判定 PASS
  • 调度器读取的不只是结构化结果,还要读取 output_text 片段,把文本中的软违规纳入状态机判断

这背后的设计思想是:自然语言不是日志附属物,而是可被滥用的接口面。一旦把它纳入协议,系统就能拦住那些"字段合法、语义违规"的软逃逸行为。


第二部分:实践——Air 插件套件 V2 与 AirCoding Alpha


十一、V2 架构总览

11.1 V1→V2 核心命题

V1 证明了制品驱动 + 上下文隔离 + 波次并行的架构方向成立。V2 要解决三个系统性问题:

  1. 可靠性:状态写入不丢失,并发操作不竞态,崩溃后可自愈
  2. 可观测性:所有引擎操作可追溯,指标可导出,异常主动通知
  3. 智能化:证据门控感知任务类型,轮询频率自适应,修复模式可学习

补充:AirCoding V1.0.0 Alpha 的当前完成态(2026-07)

AirCoding 已经不再只是"下一步想做什么"的路线图。到 V1.0.0 Alpha / 0.1.0 release 这个时间点,它已经完成了首个公开可用闭环并开源。但它的落地路径并不是"完整自研运行时已经成熟",而是更克制也更现实的一条路线:基于 OpenCode fork 的最小改造,把多 Agent 调度层、权限矩阵和关键门控内嵌进宿主运行时

当前 alpha 已实装的关键能力:

  • 5 类 Agent 已代码注册:Main / Scheduler / Worker / Architect / Reviewer 都已在运行时注册,不再只是文档里的角色想象
  • 权限矩阵已代码化:Scheduler 无写权限、Architect 仅可写 .air/shared/plan/**、Worker 无 task 权限,这些边界由代码控制而非 Prompt 自觉
  • 确定性调度器已落地coordinator_tick 已承担 task-graph.json 的 DAG 就绪计算、状态迁移、重试预算、里程碑审查预算、scheduler-state.json 实时落盘
  • 关键门控已进入 hook / tool 层:派发 Scheduler 前强制检查 plan.md + task-graph.json;Worker 缺少 cppcheck 或输出降级关键词会被打回;Reviewer 缺少 Code-to-Design 对照表或只凭表面证据判 PASS 会被强制重审
  • 最小工程闭环已成立:架构产物、任务图、调度状态、调试记录都已有明确目录约定,系统已具备可恢复、可审计、可追踪的最小工程能力

当前 alpha 仍未完全到位的部分:

  • 仍受宿主框架约束:当前主实现仍主要复用 OpenCode 的 Agent、Session、BackgroundJob、Plugin Hook 和 Tool Registry,而不是完整自研 EventBus + NDJSON IPC 运行时
  • 理想形态仍在后续路线:语言无关运行时、经验学习/记忆层、独立事件存储、动态权限切换等更完整的设计,仍属于后续演进目标

因此,对 AirCoding Alpha 最准确的表述不是"只有 shell 雏形",也不是"完整独立运行时已完成",而是:它已经完成了一版可公开使用、可公开审视的工程化 Alpha,用宿主内嵌的方式验证了关键约束能否从插件层继续推进到 Agent 框架层。

11.2 统一插件架构

V1 由 8 个独立插件组成,各自有独立的安装、注册和运行时。V2 将 8 个插件统一为 1 个插件(airplan-v2)12 种模式

模式 对应 V1 插件 V2 核心改进
/arc AirArc 三阶段门控、plan mode 阻断、工具白名单只读、弱模型安全审计、DAG 产出、边界测试注入
/eng AirEng 中文锁定、自主决策、ScheduleWakeup 轮询、调度职责边界、事务化合并、ADR 级联失效、worktree 并行
/do AirDo 全专家插件强制路由、UI 任务 frontend-design Skill、task_id 注入防护
/dbg AirDbg EvidenceFirstGate 先读后写门控、步骤追踪不可跳过、修复前 git snapshot、选择性快照
/xdb AirXDB DRM/KMS 原生截图、Xvfb headless CI、多后端自动降级
/ndb AirNDB TLS 解密、pcapng 支持
/sdb AirSDB 六语言后端(cppcheck/clang-tidy/clippy/go-vet/tsc/mypy)、diff 模式
/ctx AirContext 压缩质量校验、自适应 Token 估算、陈旧锁检测、三级降级压缩
/dep 新增 SSH 远程构建 + scp + MD5 校验 + systemd 生命周期 + 冒烟验证
/tst 新增 统一测试执行(pytest/googletest/jest/go test/cargo test)+ 结构化报告
/sec 新增 制品敏感数据扫描 + 白名单 + advisory/blocking 模式
/rvr 新增 需求一致性审查 + Code-to-Design 对照 + 高风险审计 + verdict 控制合并

11.3 流水线拓扑

  ┌──────────┐     ┌──────────┐     ┌──────────┐     ┌──────────┐
  │  /arc    │────►│  /eng    │────►│  /do     │────►│  /dbg    │
  │ (规划)   │     │ (调度)   │     │ (执行)   │     │ (调试)   │
  └──────────┘     └──────────┘     └──────────┘     └────┬─────┘
       │                │                │                  │
       │  task-graph    │  Agent 子代理   │ finish 路由链    │
       │  + plan-delta  │  run_in_bg     │                  │
       │                │                ├──────────────────┤
       │                │                ▼                  ▼
       │                │          ┌──────────┐       ┌──────────┐
       │                │          │  /xdb    │       │  /ndb    │
       │                │          │(GUI证据) │       │(网络证据)│
       │                │          └──────────┘       └──────────┘
       │                │                │                  │
       │                │                ▼                  ▼
       │                │          ┌──────────┐       ┌──────────┐
       │                │          │  /sdb    │       │  /rvr    │
       │                │          │(静态分析)│       │(需求审查)│
       │                │          └──────────┘       └──────────┘
       │                │                                   │
       │                │     ┌──────────────┐              │
       │                │     │    /dep      │              │
       │                │     │   (部署)     │              │
       │                │     └──────────────┘              │
       │                │     ┌──────────────┐              │
       │                │     │    /tst      │              │
       │                │     │   (测试)     │              │
       │                │     └──────────────┘              │
       │                │     ┌──────────────┐              │
       │                │     │    /sec      │              │
       │                │     │ (安全扫描)   │              │
       │                │     └──────────────┘              │
       │                │                                   │
       │                └───────────────────────────────────┘
       │                          │
       │                    ┌──────────┐
       └───────────────────►│  /ctx    │
                            │(上下文)  │
                            └──────────┘

关键变化:V1 的 AirDo 只路由到 AirDbg/AirXDB。V2 的 /do 在 finish 时执行全专家插件强制路由链——根据任务类型和状态,依次路由到 /dbg、/xdb、/ndb、/sdb、/rvr,无强制路由时才允许 merge。

11.4 基于制品的通信协议(V2 扩展)

AirPlan/
├── AGENTS.md                              # 项目级 AI 上下文(多模式标记块共管)
├── plan.md                                # 总体执行计划
├── todo.md                                # 结构化任务表(人可读,DAG 的辅助视图)
├── docs/
│   ├── architecture/
│   │   ├── adr/ADR-NNNN-*.md             # 架构决策记录
│   │   └── c4/module.md                  # C4 模块边界文档
│   ├── debug/
│   │   ├── debug-log.md / gui-debug-log.md
│   │   └── airxdb-artifacts/
│   ├── network/
│   │   ├── airndb-log.md
│   │   └── airndb-captures/
│   ├── reviews/
│   │   └── {task_id}-review.md           # V2: AirRvr 审查报告
│   └── staticanalysis.md
└── state/
    ├── airarc/reviews/
    │   ├── execution-plan.json
    │   ├── parallel-review.json
    │   ├── task-graph.json                # V2: 动态 DAG(调度权威来源)
    │   └── plan-delta.json                # V2: 增量重规划差异
    ├── aireng/
    │   ├── state.json / plans/
    │   ├── dispatch/{wave-id}.json
    │   ├── archive/{task-id}-{ts}.json    # V2: 已合并结果归档
    │   └── repairs/{task-id}/{repair-id}/
    ├── airdo/tasks/{task-id}/
    │   ├── brief.md / subagent-handoff.md
    │   ├── result.json / worker-state.json
    ├── airdbg/{state,sessions,snapshots}/ # V2: 新增 snapshots 目录
    ├── airxdb/{state,requests,sessions}/
    ├── airndb/
    ├── airsdb/reports/
    ├── airdep/sessions/                   # V2: 部署会话
    ├── airtst/reports/                    # V2: 测试报告
    ├── airrvr/reviews/                    # V2: 审查报告
    ├── airsec/                            # V2: 安全扫描
    ├── aircontext/                        # V2: 上下文管理
    └── events.jsonl                       # V2: 事件日志(完整时间线)

V2 新增 events.jsonl——结构化事件日志(JSONL 格式),与 state.json 互补:state.json 是当前快照,事件日志是完整时间线。事件类型覆盖全生命周期:

事件类型 触发时机 负载信息
task.dispatched Eng 派发任务 taskId, waveId
task.entered Worker 进入 taskId, uiRouting
task.finished Worker 完成 taskId, status, routingTargets
task.completed 合并成功 taskId, archivePath
task.blocked 任务阻塞 taskId, status
merge.started / merge.completed 合并开始/完成 taskId, appliedDocCount
intervention.stall 停滞检测 taskId
worker.timeout Worker 超时 taskId, ageSeconds
eng.replan.triggered 增量重规划 added, removed, modified
adr.change.detected ADR 变更检测 adrId, kind
adr.invalidation ADR 级联失效 adrId, invalidatedCompleted, cascadedDownstream
worktree.merge.conflict Worktree 合并冲突 taskId, action
context.compacted 上下文压缩 compressionLevel, tokens

十二、核心实现详解

12.1 调度算法:从静态表格到动态 DAG

V1 的静态表格调度

V1 的 AirArc 产出 todo.md 表格,AirEng 基于表格解析任务、构建依赖边、波次分组。当需求变更时 Arc 全量重新生成表格,Eng 无法增量吸收,需多轮 AI 迭代恢复。

V2 的 DAG 调度

V2 的 AirArc 同时产出 task-graph.json(动态 DAG)和 todo.md(人可读辅助视图)。调度逻辑从 DAG 计算而非表格解析:

输入: todo.md + task-graph.json

1. 构建 DAG → TaskGraph (TaskNode + Edge)
2. 注入边界测试任务 → _inject_boundary_tests()
   - 按 files_dirs 推断模块(取第一级目录作为模块名)
   - 每个模块创建接口测试 + 单元测试任务
   - 实现任务 → 测试任务建立依赖边
3. 依赖边构建 → review.py build_parallel_review()
4. 波次调度 (拓扑排序):
   ready_tasks() → 入度 = 0 且 status = TODO 的任务
   调度冻结时返回空列表
5. 区域冲突检测 → RegionConflictDetector
   NONE: 直接并行
   SOFT: worktree 隔离并行
   HARD: 强制串行
6. 产出 execution-plan.json + task-graph.json

增量重规划(需求变更时):

1. todo.md mtime > task-graph.json mtime → 触发 maybe_replan()
2. 全量重建新 DAG → new_graph.diff(old_graph) → PlanDelta
3. old_graph.apply_delta(delta) → 保留已调度任务的 DISPATCHED/DONE 状态
4. 写回 task-graph.json + plan-delta.json
5. emit ARC_REPLANNED 事件

12.2 全链路上下文隔离

AirEng 派发 /do Worker 时使用 Agent 工具(run_in_background: true),每个子 Agent 拥有独立上下文,天然满足 fork_context=false

V2 的 spawn_workers() 标准化了派发流程:

def spawn_workers(project_root, task_ids) -> list[dict]:
    """为每个 ready 任务准备 Agent 派发指令。
    返回 Agent 调用参数列表,Eng Agent 遍历列表逐个调用。"""
    for tid in task_ids:
        node = graph.nodes.get(tid)
        instructions.append({
            "description": f"Do Worker: {tid}",
            "subagent_type": "general-purpose",
            "run_in_background": True,  # 关键:后台运行,Eng 不阻塞
            "prompt": f"你是 AirDo Worker,任务 ID: {tid}...\n"
                      f"## 任务\n{task_text}\n"
                      f"## 文件范围\n{files}\n"
                      f"## 完成标准\n{done_when}\n"
                      f"## 工作流程\n1. 初始化 Worker 状态\n"
                      f"2. 读取项目文件\n3. 实现任务需求\n"
                      f"4. 运行 finish 命令\n",
        })

传递的信息(5K-20K token):任务描述 + 文件范围 + 完成标准 + 6 个必读文件路径 + 10 条执行契约。
不传递的信息:调度器 200K 对话历史、其他 Worker 状态、引擎内部 state。

信噪比提升约一个数量级。

12.3 全专家插件强制路由链

V1 的 AirDo finish 时只有两条路由(GUI 关键词 → AirXDB,blocked → AirDbg),且为建议性而非强制。V2 将路由升级为 6 级强制链

finish_worker() 路由决策(按优先级):

┌─ 1. blocked / failed → 强制 AirDbg ────────────── (最高优先级)
│    "AirDbg mandatory before return"
│
├─ 2. done 但无 validations + 无 filesChanged → 强制 AirDbg
│    "done without evidence — mandatory debug review"
│
├─ 3. GUI 任务(关键词命中)且无 xdbSessions → 强制 AirXDB
│    "GUI task requires screenshot evidence"
│
├─ 4. 网络任务(关键词命中)且无 ndbSessions → 强制 AirNDB
│    "network task requires packet capture evidence"
│
├─ 5. C/C++ 文件变更(.cpp/.h/.hpp)且无 sdbReports → 强制 AirSDB
│    "C/C++ task requires static analysis"
│
├─ 6. 所有 done 任务且无 rvrReviews → 强制 AirRvr
│    "completed task requires requirements review"
│
└─ 无强制路由触发 → merge ──────────────────────── (最低优先级)

返回 routingDecisions 列表(可能有多个路由目标),Worker 依次处理后重新 finish。路由决策由 Python 代码生成,不依赖 LLM 判断——即使 LLM 尝试跳过,代码层仍然强制执行

12.4 事务化合并流水线

V1 的 merge_worker_result() 执行 8+ 次文件写入,中间崩溃导致不一致。V2 引入事务语义的 6 阶段合并流水线

merge_worker_result(project_root, result_path):
  state_lock = FileLock(state.json)
  todo_lock  = FileLock(todo.md)

  with state_lock:
    ┌─ Phase 1: 验证 ──────────────────────────────────────┐
    │  enforce_doc_sync_requirements(result)                │
    │  - deployRequired → 必须有 deploy 验证                │
    │  - documentUpdates 路径必须在 AirPlan/ 内             │
    │  失败 → 抛 ValueError,不触碰文件系统                  │
    ├─ Phase 1.5: Rvr 审查(可选)─────────────────────────┤
    │  reviewPolicy.requireBeforeMerge 或 result.requireReview │
    │  verdict=fail → 阻止合并                              │
    │  verdict=conditional-pass → 记录遗留项但允许合并       │
    ├─ Phase 2: 归档 ──────────────────────────────────────┤
    │  archive/{task_id}-{timestamp}.json                   │
    │  原子写入,可重试                                      │
    ├─ Phase 3: 应用文档更新 ──────────────────────────────┤
    │  apply_document_updates(result.documentUpdates)       │
    │  write / append 两种动作                               │
    ├─ Phase 4: 同步引擎管理文档 ──────────────────────────┤
    │  sync_engine_managed_docs(plan.md, debug-log.md, ...) │
    │  去重:检查 taskId 标记行是否已存在                     │
    ├─ Phase 5: 更新 todo(嵌套 FileLock)────────────────┤
    │  update_todo_after_merge()                            │
    │  动态定位 Status 列(不硬编码列索引)                   │
    │  附加 <!-- merged:path --> 引用便于追溯                │
    ├─ Phase 6: 更新引擎状态 ──────────────────────────────┤
    │  state.json 原子写入                                   │
    │  mergedResults 截断至 100 条(防止无界增长)            │
    │  移除 activeWorkers 中已完成的任务                     │
    ├─ Phase 6.5: TaskGraph 状态同步 ─────────────────────┤
    │  task-graph.json 节点 status → DONE                   │
    │  防止下次 dispatch 重复派发已完成任务                   │
    └──────────────────────────────────────────────────────┘

  emit MERGE_COMPLETED + TASK_COMPLETED / TASK_BLOCKED

12.5 AirArc 三阶段门控

V1 中 AirArc 频繁被 Agent 内置 plan mode 劫持,且在用户仅说一两句时就立即生成执行计划。V2 从工具层和代码层双重阻断:

工具层(命令文件 frontmatter)

allowed-tools: "[Read, Glob, Grep]"  # 只有只读工具
deny-plan-mode: true                  # 硬性阻断 plan mode

代码层(ArcPhaseGate)

三阶段流程(不可跳过):

Phase 1: discussing(默认)
  - 与用户反复讨论需求细节、边界条件、隐含约束
  - 主动提问澄清模糊点
  - 分析现有代码库结构
  - 提出多种架构方案及优劣对比
  - execution-plan.json 写入被禁止

Phase 2: proposing
  - 向用户呈现推荐架构方案
  - 明确等待确认:"请确认此架构方案是否符合预期"
  - 用户有异议 → 回到 Phase 1
  - execution-plan.json 写入被禁止

Phase 3: confirmed
  - 仅在用户说"确认"/"可以"/"同意"后自动推进
  - 允许生成 execution-plan.json 和 task-graph.json
  - 规划产出严格对应用户确认的架构方案

parallel_review_mode() 在写入前检查 gate.can_write_plan(),phase 不是 confirmed 则返回 {"blocked": true, "reason": "arc phase is 'discussing'..."}

12.6 AirDbg 先读后写门控

V1 的 AirDbg 7 步工作流为建议性——模型经常跳过取证直接修改代码,引入新问题且污染代码库。V2 通过 EvidenceFirstGate 硬性执行:

class EvidenceFirstGate:
    EVIDENCE_TYPES = [
        "screenshot",        # AirXDB 截图
        "packet_capture",    # AirNDB 抓包
        "static_analysis",   # AirSDB 静态分析
        "log_analysis",      # 日志分析
        "code_trace",        # 代码追踪(读取相关文件、调用链分析)
        "reproduction",      # 复现步骤执行
    ]

    def can_modify_code(self) -> bool:
        return len(self._collected_evidence) > 0

    def gate_check(self) -> None:
        if not self.can_modify_code():
            raise WorkflowViolation(
                "未执行任何取证行为,禁止修改代码。")

步骤追踪机制:

步骤 名称 推进条件 特殊规则
1 confirm_symptoms 提供 symptom/expected/actual 取证步骤,计入 collectedEvidence
2 load_context 无强制证据 取证步骤,计入 collectedEvidence
3 reproduce 提供 reproduction_steps 可跳过(标记为 non-reproducible)
4 locate_root_cause 提供 root_cause_analysis 取证步骤,计入 collectedEvidence
5 fix 提供 fix_description + files_changed 硬性门控:collectedEvidence 非空
6 verify 提供 validation_result 同类证据验证
7 close_out 提供 residual_risk + adr_updates 更新项目文档

修复前快照:pre_fix_snapshot() 在步骤 5 执行前自动创建 git tag 回滚点。V2 改进为选择性快照——只提交 Worker result 中声明的 filesChanged 范围内的文件,避免全量 commit 混入无关变更。

12.7 Worktree 隔离并行(同文件不同区域)

V1 的冲突检测粒度为文件级。实际场景中,同一文件的不同区域可能互不影响(如 Qt 组件样式 vs 状态机逻辑),被迫串行降低了并行效率。

V2 引入三级冲突检测 + git worktree 隔离

RegionConflictDetector.detect():

  file_overlap = set(task_a.write_set) & set(task_b.write_set)
  if not file_overlap → NONE(直接并行)

  if 无区域信息 → SOFT(worktree 隔离并行)

  for fpath in file_overlap:
    ra = regions_a[fpath]  # [(start_line, end_line), ...]
    rb = regions_b[fpath]
    if 行号区间重叠 → HARD(必须串行)
    else → SOFT(worktree 隔离并行)

WorktreeIsolation 生命周期:

1. create_worktree(task_id, base_ref="HEAD")
   → git worktree add -b air-{task_id} {wt_path} HEAD
   → Worker 在独立 worktree 目录中执行

2. merge_back(task_id, wt_path)
   → git merge --no-ff air-{task_id}
   → 成功: cleanup(task_id) → git worktree remove + branch -D
   → 失败: _abort_merge() → 返回 Conflict 列表

3. 合并失败时的三级降级:
   → 升级到 AirDbg(调试冲突)
   → AirDbg 也失败 → 降级为串行重执行
   → emit WORKTREE_MERGE_CONFLICT 事件

Eng 的 monitor_engine() 在每轮轮询中自动检查 .git/worktrees/air-* 目录,处理已完成但未 merge 的 worktree。

12.8 AirEng 调度引擎 V2

角色边界硬性约束

V2 从 SKILL.md 和代码层双重约束 AirEng 的职责边界:

核心职责:调度,不是编码

默认禁止:编写源代码、修改项目文件

极端接管(唯一例外,全部条件满足才允许):
  1. 子代理陷入循环阻塞,修复预算已耗尽
  2. 问题已通过 AirDbg 定位到明确的根因
  3. 修复范围极小(≤5 行改动)
  4. 继续等待 Worker 重派发已无意义
  → 进入前必须记录 EXTREME_TAKEOVER 日志
  → 即使接管也必须调用相关专家插件(Dbg/XDB/NDB/SDB/Rvr)

监控循环 V2

monitor_engine():
  1. 遍历 activeWorkers:
     a. Worker 存活时间 > 2 小时 → wall-time-exceeded → terminate
     b. state 文件 mtime > 5 分钟 → stalled → re-dispatch-or-block
     c. status = done → ready_to_merge
  2. 资源压力检测: loadavg > 2× CPU 数 → 暂停派发
  3. ADR 变更检测: ADRWatcher.detect_changes()
     → superseded/modified → handle_adr_invalidation()
  4. Worktree 合并检查:
     → 已完成但未 merge 的 worktree → check_worktree_merge_status()
     → merge 失败 → 升级到 AirDbg → 再失败 → 降级串行
  5. emit ENGINE_CYCLE 事件(stalledCount, readyToMerge, interventionCount)

派发决策链

dispatch_worker_group():
  1. maybe_replan() — 检查 todo.md mtime vs task-graph.json mtime
     → todo 更新 → 触发增量重规划
  2. 检查调度冻结(dispatch_frozen = true → 返回 blocked)
  3. 检查 block-release verdict(AirRvr 终审 → 阻止所有派发)
  4. _select_ready_tasks() — 从 DAG 计算入度为 0 的 TODO 任务
     → DAG 中 ready 为空时不 fallback 到 todo.md(空列表也是正确答案)
  5. 区域冲突检测(多任务时)
     → HARD 冲突 → 强制串行,只派第一个
     → SOFT 冲突 → 标记 worktree 隔离
  6. 写 dispatch payload → emit TASK_DISPATCHED

12.9 AirRvr 需求审查器(V2 新增)

V1 中任务"完成"的判定仅依赖 Worker 自报 + AirEng 结构验证。没有任何组件将交付物与原始需求进行独立比对。AirRvr 填补了这一空白。

多维度审查

审查维度 检查内容 产出
需求覆盖度 原始需求中的每个要求点是否被交付物覆盖 coverage: [{requirement, status, evidence}]
意图一致性 交付物是否解决了需求想解决的真正问题 intentAlignment: aligned / divergent
回归风险 变更是否破坏了需求的已有功能 regressionRisk: none / low / medium / high
代码质量 复杂度、可读性、重复率、异常处理 codeQuality: {complexity, readability, ...}
生命周期健壮性 资源释放、连接管理、超时/重试/降级 lifecycleHealth: {resourceLeak, ...}
运行时稳定性 内存泄漏、竞态条件、崩溃路径 runtimeStability: {crashRisk, ...}
Code-to-Design 代码实现与设计文档逐行对照 codeToDesignTable: [{designRef, codeLocation, status}]
日志标准 spdlog 集成、非标准日志、debug/release 开关 loggingChecks: {spdlogIntegrated, ...}
高风险审计 生命周期/空指针/悬垂指针/异常安全/并发 highRiskAudit: {lifecycle, nullPointer, ...}

高风险审计五项检查(里程碑审查时强制执行):

生命周期风险:
  - 资源申请与释放是否配对(new/delete, malloc/free, open/close)
  - RAII 是否覆盖所有资源持有
  - 异步操作的回调/完成是否保证执行

空指针/悬垂指针:
  - 指针使用前是否判空
  - 智能指针生命周期是否覆盖使用范围
  - 回调闭包中捕获的指针是否仍然有效
  - 容器元素删除后迭代器是否失效

异常安全:
  - 异常路径中资源是否正确释放
  - 是否存在异常吞没(catch 后无处理)
  - 跨模块边界是否有异常传播保护

并发风险:
  - 共享状态是否有锁保护
  - 锁顺序是否一致(防死锁)
  - 条件变量是否有虚假唤醒保护

verdict 控制合并

verdict 行为 集成点
pass 正常合并 merge Phase 1.5
conditional-pass 合并但记录 residualItems state.json
fail 阻止合并,要求修订 merge 抛 ValueError
deliveryVerdict = block-release 阻止所有后续派发 dispatch_worker_group()

三种审查模式:

模式 触发时机 审查范围
per-task 单个任务完成后(/do finish 自动路由) 单任务
per-wave 一个波次所有任务完成后 整波次
per-milestone 项目阶段结束时 全量(比对 requirements.md)

12.10 AirDep 部署器(V2 新增)

V1 无部署插件,导致"完成但未部署"事故(T-028b 发现 4 个 "done" 任务未实际部署,延迟发布一整天)。AirDep 提供标准化的部署流水线:

deploy() 完整流程:

  Step 1: 远程构建(可选)
    SSH → cd {build_dir} && {build_cmd}
    超时 600s

  Step 2: 二进制传输 + MD5 校验
    scp local_binary → remote:/tmp/
    local_md5 = md5_file(local)
    remote_md5 = SSH md5sum remote
    不匹配 → 返回失败 "md5 mismatch after transfer"

  Step 3: 部署二进制
    SSH mv /tmp/{binary} → {deploy_dir}/

  Step 4: systemd 生命周期
    SSH systemctl daemon-reload
    SSH systemctl restart {service_name}
    SSH systemctl is-active {service_name}
    返回 service_status

  Step 5: 冒烟验证(可选)
    SSH {smoke_test_cmd}
    记录 smoke_test_passed

  Step 6: 持久化
    DeploymentRecord → state/airdep/sessions/
    emit DEPLOY_COMPLETED 事件

与合并流水线集成:deployRequired=true 时,enforce_doc_sync_requirements() 验证 result 中必须包含 remote-deploy-verifyremote-binary-md5 类型的 validation。

12.11 AirTst 测试运行器(V2 新增)

统一测试执行接口,支持 5 种框架:

框架 命令 解析方式
pytest python -m pytest --json-report -q JSON summary
GoogleTest/CTest ctest --output-on-failure 文本 + JSON 双解析
jest/vitest npx jest --json JSON testResults
go test go test -json ./... JSONL 事件流
cargo test cargo test -- --format=json JSONL 事件流

产出结构化 TestRunResult{framework, total, passed, failed, disabled, duration, failures}

与 AirArc 集成:规划阶段自动注入边界测试任务(T-TEST-001 等),标记 test_required=true,Done When 强制包含"测试通过"。

12.12 AirSec 安全扫描器(V2 新增)

扫描制品中的敏感数据,防止 API 密钥、令牌、密码泄露到项目文档:

SECRET_PATTERNS (6 种):
  - api_key:     api_key = "..."
  - aws_key:     AKIA...
  - private_key: -----BEGIN RSA PRIVATE KEY-----
  - token:       token = "..."
  - jwt:         eyJ...
  - url_credential: 603K9s2c8@1M7s2y4Q4x3@1q4Q4x3V1k6Q4x3V1k6#2M7$3g2J5i4K6y4m8M7r3q4K6M7%4N6G2M7X3c8Q4y4o6m8Q4x3X3g2Q4x3X3g2Q4x3X3f1`.

三层过滤:
  1. 内容模式匹配 → 原始发现
  2. 允许列表过滤(EXAMPLE, YOUR_API_KEY, placeholder 等)
  3. 文件名白名单过滤(.example., test_, mock_, _test.py, .fixture.)

两种运行模式:
  - advisory: 只报告,不阻止合并
  - blocking: 发现敏感数据时阻止合并(merge Phase 1 检查 clean=false)

12.13 AirContext V2 改进

压缩质量校验

MUST_PRESERVE_PATTERNS = [
    r"[A-Za-z0-9_\-/]+\.(py|ts|js|cpp|h|md|json|yaml)",  # 文件路径
    r"ADR-\d{4}",                                          # ADR 引用
    r"TODO|FIXME|HACK",                                    # 未完成项
    r"INV-\d+",                                            # 不变量引用
]

校验逻辑:对比原始文本和摘要中各模式的匹配集合,丢失 > 30% 则标记为失败。失败触发三级降级:

降级级别 策略 适用场景
RETRY 重新压缩(换 prompt) 首次失败
FALLBACK_MODEL 换模型 + 简化 prompt + 放宽 token 限制 重试失败
TRUNCATE 激进截断(保留最近 50 行 + 所有 ADR 引用行) 最终兜底

陈旧锁检测

def acquire_compactor_lock(lock_path):
    try:
        fd = os.open(lock_path, O_CREAT | O_EXCL | O_WRONLY)
        os.write(fd, str(os.getpid()))
        return True
    except FileExistsError:
        pid = int(lock_path.read_text())
        os.kill(pid, 0)  # 不发信号,只检查进程存在
        → 进程存活 → 返回 False(锁有效)
        → 进程不存在 → 删除陈旧锁 → 重试

12.14 AirSDB V2 多语言静态分析

V1 仅支持 Cppcheck + C/C++。V2 扩展为 6 种后端:

后端 语言 工具
Cppcheck C/C++ cppcheck --check-level=exhaustive
Clang-Tidy C/C++ clang-tidy
Clippy Rust cargo clippy
go vet Go go vet + staticcheck
tsc TypeScript tsc --noEmit
mypy + ruff Python mypy + ruff

新增 diff 模式:比较两次扫描结果,高亮新增/消除的 finding。通过 (file, line, rule_id) 三元组匹配,产出 DiffReport(new_findings, resolved_findings, unchanged_count)

12.15 AirXDB V2 扩展截图能力

V1 仅支持通用桌面截图。V2 扩展为多后端自动降级:

后端 适用场景 技术实现
KMS grab 嵌入式 DRM/KMS 显示 ffmpeg -f kmsgrab -i /dev/dri/card0
Xvfb CI headless 环境 Xvfb :99 + xwd -root
fallback 通用桌面环境 Midscene.js / Playwright

--prefer auto 时按 kms → xvfb → fallback 顺序自动检测。


十三、基础设施层

13.1 原子 I/O(消除 V1 数据损坏)

V1 使用 path.write_text() 直接覆盖 JSON 文件——进程崩溃时 state.json 截断,下次加载 JSONDecodeError。V2 的 atomic_json_write()

写入流程:
  1. 旧文件 → os.replace(path, path.bak)  # 单级轮转备份
  2. tempfile.mkstemp(dir=path.parent)     # 同目录临时文件
  3. os.write(fd, json_data)               # 写入临时文件
  4. os.close(fd)
  5. os.replace(tmp, path)                 # POSIX 原子替换

安全加载:
  1. json.loads(path.read_text())          # 正常加载
  2. JSONDecodeError → 尝试 .bak 恢复      # 自动从备份恢复
  3. .bak 不存在 → 返回 None + 日志告警     # 不静默吞异常

13.2 文件锁(消除 V1 并发竞态)

V1 无任何锁、互斥量或原子操作。两个 Worker 同时完成时 todo.md 读-改-写竞态。V2 的 FileLock

class FileLock:
    """基于 fcntl.flock 的进程级文件锁"""
    def __enter__(self):
        self._fd = os.open(path, O_CREAT | O_RDWR)
        while True:
            fcntl.flock(self._fd, LOCK_EX | LOCK_NB)  # 非阻塞获取
            → 成功 → return self
            → 超时 → raise TimeoutError
            → 等待 0.1s 重试

    def __exit__(self):
        fcntl.flock(self._fd, LOCK_UN)
        os.close(self._fd)

所有 state.jsontodo.md 的读-改-写操作必须持有对应锁。合并流水线中嵌套两层锁(state_lock + todo_lock),保证跨文件一致性。

13.3 公共工具层(消除 V1 代码重复)

V1 中 _json_dump 5 份、_ordered_unique 4 份、policy normalization 3 份、marker block upsert 2 份、_session_stamp 格式不一致。V2 统一为 air_runtime/utils.py

函数 消除的重复 功能
ordered_unique() 4 份 保序去重,支持字符串和字典列表
session_stamp() 格式不一致 统一文件系统安全时间戳
now_iso() 多处 ISO 格式 UTC 时间戳
normalize_policy() 3 份 通用策略合并,类型自动转换
sanitize_task_id() 路径注入风险 正则校验 [A-Za-z0-9_\-\.]+
sanitize_marker() HTML 注入风险 拒绝 --><!--
truncate_history() 无界增长 截断至 max_items(默认 100)

13.4 air_runtime 模块结构

air_runtime/
  __init__.py
  contracts.py         # 数据契约(WorkerResult, TaskRecord, DeploymentRecord)
  io.py                # 原子 I/O(替代 5 份 _json_dump)
  lock.py              # 文件锁(fcntl.flock)
  utils.py             # 公共工具(消除重复代码)
  events.py            # 事件日志(JSONL + 轮转截断)
  task_graph.py        # 动态任务依赖图(DAG + PlanDelta + ADR 级联失效)
  adr_watcher.py       # ADR 文件变更监控(SHA256 hash 对比)
  worktree.py          # git worktree 隔离并行(区域冲突检测)
  partial_replanner.py # 局部重规划(仅受影响任务子集)
  evidence_gate.py     # 任务类型感知证据门控
  paths.py             # 路径约定
  todo_parser.py       # TODO 解析(动态列索引)
  review.py            # 并行审查(依赖环检测、写集冲突)
  project_bootstrap.py # 项目引导(幂等创建 17 个制品)
  installer.py         # 安装器(动态路径解析 + 安装后验证)
  deploy_runtime.py    # AirDep 运行时
  test_runtime.py      # AirTst 运行时(5 框架解析器)
  sec_runtime.py       # AirSec 运行时(6 模式 + 3 层过滤)
  review_runtime.py    # AirRvr 运行时(审查报告 + 高风险审计)
  sdb_backends.py      # AirSDB 多后端
  xdb_capture.py       # AirXDB 多后端截图
  modes/
    arc_mode.py        # AirArc 模式(三阶段门控 + DAG 构建 + 弱模型安全)
    eng_mode.py        # AirEng 模式(调度引擎 + 事务化合并 + ADR 级联)
    eng_orchestrator.py # AirEng 编排器
    do_mode.py         # AirDo 模式(全专家路由链 + UI 检测)
    dbg_mode.py        # AirDbg 模式(7 步追踪 + 先读后写 + 快照)
    merge_pipeline.py  # 合并管线(6 阶段纯函数集合)
    xdb_mode.py        # AirXDB 模式
    sdb_mode.py        # AirSDB 模式
    ndb_mode.py        # AirNDB 模式
    ctx_mode.py        # AirContext 模式(三级降级 + 质量校验)
    dep_mode.py        # AirDep 模式
    tst_mode.py        # AirTst 模式
    sec_mode.py        # AirSec 模式
    rvr_mode.py        # AirRvr 模式

十四、架构状态持久化机制

14.1 标记块命名空间:多模式共管同一文件

AirPlan/AGENTS.mdAirPlan/docs/architecture/c4/module.md 被所有模式共同维护,通过两层标记块命名空间避免互相覆盖:

模式层(各模式独立维护):

标记块 所有者 内容
<!-- AIRARC:BEGIN/END --> /arc 架构规划工作流指令
<!-- AIRENG:BEGIN/END --> /eng 调度引擎工作流指令
<!-- AIRDO:BEGIN/END --> /do 任务执行器工作流指令
<!-- AIRDBG:BEGIN/END --> /dbg 调试工作流指令
<!-- AIRXDB:BEGIN/END --> /xdb GUI 证据采集工作流
<!-- AIRNDB:BEGIN/END --> /ndb 网络证据采集工作流
<!-- AIRSDB:BEGIN/END --> /sdb 静态分析工作流

引擎层(merge_pipeline.py 在每次合并时自动更新):

标记块 所在文件 自动写入内容
<!-- AIR-ENGINE:AGENTS-SYNC:BEGIN/END --> AGENTS.md 最新合并任务的完整审计记录
<!-- AIR-ENGINE:C4-SYNC:BEGIN/END --> c4/module.md 最新合并对模块边界的影响
<!-- AIR-ENGINE:TODO-RUN-LOG:BEGIN/END --> todo.md 累积合并日志

14.2 合并去重(V2 修复 P3-1)

V1 中 AGENTS.md 持续膨胀——同一任务记录重复 2-3 次。V2 的 sync_engine_managed_docs() 在追加标记行前检查是否已存在:

# 去重:若该 taskId 的标记行已存在,则不再追加
if any(line.lstrip().startswith(marker_prefix) for line in existing.splitlines()):
    continue

同样,update_todo_after_merge() 在更新行内 <!-- merged:... --> 引用前先剥离已有引用:

cleaned = _strip_merged_refs(line)  # 去除行内所有已存在的 merged 引用

十五、复杂项目长期迭代管理

15.1 任务生命周期与状态管理

V2 的任务生命周期扩展了 INVALIDATED 状态(ADR 级联失效):

TaskGraph 节点状态:
  TODO ──(调度)──→ DISPATCHED ──(合并成功)──→ DONE
                       │                        │
                       └──(合并失败)──→ BLOCKED   │
                                            │    │
  DONE/DISPATCHED ──(ADR变更)──→ INVALIDATED ◄───┘

Worker 状态:
  entered → implementing → finished → archived

引擎状态:
  idle → planning → dispatching → monitoring → merging → completed | blocked

修复状态:
  queued → active → resolved | queued(预算内重试)

ADR 失效流程:
  ADR superseded → dispatch_frozen → INVALIDATED → git revert → Arc replan → unfreeze

15.2 修复预算与自动重试

当任务返回 blocked 或验证失败时,系统自动创建修复尝试:

执行 → blocked/failed
  → ensure_repair_attempts_for_result()
    → 创建 RepairAttempt
    → 写入 attempt.json(完整失败上下文)
    → 写入 repair-brief.md(修复指引)
    → 重新派发 Worker
      → done: 修复成功 → resolved
      → blocked: 预算未耗尽 → 再试
      → 预算耗尽 → 升级到用户

V2 配置:repairPolicy.maxAttempts = 3

15.3 停滞检测与干预

V2 的停滞检测增加了 Worker 超时和资源压力维度:

检测类型 条件 动作
文件停滞 state 文件 mtime > 300s re-dispatch-or-block
存活超时 Worker 存活 > 7200s terminate-and-block
资源压力 loadavg > 2× CPU 数 暂停派发
Worktree 冲突 merge_back 失败 upgraded-to-airdbg → downgraded-to-serial
ADR 变更 SHA256 hash 变化 invalidate-by-adr

15.4 文档级联:前序任务如何影响后续任务

Wave 1 (T-001, T-002) 完成并合并
  → todo.md: T-001 DONE, T-002 DONE
  → task-graph.json: 节点 status 同步为 DONE(Phase 6.5)
  → ADR/C4/plan.md: 文档更新已应用
  → AGENTS.md: AGENTS-SYNC 块已刷新(去重后)
  → events.jsonl: MERGE_COMPLETED + TASK_COMPLETED 事件已记录

Wave 2 (T-003, T-004) 派发
  → Worker 读取 Required Reads (6 个文件)
  → 看到的是已包含 Wave 1 产出的最新文档
  → Worker 无需与 Wave 1 的 Worker 通信
  → 自动获得前序工作的全部上下文
  → AirRvr 审查时可引用 Wave 1 的审查报告

十六、多模型交叉审计实践

16.1 AirCoding V1.0.0 Alpha 交叉审计

4 个模型对 146 个源文件独立审计,产出 18+ 份报告:

模型 评级 发现数 阻断级 审计角度
DeepSeek B+ 97 10 任务完成度
Opus 4.8 C+ 140+ 18 逐字段对照规范
MiniMax-M3 C+ 38+ 18 可执行性 + 治理
Qwen3.7-Max D+ 84 31 需求覆盖 + 规范一致性%

评级分歧根因:DeepSeek 以"123/123 文件创建"为主轴 → B+;其余三模型以"与冻结规范的语义一致性"为主轴 → C+/D+。Meta 裁决:文件存在 ≠ 语义正确,综合评级 C。

16.2 4 轮递进审查(系统详细设计)

轮次 模型 重点 评分
1 DeepSeek 基线覆盖性全量核对 9.6/10
2 MIMO 2.5 Pro 内在一致性 + 架构合理性 9.4/10
3 GPT-5.5 Pro 基线间冲突检测 Requires repair
4 Opus 4.8 前轮验证 + 根因分析 9.1/10

16.3 三视角审查(概要设计)

视角 模型 独有发现
架构师 MIMO 2.5 Pro 模块边界、依赖方向
开发者 DeepSeek V4 Pro 接口完整性、测试覆盖
用户 Opus 4.7 原始 UX 需求未进入 plan/todo(其他视角不可见)

十七、配套工程实践

实践 方案 解决的问题
air_runtime 共享库 36 模块 ~6,000 行 12 模式核心逻辑去重
统一插件安装器 动态路径解析 + 安装后自动验证 安装后插件不可用
sub2api 多账号整合 代理层整合多个 Codex Plus 账号 5x PLUS 无中断长任务执行
New API 多模型路由 one-api 分支的统一 API 代理 多模型交叉审计的异构 API 聚合
CC-Switch 本地代理 本地供应商管理与故障转移 供应商可用性保障
ScheduleWakeup 系统级定时唤醒替代 Agent 自觉轮询 Agent 遗忘轮询导致无限等待
Hook 自动化 Agent Hook 机制 项目打开前自动 git pull 等

十八、V1→V2 演进:从真实损失到系统性修复

18.1 P0 缺陷修复清单(已造成实际损失)

V1 缺陷 实际影响 V2 修复方案 保障层级
AirXDB 假阳性阻塞 11+ 任务触发虚假修复循环 EvidenceGatePolicy 任务类型感知 L1 代码
部署验证缺口 4 个 "done" 任务未实际部署 deployRequired + deploy 验证强制 L1 契约
非原子写入 state.json 截断致 JSONDecodeError atomic_json_write (tempfile + os.replace) L1 基础设施
零并发控制 todo.md 读-改-写竞态 FileLock (fcntl.flock) L1 基础设施
AirArc 被 plan mode 劫持 架构器偏离规划职责 allowed-tools 只读 + deny-plan-mode L1 工具
AirEng 停下来问不自主决策 调度流程反复中断 SKILL.md 中文锁定 + 自主决策指令 L1 指令
AirEng 无状态轮询 子线程卡死后无限等待 ScheduleWakeup + 硬编码监控循环 L1 指令+代码
AirDo 不调用 AirDbg 直接报 blocked 或 false-done finish_worker 强制路由链 L1 代码
安装器路径错误 安装后插件无法识别 动态路径解析 + post_install_verify L1 代码
AirEng 偏离调度写代码 破坏隔离架构 极端接管条件 + 工具权限分层 L1 指令+代码

18.2 P1 缺陷修复清单(限制可靠性)

V1 缺陷 V2 修复方案
硬编码开发者路径 路径约定模块 paths.py
_json_dump 5 份重复 air_runtime/io.py 统一
_ordered_unique 4 份重复 air_runtime/utils.py 统一
todo.md 列索引硬编码 动态列定位(已知状态词搜索)
并发度上限硬编码为 3 state.concurrency 可配置
子进程无超时 所有 subprocess.run 加 timeout
task_id 路径注入 sanitize_task_id() 正则校验
标记注入风险 sanitize_marker() 拒绝注释分隔符
静默吞异常 日志告警 + safe_json_load .bak 恢复
Arc 重规划后 Eng 无法衔接 TaskGraph + PlanDelta 增量吸收
同文件无冲突任务被迫串行 RegionConflictDetector + WorktreeIsolation
AirArc 跳过需求探讨 ArcPhaseGate 三阶段门控
AirDbg 未取证就改代码 EvidenceFirstGate 先读后写门控
项目缺乏标准化日志 AirArc 强制 spdlog + AirRvr 检查
边界无测试 + 终审缺高风险检查 _inject_boundary_tests + HighRiskAudit
UI 任务无专业 Skill frontend-design Skill 自动安装 + 强制路由
ADR 变更无级联失效 ADRWatcher + invalidate_by_adr + 10 步闭环
Dispatch → Worker 断链 spawn_workers + 指令操作化伪代码
Dispatch 指令歧义 可执行步骤替代意图描述
Merge 后 TaskGraph 不同步 Phase 6.5 自动同步节点 status

18.3 V2 度量目标

指标 V1 基线 V2 目标
AirXDB 假阳性率 ~60%(11/18 任务) < 5%
状态文件损坏率 已知发生 0%(原子写入 + .bak 恢复)
部署一致性事故 1 次关键事故 0 次(deployRequired 强制)
空壳修复循环 11+ 次 0 次(证据门控 + 强制路由)
代码重复度 _json_dump 5 份 每函数 1 份
AirArc plan 模式劫持 频繁发生 0 次(工具白名单硬阻断)
AirEng 轮询遗忘 频繁发生 0 次(ScheduleWakeup)
AirDo 跳过 AirDbg 频繁发生 0 次(强制路由链)
AirDbg 未取证就改代码 频繁发生 0 次(EvidenceFirstGate)
需求变更后调度恢复 多轮 AI 迭代 < 1 次(增量 delta 吸收)
同文件无冲突任务串行率 100% 串行 < 20%(worktree 并行)
ADR 变更后旧代码残留 无自动清理 0 次(级联失效 + git revert)
Dispatch → Worker 断链 Agent 回退自己写代码 0 次(spawn_workers + 操作化指令)
Merge 后重复派发 已完成任务再次 dispatch 0 次(Phase 6.5 同步)

十九、演变史:从 Prompt 插件到代码级 Agent

Air 插件套件的架构不是一次设计出来的——它经历了 9 个阶段、多次生产事故驱动的迭代,才从 3 个纯 Markdown 指令插件演化为具备代码级保障的统一调度平台。这条演变路径本身就是 AI Agent 工程化的一个缩影:每一次架构跃迁都源于一次真实的失败

19.1 时间线总览

2026 Q1 初    01 三个 Codex CLI 工作流插件(AirArc + AirDo + AirDbg)
              │  纯 Markdown 指令,无代码执行,人工串联
              ▼
2026 Q1 中    02 AirDbg 不好用 → 增加 AirXDB(GUI 截图)+ AirNDB(网络抓包)
              │  "证据"概念萌芽,但仍靠 SKILL.md 建议
              ▼
2026 Q1 末    03 增加 AirSDB(静态分析)→ 6 插件 + 统一安装器 = 第一代插件包
              │  证据三件套(截图/抓包/静态分析)齐全
              ▼
2026 Q1-Q2   04 优化插件包 → 第一代手动插件包的生产版本
              │  打磨 SKILL.md 指令、修复安装器、完善模板
              ▼
2026 Q2 初    05 上下文爆炸 → AirContext(Hook + 外部 LLM 压缩 + JSONL DAG)
              │  上下文管理从"不管"变成"必须管"2026 Q2 中    06 插件多了、文件多了、太慢 → AirPlan-Para(air_runtime 共享库 + 表格调度)
              │  架构跃迁:从"独立插件集合""有共享引擎的调度系统"2026 Q2 末    07 多个版本迭代 → AirPlan-ParaV2(稳定并发版本)
              │  修复并发 bug、稳定 air_runtime ~4,500 行
              ▼
2026 Q3 初    08 中途需求变更 + LLM 不按预期执行 → AirPlan V2(统一插件 + 12 模式)
              │  三个周末重写:8 插件合 1、DAG 动态调度、L1 代码级保障
              ▼
2026 Q3 中    09 碰撞到 Plugin 边界 → AirCoding(独立 Agent,Fork OpenCode)【Alpha 已完成并开源】
                 从"插件""宿主内嵌调度层":在 OpenCode 内注册 Agent、coordinator 工具与 plugin hook,把工具白名单、状态机与审查门控落到代码;独立运行时仍是下一阶段目标

19.2 阶段 01:三个工作流插件(起源)

组件:AirArc(架构规划)、AirDo(任务执行)、AirDbg(调试)

架构:三个独立的 Codex CLI 插件,每个由 SKILL.md(自然语言指令)+ 命令文件(.md 入口)+ Python 引导脚本 + plugin.json 清单组成。

核心设计决策(贯穿至今):

  • AirPlan/ 目录约定:plan.md、todo.md、docs/、state/ 的目录结构在此阶段就已确立
  • AGENTS.md + ADR + C4 三件套:项目认知通过结构化文档外化,不依赖特定会话
  • 7 步调试工作流:confirm → load → reproduce → locate → fix → verify → close 的流程在第一天就存在

控制方式:100% Markdown 指令。SKILL.md 告诉 AI "你应该这样做",AI 是否遵守完全取决于模型的自觉性。

驱动下一阶段的问题

  • AirDbg 的调试质量差——没有证据支撑就猜测修复,引入更多 bug
  • 没有跨插件协调——AirArc 规划完需要人工切换到 AirDo,AirDo 完成后需要人工切换到 AirDbg
  • GUI 问题无法验证——嵌入式设备上跑的应用,"进程存在"不等于"界面渲染正确"
  • 上下文全在一起运行十分钟直接1M爆满

19.3 阶段 02:增加图形和网络取证

新增:AirXDB(GUI 截图取证)、AirNDB(网络抓包取证)

关键概念萌芽证据——不同类型的问题需要不同类型的直接证据。

AirXDB 基于 Midscene.js,支持 Playwright(Web 应用)、Chrome Bridge(Chrome 扩展)、Desktop(桌面应用)、MCP(协议桥接)四种模式。支持远程设备截图(SSH → 远程执行 → base64 传输 → 本地解码)。

AirNDB 基于 tcpdump/WinDump,支持 BPF 过滤器、定时捕获、远程 SSH 抓包。

学到的教训

"证据"这个概念看似简单,但它是整个 Air 体系的基石。没有证据约束的 AI 调试器,和一个随机修改代码的脚本没有区别。AirDbg 在没有截图的情况下"修复"了 GUI 问题,结果引入 3 个新 bug——因为它修复的是自己猜测的原因,而不是实际的问题。

驱动下一阶段的问题

  • C/C++ 代码质量问题——仅靠调试和截图无法覆盖内存泄漏、空指针等静态缺陷

19.4 阶段 03:静态分析 + 第一代插件包

新增:AirSDB(Cppcheck 静态分析)+ 统一安装器 + manifest.json

AirSDB 的亮点是跨平台自动安装——自动检测系统包管理器(winget/choco/scoop/apt/dnf/yum/apk/pacman/brew),下载安装 cppcheck,支持本地和远程 SSH 扫描,产出 XML 报告解析为 JSON。

统一安装器install_air_suite.py)将 6 个插件打包部署:

  • 复制插件到用户目录
  • 同步 skills 到 .agents/skills/
  • 更新 marketplace.json
  • 支持 --verify-only--dry-run--plugins 过滤

证据三件套成型

证据类型 插件 适用场景
GUI 截图 AirXDB 界面渲染、布局、交互验证
网络抓包 AirNDB RTSP/HTTP/TCP 协议调试
静态分析 AirSDB C/C++ 内存安全、代码质量

驱动下一阶段的问题

  • 6 个插件的 SKILL.md 指令打磨不均匀,有些插件的执行质量明显低于其他
  • 安装器在不同系统上路径解析不一致
  • 人工串联插件的效率瓶颈——一个完整的开发流程需要在 AirArc → AirDo → AirDbg → AirXDB 之间反复切换

19.5 阶段 04:第一代手动插件包(生产版本)

这是阶段 03 的打磨版——相同的 6 插件架构,但每个插件的 SKILL.md 指令经过多轮优化,安装器路径问题修复,文档模板标准化。

关键改进

  • AirArc 增加了工作分类(分析/设计/重构/执行),产出 requirements.md → solution-architecture.md → C4 → ADR → plan.md → todo.md 的完整链路
  • AirDo 增加了 plan.md 和 todo.md 的读取,按顺序执行任务
  • AirDbg 增加了与 AirXDB/AirNDB/AirSDB 的协作指令

学到的教训

Markdown 指令优化存在天花板。无论 SKILL.md 写得多详细、多精确,AI 仍然会偶尔偏离——跳过步骤、忘记调用协作插件、在不该修改代码时修改代码。这不是模型质量问题,而是控制方式的根本局限:自然语言指令是建议性的,不是强制性的。

驱动下一阶段的问题

  • 长会话中上下文窗口爆炸——对话到后期,AI 对早期架构决策的记忆出现幻觉

19.6 阶段 05:上下文爆炸 → AirContext

问题:AI Agent 执行复杂开发任务时,对话历史快速膨胀。一轮完整的开发流程(读代码 → 搜索 → 修改 → 测试 → 调试)就可以产生 50K-100K token 的上下文。当接近模型的上下文窗口上限时,AI 框架的内置自动压缩(auto-compact)会粗暴截断,丢失关键的架构决策和未完成工作项。

解决方案:AirContextServer——一个独立的上下文管理插件,替代框架的内置压缩。

架构

┌────────────────────────────────────────────────┐
│  Wrapper (bin/aircontext)                       │
│  包装 claude CLI,劫持启动和恢复流程              │
├────────────────────────────────────────────────┤
│  4 个 Hook:                                     │
│  SessionStart → 验证配置                         │
│  UserPromptSubmit → 配置无效时阻止 prompt         │
│  PostToolUse → 估算 token,超阈值触发压缩         │
│  PreCompact → 阻止框架内置自动压缩                │
├────────────────────────────────────────────────┤
│  Compactor 后台进程:                             │
│  1. 获取 compactor.lock(O_CREAT | O_EXCL)      │
│  2. 从 JSONL 文件加载消息链(DAG 遍历)           │
│  3. 切分:head(送入压缩)| tail(逐字保留 10 条) │
│  4. 序列化 head → 纯文本(丢弃 thinking blocks)  │
│  5. 调用外部 LLM + rules.md 规则 → 压缩摘要      │
│  6. 写入 JSONL:summary (parentUuid=null) +       │
│     continuation prompt → 形成新链根              │
│  7. SIGTERM → claude --resume → 加载压缩上下文    │
└────────────────────────────────────────────────┘

关键设计创新

  • parentUuid=null 技巧:摘要消息的 parentUuid 设为 null,在 JSONL DAG 中创建一个新的"孤岛"根节点。后续消息从摘要开始形成新链,旧消息变为不可达的死链。claude --resume 加载时只遍历到新链,获得一个"干净"的起点
  • 外部 LLM 压缩:不使用会话自身的模型做压缩——避免"自己压缩自己"的认知偏差。压缩模型只看序列化的文本,不了解对话历史,产出更客观的摘要
  • 三级信息保留策略:永久保留(最后 10 条)→ 高优先级(文件路径、ADR、TODO)→ 低优先级(搜索结果、完成确认)

学到的教训

上下文管理不是"锦上添花"——它是 AI Agent 长时间运行的生存前提。没有上下文压缩,一个 200K token 窗口的模型在 3-4 小时的开发任务中就会耗尽空间。而框架内置的压缩策略太粗暴,无法区分"架构决策"和"一次性搜索结果"的价值差异。

驱动下一阶段的问题

  • 6 个插件串行执行太慢——一个包含 20 个任务的项目,每个任务 15 分钟,串行需要 5 小时
  • 插件之间的协调全靠人工——AirArc 规划完后需要人工启动 Airdo,Airdo后需要人工启动 Airdbg

19.7 阶段 06:AirPlan-Para(架构跃迁——共享引擎)

这是整个演变史中最关键的架构跃迁——从"独立插件集合"到"有共享引擎的调度系统"。

新增核心组件lib/air_runtime/(~3,700 行共享 Python 运行时库)

air_runtime/
  contracts.py    (~618 行)  结构化数据契约
  engine.py       (~500 行)  调度引擎
  worker.py       (~373 行)  Worker 生命周期
  review.py       (~239 行)  DAG 并行审查
  todo_parser.py  (~161 行)  Markdown 表格解析
  doc_sync.py     (~351 行)  文档同步
  debug_runtime.py (~414 行) 自动调试
  airxdb_runtime.py (~818 行) 自动 XDB
  repair_runtime.py (~374 行) 自动修复
  paths.py                  路径约定

三个划时代的设计决策

① 结构化数据契约替代 Markdown 通信

V1 之前,插件之间通过 Markdown 文件传递信息——AirArc 产出 todo.md,AirDo 读取 todo.md。但 todo.md 是给人看的,不是给机器解析的。contracts.py 引入了 TaskSpecWorkerResultValidationRecordDocumentUpdate 等类型化数据结构:

class WorkerResult:
    task_id: str
    status: str  # done | blocked | failed
    files_changed: list[str]
    validations: list[ValidationRecord]
    document_updates: list[DocumentUpdate]

这意味着:引擎可以程序化地验证 Worker 的产出,而不是靠 AI 阅读 Markdown 来判断。

② DAG 依赖感知的并行调度

review.pybuild_parallel_review() 实现了第一版并行调度算法:

1. 解析 todo.md → TaskRecord 列表
2. 构建依赖边([deps: T-xxx] 标注)
3. 拓扑排序 → 波次分组
4. 贪心并行分组:每个任务放入第一个无写集冲突的组
5. 冲突检测:写集重叠的任务强制串行

③ 隔离 Worker 子代理

engine.pydispatch_worker_group() 为每个任务创建独立的 AirDo 子代理,传递 fork_context=false——子代理不继承调度器的对话历史,只获得 brief.md 和 handoff.md。这是上下文隔离原则的第一次代码实现。

学到的教训

并行执行的正确性取决于冲突检测的完备性。第一版上线后,两个任务同时修改同一个 CMakeLists.txt,后完成的覆盖了先完成的——产出需要人工修复 3 个文件,效率反而低于串行。这证明了"朴素并行"在有写集冲突时是反效率的。

驱动下一阶段的问题

  • 并发不稳定——偶尔出现状态文件损坏(非原子写入)
  • AirXDB 假阳性率 ~60%——非 GUI 任务也被要求提供截图
  • 引擎的 5 分钟轮询依赖 AI "自觉执行",经常遗忘

19.8 阶段 07:AirPlan-ParaV2(稳定并发版本)

经过多个版本的迭代修复,air_runtime 稳定在 ~4,500 行。这一阶段主要修复了:

  • 并发竞态:引入基础的锁机制,防止两个 Worker 同时完成时的 todo.md 读-改-写冲突
  • AirXDB 误触发:增加了基础的关键词过滤(但仍不够精确,假阳性率仍高)
  • 修复预算maxAttemptsPerTask = 2,防止无限修复循环
  • 引擎状态持久化:state.json 包含完整的运行时状态,崩溃后可恢复

学到的教训

并发系统的可靠性不是一步到位的——它需要在真实负载下反复暴露问题、反复修复。AirPlan-Para 经历了 3 个小版本才达到"稳定可用"状态。每次版本迭代都伴随着一次 state.json 损坏或 todo.md 竞态的事故报告。

驱动下一阶段的问题(V2 设计文档中的 P0/P1 缺陷清单):

  • 非原子写入导致 state.json 截断 → JSONDecodeError
  • AirArc 被 Agent 框架的 plan mode 劫持
  • AirEng 停下来问用户而不是自主决策
  • AirDo 跳过 AirDbg 直接返回 blocked
  • AirDbg 不取证就改代码
  • 中途需求变更后调度需多轮 AI 迭代恢复
  • 同文件无冲突任务被迫串行

19.9 阶段 08:AirPlan V2

这是从"建议性约束"到"代码级保障"的范式跃迁。花费三个周末,将 8 个分散插件重构整合为 1 个统一插件 12 种模式,重写了整个调度引擎。

核心动机:V1(阶段 06-07)证明了制品驱动 + 上下文隔离 + 波次并行的架构方向成立,但所有关键约束都停留在 SKILL.md 的自然语言层面——AI 可以选择遵守,也可以选择忽略。真实项目数据(DecodePlayer 系列、AirCoding V1.0.0 Alpha)证明这种"建议性约束"不够。

V2 的哲学转变

V1: "你应该在修改代码前进行取证"     → AI 可以跳过
V2: can_modify_code() == False      → 代码层面不允许

V1: "AirArc 不应该写代码"            → AI 可以被 plan mode 劫持
V2: allowed-tools: [Read, Glob, Grep] → Agent 框架层面没有写工具

V1: "AirDo 应该调用 AirDbg"          → AI 可以直接返回 blocked
V2: finish_worker() 返回 routing      → 代码层面必须经过 AirDbg

V1: "调度器应该每 5 分钟轮询"         → AI 可以忘记
V2: ScheduleWakeup(delaySeconds: 300) → 系统级定时唤醒

8 合 1 的工程价值

V1(8 个独立插件) V2(1 个统一插件 12 模式)
每个插件独立安装、注册、版本 一次安装,12 个模式全部可用
插件间通信靠文件 + 人工切换 统一的 air_runtime 库 + 自动路由链
每个插件维护自己的 _json_dump 统一的 atomic_json_write
SKILL.md 约束不跨插件 L1 代码级保障覆盖全链路
静态 todo.md 表格调度 动态 TaskGraph DAG 调度

新增的 4 个模式

模式 填补的空白
/dep(AirDep) V1 无部署 → "完成但未部署"事故
/tst(AirTst) V1 无统一测试 → 边界无测试覆盖
/sec(AirSec) V1 无安全扫描 → 制品敏感数据泄露风险
/rvr(AirRvr) V1 无需求审查 → 交付物偏离需求无人检出

19.10 阶段 09:AirCoding——碰撞到 Plugin 边界并完成 Alpha

核心发现:当 Air 插件套件在 Claude Code CLI 上运行时,无论 V2 的 L1 代码级保障做得多好,有一个层面始终无法控制——Agent 框架本身的行为

具体表现:

  • Agent 框架的 plan mode 可以覆盖 SKILL.md 的角色指令(AirArc 被劫持)
  • Agent 框架的 auto-compact hook成 AirContext 并不稳定
  • Agent 框架的 allowed-tools 是 per-command 而非 per-context 的,无法在一个 Agent 内动态切换工具权限
  • Agent 框架不保证"自觉执行"的循环(轮询遗忘)

结论插件范式有天花板。你可以在插件层做代码级保障,但你无法控制宿主 Agent 框架的行为。当宿主框架的行为与你的工程约束冲突时,你只能二选一:要么忍受宿主框架的限制,要么拥有自己的运行时。

当前状态:AirCoding 现在已经不是"只剩路线图"的原型了。Alpha 版本已经完成首个公开可用闭环并开源,但它的实现形态也需要准确描述:它并不是"完整自研运行时已成型",而是基于 OpenCode v1.17.4 fork 的最小改造,通过 Agent 注册、Tool Registry、coordinator 工具、Plugin Hook 和权限矩阵,把 V2 里验证过的关键约束直接植入宿主运行时。

Alpha 已经落地的能力

  • Main / Scheduler / Worker / Architect / Reviewer 五类 Agent 已进入运行时注册表,不再只是文档角色
  • 子 Agent 的工具边界已由代码级权限矩阵硬控,例如 Scheduler 无 Write/Edit/Bash,Architect 只能写 .air/shared/plan/**
  • coordinator_tick 已承担最小确定性调度闭环:读取 task-graph.json、做 DAG ready 计算、处理状态迁移、执行 retry / milestone budget,并把状态实时写入 scheduler-state.json
  • Worker 的 cppcheck 强制、降级关键词扫描,Reviewer 的 Code-to-Design 对照表检查、表面证据 PASS 拦截,已经进入 hook / tool 层,而非只靠 Prompt 自觉
  • .air/shared/plan/*.air/local/* 的目录分层已成型,架构认知、执行状态和调试记录开始有了稳定的文件落点

当前仍未完成的部分

  • 目前主要复用 OpenCode 的 Session / BackgroundJob / Plugin Hook / Tool Registry,而不是完整自研的 EventBus + NDJSON IPC runtime
  • 更理想的语言无关运行时、持久事件总线、学习记忆层、动态权限切换等能力,仍处于后续演进目标
  • 宿主框架的约束仍然存在,因此这版 Alpha 更准确的定义是:把关键工程约束嵌进宿主框架的一次成功验证,而不是独立运行时的终点

这个阶段的意义已经从"勾勒边界"前进到"验证路线":它不再只是告诉我们插件范式的边界在哪里,而是进一步证明了一个更重要的判断——要想让关键约束可靠生效,必须把它们推进到宿主运行时层,而不能永远停留在插件层的自然语言约定里。

19.11 演变史的核心规律

回顾 9 个阶段,可以提炼出三条贯穿始终的演变规律:

规律一:控制方式的硬化

阶段 01-05:  自然语言指令(SKILL.md)         → "请遵守这个规则"
阶段 06-07:  运行时检查(Python 函数返回值)    → "不遵守就报错"
阶段 08:     代码级门控(工具白名单 + 数据契约) → "不遵守就阻断"
阶段 09:     架构级不可能(运行时所有权)        → "不可能违反"(方向已定,仍在原型阶段)

每次硬化都由一次真实失败驱动:AirDbg 不取证就改代码 → EvidenceFirstGate;AirArc 被 plan mode 劫持 → deny-plan-mode;AirEng 忘记轮询 → ScheduleWakeup;Agent 框架覆盖插件行为 → Fork 拥有自己的运行时。

规律二:问题驱动而非设计驱动

没有任何一个架构决策是"提前设计好的"——它们都是问题暴露后的被迫应对

暴露的问题 驱动的架构决策
AirDbg 盲改代码引入 bug 证据先于修复原则(阶段 02)
长会话上下文爆炸 AirContext 透明压缩(阶段 05)
串行执行太慢 DAG 并行调度(阶段 06)
朴素并行写集覆盖 写集冲突检测 + 波次分组(阶段 06)
非原子写入导致状态损坏 atomic_json_write + .bak 恢复(阶段 08)
两个 Worker 同时完成竞态 FileLock (fcntl.flock)(阶段 08)
需求变更后调度无法恢复 TaskGraph DAG + PlanDelta(阶段 08)
ADR 变更后旧代码残留 ADR 级联失效 + git revert(阶段 08)
Agent 框架覆盖插件行为 Fork OpenCode + 宿主内嵌调度层(阶段 09,Alpha 已完成并开源)

规律三:可检查性的坚持

从阶段 01 到阶段 09,无论架构如何变化,有一条线始终未断:所有中间状态都是人类可读文件

  • 阶段 01-07:AirPlan/ 目录树(Markdown + JSON)
  • 阶段 08:events.jsonl 补充了完整时间线
  • 阶段 09:继续坚持纯文件状态(plan.md / task-graph.json / scheduler-state.json),同时把调度逻辑和门控逻辑推进到宿主运行时;独立 EventBus / 持久事件流仍是后续目标

这意味着:即使在最复杂的并行调度场景中,开发者随时可以 cat task-graph.jsoncat scheduler-state.json,或在需要时 tail events.jsonl 了解系统的精确状态。没有二进制数据库、没有私有格式、没有需要特殊工具才能解读的状态。

可检查性是信任的前提——如果你无法观察一个系统的内部状态,你就无法信任它的决策。对于 AI Agent 这样的非确定性系统,这一原则的价值比任何算法优化都大。


二十、原理篇实现细节补充

本章集中承载第一部分(原理篇)各章交叉引用过来的实现细节。每一条都可追溯到原理篇的具体小节,避免原理与实践混杂。

20.1 架构状态同步的合并流水线(对应 6.4)

每次任务合并时,merge_pipeline.py 按 6 个阶段顺序执行——任一阶段失败则整个合并回滚:

  1. Phase 1 — enforce_doc_sync_requirements:验证 Worker 是否提交了所要求的架构文档更新;deploy_required 的任务必须有远程部署验证;路径必须落在项目根目录内
  2. Phase 2 — apply_document_updates:将 Worker 提交的 DocumentUpdate 应用到 ADR、C4、AGENTS.md 等项目文档
  3. Phase 3 — sync_engine_managed_docs:引擎自动写入同步标记块(AIR-ENGINE:AGENTS-SYNC / C4-SYNC / TODO-RUN-LOG),追加前检查去重
  4. Phase 4 — update_todo_after_merge:更新任务表中的状态和验证摘要,支持动态列定位(按已知状态词搜索列头)
  5. Phase 5 — atomic persist:使用 atomic_json_write()(tempfile + os.replace())原子写入 state.json,失败时自动从 .bak 恢复
  6. Phase 6 — FileLock release:释放 FileLock(fcntl.flock)

Phase 6.5 — TaskGraph sync:若启用了动态 DAG,合并后还需把 Worker 的 filesChanged、验证摘要、documentUpdates 反映回 TaskGraph,更新对应 TaskNode 的状态。

标记块命名空间(两层隔离避免模式间互相覆盖):

  • 模式层(各模式独立维护):<!-- AIRARC:BEGIN/END --><!-- AIRENG:BEGIN/END --><!-- AIRDO:BEGIN/END --><!-- AIRDBG:BEGIN/END --><!-- AIRXDB:BEGIN/END --><!-- AIRNDB:BEGIN/END --><!-- AIRSDB:BEGIN/END -->
  • 引擎层(merge_pipeline.py 自动写入):<!-- AIR-ENGINE:AGENTS-SYNC:BEGIN/END --><!-- AIR-ENGINE:C4-SYNC:BEGIN/END --><!-- AIR-ENGINE:TODO-RUN-LOG:BEGIN/END -->

20.2 ADR 变更级联失效的 10 步闭环(对应 6.5)

V2 的 handle_adr_invalidation() 实现完整的 10 步闭环:

1. ADRWatcher 每轮轮询时 SHA256 对比所有 ADR 文件 hash
2. 检测到 superseded / modified 变更 → 触发级联失效
3. TaskGraph.invalidate_by_adr() 冻结调度(dispatch_frozen = true)
4. 标记所有引用该 ADR 的已完成任务为 INVALIDATED
5. 标记进行中任务为 INVALIDATED,中止对应 Worker
6. BFS 遍历下游依赖 → 级联失效所有受影响的后继任务
7. 创建 git tag 回滚快照
8. git revert 已合并的旧代码(按 task_id 查找对应 commit)
9. PartialReplanner 生成局部重规划请求(仅重新规划受影响部分)
10. AirArc 基于新 ADR 重新生成任务 → apply_delta() → 解冻调度

关键数据结构

  • TaskNode.adr_refs:每个任务节点记录它引用的 ADR ID 列表,建立架构决策 → 具体任务的溯源链
  • PartialReplanner:提取未受影响 DONE 任务的公共接口约束,确保重规划不破坏稳定依赖
  • dispatch_frozen:级联失效期间 ready_tasks() 返回空列表,阻止任何新任务派发
  • git tag 回滚点:精确定位需要回退的 commit,避免全量回滚

20.3 TaskGraph 数据结构与 PlanDelta(对应 8.3)

class TaskGraph:
    nodes: dict[str, TaskNode]   # 每个任务是一个节点
    edges: list[Edge]            # 依赖/冲突/同步边
    dispatch_frozen: bool        # ADR 级联失效时冻结

class TaskNode:
    id: str
    status: str          # TODO | DISPATCHED | DONE | BLOCKED | INVALIDATED
    task: str            # 任务描述
    write_set: list      # 声明的写集(用于 RegionConflictDetector 冲突检测)
    adr_refs: list       # 引用的 ADR(溯源链,供 invalidate_by_adr 使用)
    test_required: bool  # 边界测试标记(AirArc 在 _inject_boundary_tests 时设置)

PlanDelta 结构

class PlanDelta:
    added: list[TaskNode]        # 新增任务
    removed: list[str]           # 移除的任务 ID
    modified: list[TaskNode]     # 修改的任务
    edge_changes: list[Edge]     # 新增/移除的依赖边

四项核心能力的实现

  • apply_delta():增量更新图结构,已调度(DISPATCHED/DONE)任务不受影响
  • apply_full_replace():保留已完成任务的 DONE 状态,避免重新调度
  • diff():对比新旧两个 DAG,自动产出精确的 PlanDelta
  • ready_tasks():返回入度为 0 且状态为 TODO 的节点;调度冻结时返回空列表

20.4 五种 L1 机制的具体代码实现(对应 10.2)

① 工具白名单:命令文件 frontmatter 声明 allowed-tools: [Read, Glob, Grep],AirArc 配合 deny-plan-mode: true 在 Agent 框架层面阻断写操作和 plan mode。

② Python 门控函数

  • ArcPhaseGate:AirArc 写入前必须处于 confirmed 阶段(discussing → proposing → confirmed),否则拒绝
  • EvidenceFirstGate:AirDbg 未取证前 can_modify_code() 返回 False
  • EvidenceGatePolicy:根据任务类型(GUI / NETWORK / STATIC_ANALYSIS / CODE_ONLY)分类,替代 V1 的无差别触发

③ 数据结构约束

  • WorkerResult.validate_for_finalize():deployRequired 必须有 deploy 验证;done 必须有 validations 或 filesChanged
  • sanitize_task_id():正则校验防止路径注入
  • sanitize_marker():拒绝 HTML 注释分隔符,防止标记注入

④ 强制路由链finish_worker() 按 6 级优先级路由——blocked/failed → AirDbg、无取证 → AirDbg、GUI 任务 → AirXDB、网络任务 → AirNDB、C/C++ 任务 → AirSDB、所有 done → AirRvr。路由是代码级强制,不可跳过。

⑤ 原子操作 + 并发控制

  • atomic_json_write():写入前创建 .bak 备份,使用 tempfile + os.replace() 原子替换
  • safe_json_load():JSONDecodeError 时自动从 .bak 恢复
  • FileLockfcntl.flock(LOCK_EX | LOCK_NB) 带 timeout 重试

20.5 指令操作化的具体示例(对应 10.3)

AirEng 派发 Worker 的操作化步骤(从"读取派发清单 spawn 子代理"这一意图描述升级而来):

dispatch 返回 {waveId, taskIds, dispatchPath}。然后按以下步骤操作,不可跳过:

1. 从 dispatch 返回值中取 taskIds 列表
2. 对 taskIds 中的每个 tid,在同一条消息中并发调用 Agent 工具:
   Agent(
     description: "Do Worker: {tid}",
     subagent_type: "general-purpose",
     run_in_background: true,
     prompt: "你是 AirDo Worker..."
   )
3. 所有 Worker spawn 完成后,进入 monitor 状态

AirDo 路由链的操作化(对应 20.4 ④ 强制路由链):

def finish_worker(task_id, result):
    if result.status in ("blocked", "failed"):
        return route_to("airdbg", task_id)
    if not result.evidence and needs_evidence(result):
        return route_to("airdbg", task_id)
    if is_gui_task(result):
        return route_to("airxdb", task_id)
    if is_network_task(result):
        return route_to("airndb", task_id)
    if is_cpp_task(result):
        return route_to("airsdb", task_id)
    return route_to("airrvr", task_id)

每一步都是确定的操作,消除了 Agent 的推理负担——不再需要猜测工具名、参数格式或数据来源。


二十一、总结

Air 插件套件 V2 的十五个工程原则:

  1. 制品驱动通信 — 插件间通过结构化文件通信,实现可检查、可恢复、可审计的松耦合
  2. 三层上下文边界 — 会话级压缩 + 任务级隔离 + 项目级制品,三个尺度管理上下文质量
  3. 隔离驱动的并行效率 — 上下文隔离是并行调度的前提;没有隔离,并行度越高,腐烂越快
  4. 证据先于修复 — 截图、抓包、静态分析作为修复前置条件,消除虚假验证
  5. 闭环自动修复 — 执行→失败→调试→修复→重执行的自动循环,预算耗尽才升级人工
  6. 透明上下文压缩 — 三级降级 + 质量校验,~10 倍压缩比,保留关键决策
  7. 多模型交叉审计 — 并行/递进/多视角审查 + 交叉确认矩阵,将单模型盲区转化为可量化置信度
  8. 架构状态持久化 — C4 + ADR + 标记块 + 6 阶段合并流水线,架构文档不可能落后于代码
  9. 范围约束降本 — 规划-执行分离 + 6 文件必读 + 预填充模板 + 弱模型安全,廉价模型在约束上下文中达到昂贵模型效果
  10. 长期迭代管理 — 文件状态 + 波次递进 + 修复预算 + 文档级联 + 回归防护,跨会话/跨模型/跨设备的工程连续性
  11. L1 代码级保障(V2) — 关键约束从自然语言建议升级为 Python 门控 + 工具白名单 + 数据契约的硬性执行
  12. 动态图调度(V2) — TaskGraph DAG 替代静态表格,增量重规划 + ADR 级联失效 + worktree 隔离并行
  13. 全专家插件路由(V2) — finish 时 6 级强制路由链(Dbg→XDB→NDB→SDB→Rvr),路由不是建议而是代码级强制
  14. 指令操作化(V2) — 关键操作路径从意图描述升级为可执行伪代码,消除 Agent 推理歧义
  15. 需求一致性审查(V2) — AirRvr 独立审查交付物与需求的一致性,含高风险审计 + Code-to-Design 逐行对照

将 AI Agent 从不可控的对话式工具,转变为可审计、可续接、可验证、可交叉检验的工程化执行平台。V2 在 V1 的基础上,将"建议性约束"系统性升级为"代码级保障",针对真实项目中暴露的 P0/P1 缺陷逐项给出工程化对策。而阶段 09 的 AirCoding,则把这条路线继续推进到了宿主运行时内部:它已经完成首个公开 Alpha 并开源,用 OpenCode fork + Agent 注册 + coordinator 工具 + plugin hook 验证了"关键约束必须宿主内嵌"这一路线;但完全独立的运行时、事件总线和语言无关内核,仍是下一阶段。


[内核课程]《Windows内核攻防实战》!从零到实战,融合AI与Windows内核攻防全技术栈,打造具备自动化能力的内核开发高手。

收藏
免费 0
打赏
分享
最新回复 (2)
雪    币: 778
活跃值: (923)
能力值: ( LV3,RANK:30 )
在线值:
发帖
回帖
粉丝
2
看见群友发帖,支持一下!
1天前
0
雪    币: 1086
活跃值: (480)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
3
学计算机睡觉 看见群友发帖,支持一下![em_079]
哇,谢谢,喵喵喵喵喵
1天前
0
游客
登录 | 注册 方可回帖
返回