深入拆解 Skill、MCP、RAG、Agent 与智能体运行机制

作者:公子世无双2026.11.04 11:42浏览量:0

简介:本文面向开发者、技术负责人及架构师,系统拆解智能体、技能、模型上下文协议、检索增强生成等概念之间的底层逻辑与协作方式。你将理解从“用户直接调用大模型”到“用户通过智能体调用大模型”的演进原因,掌握函数调用、工具服务化、知识检索增强等关键设计,并学会如何验证和排查智能体链路中的常见问题。

一、教程目标

本教程的目标是帮助开发者、技术负责人以及企业技术决策者真正理解现代智能体应用背后的几个高频概念:智能体、技能、模型上下文协议、检索增强生成,以及它们与底层大模型之间的协作方式。

很多人第一次接触这些概念时,容易把它们当成相互独立的“产品功能”或“平台模块”。实际上,它们描述的是同一套问题在不同层次上的解决方案。理解这些概念之间的关系,比背下每个名词的定义重要得多。

完成本教程后,你将能够:

  1. 说清楚用户、智能体与大模型之间的调用链路为什么必然出现;
  2. 理解函数调用为何采用结构化输出,而不是随意使用自然语言;
  3. 理解工具为什么需要从智能体内部抽离成独立服务;
  4. 理解模型上下文协议解决的到底是什么问题;
  5. 理解检索增强生成在链路中的位置,以及它为什么不能替代模型本身;
  6. 根据业务场景选择合理的架构拆分方式,并对常见问题进行排查。

本教程不依赖任何特定云厂商或平台。文中出现的架构模式、配置思路和示例均为通用技术表达,可用于大多数主流开发环境。


二、适用场景

这套知识适用于以下典型场景:

  • 你正在开发一个需要调用外部工具、查询业务数据或执行具体操作的应用;
  • 你希望让自己的应用能够通过大模型理解用户意图,但又不希望模型直接触碰敏感系统;
  • 你正在评估是否需要引入智能体框架,或者是否应该把工具拆成独立服务;
  • 你所在团队对“模型上下文协议”“检索增强生成”等概念存在不同理解,需要一份相对清晰的工程视角说明;
  • 你希望从架构层面理解这些技术的边界,而不是只停留在概念介绍。

如果你主要负责业务开发、后端架构、平台工程或技术选型,本文会比较适合你。阅读本文不需要深入掌握某一种大模型框架,但建议对“大模型通过接口接收提示词并返回文本”这一基本工作方式有初步了解。


三、前置准备

在开始拆解之前,建议你先建立几个基础认知。

3.1 基础概念准备

你需要理解大模型的基本工作方式:调用方构造一段提示词,通过接口发送给模型,模型返回一段生成结果。这个结果通常是自然语言文本。

在这个前提下,你还需要理解两个重要限制:

  1. 模型不能直接执行外部操作。例如,它不能自己发邮件、查数据库、调用支付接口或重启服务。
  2. 模型返回的自然语言不利于程序稳定解析。程序很难从一段自由文本中稳定提取需要执行的动作和参数。

这两点限制几乎是后续所有架构演进的起点。

3.2 环境准备

如果你想边阅读边做实验,可以准备以下通用环境:

  • 一个能够调用大模型接口的开发环境;
  • 一个可以运行后端服务的语言运行时,例如使用常见后端语言即可;
  • 一个可以模拟外部工具的服务,例如一个查询天气、查询订单或查询库存的接口;
  • 一个简单的接口调试工具,用于观察请求和响应结构。

这些环境不需要依赖特定云平台。使用本地开发环境或任意主流云服务均可完成验证。

3.3 预期目标

完成学习后,你应该能够用自己的语言向同事解释下面这条链路:

  1. 用户 -> 智能体 -> 大模型

并且能够说明:

  • 为什么智能体会出现在用户与大模型之间;
  • 为什么大模型返回给智能体的内容需要结构化;
  • 为什么工具调用最终需要从智能体内部抽离出来;
  • 为什么企业知识往往不适合直接塞进模型提示词,而需要检索增强生成配合。

四、实施步骤

下面按照架构演进的顺序逐步拆解。每一节都回答三个问题:当前存在什么问题、采用什么方式解决、解决方案引入了什么新问题。

步骤一:从“用户直接调用大模型”开始

最简单的架构是:

  1. 用户 -> 大模型

用户把问题发给大模型,大模型返回答案。这个阶段只适合纯粹文本类任务,例如总结、改写、翻译、问答等。

