☰
AI应用工程化底座:多供应商接入、Agent编排与MCP/RAG扩展实战
2026/10/7 2:18:44 网站建设 项目流程

说实话,这两年做AI应用开发,最让人头疼的不是大模型能力不够,而是整个开发链条太碎了:模型要接这个厂那个厂,工具函数散落各处,知识库和Agent老死不相往来,上一套对话逻辑换个供应商就全得重写。XXL-AI这个平台,核心就是把“Agent编排、多供应商、MCP + SKILL + RAG扩展”这几件事揉到一个工程化底座里,让AI应用从“能跑”变成“能稳定交付、能长期维护”。这篇东西我会把这些模块拆开讲清楚,包括设计思路、实现细节和我实际踩过的坑,适合正在搭AI应用平台、或者想给自己的Agent项目引入工程化规范的团队参考。

1. 整体定位与设计思路

1.1 这套平台到底解决了什么问题

我先说个很典型的场景。团队里有人用OpenAI做了个原型,效果不错,要上线了,发现成本扛不住,想换国产模型。结果呢?代码里到处都是OpenAI的SDK调用,tool calling的格式不一样,system prompt里写死了一些行为,一换供应商,整个推理链路全崩。这就是典型的“模型供应商锁定”。

XXL-AI的定位不是再做一个“套壳工具”,而是把AI应用开发里那些反复出现的通用问题统一收口。它把模型接入、Agent调度、工具扩展、知识库检索、任务运行这几层拆成模块,每层都定义了清晰的协议。你写业务的时候关心的是“这个流程怎么编排”,不用管底层是哪个模型在跑。数据表、代码库、文档里的知识和Agent之间的对接,通过RAG和MCP统一打通。

这个思路借鉴了后端开发里的“接口隔离”原则——把变的部分和不变的部分切开。供应商会变、模型会升级、工具会增删,这是变的部分;Agent的基本执行循环、会话管理、权限控制、任务队列,这是相对不变的部分。平台的主要精力就花在稳定这部分,同时给变的这部分留好扩展位。

1.2 技术选型与整体架构

技术栈上我选了Python为主力语言,不是因为它性能最好,而是因为AI生态里最成熟的东西都在Python这边。不管是LangChain的生态、各类向量库的客户端,还是MCP的官方SDK,Python支持都是最优先的。底层跑异步任务,平台核心用FastAPI提供API服务,配合Celery处理长耗时任务,向量库用的Milvus,关系数据用PostgreSQL,Agent的每一次中间状态都用JSON Lines存下来方便回放。

整体架构不是微服务——对大部分业务来说微服务的成本是纯负担——而是模块化单体。所有模块在同一个进程内以插件方式加载,按业务量横向扩展实例就行。网关层做任务分发和会话路由,核心编排层管Agent状态机,扩展层通过MCP Server和Skill包接入外部能力,知识层做文档解析、向量化、召回重排。模块间通过内部事件总线通信,比如“RAG召回完成”会触发“Agent生成答案”这个节点,但两者不直接耦合。

这个架构最大的好处是:接一个新供应商,或者加一种知识库类型,不需要动主流程代码,注册一下协议实现就行。后面讲到的多供应商、Agent编排、扩展机制,全部建立在这套模块化基础上。

1.3 和LangChain、Dify这类方案的区别在哪

LangChain是一个工具链,它给你的是积木,但怎么搭、搭完怎么运维,它不管。Dify是一个应用平台,上手确实快,但对内部系统定制、私有协议接入、细粒度权限控制这些场景,你会发现被平台框架框住了。XXL-AI走的是中间路线:核心运行时的协议是固定的,但每个扩展点都允许你用自己的实现替换默认实现。

举个例子,同为Agent编排,LangChain的AgentExecutor是以“工具调用”为中心的,所有东西都围绕tools转。在XXL-AI里,Agent执行单元是“节点”,一个节点可以是一次模型调用、一次工具执行、一次RAG检索、一次人工审批,甚至是一段自定义的Python代码。编排器把节点串成DAG,支持条件分支、循环、并行。不是“Agent里塞工具”,而是“流程里有Agent节点”,这两种心智模型做出来的系统,复杂度天花板完全不同。

2. 多供应商接入与模型路由

2.1 供应商抽象层设计

