Autocode:基于多 Agent 协作的自动化代码实现引擎

当详细设计文档(DDD)不再只是"被阅读"的文档,而是可以被直接"执行"的输入------本文将揭示一个多 Agent 协作引擎如何将设计文档转化为可交付的代码,并通过双层质量门禁和迭代反馈循环保证输出质量。

引言

在软件工程实践中,从设计到代码的转化始终是一个高成本环节。即使有了完善的详细设计文档(DDD),将其转化为高质量的代码实现依然需要大量的工程劳动------编码、自测、审查、修复、再审查。当大语言模型(LLM)展现出代码生成能力后,一个自然的问题是:能否让 AI 自动完成从设计文档到代码实现的闭环?

这个问题的难点不在于"生成代码"本身,而在于四个核心挑战:

  1. 需求理解的准确性:LLM 对需求的理解可能存在偏差,一次生成很难完全对齐设计意图
  2. 输出质量的保证:生成的代码是否能通过编译、测试、代码规范检查?
  3. 多角色协作的一致性:编码、审核、测试等角色需要协同,而非简单的一次性生成
  4. 功能粒度与幻觉的矛盾:一次性要求完成的功能越多,LLM 产生的幻觉越多,审核的难度也越大。这是一个被低估但极为关键的问题

第四个挑战引出了 Autocode 最核心的设计哲学:拆小、聚焦、逐个击破。 当你让 LLM 一次性实现"用户管理模块"时,它可能同时"发明"不存在的数据库表、虚构未定义的接口、混淆业务逻辑的边界------因为任务太模糊,LLM 会用幻觉填补信息空白。但如果你让它实现"UserService.login 方法的参数校验",任务边界清晰,幻觉空间被大幅压缩,审核也变得简单------你只需要检查校验逻辑是否完整,而不需要理解整个模块。

Autocode 的所有设计------从 DDD 输入格式要求 functionPoint(功能点)必填,到 Plan 阶段的多轮交互式澄清,到 Code 阶段的迭代修复------都服务于这一哲学:将功能拆分到最细粒度,让每次生成聚焦于一个明确的点,让审核聚焦于一个可判定的范围。

Autocode 正是为了解决这些问题而设计的。它不是一个简单的"代码生成器",而是一个多 Agent 协作的自动化代码实现引擎------通过两阶段执行模型、双层质量门禁、迭代反馈循环和多 Agent 轮换策略,将 DDD 文档转化为经过质量验证的可交付代码。

系统架构概览

Autocode 采用分层架构,自上而下分为入口层、编排层、迭代层、执行层和支撑层,各层职责清晰、耦合度低。

入口层 提供 CLI 和 Web 两种运行模式,通过 UserInteraction 接口解耦用户交互方式。

编排层 是系统的大脑,WorkflowOrchestrator 负责阶段调度(Plan → Code)、恢复检测和分支管理,AgentHarnessImpl 驱动单应用的完整生命周期。

迭代层 管理编码阶段的迭代循环,IterationLoopRunner 串行执行四个步骤,PhaseRunner 采用模板方法模式消除审核和测试的重复逻辑。

执行层封装了 Agent 执行的复杂性------重试、超时、轮换策略。

支撑层提供硬门禁检查、Prompt 构建、评分提取、状态持久化等基础能力。

这种分层设计的好处是:修改 Agent 行为主要通过编辑 Prompt 模板(而非 Java 代码),扩展新的 Agent 只需实现接口并注册枚举,质量门禁通过接口扩展。

两阶段执行模型:Plan → Code

Autocode 的核心设计理念是**"先理解,再实现"**------将工作流明确划分为 Plan(规划)和 Code(编码)两个阶段。

Plan 阶段:多轮交互式规划

Plan 阶段的目标是消除需求歧义,建立清晰的实施计划。这个过程不是一次性的,而是多轮交互式的:

  1. Agent(PLAN) 分析 DDD 内容,探索代码库
  2. PlanOutputParser 解析输出,提取问题清单
  3. 如有问题 → 通过 ConfirmInteractor 收集用户回答 → 下一轮
  4. 如无问题 → 输出最终实施计划

PlanOutputParser 支持四种解析策略(按优先级):JSON 对象解析 → 代码块内容提取 → 混合格式解析 → 原始内容回退。这种多策略解析的设计是为了兼容不同 LLM 输出格式的差异。

Plan 阶段的关键设计决策是:将需求理解从代码实现中分离出来。实践表明,首次编码失败的主要原因是需求理解偏差,而非编码能力不足。先投入时间在规划阶段对齐意图,可以显著提高后续编码的成功率。

