Skip to content

L5 · 如何编排任务并组织多个 Agent 协作? - Orchestration & Collaboration ​

所属知识库:Agent 全栈技术地图
所属领域:03 · Agent System
所属章节:02 · Agent System 是如何构建和运行的? - Technical Architecture
文档类型:多 Agent 编排机制、协作架构与工程实践研究
版本:v1.1
更新日期:2026 年 10 月 28 日
核心问题:Agent System 如何将复杂任务分解为可执行的工作单元,建立任务依赖与分配策略,协调一个或多个 Agent 的执行、通信、交接、共享状态与结果汇总?如何在并发、失败、预算、权限、人工审批和不可信输出条件下保持协作过程可控、可恢复、可观测,并判断何时值得采用多 Agent 架构?

专题导读 ​

本篇属 Technical Architecture。当任务超出单次模型调用或单个 Agent Run 的工作范围时,系统需要决定:哪些工作可以拆分,哪些必须按顺序完成,哪些可以并行,哪个 Agent 应当承担某项职责,以及如何判断整体任务已经结束。这些问题属于 Orchestration & Collaboration(编排与协作) 的研究范围。编排负责建立并执行任务之间的控制关系;协作关注多个执行主体如何交换信息、交接责任、共享证据并形成一致产物。两者密切相关,但并不等价:固定工作流可以编排多个步骤而没有多个 Agent;多个 Agent 可以交流,但如果缺乏任务所有权、完成条件和冲突处理,也不构成可靠的协作系统。

本篇承接 L4 Agent Engine 的单 Run 执行契约,在其上研究任务图、协调器、工作分配、消息协议、交接、共享状态、并发控制、失败传播、结果仲裁与端到端验收。L1 提供进程和隔离环境,L2 提供持久化、队列、事件与身份服务,L3 提供模型调用能力,L4 驱动具体 Agent Run,L5 管理跨 Run、跨角色和跨任务的控制关系,L6 再将这些能力暴露给用户和业务系统。L5 不要求所有系统都采用多个模型角色、分布式部署或复杂框架;合理的单 Agent + 工具工作流有时更可靠。

全文以“技术研究报告 Studio”为贯穿案例:选题 Agent 提出研究方向,审核 Agent 提出审查意见,研究 Agent 采集证据,分析 Agent 比较观点,写作 Agent 形成报告,最终由用户确认发布。重点不是把这些名称排成一张流程图,而是研究任务契约如何传递、返工如何有界、证据如何追溯、并行结果如何合并,以及在审批、失败和资源约束下如何维持系统一致性。文中的中立数据模型、算法示例与验收方案属于工程参考设计;官方框架机制与本地实验的证据边界在文末单独说明。

一、研究定位:L5 的对象、边界与必要性 ​

1.1 编排不等于“让多个 Agent 聊天” ​

任务编排(Orchestration) 是把目标转化为具有依赖、执行条件、资源约束和完成判据的任务集合,并控制其启动、等待、重试、终止及汇总的机制。协作(Collaboration) 是多个执行主体在共同目标下,通过明确协议交换工作产物、反馈和责任的过程。协调(Coordination) 侧重共享资源、顺序与冲突的安排。通信(Communication) 只是信息传输能力,不能单独保证任务正确完成。

可以把 L5 的最低责任概括为:接收整体任务契约;形成可执行计划或工作图;把子任务映射到执行主体;追踪依赖和状态;接收结果并校验契约;在失败、返工或审批时作出受约束的控制决定;最终形成可审计的整体终态。一个固定 DAG 编排器可以满足这些责任而不包含多 Agent;多 Agent 只是其中一种执行组织方式。

1.2 L4 与 L5 的职责分界 ​

层次主要控制对象核心责任
L3 Model Services模型请求协议适配、路由、计量、错误映射
L4 Agent Engine单个 Agent Run决策循环、工具执行、Run 状态与终止
L5 Orchestration跨任务与跨 Run依赖、分配、交接、协作、汇总与整体终态
L6 Application用户交互配置需求、展示进度、审批和交付

在小型应用中,同一进程或函数可以同时承担 L4 与 L5 的职责;逻辑分层不要求物理分布式部署。重要的是能够区分:谁决定“这个 Agent 的下一步动作”,谁决定“下一个子任务应该由哪个 Agent 执行”。若一个框架把两者放在同一 Runner 中,研究时仍应按职责识别。

1.3 何时不需要多 Agent ​

任务短、依赖少、专业分工收益低、上下文足够、权限边界简单时,单 Agent + 明确工具通常更容易调试、成本更低。只有当任务存在可验证的专业分工、相对独立的并行工作、不同工具权限、不同模型能力、独立审核或组织责任时,多 Agent 才可能创造净收益。增加角色数量本身不是能力提升证据。

二、任务图:把目标转换为可执行的依赖结构 ​