多供应商这件事,难的不是多写几个SDK调用,而是把各家模型在“能力边界”和“行为习惯”上的差异抹平。我定义了一套供应商接口(Provider Interface),核心就几个方法:chat、stream_chat、embed、tool_call、count_tokens。每个供应商适配器实现这套接口,平台内部只跟接口打交道。

实际操作中,最麻烦的是tool calling格式的差异。OpenAI的tool格式是functions数组,Anthropic是tools带input_schema,国产模型各家又各有各的变体。我在适配层里做了统一转换,内部用一套JSON Schema描述工具,适配器负责翻译成各家模型认识的格式。这个翻译层会吃掉很多性能,但值得——因为上层业务代码永远不用关心“当前这个模型是哪个厂的”。

供应商适配完还要配一组元数据:支持的上下文长度、是否支持并行工具调用、是否支持流式输出、价格倍率、输入输出限流阈值。这些元数据是后面路由决策的基础。

2.2 模型路由与降级策略

路由不能是简单的随机轮询或固定优先级。我在平台里做了一个可配置的路由规则引擎,支持按业务线、按用户等级、按预算、按延迟要求做决策。规则大致长这样:

  • 正式业务线默认走主力供应商标识(比如内部代号A),当A的响应延迟超过3秒或连续报错2次,自动降级到备用供应商B。
  • 内部测试流量全部走便宜模型,结果校验通过后的人工评测抽样才走旗舰模型。
  • 重试逻辑分两层:单次请求内,超时重试一次换供应商;任务队列层,整个Agent任务失败后重新入队,从断点继续。

我踩过一个比较隐蔽的坑:某些供应商的模型虽然API返回200,但内容质量明显劣化,比如空回复、胡言乱语。硬指标检测不出这种问题。后来加了个软校验:对关键业务回复做一轮长度检查和关键词命中检查,不达标直接降级重跑。这个“质量降级”开关很管用,但要注意别对普通场景开启,会影响整体响应速度。

2.3 密钥管理与配额控制

密钥这关必须做在平台层,不能散落在业务代码和服务端环境变量里。我做了个独立的密钥管理模块,密钥只在调用供应商API前一刻从加密存储里取出,用完立刻销毁引用。每个接入方分配独立的API Key,配额限流在平台网关统一执行,不同供应商的余额和配额在统一看板里聚合展示。这样不管是成本归因还是异常审计,都有据可查。

3. Agent编排:从单轮问答到多步任务

3.1 Agent执行循环的工程化改造

论文里的Agent执行循环很简单:观察、思考、行动。但它是不管状态持久化、不考虑中断恢复、不关心对话轮次预算的。工程化编排的第一步,就是把这套循环变成一个有确定语义的状态机。

状态机的流转大概是:IDLE(等待输入) →PLANNING(生成计划) →EXECUTING(执行当前步骤) →REFLECTING(观察结果并评估) →COMPLETED或FAILED。用户请求进来,先判断是否需要规划,能一步完成的直接走单轮;多步任务进入规划阶段,编排器根据模型输出拆出步骤清单,每个步骤包含“调用哪个节点、传什么参数”。

这个状态机的状态在每次转换时都持久化到数据库。为什么要持久化?因为真实场景里一个任务可能会跑几分钟甚至更久,中间可能经历服务重启、模型超时。如果状态只留在内存里,一个重启就全丢了。持久化之后,任务可以从最近的Checkpoint继续跑。

3.2 节点粒度与编排范式

我把节点分成几类:

  • LLM节点:调用模型生成文本或JSON,这是最常用的一类。
  • Tool节点:执行一个MCP工具或内置技能,比如查数据库、调外部API。
  • RAG节点:根据检索式(query)去向量库里面召回内容,再拼成上下文。
  • Flow节点:控制类节点,包括条件判断IF、循环FOR、并行FORK/JOIN。
  • Human节点:挂起任务,等待人工输入或审批,常见于需要确认后才能继续的场景。

编排的核心画布是一个DAG(有向无环图)。模型不负责直接画图——业界流行的完全让模型自己规划工具链的做法,在工程项目里太不可控。我采用“模板优先”的策略:对于高频业务,编排图是人工配置好的,模型只负责填参数和执行顺序微调;对于探索性任务,模型可以提一个计划,由编排器校验计划合法性(节点存在性、参数类型、依赖关系)后再执行。