Code 阶段:四步迭代循环

Code 阶段是一个"编码 → 硬门禁 → 审核 → 测试"的迭代循环:

vbnet 复制代码
Step 1:   编码/修复 → PromptBuilder 构建指令 → Agent(IMPL) 执行
Step 1.5: 硬门禁 → HardGateChecker 检查(编译+测试+Lint)
Step 2:   审核 → Agent(REVIEW) 审核 → ScoreExtractor 评分
Step 3:   测试 → Agent(TEST) 测试 → ScoreExtractor 评分 [可选]

迭代终止条件包括:评分达标(≥ passingScore)、达到最大迭代次数(默认 42 次)、连续失败 ≥ 3 次、Agent 报告无法实现、上下文溢出等不可恢复错误。

反馈循环:越修越好

当审核或测试未通过时,系统会构建包含上一轮评分、具体反馈和改进建议的上下文,传递给下一轮的编码 Agent。这种结构化反馈机制确保每次迭代都有明确的改进方向,而非盲目重试。

多 Agent 协作与轮换策略

Autocode 的 Agent 系统采用"工具 + 模型 + 角色"的配置方案,同一工具可配不同模型承担不同职责。

四种 Agent 角色

审核轮换:避免单一视角偏见

审核 Agent 采用 (iteration - 1) % N 的轮换策略,N 为配置的 review Agent 数量。这意味着如果配置了两个审核 Agent,第一轮迭代使用 Review-1,第二轮使用 Review-2,第三轮回到 Review-1,如此循环。

为什么审核需要轮换? 实践发现,同一个审核 Agent 容易对同一类问题"视而不见"(类似于人类审核的盲区)。轮换不同 Agent 可以带来不同的审核视角,互补发现更多问题。

Agent 实现:CLI 包装模式

所有 Agent 实现都采用 CLI 包装模式------AbstractAgent 封装了通用的 CLI 进程执行、输出解析、会话管理和超时控制,具体实现(ClaudeAgentCodexAgentOpenCodeAgent)只需关注特定工具的参数构造和输出格式解析。

ClaudeAgent 为例,它使用 --output-format stream-json 获取流式 JSON 输出,通过 ClaudeStreamJsonParser 实时解析结果,支持 --resume 进行会话恢复。AgentExecutor 在外层提供重试(指数退避)、超时保护和错误分类检测(上下文溢出、配额超限、API 失败等)。

双层质量门禁机制

质量保证是 Autocode 区别于简单代码生成工具的关键特性。系统实现了硬门禁(HARD)和软门禁(SOFT)双层检查机制。

硬门禁:客观事实检验

硬门禁在编码后立即执行,检查三项客观指标:

  1. 编译检查 :```mvn clean compile/go build/npm run build/cargo build`
  2. Lint 检查checkstyle:check / golangci-lint / eslint / clippy
  3. 测试运行 :```mvn clean test/go test/npm test/cargo test`

硬门禁的关键设计是自动语言检测和 JDK 版本管理LanguageDetector 通过项目根目录文件识别语言(pom.xml → Java、go.mod → Go),JdkDetector 跨平台检测本地 JDK 版本,采用"精确匹配优先、高版本兼容回退"的策略,并在启动时一次性检测缓存。

硬门禁失败的处理是系统设计的一个关键决策:直接跳过审核和测试步骤,进入下一轮迭代。原因很简单------编译都不过的代码,让审核 Agent 去看是浪费资源。

软门禁:主观质量评估

软门禁由 Agent LLM 执行,审核 Agent 按 5 个维度加权评分:

评分通过 ScoreExtractor 从 Agent 输出中提取,≥ passingScore(默认 85)即为通过。ScoreExtractor 同样采用多策略提取,兼容不同格式的 LLM 输出。

两层门禁的协同

硬门禁保证代码的"客观正确性"(能编译、能通过测试、符合代码规范),软门禁保证代码的"主观质量"(符合设计意图、有良好的测试覆盖、没有安全隐患)。两层门禁的配合,既避免了"编译通过但逻辑错误"的问题,也避免了"LLM 认为很好但实际编译不过"的尴尬。

状态管理与断点恢复

Autocode 的状态管理采用三层结构设计,核心目标是支持多应用并行时的状态隔离和断点恢复。

三层状态结构