2.1 任务、工作单元与执行实例 ​

建议区分四个对象:Workflow/Job 表示用户提交的整体目标;TaskNode 表示可独立验收的工作单元;Attempt 表示某个节点的一次执行尝试;AgentRun 是 L4 为某次尝试实际驱动的执行实例。一个节点可能重试多次,也可能由规则函数而非 Agent 完成;一个 AgentRun 不应在没有显式契约的情况下同时被多个节点当作已完成的同一工作。

中立的任务节点结构可以表示为:

json
{
  "workflow_id": "research-2026-001",
  "node_id": "evidence-review",
  "kind": "agent_task",
  "depends_on": ["source-collection"],
  "input_refs": ["artifact://sources-v3"],
  "output_schema": "EvidenceReview.v2",
  "assigned_role": "reviewer",
  "attempt_limit": 2,
  "deadline_at": "2026-10-28T15:00:00Z",
  "approval_policy": "none",
  "budget": {"max_model_calls": 8, "max_cost_units": 30},
  "state": "PENDING"
}

这里的 URI、Schema、预算单位均为示意。实际系统还应记录租户、请求身份、配置版本、数据分类、权限范围、幂等键、关联 trace ID 与任务契约版本。子任务不是一段随意的自然语言指令;至少需要明确输入、输出、约束、验收规则和失败语义。

2.2 DAG 与动态工作图 ​

静态 DAG(有向无环图) 适合依赖在运行前已知的流程;拓扑排序可以保证前置任务完成后再执行后继节点。动态任务图允许 Agent 在运行中提出新增节点、重规划或返工边。动态能力提高灵活性,也引入新风险:依赖环、无限扩张、重复工作、未经批准的任务升级和预算失控。

建议将“任务图变更”视为受控操作:新节点必须通过 Schema 校验、权限检查、预算评估、依赖环检测及版本控制;涉及外部发布或不可逆副作用的变更还需要人工审批。不能让模型直接改写可信调度器内部状态。

2.3 任务图的控制语义 ​

常见依赖条件至少包括:ALL_SUCCESS(所有前置节点成功)、ANY_SUCCESS(任一满足条件)、QUORUM(达到法定数量)、ON_FAILURE(失败补偿或复盘)、MANUAL_GATE(人工批准)。这些语义必须在任务契约中显式声明。比如三名审核 Agent 的多数意见并不天然等于事实正确;投票只是聚合策略,仍需外部证据与规则支持。

text
用户提出研究目标
       │
       ▼
[选题生成] ──> [选题审核] ──不通过──┐
       ▲                            │
       └────── 有界返工(新版本) ────┘
                    │通过
                    ▼
               [用户确认]
                    │
         ┌──────────┼──────────┐
         ▼          ▼          ▼
     [文献检索] [官方文档] [案例采集]
         └──────────┼──────────┘
                    ▼
              [证据校验与去重]
                    ▼
                [分析写作]
                    ▼
               [终审与交付]

图中的返工是一个受限循环,不是 DAG 内部的无界环。工程实现可通过“新版本的节点实例”或明确的有限状态转换表示;对外展示的逻辑流程与调度器内部的数据结构不必完全相同。

三、协作拓扑:集中、层级、对等与混合 ​

3.1 集中式 Supervisor ​

Supervisor 接收整体目标,拆分任务、分派 Worker、审核中间结果并汇总。优点是任务所有权和预算归属清晰;风险是协调器成为瓶颈、单点故障或错误决策放大器。Supervisor 不一定由 LLM 实现;确定性调度器往往更适合执行权限、依赖和预算规则,LLM 可以在受控边界内提出规划建议。

3.2 层级式协作 ​

总协调器下设研究组、写作组、审核组等子协调器。适合组织规模较大、任务层级稳定的场景;代价是额外的通信、汇总和责任追踪成本。每一级应明确最大委派深度、预算继承规则和终止传播,防止无限委派。

3.3 对等与黑板模式 ​

对等模式允许 Agent 直接交换任务或建议,适合分散探索,但容易出现循环讨论、重复任务和责任不清。黑板(Blackboard)模式通过共享工作区交换证据和中间成果;它提供共享信息载体,不自动解决并发覆盖、事实冲突和访问控制。共享黑板应具备版本、作者、来源、状态、权限和冲突检测。

3.4 事件驱动与混合模式 ​

事件驱动适合异步长任务,例如 SOURCE_COLLECTED 触发证据审查。事件是“已发生的事实”或“待处理的信号”,不应与命令混淆。事件重复、乱序、延迟是实际工程中需要处理的常态。混合模式通常更实用:确定性调度器维护任务状态,Agent 负责有边界的语义工作,事件系统解耦长任务,人工节点处理高风险决策。

