Spring AI Multi-Agent 生产级实战:从原理、架构到高并发落地一、先说结论:生产环境为什么要做 Multi-Agent很多团队第一次做 AI 系统,直觉上会先做一个“万能 Agent”:一个系统 Prompt一组工具一个模型入口所有业务都往里塞这个方案在 Demo 阶段很顺,但进入生产后会迅速暴露 4 个结构性问题:问题表现根因上下文膨胀Token 成本高、响应慢所有职责都塞到一个 Prompt 中指令冲突回答风格不稳定、工具调用混乱同一 Agent 同时承担规划、检索、执行、总结故障半径过大一个环节失败导致整链路失败没有职责隔离与可降级设计难以扩展新场景接入越来越慢缺少统一的角色建模、编排协议与治理机制所以,**Multi-Agent 并不是“为了高级而高级”,而是把大模型系统从 Prompt Demo 升级为可治理的软件系统。**从架构视角看,Multi-Agent 的本质是 3 件事:职责拆分:让不同 Agent 只处理自己最擅长的领域。执行编排:把多个 Agent 串成有状态的业务流程。工程治理:对成本、延迟、故障、审计、扩容做系统化控制。二、什么样的场景真正适合 Multi-Agent不是所有 AI 需求都需要拆成多智能体。判断标准很简单:2.1 适合 Multi-Agent 的场景任务链路长:需要“理解意图 - 检索 - 执行工具 - 汇总回复”角色边界清晰:不同步骤需要不同 Prompt、工具集、模型策略需要异步化:部分步骤耗时长,不能让用户一直同步等待需要治理:希望按 Agent 粒度做限流、扩容、熔断、灰度需要审计:必须知道“哪个 Agent 在什么时候做了什么决定”2.2 不适合 Multi-Agent 的场景单轮问答工具数量很少,流程固定没有明显职责边界业务还处于试验阶段,优先验证价值而非过度架构一个非常实用的经验是:当一个 Agent 同时承担“规划、检索、执行、风控、总结”五类职责时,就该拆了。三、企业级 Multi-Agent 的核心设计原则要把 Multi-Agent 做成生产系统,建议遵循以下设计原则。3.1 Agent 不是类,而是可治理的执行单元在工程上,Agent 不应只是一个chatClient.prompt().call()的代码片段,而应该具备:唯一身份:agentCode明确职责:输入、输出、边界、依赖独立治理:超时、重试、并发、熔断、限流可观测:耗时、成功率、Token 用量、失败原因可编排:能被工作流引擎或编排层调度3.2 上下文必须分层很多项目出问题,不是因为模型不够强,而是上下文管理混乱。建议把上下文拆成 4 层:userContext:用户本轮输入与用户画像conversationContext:会话历史摘要workflowContext:当前流程内的中间结果executionContext:超时、traceId、tokenBudget、tenantId 等运行信息这样做有两个好处:避免所有 Agent 都拿到全部上下文,减少 Token 浪费让每个 Agent 只读取自己所需的最小上下文,降低幻觉和误操作概率3.3 编排层必须独立于 Agent不要把流程控制硬编码进某个 Agent 里。正确方式是:Agent 只负责“做事”Orchestrator 负责“决定谁在什么时候做什么”否则后期一旦需要并行执行、失败补偿、流程回放、灰度切流,维护成本会非常高。3.4 模型调用必须可替换生产系统不能把业务逻辑直接绑定到某个具体模型厂商。要做到:Prompt 与模型参数配置化模型路由抽象化响应结构标准化超时、重试、fallback 策略统一化Spring AI 的价值就在这里,它把模型接入层标准化了,业务代码可以围绕ChatClient、ChatModel、ToolCallback展开,而不是深耕某一家 API 细节。四、整体架构:从入口到执行再到治理下面是一套更接近生产落地的参考架构。┌────────────────────────────┐ │ API Gateway │ │ 鉴权 / 限流 / 灰度 / 审计 │ └─────────────┬──────────────┘ │ ┌─────────────▼──────────────┐ │ Session Coordinator │ │ 会话接入 / Trace / 配额控制 │ └─────────────┬──────────────┘ │ ┌───────────────────▼───────────────────┐ │ Agent Orchestrator │ │ 路由 / DAG / 状态机 / 重试 / 补偿 / SLA │ └───────┬──────────────┬───────────────┘ │ │ ┌──────────▼───────┐ ┌────▼─────────────┐ │ Planner Agent │ │ Policy Agent │ │ 任务规划 / 路由 │ │ 风控 / 审批 / 规则 │ └──────────┬───────┘ └────┬─────────────┘ │ │ ┌──────────────────▼──────────────▼─────────────────┐ │ Domain Agents │ │ RAG Agent / Tool Agent / SQL Agent / Summary Agent │ └────────────┬─────────────┬─────────────┬──────────┘ │ │ │ ┌──────▼──────┐ ┌────▼─────┐ ┌────▼──────┐ │ Vector Store │ │ Tool Hub │ │ Memory Hub │ │ Milvus/PGV │ │ HTTP/RPC │ │ Redis/DB │ └──────┬──────┘ └────┬─────┘ └────┬──────┘ │ │ │ ┌──────▼───────────────────────────▼──────┐ │ Observability Governance Layer │ │ Prometheus / SkyWalking / OTel / DLQ │ └──────────────────────────────────────────┘4.1 各层职责层次职责关键技术接入层鉴权、租户隔离、速率限制、会话入口Gateway、JWT、Sentinel协调层会话状态、token 预算、trace 生成Redis、Micrometer编排层Agent 路由、DAG 执行、失败补偿Spring Boot、Kafka、状态机Agent 层专项能力执行Spring AI、Tool Calling、RAG能力层向量检索、外部工具、记忆存储Milvus、Redis、HTTP/RPC治理层指标、日志、追踪、告警、审计Prometheus、SkyWalking、ELK4.2 为什么推荐“同步入口 + 异步内核”用户入口可以是同步 HTTP 或 SSE,但内部执行建议尽量事件化、异步化:用户不需要知道底层到底是串行还是并行可以把长耗时步骤从同步线程中剥离更容易做削峰、重试、死信、补偿更适合高并发场景下独立扩缩容这也是企业 Multi-Agent 和 Demo 项目最核心的差别之一。五、技术选型:为什么是 Spring AI,而不是简单拼 SDK5.1 Spring AI 的优势对 Java 团队来说,Spring AI 的真正价值不是“能调模型”,而是它把 AI 能力纳入了 Spring 生态:用统一接口屏蔽不同模型供应商差异可以无缝接入 Spring Boot 配置体系能复用 Spring 的依赖注入、AOP、配置中心、监控能力与 WebFlux、消息中间件、缓存、数据库、网关天然集成5.2 推荐的生产组合领域推荐选型应用框架Spring Boot 3.xAI 抽象层Spring AI高并发 WebSpring WebFlux消息总线Kafka缓存与会话Redis向量检索Milvus / PGVector配置中心Nacos / Apollo限流熔断Sentinel / Resilience4j可观测Micrometer + Prometheus + SkyWalking容器编排Kubernetes5.3 不建议直接把 LangChain 风格逻辑硬塞进生产主链路原因很现实:业务边界容易被 Prompt 流程吞掉状态可见性弱,问题难排查与已有微服务治理体系融合成本高如果你已经有成熟的 Spring Cloud / K8s / Kafka 基建,那么用 Spring AI 做“模型层标准化”,再用自己的编排层做业务治理,通常更稳。六、核心对象建模:让 Agent 具备生产属性这一节给出一套更完整的生产级代码骨架。6.1 Agent 抽象public interface Agent { String code(); String description(); AgentType type(); MonoAgentResult execute(AgentRequest request); }public enum AgentType { PLANNER, RAG, TOOL, POLICY, SUMMARY }6.2 请求上下文import lombok.Builder; import lombok.Value; import java.time.Instant; import java.util.List; import java.util.Map; @Value @Builder(toBuilder = true) public class AgentRequest { String traceId; String sessionId; String tenantId; String userId; String userInput; ListMessageSnapshot history; W