yaml 复制代码
WorkflowState(全局)
  ├── dddName / functionPoint / branchName
  ├── currentPhase / overallStatus
  ├── plan: PlanState(规划轮次记录)
  └── apps: Map<String, AppCodeState>(多应用并行隔离)
        └── code: CodePhaseState
              ├── iteration / lastScore / consecutiveFailures
              ├── currentStep: IterationStepType(断点定位)
              └── iterations: List<CodeIteration>

为什么是三层? 当一个功能改动涉及多个应用时(例如,"用户登录"需要同时改 user-serviceauth-service),各应用在独立的线程中并行执行,但迭代进度不同。如果只用两层结构(全局 + 迭代),多应用的状态会互相覆盖。三层结构中,每个应用持有独立的 AppCodeState,修改互不影响。

断点恢复

currentStep 字段记录了当前迭代执行到哪个步骤(IMPLEMENTATION → HARD_GATE → REVIEW → TEST)。恢复时,shouldRunStep() 方法会跳过已完成的步骤,从断点处继续。这意味着如果第 10 次迭代在审核步骤因网络中断而失败,恢复后不需要重新执行编码和硬门禁,直接从审核步骤开始。

并发安全

多应用并行写同一个 workflow-state.json 文件时,save() 方法使用 synchronized 保证全量序列化写文件不交叉。此外,RepoLockManager 保证同一仓库不会被多个应用并发写入,避免 Git 操作冲突。

双模式运行:CLI 与 Web

Autocode 支持两种运行模式,通过 Spring Profile 切换:

  • CLI 模式 (默认):CliRunner 解析命令行参数,CliUserInteraction 基于控制台交互
  • Web 模式--spring.profiles.active=web):TaskController 提供 REST API,WebUserInteraction 基于 CompletableFuture + WebSocket 异步交互

两种模式共享相同的编排和执行逻辑,差异仅在于用户交互方式。Web 模式下的 LogWebSocketHandler 支持实时日志推送和断线重连历史回放(最多缓存 5000 行),TaskManager 管理异步任务的完整生命周期。

Web 模式的 WebUserInteraction 实现了一个精巧的异步交互机制:通过 CompletableFuture 阻塞等待 Web 端用户操作,REST API 回调完成 Future,ThreadLocal 维护当前 taskId 支持多任务并发。这使得同一套编排逻辑无需修改即可在两种模式下运行。

Prompt 工程与模板系统

Autocode 的 Agent 行为主要通过 Prompt 模板控制,而非硬编码在 Java 代码中。模板按角色划分:

  • plan.md:规划角色的多轮分析指令、问题输出格式、计划制定规范
  • implementation.md:编码角色的 TDD 工作流指令、自检清单、输出格式
  • review.md:审核角色的 5 维度审核标准、加权评分规则、报告格式
  • test.md:测试角色的验证标准、覆盖率要求、验收条件
  • program.md:全局规则,包括代码规范、质量自检、迭代控制、权限边界

PromptBuilder 按阶段流式构建 Prompt:DDD 内容 + program.md 全局规则 + Agent 角色指令 + 反馈上下文 + 会话历史。这种设计使得修改 Agent 行为主要通过编辑 Markdown 模板,开发者不需要理解 Java 代码即可调整 Agent 策略。

多应用并行执行

当一个功能改动涉及多个应用时(DDD 内容中通过多个 appName:{xxx}; 声明),系统自动按应用拆分并并行执行:

  1. DddChangePoint.parseMultiApp() 按 appName 拆分为多个 DddAppChangePoint
  2. WorkflowOrchestrator 使用线程池并行执行各应用
  3. 各应用独立的 AppCodeState 存放在 WorkflowState.apps Map 中
  4. RepoLockManager 保证同一仓库不并发写

这种设计使得跨应用的功能改动(如"用户登录"需要同时改 user-serviceauth-service)可以在一次执行中完成,而非手动分别执行。

关键设计决策回顾

实践:系统自举

Autocode 最有说服力的实践,不是某个外部项目的试用,而是它用自己实现了自己

在完成前期的主体框架搭建后,Autocode 的后续所有功能开发------从多应用并行支持、Web 模式、Plan 阶段多轮交互,到双层质量门禁、状态断点恢复、Agent 轮换策略------都是由 Autocode 自身自举完成的。开发者编写 DDD 文档,Autocode 读取文档、规划、编码、自检、审核、迭代,最终产出代码。