但很快就会出现一个实际问题:用户希望大模型帮助处理现实世界中的任务。

例如:

  • “帮我查一下今天的订单量”;
  • “帮我把这条消息发给某个群”;
  • “帮我生成一份报表并保存到文档系统”。

大模型本身无法完成这些动作。它可以生成一段看起来像答案的文字,但不能真正调用业务系统。此时,仅靠“用户直接调用大模型”已经不够。

步骤二:引入智能体,承担“调用者”角色

为了让模型能够完成更复杂的任务,我们在用户与大模型之间增加一层程序。这层程序通常被称为智能体。

架构变为:

  1. 用户 -> 智能体 -> 大模型

智能体的职责至少包括:

  1. 接收用户请求;
  2. 组装提示词;
  3. 调用大模型;
  4. 解析大模型返回内容;
  5. 根据解析结果决定下一步动作;
  6. 执行模型无法直接完成的本地操作;
  7. 把最终结果返回给用户。

可以这样理解:大模型仍然负责语言理解和生成,但它不再是唯一的执行者。智能体成为把握流程的那个角色。

这一层出现后,模型的能力边界被扩展了。模型不需要自己操作外部系统,只需要告诉智能体“我需要调用什么、参数是什么”,再由智能体去执行。

但这里马上会遇到一个工程问题:智能体如何准确理解模型的返回?

步骤三:用结构化约定降低解析成本

如果大模型返回的是自然语言,例如:

  1. 好的,我建议你调用一下天气查询功能,城市是北京,时间是明天。

智能体程序需要从这句话里准确识别出“天气查询”“北京”“明天”等信息。自然语言解析难度较大,而且稳定性难以保证。

更合理的做法是让大模型按照约定格式返回结构化内容。例如:

  1. {
  2. "action": "query_weather",
  3. "params": {
  4. "city": "北京",
  5. "date": "2026-01-14"
  6. }
  7. }

这样,智能体解析成本极大降低,后续动作也可以可靠执行。

这种“约定大模型按照固定格式返回,从而方便程序解析”的机制,在工程上通常被称为函数调用。它的本质不是新的模型能力,而是调用双方对接口格式的一种约定。

这里需要特别注意:函数调用并不是让模型真正执行函数,而是让模型输出一个“意图明确、参数明确”的结构化对象。真正执行函数的是智能体程序。

步骤四:把工具从智能体中抽离

在早期实现中,很多开发者会把工具调用逻辑直接写在智能体代码里。例如,智能体内部直接写死天气查询、订单查询、库存查询等逻辑。

这样做开发速度快,但扩展成本会越来越高。每增加一个工具,都要修改智能体代码;每调整一个工具接口,都要同步修改调用逻辑。随着工具数量变多,智能体内部会变得非常臃肿。

更合理的做法是:把每个工具独立成服务。工具单独部署、单独维护、单独升级。智能体不再关心工具内部如何实现,只关心如何发现和调用这些工具。

于是架构逐步演进为:

  1. 用户 -> 智能体 -> 大模型
  2. -> 工具服务群

但工具独立部署之后,又出现了一个新问题:智能体如何知道有哪些工具、每个工具怎么调用?

如果没有统一规范,每个工具都可以自定义接口格式。例如:

  • 工具 A 使用 POST 请求;
  • 工具 B 使用 GET 请求;
  • 工具 C 的参数命名风格完全不同。

智能体需要为每个工具单独适配,耦合问题并没有彻底解决。

步骤五:用统一协议连接工具与智能体

为了解决“智能体与工具之间如何互相发现、描述和调用”的问题,需要一套统一约定。这套约定通常被概括为模型上下文协议。

它主要回答几个问题:

  1. 工具如何向外部声明自己的存在;
  2. 工具如何描述自己的能力,例如名称、描述、输入参数结构;
  3. 智能体如何发现当前可用的工具列表;
  4. 智能体如何按照统一格式调用某个工具;
  5. 工具如何返回结构化结果。

可以把这个协议理解为工具服务与智能体之间的接口规范。它的价值不在于“让模型更强”,而在于降低智能体与外部工具之间的集成成本。

整个链路可以进一步表示为:

  1. 用户 -> 智能体 -> 大模型
  2. -> 协议层 -> 工具服务群

当工具数量较多、或者工具由不同团队维护时,这种协议的价值会非常明显。智能体只需要面向协议层开发,不需要为每个工具单独写适配逻辑。

步骤六:引入检索增强生成,补充模型知识