3.3 多Agent协作落地

多Agent听着高级,实际工程里用不好就是灾难。我做了一个比较务实的模式:主Agent(Supervisor)+ 子Agent(Worker)。主Agent负责拆解任务并把子任务分发给不同的Worker,Worker各自独立执行完把结果返回给主Agent汇总。每个Worker也是一个编排图,只不过它的输入输出都按协议规范化。

多Agent模式下最头疼的是上下文管理。信息在Agent间传来传去,如果全量透传,上下文窗口很快爆掉。我做法是:每个Agent只接收跟自己的子任务相关的上下文切片,输出时只输出“结构化结果摘要”而不是原始日志。传递的协议是一个标准JSON格式,包含status、summary、data_ref(指向结果存储的引用)、confidence。模型生成的内容如果解析不合法,编排器会把失败信息反馈给它并要求重新生成,最多重试两次,超过就标记失败并通知主Agent。

3.4 编排的可观测性:回放与调试

这个可能是我做这个平台以来最值得的一个模块。Agent跑的过程中,每一步的输入输出、token消耗、模型名、中间决策理由,全部以事件流方式记录到本地存储。有专门的调试页面可以像看视频回放一样,一步步回看Agent当时看到了什么、为什么选择了这个工具、模型返回了什么样的中间内容。

调Agent最痛苦的其实是“不确定性”。同样的输入换个模型温度调低,结果可能就变了。回放日志能把“当时发生了什么”钉死,排查问题不用靠猜。建议做Agent编排的团队,早期就把可观测性当核心功能来投入,这比花时间调prompt值得多。

4. 扩展机制:MCP、SKILL与RAG

4.1 MCP在平台里的定位:外部工具的通用插口

MCP(Model Context Protocol)本质上是一个标准化协议,让AI应用能统一连接外部数据源和工具。我把它比作AI世界的USB接口:以前每种设备要专属线缆(各家API),现在只要设备支持MCP,插上就能用。在XXL-AI里,MCP Server是Tool节点的数据来源,通过协议接入,平台不用关心工具背后的实现细节。

实际接入要区分两种传输模式:本地用的stdio模式,适合跑在本机的命令行工具;远程用的SSE/streamable HTTP模式,适合部署在服务端的工具服务。平台内置了MCP Client的管理器,启动时会根据配置连接对应的MCP Server,拉取工具列表,注册到工具注册表。工具注册表的每一项都有名字、描述、参数JSON Schema、所属Server、是否需要鉴权等信息。

接MCP时有个常见误区:以为所有工具都能无脑给Agent用。不是的,工具越多人选越难,模型经常挑错。我维护了一个“工具白名单”机制,每个Agent实例只挂载它明确需要的那几个工具,而不是全局共享全部。宁可需要时动态再加,也不要一上来就把100个工具塞给模型。

4.2 SKILL:把Prompt、工具和流程打包成技能单元

SKILL是比单个工具粒度更大的扩展单元。一个Skill可以包含:

  • 一组预置的Prompt模板(用于引导模型理解任务)
  • 若干工具调用序列(比如“先搜索再总结再翻译”)
  • 文件资源(比如领域词表、参考示例)
  • 元数据(版本号、作者、适用场景、输入参数定义)

这有点像给模型发了一本“岗位手册”——不仅告诉它可以用哪些工具,还教会它这类任务的标准作业流程。比如“合同审查”这个Skill,包含的流程是:解析合同文本 → 提取关键条款 → 与标准条款库比对 → 输出风险清单。模型执行时按照Skill定义的步骤走,比让它自由发挥稳定得多。

Skill的格式我用了YAML加Markdown组合,YAML存元数据和配置,Markdown存实际指导内容。这样非程序员也能通过编辑文件来维护技能。版本控制走Git,每个Skill有独立仓库,平台通过注册机制加载。上线新Skill前走一轮自动测试:用固定的输入样本跑一遍,断言输出结构合法性和关键词覆盖。

4.3 RAG:知识库不是向量数据库的堆砌