模式主要优势主要代价典型条件
固定工作流可预测、易验收适应性有限流程稳定
Supervisor责任清晰协调器瓶颈任务需动态分派
层级协作便于分组组织开销大多层复杂项目
对等协作探索灵活难控制收敛低风险探索
黑板协作共享中间产物冲突与一致性多角色共用证据
混合架构兼顾灵活与控制设计复杂长期运行系统

四、任务分解与分配:从规划建议到可信调度 ​

4.1 分解质量的判断 ​

良好的子任务应有清晰目标、有限范围、可获得的输入、可验证输出和合理依赖。任务切得过细会增加调用、通信和上下文重复成本;切得过粗则难以并行、审核和故障隔离。可采用“最小可验收工作单元”作为经验原则,而不是强制固定粒度。

分解过程可分为:需求解析、约束识别、候选任务生成、依赖推断、资源评估、图合法性检查、审批与提交。模型可以帮助生成候选任务图,但最终提交必须经过可信控制器检查。

4.2 能力与权限双重匹配 ​

任务分配不能只依据 Agent 名称或角色描述。建议建立能力声明(可处理的任务类型、工具、模型、语言、数据格式)、执行条件(当前负载、可用预算、时限)以及授权边界(可访问数据与允许动作)。分配流程应先过滤不可执行或未授权的候选,再比较预计质量、延迟、成本和风险。

示意评分可以写作:utility = expected_quality - λ1*latency - λ2*cost - λ3*risk。该公式仅用于解释多目标取舍,权重不是通用标准,expected_quality 也需要由历史评测或人工规则支持。安全与合规限制应作为硬过滤条件,不能用高质量评分抵消越权。

4.3 计划修订与版本 ​

每次重规划都应产生新版本,记录:触发原因、旧图与新图差异、已完成节点如何继承、未完成节点如何取消、预算变化、用户审批要求。不能简单删除已执行节点,因为外部副作用、已产出证据和审计轨迹仍然存在。

五、Agent 间通信:消息协议与可信边界 ​

5.1 消息不是共享思维 ​

Agent 间通信通常通过文本、结构化消息、工具结果或持久化产物引用实现。即使多个 Agent 共享对话历史,也不代表它们共享同一内部状态或对证据形成一致理解。应区分 command(请求执行)、event(已发生事实)、artifact(可复用产物) 和 feedback(审查意见)。

建议的消息信封:

json
{
  "message_id": "msg-019",
  "workflow_id": "research-2026-001",
  "sender": "researcher@v2",
  "recipient": "reviewer@v1",
  "kind": "ARTIFACT_READY",
  "correlation_id": "task-source-003",
  "causation_id": "msg-018",
  "artifact_ref": "artifact://evidence-bundle-v4",
  "schema_version": "1.0",
  "classification": "internal",
  "created_at": "2026-10-28T12:00:00Z"
}

sender 是声明的逻辑身份,必须由可信消息通道鉴别;不能只相信模型生成的字符串。correlation_id 关联业务任务,causation_id 追溯触发链。消息体应有大小限制、Schema 校验、敏感字段处理和幂等消费策略。

5.2 Handoff 与 Delegation 的区别 ​

Handoff(交接) 通常意味着当前执行主体将某项工作或会话控制转移给另一主体;Delegation(委派) 通常意味着委派者保留整体责任并等待子任务结果。不同框架的术语和 API 不完全一致,不能将其当成统一协议。工程上应明确:交接是否转移控制权、原 Agent 是否暂停、谁拥有子任务预算、谁负责最终汇总、失败后回到哪里。

5.3 上下文传递的最小化 ​

把完整对话和所有原始文档无差别转发给每个 Agent,会造成成本、隐私和提示注入风险。建议按角色提供最小必要上下文:任务目标、输入产物引用、证据摘要、约束、输出 Schema 和可访问资源。需要引用原始证据时由受控数据层按权限读取,而不是在多 Agent 消息中复制敏感材料。

5.4 不可信输出的传播风险 ​

一个研究 Agent 从网页中读取的文本可能含有恶意指令;若审核 Agent 将其当作系统命令,信任边界就被穿透。Agent 间的自然语言内容应视为数据,不能自动升级为授权、系统指令或可执行任务图变更。权限、发布、付款、文件删除等行为应在可信控制层重新验证。

六、共享状态与成果:协作不是覆盖同一个文档 ​

6.1 状态分层 ​

建议至少区分:整体 Workflow 状态、节点状态、Agent Run 私有状态、共享事实与证据状态、交付产物状态。共享状态不应直接暴露所有 Agent 的内部推理历史;可以共享经过验证的结论、引用、决策记录和必要的上下文摘要。

6.2 并发写入与版本控制 ​

当研究 Agent 与分析 Agent 同时修改“研究结论”时,简单的最后写入覆盖会丢失内容。可采用不可变产物版本、乐观并发控制(expected_version)、按字段合并或显式冲突队列。若两份证据互相矛盾,不能靠字符串拼接解决;需要保留来源、时间和争议状态,并交由审查规则或人工仲裁。