在真实业务中,还有一个非常常见的问题:大模型不知道企业内部的最新知识。

例如,企业内部文档、产品说明、运维手册、历史工单等,可能并没有出现在模型的训练数据中。即使出现过,也可能不是最新版本。

如果每次都把这些资料全部塞进提示词,不仅成本高,还容易超出上下文窗口限制。更重要的是,大量无关内容会干扰模型判断。

检索增强生成提供了一种更实用的方式。它的核心流程如下:

  1. 用户提出问题时,先从知识库中检索相关内容;
  2. 将检索到的片段与原始问题一起组装成提示词;
  3. 大模型基于补充材料生成回答。

这可以理解为“先找资料,再回答问题”。

检索增强生成并不意味着模型具备了新的记忆能力,而是通过外部系统动态补充上下文。它解决的是“模型知识不完整”的问题,而不是“模型不会调用工具”的问题。

因此,检索增强生成与工具调用并不冲突。一个成熟的智能体应用中,二者可能同时存在:

  1. 用户 -> 智能体 -> 大模型
  2. -> 工具服务群
  3. -> 知识检索服务

工具服务负责执行动作,知识检索服务负责补充知识。它们解决的是不同层面的问题。


五、配置说明

这里不涉及具体平台的专有配置,只讨论通用设计要点。

5.1 函数调用格式设计

建议在设计函数调用格式时遵循以下原则:

  • 动作名称使用明确、稳定的标识;
  • 参数使用结构化字段,避免把复杂信息压成一个长字符串;
  • 参数类型尽量简单,优先使用字符串、数字、布尔值和数组;
  • 为每个动作设计清晰的语义描述,方便模型判断何时调用;
  • 为每个参数设计说明信息,避免模型误解参数含义。

一个通用示例如下:

  1. {
  2. "name": "query_order",
  3. "description": "根据订单号查询订单状态",
  4. "parameters": {
  5. "order_id": {
  6. "type": "string",
  7. "description": "订单号"
  8. }
  9. }
  10. }

这种结构既方便大模型生成,也方便智能体校验。

5.2 工具服务注册信息

当工具独立部署后,每个工具服务至少需要对外提供以下信息:

  • 工具名称;
  • 工具描述;
  • 工具用途;
  • 输入参数结构;
  • 输出结构说明;
  • 调用方式说明。

这些信息不一定要固定为某一种具体格式,但必须足够稳定和规范。智能体或协议层可以据此自动发现工具,并生成可调用说明。

5.3 知识库切片与检索

检索增强生成的效果很大程度上取决于知识库的整理方式。通常建议:

  • 将长文档拆分为适当大小的片段;
  • 每个片段保留标题、章节等上下文元数据;
  • 检索时优先返回相关度高且不过长的内容;
  • 在提示词中明确告诉模型“以下是参考资料,请基于资料回答”。

不要把所有知识全部拼接进提示词。这样既容易超出上下文限制,也会让模型难以抓住重点。


六、示例说明

下面用一个通用业务场景说明整体链路如何协作。

假设用户向智能体发出请求:

  1. 帮我查一下某订单是否存在支付风险。

智能体首先调用大模型,大模型根据工具描述判断需要调用订单查询工具,于是返回结构化结果:

  1. {
  2. "action": "query_order",
  3. "params": {
  4. "order_id": "20260114001"
  5. }
  6. }

智能体解析后,通过协议层调用订单服务,获得订单基本信息,例如金额、支付方式、创建时间、用户标签等。

随后,智能体再次调用大模型,将订单信息与用户原问题一并传入。此时,大模型可能还需要参考企业内部风险规则。于是智能体先调用知识检索服务,取回相关规则片段,再交给大模型进行判断。

最终,大模型输出分析结论,智能体将结论整理后返回给用户。

整个过程可以表示为:

  1. 用户
  2. -> 智能体
  3. -> 大模型:判断意图,生成工具调用
  4. -> 工具服务:查询订单
  5. -> 知识检索:补充风险规则
  6. -> 大模型:基于补充材料生成最终结论
  7. -> 返回用户

这个例子说明,智能体架构通常不是一次模型调用就能完成任务的。它往往需要在模型、工具和知识服务之间进行多轮协调。


七、结果验证

在完成接入或开发后,建议从以下几个方面验证链路是否正常。

7.1 验证模型输出是否稳定

首先验证大模型是否按照约定格式返回结构化内容。可以通过固定输入用例观察输出结果。

重点观察:

  • 动作名称是否准确;
  • 参数是否完整;
  • 是否出现多余文本;
  • 是否存在无法解析的内容。

