--- title: "01-A2A协议与Agent生态全景" created: 2026-05-15 tags: - 博客 --- # A2A协议与Agent生态全景 前面咱们学了 MCP(Model Context Protocol),它是一个让 AI 发现和调用工具的标准化协议,本质上解决的是**垂直方向**的问题——一个 Agent 如何获取和使用外部能力。 但现实世界中的工作不是一个人完成的,而是团队协作的结果。随着 Agent 在各行各业的部署,一个新问题浮出水面:**当多个 Agent 需要互相通信、协商、协作时,它们之间用什么"语言"?** 这就是 A2A(Agent-to-Agent Protocol)要解决的问题。 ## 从单人干活到团队协作 先想一个场景。你是一家电商公司的技术负责人,公司已经部署了三个 Agent: - **客服 Agent**:处理用户咨询、退货退款 - **仓储 Agent**:管理库存、发货、入库 - **物流 Agent**:对接快递公司、追踪包裹 之前它们各干各的,没问题。但有一天,一个用户问客服:"我前天买的蓝牙耳机怎么还没到?" 客服 Agent 能查到订单,但查不到包裹位置——那是物流 Agent 的地盘。客服 Agent 需要去问物流 Agent:"订单 #12345,帮我查下物流状态。"物流 Agent 查完回一句:"快递员正在派送中,预计下午 3 点前到。" **Agent 和 Agent 之间的这条通信链路,就是 A2A 来标准化的事情。** 你可能会问:"这不就是 API 调用吗?客服 Agent 调一下物流 Agent 的 API 不就行了?" 这里有一个关键区别。 ## 为什么 API 调用不够用 普通的 API 调用是**结构化、预定义的**: ``` POST /logistics/track Body: {"orderId": "12345"} Response: {"status": "delivering", "eta": "2026-05-15 15:00"} ``` 这在工作流程完全确定时够用。但 Agent 之间的交互往往是**非结构化的、上下文相关的、需要协商的**。比如: - **任务协商**:"这个需求我一个人搞不定,你能帮忙做 A 部分吗?" - **信息澄清**:"你说的'那个客户'是指张三还是李四?最近两天都在和他们沟通。" - **结果确认**:"我分析出了三种方案,你帮我看看哪个更合适?" - **能力发现**:"我没有翻译功能,哪个 Agent 能做中译英?" - **进度同步**:"我已经完成了数据清洗,可视化部分转交给谁?" 这些交互的特点是:**不确定的、上下文敏感的、像人和人之间的对话**。而传统 API 是为确定性的机器间通信设计的,不太适合这种场景。 ## A2A 是什么 > **A2A(Agent-to-Agent Protocol)** 是 Google 于 2025 年 4 月发布的开放协议,定义了 AI 智能体之间如何进行标准化的任务协调、信息交换和能力发现。 把它和我们已经学过的概念放在一起看,层次关系就清楚了: ``` A2A(水平协作) Agent ←──→ Agent ←──→ Agent ↓ ↓ ↓ MCP MCP MCP(垂直能力) ↓ ↓ ↓ 工具/API 工具/API 工具/API ``` - **MCP**:Agent 向下获取能力(调用工具、读取资源) - **A2A**:Agent 之间横向协作(任务委托、信息交换、能力发现) 两者不是竞争关系,而是互补关系。 ### A2A 的核心设计 A2A 基于几个关键设计理念: **1. 基于"Agent Card"的能力发现** 每个 Agent 发布一张"名片"(Agent Card),描述自己能做什么: ```json { "name": "物流追踪Agent", "description": "负责查询快递物流状态、计算预计送达时间、处理物流异常", "url": "https://logistics-agent.company.com/a2a", "capabilities": { "streaming": true, "pushNotifications": false }, "skills": [ { "id": "track_package", "name": "追踪包裹", "description": "根据订单号查询包裹的实时物流状态" }, { "id": "estimate_delivery", "name": "预计送达", "description": "计算预计送达时间,支持多快递公司" }, { "id": "report_exception", "name": "物流异常上报", "description": "上报丢件、破损、滞留等物流异常情况" } ], "defaultInputModes": ["text", "file"], "defaultOutputModes": ["text"] } ``` 当客服 Agent 需要查询物流时,它先看物流 Agent 的 Agent Card,发现它有 `track_package` 技能,然后发起任务。**Agent Card 让 Agent 能自动发现"谁可以做什么",而不需要人工配置调用关系。** **2. 任务(Task)为核心** A2A 的通信以"任务"(Task)为单位,不是一次性的 API 调用。一个 Task 有其生命周期: ``` 创建(Created)→ 处理中(Processing)→ 完成(Completed) → 失败(Failed) → 需要澄清(NeedsClarification) ``` 这比 API 请求-响应模型更灵活。比如物流 Agent 处理到一半发现订单号模糊,它可以把 Task 状态设为"NeedsClarification",附带一个澄清问题。客服 Agent 收到后,去问用户,然后把澄清信息补上,Task 继续。 **3. 多模态通信** A2A 支持文本、文件、图片、视频等多种内容格式。Agent 之间不仅能"说话",还能共享文件、传图片、交换结构化数据。 **4. 流式和非流式支持** Agent 的推理和操作可能需要时间。A2A 支持流式返回中间状态,让请求方知道任务在进展中,而不是干等。 ## A2A 的任务生命周期 理解了 Task 的概念后,我们走一遍完整的 Task 生命周期: ``` 阶段1: 任务创建 客服Agent → 物流Agent: "帮我查订单 #12345 的物流状态" Task状态: Created 阶段2: 任务处理中 物流Agent: 1. 解析订单号 2. 调用快递公司 API 3. 等待结果返回... Task状态: Processing 阶段2.1: [可能的] 需要澄清 物流Agent → 客服Agent: "订单 #12345 对应两个快递单号:SF123 和 YT456,你要查哪个?" Task状态: NeedsClarification 客服Agent → 用户 → 客服Agent → 物流Agent: "查 SF123" Task状态: Processing(继续) 阶段3: 任务完成 物流Agent → 客服Agent: { "status": "派送中", "courier": "顺丰快递", "current_location": "上海分拣中心", "eta": "2026-05-15 15:00", "tracking_url": "https://sf-express.com/track/SF123" } Task状态: Completed ``` > 注意 Task 和 API Call 的关键区别:**Task 是有状态的、长生命周期的、可能需要多次交互的。** API Call 是一次请求一次响应就结束了。A2A 的 Task 可以跨越多轮对话、多次人员介入、多个 Agent 的协作。 ## A2A vs MCP vs Function Call 这可能是你最关心的问题:学了 Function Call,学了 MCP,现在又来个 A2A,它们三个到底怎么区分? | 维度 | Function Call | MCP | A2A | | --- | --- | --- | --- | | **通信方向** | LLM → 工具 | Agent → 工具服务 | Agent ←→ Agent | | **解决的问题** | "该调哪个函数,传什么参数" | "如何标准化管理和发现工具" | "Agent 之间怎么协作" | | **核心单位** | 一次工具调用 | 一个工具服务器 | 一个任务(Task) | | **有状态吗** | 否(单次调用) | 否(连接有状态,调用无状态) | 是(Task 有完整生命周期) | | **谁定义的** | 各 LLM 厂商各自实现 | Anthropic | Google | | **协议层** | 不是协议,是 LLM 功能 | JSON-RPC 2.0 | HTTP + SSE + JSON | | **类比** | 人的"动手能力" | USB Type-C 标准接口 | 团队协作工作流 | ### 它们在同一个系统中的位置 想象一个完整的 Agent 系统: ``` 用户: "帮我分析竞品A的价格策略,然后生成一份报告发到老板邮箱" ↓ ┌─────────────────────────────────────────┐ │ 编排Agent(使用 A2A 协调子Agent) │ │ ┌──────┐ A2A ┌──────┐ A2A ┌──────┐ │ │ │数据 │←────→│分析 │←────→│报告 │ │ │ │Agent │ │Agent │ │Agent │ │ │ └──┬───┘ └──┬───┘ └──┬───┘ │ │ │MCP │MCP │MCP │ │ ↓ ↓ ↓ │ │ [爬虫工具] [统计工具] [邮件工具] │ │ [数据库] [图表工具] [文档模板] │ └─────────────────────────────────────────┘ ``` - 编排 Agent 通过 **A2A** 把子任务分派给数据 Agent、分析 Agent、报告 Agent - 每个子 Agent 通过 **MCP** 调用自己需要的工具 - 工具内部使用 **Function Call** 机制让 LLM 决定调用哪个函数 三者互不冲突,协同工作。 ## A2A 的 Java 实践 虽然没有 Spring AI 官方的 A2A 支持,但你可以基于 HTTP 和 JSON 实现 A2A 的核心机制: ### Agent Card 的定义 ```java @Data public class AgentCard { private String name; private String description; private String url; private Map capabilities; private List skills; @Data public static class Skill { private String id; private String name; private String description; } } ``` ### Agent Card 端点 ```java @RestController @RequestMapping("/a2a") public class A2AController { private final AgentCard myCard; public A2AController() { this.myCard = new AgentCard(); myCard.setName("物流追踪Agent"); myCard.setDescription("负责查询快递物流状态"); myCard.setUrl("https://logistics-agent.company.com/a2a"); myCard.setSkills(List.of( new AgentCard.Skill("track_package", "追踪包裹", "根据订单号查询物流"), new AgentCard.Skill("estimate_delivery", "预计送达", "计算预计送达时间") )); } // Agent Card 端点:任何 Agent 都可以访问 @GetMapping("/.well-known/agent-card.json") public AgentCard getAgentCard() { return myCard; } // Task 端点:接收其他 Agent 的任务 @PostMapping("/tasks") public ResponseEntity createTask(@RequestBody TaskRequest request) { // 根据请求中的 skill ID 路由到具体处理逻辑 String skillId = request.getSkillId(); String result = switch (skillId) { case "track_package" -> trackPackage(request.getParameters()); case "estimate_delivery" -> estimateDelivery(request.getParameters()); default -> throw new IllegalArgumentException("Unknown skill: " + skillId); }; return ResponseEntity.accepted().body(new TaskResponse("processing", result)); } } ``` ### Agent 间调用 ```java @Service public class AgentCollaborationService { private final RestClient restClient; public AgentCollaborationService(RestClient.Builder builder) { this.restClient = builder.build(); } /** * 发现其他 Agent 的能力 */ public AgentCard discoverAgent(String agentBaseUrl) { return restClient.get() .uri(agentBaseUrl + "/.well-known/agent-card.json") .retrieve() .body(AgentCard.class); } /** * 向另一个 Agent 发起任务 */ public TaskResponse delegateTask(AgentCard targetAgent, String skillId, Map params) { TaskRequest request = new TaskRequest(); request.setSkillId(skillId); request.setParameters(params); return restClient.post() .uri(targetAgent.getUrl() + "/tasks") .body(request) .retrieve() .body(TaskResponse.class); } } ``` ## Agent 生态全景图(2026 年 5 月) 学完这么多概念,你可能需要一个全景视角。以下是当前 AI Agent 生态的整体格局: ### 基础设施层 | 组件 | 代表技术 | 作用 | | --- | --- | --- | | **大模型** | GPT-5.x, Claude 4.5, Gemini 3.1, DeepSeek-V3.2/R1 | 提供理解和推理能力 | | **推理模型** | o3, R1, Qwen3-Slow | 提供深度推理能力 | | **嵌入模型** | text-embedding-v3, bge-m3 | 向量化文本,支撑 RAG | | **向量数据库** | Milvus, Qdrant, PGVector | 存储和检索向量 | ### 协议与标准层 | 协议 | 发布时间 | 发起方 | 解决问题 | | --- | --- | --- | --- | | **Function Call** | 2023 | OpenAI | LLM 如何输出工具调用指令 | | **MCP** | 2024.11 | Anthropic | Agent 如何标准化管理工具 | | **A2A** | 2025.04 | Google | Agent 之间如何协作通信 | | **AGENTS.md** | 2025 | 社区 | 项目如何向 AI 描述自己 | ### 框架与运行时层 | 框架 | 语言 | 特点 | | --- | --- | --- | | **Spring AI** | Java | Spring 生态,企业级 | | **Spring AI Alibaba** | Java | 增强版,Graph 工作流 + 百炼集成 | | **LangChain** | Python/JS | 最成熟,生态最丰富 | | **LangGraph** | Python | 有状态工作流编排 | | **CrewAI** | Python | 多 Agent 协作,角色扮演 | | **AutoGen** | Python | 微软,自主对话 Agent | | **Dify** | 低代码 | 可视化编排,快速搭建 | ### 产品与平台层 | 产品 | 类型 | 核心能力 | | --- | --- | --- | | **OpenClaw(龙虾)** | 自托管 Agent 运行时 | 7×24 自主执行,多平台集成 | | **Paperclip** | Agent 编排平台 | 创建完整 AI"公司" | | **Claude Code** | AI IDE/CLI | 终端中的 AI 编程助手 | | **Cursor** | AI IDE | 集成 AI 的代码编辑器 | | **Codex CLI** | AI CLI | OpenAI 的命令行 AI 工具 | | **Operator** | AI 浏览器操作 | OpenAI 的网页操作 Agent | ### 这个格局告诉我们的几件事 **1. 协议统一正在进行** 2024-2025 年,MCP 和 A2A 分别解决了 Agent 的"向下获取能力"和"水平协作"的标准化问题。虽然它们来自不同的厂商(Anthropic 和 Google),但社区已经在同时采纳两者。未来的 Agent 系统大概率是 **MCP + A2A** 的组合。 **2. 从"框架"到"平台"** 2023-2024 年的主题是框架(LangChain、Spring AI、CrewAI),让开发者能搭建 Agent。2025-2026 年的主题是平台(OpenClaw、Paperclip、Dify),让 Agent 能长期运行、自我管理。这类似于软件工程从"写代码"到"运维"的演进——Agent 也需要 DevOps。 **3. Agent 正在"向下扎根"** Agent 不再只是对话界面后面的一个后端服务。它正在进入操作系统层面——Claude Code 在你的终端里,OpenClaw 在你的桌面上,Operator 在你的浏览器里。Agent 越接近操作系统,它能做的事情就越多,但也越需要安全边界的约束。 **4. Skills 成为可复用单元** Skills(技能包)成为一个跨框架的概念。Spring AI、Claude Code、OpenClaw、Codex CLI 都有自己的 Skills 体系。虽然格式还没统一,但理念基本一致:目录结构、声明式元数据、渐进式加载、按需执行。Skills 可能成为 Agent 时代的"npm 包"或"App Store"。 ## 小结 **A2A 是什么**:Google 发布的 Agent 间通信协议,解决 Agent 如何发现彼此能力、发起任务、协调协作的问题 **和 MCP 的关系**:互补而非竞争 - MCP = 垂直(Agent → 工具) - A2A = 水平(Agent ←→ Agent) **Task 为核心**:A2A 以有状态、长生命周期的 Task 为单位,而非一次性 API 调用,支持澄清、协商、中断恢复 **技术选型参考**: - 单个 Agent + 少量工具 → Function Call 就够了 - 大量工具 + 跨团队复用 → 加 MCP - 多 Agent 协作 → 加 A2A - 需要 7×24 自主运行 → 上 OpenClaw 类平台 **Agent 生态趋势**: 1. 协议统一(MCP + A2A 组合) 2. 从框架到平台(Agent DevOps) 3. Agent 向下扎根(进入 OS 层面) 4. Skills 成为可复用单元 下一篇咱们来聊聊 **Vibe Coding 与 AI 驱动的开发新范式**——当 AI 不只是辅助编码,而是彻底改变软件开发的方式。