6.3 产物与证据血缘 ​

每个关键产物建议记录 artifact_id、版本、作者 AgentRun、输入产物列表、引用来源、生成时间、校验状态和内容摘要。报告中的关键主张应能追溯到证据记录;引用存在不等于证据支持主张。对于同一事实的多次改写,尽量保留主张与证据映射,而不是只保留最终段落。

6.4 共享数据库不等于共享授权 ​

即使所有 Agent 使用同一数据库,也需要在读写入口实施租户、项目、角色和任务级授权。不能因为 Agent 属于同一个 Studio,就默认它可以访问所有文件、密钥和外部系统。

七、并行执行、同步屏障与结果汇总 ​

7.1 Fan-out / Fan-in ​

Fan-out 将可独立执行的任务并行分发;Fan-in 在满足依赖条件后合并结果。并行可以降低关键路径耗时,但不一定降低总计算成本。若后续汇总依赖全部结果,最慢的子任务会成为尾部延迟瓶颈;若允许部分结果,则必须明确缺失证据如何影响结论。

7.2 依赖屏障 ​

对于“研究报告必须有经过审核的证据”这一约束,写作节点的启动条件应检查证据审核状态,而不是只检查研究节点返回了文本。建议区分 COMPLETED(执行结束)和 ACCEPTED(产物验收通过),避免失败产物触发后续任务。

7.3 汇总不是简单拼接 ​

合并多个 Agent 的输出时,需要统一 Schema、去重、冲突检测、证据验证、版本选择和结论整合。多个 Agent 对同一结论一致并不保证正确,尤其在共享模型、共享错误来源或相同 Prompt 的情况下,错误可能高度相关。重要事实应依据外部可核验证据而非投票数判定。

7.4 推测执行与重复工作 ​

为了降低尾延迟,可以对慢任务启动备用执行,但会增加成本和外部副作用风险。仅适用于幂等、可安全重复或纯计算任务;任何具有不可逆副作用的任务都必须先定义去重和提交策略。

八、失败、返工、取消与整体终态 ​

8.1 节点状态机 ​

参考状态:PENDING → READY → RUNNING → SUCCEEDED/FAILED/CANCELLED,并允许 WAITING_APPROVAL、RETRY_WAIT、BLOCKED 等中间状态。整体 Workflow 的终态不能简单等同于最后一个 Agent 返回成功;必须检查关键节点的验收、审批、预算和副作用记录。

8.2 失败传播策略 ​

策略适用场景关键约束
Fail-fast关键前置条件失败取消下游未启动任务
Continue可选证据源失败明确标记结果不完整
Retry暂时性故障次数、退避与截止时间
Replan方案不再可行新计划版本与预算审批
Escalate风险或歧义过高人工决策与审计
Compensate已发生可补偿副作用补偿不保证完全回滚

重试属于节点尝试层面的行为,不能无条件重跑整个工作流;否则可能重复支付、重复发布或覆盖已有产物。对于有外部副作用的操作,需要稳定的幂等键、操作账本、状态对账或人工恢复流程。消息队列的至少一次投递也不等于业务恰好一次执行。

8.3 有界审核返工 ​

选题 Agent 与审核 Agent 之间的循环必须有最大迭代次数、预算、截止时间和退出条件。审核意见应指向具体缺陷、证据和可执行修改要求。若超过上限仍未通过,应转入 NEEDS_HUMAN_REVIEW 或明确失败,而不是无限对话。

8.4 取消传播 ​

用户取消工作流时,调度器需要停止派发新任务,向运行中的 AgentRun 发出取消请求,回收受控资源并记录已完成的外部操作。取消是尽力而为的分布式控制过程;对于已经发送到第三方系统的不可逆动作,不能承诺自动撤销。

8.5 整体终止判据 ​

建议至少区分:SUCCEEDED、PARTIAL_SUCCESS、FAILED、CANCELLED、WAITING_APPROVAL、BUDGET_EXCEEDED。若用户要求所有关键证据经过审核,任何关键审核节点失败都不应标为成功。部分成功是否允许必须由任务契约预先定义。

九、资源、预算与调度公平性 ​

9.1 分层预算 ​

预算可以沿 Workflow → TaskNode → Attempt → AgentRun 分层分配。应明确预算是否可借用、重试是否消耗同一预算池、失败成本是否计入总账、模型供应商异步计费如何对账。硬预算最好在可信网关执行,而不是依赖 Agent 自行遵守。

9.2 并发限制与背压 ​

调度器需要考虑全局并发、每租户配额、每 Agent 类型并发、工具限流和模型速率限制。队列长度增加时应触发背压、拒绝或延迟接收,而不是无限创建 AgentRun。资源调度不应仅按任务数计量;不同任务的 token、CPU、内存和外部 API 成本差异可能很大。