如果模型经常返回额外说明文字,可以在提示词中强化格式要求,同时降低生成随机性。

7.2 验证工具调用链路

确认智能体能否正确地:

  • 解析模型返回;
  • 找到对应工具;
  • 传入正确参数;
  • 获取工具返回结果;
  • 将工具返回结果传递回模型或用户。

建议先使用虚拟工具或测试服务验证,避免直接调用真实业务系统。

7.3 验证知识检索效果

针对知识问答场景,可以准备若干条已知答案的问题,观察检索结果是否包含正确答案所在片段。

如果检索结果相关度低,需要检查:

  • 文档切片是否合理;
  • 向量化模型是否适合当前语料;
  • 索引是否过期;
  • 提示词是否明确要求模型基于资料回答。

八、常见问题与排查

8.1 模型没有按照格式返回

可能原因:

  • 提示词中没有明确说明输出格式;
  • 生成参数中随机性设置过高;
  • 任务描述过于复杂;
  • 调用了不擅长结构化输出的模型版本。

解决思路:

  • 在提示词中加入格式示例;
  • 降低随机性参数;
  • 简化动作数量和参数结构;
  • 在程序侧做格式校验和重试。

8.2 智能体调用了错误的工具

可能原因:

  • 工具描述不够清楚;
  • 两个工具能力边界重叠;
  • 用户问题存在歧义;
  • 模型对参数语义理解偏差。

解决思路:

  • 优化工具描述,突出使用场景;
  • 合并相似工具,减少选择困难;
  • 在调用前增加澄清环节;
  • 对关键参数做人工或规则校验。

8.3 工具服务越来越多,维护困难

可能原因:

  • 工具没有统一注册机制;
  • 接口风格不一致;
  • 缺少版本管理;
  • 缺少权限控制。

解决思路:

  • 尽早引入统一协议层;
  • 工具服务提供标准化描述信息;
  • 对工具做分级和权限控制;
  • 建立工具上下线流程。

8.4 检索增强生成效果不佳

可能原因:

  • 知识库内容过旧;
  • 文档切片过大或过小;
  • 检索策略与业务不匹配;
  • 模型没有严格依据检索结果回答。

解决思路:

  • 定期更新知识库索引;
  • 调整切片大小;
  • 使用关键词与语义检索结合的方式;
  • 在提示词中强化“仅根据检索内容回答”的要求。

九、优化建议

9.1 从架构层面划分职责

尽量把模型调用、工具调用、知识检索分开。不要让智能体代码同时承担过多职责。清晰的分层有助于排查问题和后续扩展。

9.2 工具服务优先考虑标准化

即使团队规模暂时较小,也建议从最初就为工具服务设计统一的描述和调用规范。可以避免后期大规模重构。

9.3 注意安全边界

智能体执行外部操作时,必须设置权限边界。对于高风险操作,例如删除数据、发起支付、发送通知等,建议增加人工确认环节,避免模型误判导致事故。

9.4 控制上下文长度

不要在单次提示词中放入过多信息。工具返回、知识片段和对话历史都需要控制长度,否则可能导致模型忽略关键内容,同时增加调用成本。

9.5 建立可观测性

为智能体链路补充日志与追踪能力,至少记录:

  • 每次模型调用的输入与输出;
  • 工具调用的参数与结果;
  • 检索命中的片段;
  • 最终返回给用户的内容。

这对问题排查和持续优化非常关键。


十、总结

本文从工程视角拆解了智能体相关架构的演进逻辑。

最初,用户直接与大模型交互。随着实际任务复杂度提升,需要在用户与大模型之间引入智能体,由智能体负责解析模型输出并执行模型无法完成的动作。

为了让程序稳定解析模型输出,产生了结构化调用约定,也就是通常所说的函数调用。随着工具数量增加,工具调用逻辑逐渐从智能体内部抽离,形成了独立工具服务。为了让工具服务与智能体之间互相发现和调用,又需要统一协议层,也就是模型上下文协议所解决的核心问题。

与此同时,企业内部知识往往不在模型训练数据中,因此需要检索增强生成来动态补充上下文。它解决的是知识不足问题,与工具调用解决的是不同层面的需求。

理解这些概念之间的关系后,再进行架构选型和系统设计时,就更容易判断自己真正需要的是什么:是需要一个更稳定的结构化输出,还是需要一套统一的工具协议,还是需要搭建知识检索服务。不同的需求对应不同的工程重点,不应把所有概念混为一谈。