RAG在这个平台的定位是“Agent的外部记忆”。很多团队做RAG容易掉进一个坑:以为装个向量库、把文档切一切塞进去就能用了。实际做下来,召回质量差、答非所问,往往出在文档解析、切片策略、召回重排这些前置环节。

文档解析要区分格式:PDF要先做版面分析还是直接抽文本?表格要不要转成Markdown再入库?扫描件要不要OCR?这些处理策略直接决定后面能召回什么。切片也不能一刀切固定字数,结构化文档按标题层级切,表格单独存,问答题库按语义完整度切。向量化我用了Embedding模型的同时,还会抽取关键词、实体标签一起存,召回时可以多种方式混合检索。

更关键的是检索后的重排流程。初步向量召回的top 50条结果,再丢给重排序模型算一遍相关性,取top 5。这个重排层的效果提升显著,比单纯调embedding模型明显得多。在线链路设计时,RAG节点支持设置“召回阈值”,低于阈值的就不带进上下文——不硬凑,不知道就说不知道,这能大幅减少模型幻觉。

4.4 三者的协同关系

实际用的时候,MCP、SKILL、RAG不是割裂的。一个典型的流程可能是:Agent接到任务 → 先用RAG节点检索内部知识 → 根据知识内容决定调用哪个Skill → Skill执行过程中通过MCP调用外部工具(比如查天气、发邮件、操作数据库) → 最终结果汇总返回。扩展机制协同工作的关键在于统一数据格式:RAG召回文档、MCP工具返回、Skill中间产物,全部转成标准消息结构,Agent模型的上下文里把它们混排在一起也不会乱。

5. 工程化底座:把AI应用当正经系统来运维

5.1 API网关与会话管理

工程化底座里,API网关不只做转发。它承担四个能力:认证(查询用户身份)、授权(匹配访问权限)、限流(按配额控制调用频率)、审计(记录操作日志)。任何外部请求,过了网关才会进入Agent编排层。会话管理单独做了一层,支持多轮对话里持久化上下文。用户的每次消息都与会话ID绑定,状态存储在Redis里做缓存,同时异步落库。这样Agent在长任务执行过程中,用户可以随时打断、追问,编排器会自动保留之前的中间结果。网关层的并发压力比普通Web系统高一个量级,因为一个Agent任务内部可能产生几十次模型调用,每次都要经历上下文组装、供应商路由、流式返回等开销。这里建议从一开始就设计好背压机制,比如队列长度上限,防止高峰流量打垮底层模型API。

5.2 任务队列与异步执行

Agent里耗时的操作太多了:长文档解析、批量向量化、复杂编排流程,如果全走同步API会被卡死。我把任务系统分两层:在线实时层,跑轻量级对话任务,单步响应控制在3秒内;离线任务层,跑所有重活,通过Celery队列异步执行,客户端轮询获取执行结果。离线任务的每个步骤都有单独的执行记录,失败后自动按照预置策略重试或转人工。任务状态和中间产物都要持久化,这样即使某个Worker挂了,别的Worker也能从最近的状态恢复执行。

5.3 可测试性与版本发布

AI应用工程化,最大的阻力是“不好测”。传统软件测试断言很清晰,但模型输出是概率性的,没法断言。我的做法是三层测试策略:第一层,结构测试,断言输出JSON是否符合Schema,这是硬性的;第二层,规则测试,用正则或关键词清单检查输出是否包含/不包含某些内容;第三层,采样人工评测,对一定比例的线上请求做人工打分,持续跟踪质量走势。版本发布不是一键灰度那么简单的。我做了Agent版本和Skill版本的双轨管理,一个业务流程可以同时存在多个版本,流量按比例分配,跑一周对比效果再全量切换。模型供应商的那个“版本”也要纳管,模型升级或参数调整,都得走版本发布流程,避免自动升级打乱线上效果。

6. 常见问题与排查实录

6.1 供应商切换引发的格式崩溃

有次内部做降级演练,把流量切到备用供应商后,Agent开始莫名报错。查了半天,发现是备用供应商的模型不支持并行工具调用,而主供应商支持,编排器在组装消息时没有判断这个能力位,导致工具调用序列塞到一个消息里,被模型拒绝了。这个问题的根因在于适配层没有完全屏蔽供应商差异。后来在工具调用组装逻辑里加了能力检测:如果当前模型不支持并行工具调用,就把多个工具请求拆成串行执行,并显式告知模型“一次只调用一个工具”。