这个过程验证了一个重要发现:粒度越细,越符合预期。当 DDD 文档将功能拆分到"单个方法的参数校验"或"单个配置项的解析逻辑"这种粒度时,Autocode 的输出几乎无需人工干预就能通过审核。而当功能粒度粗到"实现整个模块"时,幻觉显著增多,迭代次数从 3-5 轮暴涨到 10+ 轮,且最终结果仍可能偏离意图。

这并非巧合,而是前述"拆小聚焦"哲学的实证:细粒度任务缩小了 LLM 的"自由发挥空间",压缩了幻觉产生的土壤,也让审核 Agent 的判定标准更加明确------"这个参数校验是否覆盖了空值、类型错误、边界范围"比"这个模块设计是否合理"要容易回答得多。

系统自举的另一个启示是:Autocode 适合的是"高确定性、可细分"的工程任务,而非"开放性、探索性"的创作任务。当需求可以被精确描述、可以被客观验证时,自动化代码实现才是可靠和高效的。

展望:从工具到伙伴

基于当前实践,我们对 Autocode 的演进方向有更具体的设想:

增量式上下文管理:当前每轮迭代都传递完整上下文,随着项目规模增大,需要更智能的上下文裁剪策略,只保留与当前功能点相关的代码片段。

多仓库编排:支持跨仓库的功能改动自动编排执行顺序,识别应用间依赖关系并合理安排并行度。

学习型反馈:从历史迭代中学习常见错误模式,前置预防而非事后修复------例如,如果某类项目经常在 checkstyle 上失败,可以在 Prompt 中主动提醒编码 Agent 注意相关规范。

人机协作的终极形态:我们最终想要达到的目标,是一种**"会议模式"的工作流**------在会议开始前,开发者将一系列细粒度任务输入系统;会议期间,Autocode 在后台并行执行,逐个完成功能点的规划、编码、自检、审核;会议结束后,开发者回来时面对的不是空白屏幕,而是一系列已经完成的功能点,只需要逐个 review 每个功能点的实现质量。

这种模式的核心转变是:开发者的角色从"编码者"变为"审核者" 。不再需要亲手写代码,而是专注于验证 AI 输出是否符合设计意图、是否满足业务需求。这正是"拆小聚焦"哲学的最终指向------当每个功能点都足够小、足够明确时,审核的效率远高于从头编码。一个功能点的审核可能只需要 2 分钟,但从零开始编码可能需要 20 分钟------10 倍的效率提升。

结语

Autocode 的核心洞察可以凝练为一句话:拆小聚焦,质量闭环

一次性完成的功能越多,LLM 的幻觉越多,审核的难度越大。将功能拆分到最细粒度,让每次生成聚焦于一个明确的点,让审核聚焦于一个可判定的范围------这是解决"AI 代码质量"问题的根本路径。而两阶段执行模型、双层质量门禁、迭代反馈循环、多 Agent 轮换,都是围绕这一路径构建的质量保障机制。

系统用自己实现了自己,这既是工程实践,也是设计理念的最好验证。当我们展望"会议模式"的未来时,看到的不是 AI 替代开发者,而是 AI 将开发者从重复性编码劳动中解放出来,让其专注于更有价值的架构决策和质量把关------从写代码的人,变成审代码的人


作者简介:Autocode 开源项目核心贡献者,专注于 AI 辅助软件工程领域的实践与探索。

项目地址:github.com/wenbinzhang...

相关推荐
飞飞的AI实验室2 小时前
小米也开源了终端编程助手,我拿它跟天天用的 Claude Code 真打了一轮
ai编程·claude
leeyi2 小时前
Agent Transfer:让 AI 把任务交给更合适的 AI
aigc·agent·ai编程
universeplayer2 小时前
天天用 Claude Code 和 Codex,但你比过它们在你自己的活上谁更强吗?我写了个工具让它们同台开打
ai编程·claude·cursor
花椒技术3 小时前
Agent 不只会聊天:我们如何用 CLI 整理业务能力入口
agent·ai编程·mcp
FanetheDivine4 小时前
学习Agent开发6 langgraph速览
agent·ai编程
coderhuo4 小时前
惊呆了:AI改了三个字节,修好了一个跑不起来的adb
ai编程
threerocks6 小时前
什么?我连 A2A、MCP 都没学会,现在又来了 AG-UI、A2UI.
前端·aigc·ai编程
Coffeeee6 小时前
两个例子,帮你快速理解什么是Token
人工智能·程序员·ai编程
饼干哥哥6 小时前
用AI全自动剪辑,日更 100条爆款视频——HyperFrames、Remotion、Git使用入门
人工智能·机器学习·ai编程