9.3 公平性与优先级 ​

优先级队列可以服务紧急任务,但可能导致低优先级任务饥饿。可考虑配额、老化(aging)、租户隔离和最大等待时间。策略应与业务服务等级目标对应,不能把单一的“先来先服务”当作所有场景的最佳解。

十、架构实现:控制面、执行面与持久化边界 ​

10.1 推荐的逻辑结构 ​

text
                     L6 用户 / Studio UI
                              │
                       Workflow API
                              │
                   ┌──────────▼──────────┐
                   │ L5 Orchestrator      │
                   │ 计划校验 / 依赖调度    │
                   │ 分配 / 审核 / 汇总     │
                   └─────┬─────────┬─────┘
                         │         │
                   任务与事件      产物引用
                         │         │
                ┌────────▼───┐  ┌──▼───────────┐
                │ L2 队列/存储 │  │ L2 Artifact   │
                └─────┬──────┘  │ Store         │
                      │         └──────────────┘
              ┌───────┼────────┐
              ▼       ▼        ▼
           L4 Run A L4 Run B  L4 Run C
              │       │        │
              └───────┴────────┘
                L3 模型 / 受控工具

图中的队列和存储是可选的物理组件;单机原型可以用内存队列和本地持久化实现同一逻辑职责。对于需要跨进程恢复的生产系统,通常需要可靠持久化、可重试任务消费、租约或所有权机制,以及可审计事件记录。

10.2 控制平面与数据平面 ​

L5 的控制职责包括图版本、节点状态、分配决策和审批;数据职责包括输入证据、产物和消息内容。把大型文档直接放进调度消息会增加队列负载和敏感信息扩散;更合理的方式通常是传递受权限保护的产物引用。这里的控制面/数据面是逻辑划分,不等于 Agent Platform 中完整的多租户平台控制平面。

10.3 任务派发的原子性 ​

若调度器先把节点标为 RUNNING 再向队列发送消息,中间崩溃可能导致任务永远不执行;反过来先发送再写状态,则可能重复派发。常见设计是事务性 Outbox:在同一数据库事务内写入状态变更与待发送事件,再由独立发布器发送;消费者使用幂等键处理重复投递。Outbox 改善状态与消息发布的一致性,但不自动解决外部业务副作用的精确一次问题。

10.4 Lease、Heartbeat 与 Fencing ​

Worker 领取任务时可以取得带有效期的租约并定期续租。租约过期后其他 Worker 可以接手,但旧 Worker 可能仍在运行;仅凭超时不能阻止旧执行者继续写入。对于关键共享状态,可使用单调递增的 fencing token 或存储层版本校验,拒绝过期所有者的提交。外部系统若不支持这类校验,则仍需要额外的幂等与对账策略。

10.5 事件与状态一致性 ​

事件日志适合审计和重放部分业务决策,但不应假设重放模型推理会产生完全相同的结果。恢复时应重用已经确认的执行事实和产物,而不是随意重新调用模型或重复外部工具。对于需要重放的确定性编排逻辑,必须清楚划分可重放代码与非确定性活动。

十一、贯穿案例:研究报告 Studio 的完整协作契约 ​

11.1 角色与责任 ​

用户提交研究主题、范围、截止时间、预算和发布要求。选题 Agent 负责候选选题;审核 Agent 负责依据明确量表给出接受/返工意见;研究 Agent 负责收集可追溯证据;分析 Agent 负责比较和推断;写作 Agent 负责生成报告;终审 Agent 检查引用与契约;用户负责最终确认。Agent 的审核意见不替代可信系统的权限判定,也不替代必要的人工责任。

11.2 子任务的输入输出契约 ​

节点必要输入验收输出
选题主题与目标候选题及理由
选题审核候选题、量表通过或具体返工意见
用户确认审核通过的选题用户决定与时间记录
证据采集已确认主题、来源规则来源清单与证据摘录
证据审核证据包、核验规则来源有效性与争议记录
分析写作已审核证据主张-证据映射与草稿
终审交付草稿、验收标准审核结论与版本化报告

这里“来源有效性”不等于事实真值;系统应同时检查来源是否可访问、内容是否对应、引用是否支持主张以及资料是否过时。

11.3 一个失败场景的正确处理 ​

假设证据采集 Agent 找到三份资料,其中一份网页返回 404,另一份与官方规范冲突。正确行为不是让写作 Agent直接补全缺失内容,而是生成 EVIDENCE_INCOMPLETE 事件,标记受影响主张,决定是否重新检索、降低结论确定性或请求用户确认。若任务预算耗尽,应产生有解释的非成功终态,并保留已有可用产物。

11.4 从单 Agent 到多 Agent 的对照实验 ​