6.2 拆了MCP工具但Agent不会选

接入一个MCP Server,里面挂了20个工具,上线后发现Agent经常选错工具,或者干脆不调用工具。一开始以为是prompt写得不够清楚,调了很多版都没用。后来才发现是工具描述太相似了,模型根本没法区分。最有效的解法不是调prompt,而是做工具合并——把功能相近的工具合成一个,用“操作类型+对象”的方式让参数去区分。工具数量从20个降到8个之后,调用准确率一下就上来了。想让Agent用好工具,工具本身的设计(命名、描述、参数结构)比提示词工程重要得多。

6.3 RAG召回质量差的离线排查

用户反馈知识库问答答不对,我先看的是召回结果而不是生成结果。排查步骤是:把用户问题丢到检索链路里跑一遍,看top10召回文档是哪几篇。结果发现,很多问题召回的文档跟问题根本不相关。原因有三点:一是PDF解析时表格内容成了乱码,二是切片把一段完整的操作手册拦腰斩断,三是用户问到“图片怎么存”这种偏口语的问题跟文风正式的技术文档向量距离远。针对这三类问题,我在解析层做了表格识别,切片层按章节语义边界重切,检索层除了向量召回还加了关键词倒排混合召回。修完之后,同一批验证集的召回命中率从47%提到了78%。

6.4 长任务中断恢复的边界条件

Agent长时间任务(比如批量处理100个文件)执行到第60个时,某个外部MCP工具返回超时,整个任务失败重跑。对于已经处理完的60个文件,重跑就意味着重复消费上游接口配额,甚至产生重复数据。解决方式是在每个Tool节点执行前,给结果做幂等键,写入执行记录表。任务恢复时,先查执行记录,如果某个步骤已经成功执行过且参数没变,就直接取旧结果跳过。跑批任务这种场景对Middleware的要求很高,“断点续跑”是我认为长任务Agent管理中绝对值得优先做的几个模块之一。

6.5 上下文爆掉与费用失控

Agent任务越是复杂,中间层上下文就越膨胀,几个工具结果一拼,几万token就这么出去了。平台里做了上下文管理策略:对话历史做摘要压缩,只在关键节点保留完整细节;工具返回结果做截断,只保留与当前目标相关的字段;超出预算上限的任务,提前终止并提示用户成本超限。在预算管控这块,我是设置了每任务、每会话、每业务线三层预算上限,对应层触发即熔断。产品经理不信“AI应用成本可控”,直到看见真金白银的熔断报表,才放心大范围推广。

7. 落地经验与适用边界

把XXL-AI这套底座真正跑起来,我的核心体会是:先别急着上花哨的多Agent,优先把单Agent的编排稳定性、可观测性和扩展机制做扎实。一家公司的AI应用里,80%以上的场景其实是单Agent加工具加知识库的组合。多Agent复杂度上了一个大台阶,是在单Agent稳定之后才适合引入的,不要为了炫技去设计系统。

还有一个容易被忽视的环节是让业务团队参与Skill的定义。我发现技术团队写出来的Skill往往偏技术化,业务同事看不懂也提不了需求。后来改成“业务同事口述流程,技术同事落地成Skill”的模式,每周固定梳理一次高频操作,把其中能固化的部分沉淀成技能。这个环节跑顺之后,AI应用的复用率明显上升,不再是每个需求从零开始写流程。

如果团队从零起步,建议按这个顺序推进:先把多供应商接入和模型路由做出来,这是基础,没有它后面换模型会痛不欲生;再上单Agent编排和可观测性;然后根据实际需求逐步引入MCP工具接入和RAG知识库;SKILL沉淀放在业务已经跑通几个高频场景之后再做。这套顺序的核心逻辑是:每一层都解决一个独立的问题,且都有明确的收益验证点,不会出现做了一堆架构能力却无处可用的情况。

最后想说的是,AI应用平台的本质,跟过去做中间件平台没有区别——都是在不确定性之上建一层确定性,让业务团队能在稳定底座上安心盖楼。大模型会换代,协议会演进,供应商会换,但“流程可编排、能力可扩展、运行可观测、问题可复现”这十六个字,放在哪个时代都成立。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询