建议固定同一批任务、知识快照、验收量表和预算口径,比较:A 单 Agent 完成检索与写作;B 固定工作流分阶段执行;C Supervisor + 专业 Agent;D 增加独立证据审核。报告任务成功率、关键主张支持率、人工返工率、P95 延迟、总成本、失败类别和硬约束违规。需要按任务配对比较并重复运行;不能在实验前假定 C 或 D 一定优于 A。

十二、工程实验:最小 DAG 调度器与确定性测试 ​

12.1 实验目标与限制 ​

以下是一个可复制的 Python 3 标准库教学实验,只验证任务依赖、阻塞、失败传播和拓扑执行顺序。它不包含真实 Agent、消息队列、持久化、并行执行、分布式租约或模型 API。将它视为 L5 控制逻辑的最小示意,而不是生产级 Orchestrator。配套文件 L5-Agent-System-Orchestration-and-Collaboration-v1.1-demo.py,Python 3 标准库(含 3.9)。运行:python3 L5-Agent-System-Orchestration-and-Collaboration-v1.1-demo.py。

python
from __future__ import annotations

from dataclasses import dataclass
from typing import Callable, Dict, Tuple

@dataclass(frozen=True)
class Node:
    name: str
    deps: Tuple[str, ...]
    fn: Callable[[], str]


def run_dag(nodes: Dict[str, Node]):
    # 输入验证与环检测使用 Kahn 拓扑排序思想。
    if any(d not in nodes for n in nodes.values() for d in n.deps):
        raise ValueError("unknown dependency")
    if any(n.name != key for key, n in nodes.items()):
        raise ValueError("node key/name mismatch")
    indegree = {k: len(set(n.deps)) for k, n in nodes.items()}
    dependents = {k: [] for k in nodes}
    for key, node in nodes.items():
        for dep in set(node.deps):
            dependents[dep].append(key)
    ready = sorted(k for k, deg in indegree.items() if deg == 0)
    order = []
    while ready:
        key = ready.pop(0)
        order.append(key)
        for child in dependents[key]:
            indegree[child] -= 1
            if indegree[child] == 0:
                ready.append(child)
                ready.sort()
    if len(order) != len(nodes):
        raise ValueError("dependency cycle")

    states = {}
    outputs = {}
    for key in order:
        node = nodes[key]
        if any(states[d] != "SUCCEEDED" for d in node.deps):
            states[key] = "BLOCKED"
            continue
        try:
            outputs[key] = node.fn()
            states[key] = "SUCCEEDED"
        except Exception as exc:
            states[key] = "FAILED"
            outputs[key] = type(exc).__name__
    return states, outputs, order


def ok():
    return "accepted"


def fail():
    raise RuntimeError("source unavailable")


if __name__ == "__main__":
    plan = {
        "topic": Node("topic", (), ok),
        "sources": Node("sources", ("topic",), ok),
        "review": Node("review", ("sources",), ok),
    }
    state, out, order = run_dag(plan)
    assert all(v == "SUCCEEDED" for v in state.values())
    assert order.index("topic") < order.index("sources") < order.index("review")

    broken = {
        "topic": Node("topic", (), ok),
        "sources": Node("sources", ("topic",), fail),
        "review": Node("review", ("sources",), ok),
    }
    state, _, _ = run_dag(broken)
    assert state["sources"] == "FAILED"
    assert state["review"] == "BLOCKED"

    cyclic = {
        "a": Node("a", ("b",), ok),
        "b": Node("b", ("a",), ok),
    }
    try:
        run_dag(cyclic)
        raise AssertionError("cycle not rejected")
    except ValueError as exc:
        assert str(exc) == "dependency cycle"

    print("PASS: dependency ordering, failure blocking, cycle detection")

本地执行通过:输出 PASS: dependency ordering, failure blocking, cycle detection。

12.2 可扩展的测试矩阵 ​

测试场景预期不变量验证方式
依赖未满足下游不启动状态断言
任务图存在环拒绝提交图校验
Worker 崩溃可恢复或明确失败故障注入
重复消息无重复业务提交幂等账本
审核不通过有界返工迭代上限
人工未批准不执行受控动作网关审计
预算耗尽停止新任务预算账本
共享写冲突不静默覆盖版本冲突测试
取消工作流停止新派发取消传播测试
证据互相矛盾保留争议状态产物验收

上表除明确运行的最小代码检查外,均为待实施的工程验证计划。测试必须在真实队列、存储、模型和权限网关集成后才能支持生产结论。

十三、代表性框架与技术路线对照 ​

13.1 LangGraph ​

LangGraph 的图节点、边、状态和持久化机制适合表达有状态的任务执行与分支控制。研究 L5 时应关注图状态的所有权、并行分支合并、interrupt 与恢复、子图和任务图演化。具体行为随版本变化,不能把图节点自动等同于独立 Agent 或分布式 Worker。

13.2 OpenAI Agents SDK ​

OpenAI Agents SDK 提供 Agent、Runner、tools、handoffs 等概念,适合研究 Agent 之间的控制交接与执行循环。需要区分 SDK 的 handoff 机制与独立工作流调度器所负责的长期任务依赖、持久化队列和业务审批;后者可能需要应用层自行建设。

13.3 Microsoft AutoGen / Agent Framework ​

AutoGen 的多 Agent 会话、团队和消息驱动设计具有研究价值;微软相关 Agent 框架和文档持续演进,具体 API、项目维护状态与迁移关系必须以使用时的官方版本为准。研究重点应放在消息路由、参与者选择、终止条件和协作过程可观测性,而不是只比较 Agent 数量。

13.4 CrewAI ​

CrewAI 以角色、任务和流程等抽象组织多 Agent 工作,适合比较角色分工与任务委派。需要检查其具体版本下的任务依赖、内存、工具权限、人工审批和失败恢复语义,不能由“支持多 Agent”推断具备生产级分布式工作流保证。

13.5 Temporal 与工作流引擎 ​

Temporal 一类持久化工作流系统适合承载长任务、定时器、重试和可恢复编排。它们通常不直接提供 Agent 的语义规划能力,但可以作为可信调度与恢复层,调用 L4 AgentRun 作为活动或外部任务。必须理解工作流重放、活动重试和外部副作用之间的边界。

技术路线主要研究价值需要补足的能力
图执行框架状态图、分支、恢复业务授权与交付契约
Agent SDKHandoff、工具、Runner跨任务持久编排
多 Agent 框架角色与通信协作可证明的执行语义
工作流引擎持久任务与重试Agent 决策与语义验收
自建调度器完全可控较高维护与测试成本

这些不是互斥选项:实际系统可能以工作流引擎管理长期任务,以 Agent SDK 驱动单个 Run,以数据库和产物存储维持证据链。框架选择必须基于具体版本的实测,而不是宣传中的能力标签。

十四、性能、质量与协作收益的评估 ​

14.1 结果与过程双重评价 ​

对 L5 不能只测“所有 Agent 都回复了”。需要同时评价整体任务成功、主张证据支持、交付物质量、关键路径延迟、总模型与工具成本、重试成本、重复工作率、人工干预率和硬约束违规。若审核 Agent 发现问题并正确阻止发布,虽然工作流没有产出最终报告,这仍可能是安全目标上的正确行为;任务成功与安全门禁应分别统计。

14.2 多 Agent 的增益必须经过对照 ​

多 Agent 可能通过专业化、并行和独立审核提高质量,也可能因通信开销、错误传播、共享偏差和更多模型调用而退化。应使用相同任务集、资料快照、预算口径、评分规则和配对比较;重复运行同一任务时,统计分析不能把相关重复测量当作完全独立样本。

14.3 关键指标定义 ​

指标研究目的注意事项
Workflow Success整体任务是否达标需有明确 Oracle
Critical Path Latency关键路径耗时不等于调用耗时之和
Cost per Success成功任务摊销成本包含失败尝试成本
Handoff Failure交接错误比例区分拒绝与故障
Rework Rate审核返工比例返工不一定是坏事
Evidence Support主张与证据匹配链接存在不等于支持
Constraint Violation硬约束违规需要可信执行日志

十五、工程实施路线与验收清单 ​

建议按五个阶段逐步实现:先建立单 Agent 的稳定 L4 Run 契约;再实现固定 DAG 和确定性依赖调度;之后增加有界动态分解与角色分配;接着引入持久化任务、幂等、审批和取消;最后通过真实任务对照、故障注入、生产监测评估多 Agent 的实际收益。不要在缺少状态契约和失败语义时先建设复杂群聊界面。

交付前至少检查:

  • [ ] Workflow、TaskNode、Attempt、AgentRun 的标识和关系清晰。
  • [ ] 每个子任务有输入、输出 Schema、验收条件和权限边界。
  • [ ] 静态与动态任务图都执行依赖环检测和预算检查。
  • [ ] 角色分配同时考虑能力、负载、授权与成本。
  • [ ] 消息具备身份鉴别、关联标识、Schema 和版本。
  • [ ] Handoff、Delegation、Review 的责任转移语义明确。
  • [ ] 共享产物采用版本控制并保留证据血缘。
  • [ ] 并行任务的合并规则和缺失结果策略明确。
  • [ ] 失败、重试、返工、取消和审批均有有界终止条件。
  • [ ] 重复消息、Worker 接管与外部副作用有安全策略。
  • [ ] 预算和权限由可信控制层执行。
  • [ ] 测试覆盖正常路径、故障、冲突、审批和成本边界。
  • [ ] 多 Agent 相对单 Agent 的收益有配对实验支持。

十六、研究结论与下一专题 ​

L5 Orchestration & Collaboration 的核心,不是增加 Agent 数量,而是把多个工作单元和执行主体组织成有依赖、有责任、有状态、有证据、有退出条件的整体系统。编排决定任务何时、由谁、在什么约束下执行;协作决定信息和责任如何传递、结果如何验收、冲突如何处理。它们共同将 L4 的单 Run 执行能力提升为可交付的复杂任务能力。

工程上最重要的判断有四点:第一,任务图和消息协议必须具有可信契约,不能完全由模型自由改写;第二,Agent 间共享内容不等于共享授权,未经验证的文本不能变成执行命令;第三,持久化、重试和消息投递不能自动保证外部副作用只发生一次;第四,多 Agent 是否值得采用,需要通过质量、延迟、成本和风险的对照实验判断。对于许多任务,确定性工作流与少量专业 Agent 的组合比完全开放的 Agent 群聊更易维护。

下一专题为 「L6 · 如何将 Agent 能力提供给用户和其他系统? - Application」,将研究 Agent System 如何通过 API、交互界面、任务入口、事件订阅、审批体验和结果交付与外部世界建立稳定的应用契约。

附录 A:参考文献与原始资料入口 ​

以下列出本篇技术研究的主要官方资料入口。它们用于支持相关框架概念和工程机制的进一步核验;本篇没有在本次写作中逐一实时检查这些页面的最新版本,也未开展框架源码审计。正式工程实施时应锁定版本、核对对应 API 与文档发布日期。

  1. LangGraph - Overview:docs.langchain.com/oss/python/langgraph/overview。图执行与 Agent 编排的总体定位。
  2. LangGraph - Persistence:docs.langchain.com/oss/python/langgraph/persistence。状态、检查点和线程。
  3. LangGraph - Durable Execution:docs.langchain.com/oss/python/langgraph/durable-execution。恢复、重放和副作用注意事项。
  4. LangGraph - Interrupts:docs.langchain.com/oss/python/langgraph/interrupts。人工介入与恢复。
  5. OpenAI Agents SDK - Handoffs:openai.github.io/openai-agents-python/handoffs。Agent 之间的控制交接。
  6. OpenAI Agents SDK - Running agents:openai.github.io/openai-agents-python/running_agents。Runner、工具与执行循环。
  7. Microsoft AutoGen - Official Documentation:microsoft.github.io/autogen。多 Agent 交流与团队设计的历史及技术资料入口;需检查维护与版本状态。
  8. Microsoft Agent Framework - Official Documentation:learn.microsoft.com/en-us/agent-framework。微软 Agent 框架的现行资料入口;具体适用性需版本核对。
  9. CrewAI - Documentation:docs.crewai.com。角色、任务、团队与流程抽象。
  10. Temporal - Documentation:docs.temporal.io。持久工作流、活动、重试与执行恢复。
  11. PostgreSQL - Transaction Isolation:www.postgresql.org/docs/current/transaction-iso.html。事务隔离和并发控制。
  12. PostgreSQL - Explicit Locking:www.postgresql.org/docs/current/explicit-locking.html。并发锁与共享资源协调。
  13. OpenTelemetry - Documentation:opentelemetry.io/docs。跨组件追踪、指标与日志。
  14. OWASP GenAI Security Project:genai.owasp.org。提示注入、工具风险和 Agent 安全参考。
  15. Model Context Protocol - Specification:modelcontextprotocol.io/specification。模型与外部工具/资源的接口协议;并非完整多 Agent 编排标准。

附录 B:研究证据、实现与验证声明 ​

研究定位。 本篇属于 Agent System L5 技术架构研究。TaskNode、Attempt、消息信封、状态枚举、协作拓扑和验收矩阵是用于说明工程机制的中立参考设计,不是某个行业组织颁布的统一规范。部分术语(handoff、delegation、supervisor、blackboard)在不同框架中的具体含义可能不同。

资料边界。 框架对照基于公开技术概念与已知官方资料入口,未实时核验各框架最新版本的完整 API、许可证、维护状态或生产可靠性;不得将本篇视为框架兼容性认证或版本选型报告。数据库、事务、Outbox、租约和 fencing 的讨论属于通用分布式系统工程方法,实际保证取决于具体存储与外部系统的实现。

实验边界。 第十二节给出 Python 标准库教学示例,仅涉及顺序 DAG 执行、失败阻塞和环检测。它没有真实 Agent、LLM、数据库、消息队列、分布式 Worker 或外部副作用。即使示例测试通过,也不能证明生产级并发安全、任务恢复、模型质量、权限隔离和多 Agent 协作收益。实际运行记录应以交付时执行结果为准。

待验证事项。 动态任务图合法性、跨进程恢复、Outbox、重复消费、租约失效、fencing、权限拒绝、审批恢复、取消传播、共享状态冲突和真实模型协作收益,均需在版本锁定的集成环境中实施故障注入、回归与对照实验。任何上线结论还应结合具体任务分布、数据风险、预算和业务验收要求。