先放一张地图

很多 Agent 名词单独看都不难,真正容易混的是:它们到底谁调用谁,谁负责思考,谁负责执行,谁只是给 Agent 加能力。

可以先用这张图理解:

flowchart TD U["用户目标"] --> H["Agent Host / Runtime"] H --> I["Instructions / Prompt"] H --> S["Skills:可复用操作手册"] H --> M["Memory / State"] H --> L["Agent Loop"] L --> O["Observe:读取上下文"] O --> P["Plan:判断下一步"] P --> D{"需要外部动作?"} D -- "需要" --> T["Tools"] T --> F["Local Function"] T --> C["MCP Client"] C --> MS["MCP Server"] MS --> E["外部数据 / API / 文件系统"] F --> R["Observation:工具结果"] E --> R R --> O D -- "不需要" --> A["Final Answer / Artifact"]

一句话版:

Agent 是能围绕目标持续做事的系统;MCP 是把外部工具和数据标准化接进来的协议;Skills 是给 Agent 的可复用操作手册;Loop 是 Agent 不断观察、决策、行动、修正直到完成任务的循环。

Agent

Agent 不是单纯的“大模型”。更准确地说,Agent 是一个由模型、指令、工具、状态和运行时组成的应用。

一个普通聊天模型通常是:

flowchart LR I["输入"] --> M["模型"] --> O["输出"]

一个 Agent 更像:

flowchart LR G["目标"] --> P["模型判断下一步"] P --> T["调用工具"] T --> R["读取结果"] R --> D{"完成了吗?"} D -- "还没" --> P D -- "完成" --> F["交付结果"]

所以 Agent 的核心特征不是“会聊天”,而是能围绕一个目标跨多个步骤推进。比如:

  • 搜索项目代码。
  • 读 README 和关键模块。
  • 生成技术文档。
  • 调用上传接口。
  • 检查线上页面是否可访问。

这些动作里,模型负责判断和组织,运行时负责执行工具,工具返回结果后再进入下一步。

Model / LLM

Model 或 LLM 是 Agent 的“大脑”,但不是完整的 Agent。

模型擅长:

  • 理解自然语言目标。
  • 根据上下文做推理。
  • 决定下一步需要什么信息。
  • 生成代码、文档、计划或最终回答。

模型不直接拥有文件系统、浏览器、数据库、HTTP 请求能力。它需要通过 Host/Runtime 暴露的工具来行动。

可以把模型理解成驾驶员,把工具理解成车辆和仪表盘,把 Agent Runtime 理解成车的控制系统。

Instructions / Prompt

Instructions 是 Agent 的行为约束和工作方式。它通常分几层:

  • System instructions:最高优先级规则。
  • Developer instructions:产品或工程层面的约束。
  • User prompt:用户当前目标。
  • Skill instructions:某类任务的可复用流程。

Instructions 决定 Agent 的风格、边界和执行偏好。比如一个代码 Agent 可能被要求“先读代码再改”“不要覆盖用户已有修改”“编辑文件用 apply_patch”。

Prompt 不只是“问一句话”,它更像 Agent 的任务合同。

Context

Context 是模型当前能看到的信息,包括:

  • 用户请求。
  • 已加载的系统/开发者/技能指令。
  • 读过的文件片段。
  • 工具执行结果。
  • 当前计划和中间推理所依赖的事实。

Agent 能不能稳定做复杂任务,很大程度取决于 Context 管理。上下文太少会乱猜;上下文太多会挤掉关键内容。

所以很多 Agent 系统会做 progressive disclosure:先只给模型技能名称和简介,真正需要时再加载完整技能说明或参考文件。

Tool

Tool 是 Agent 可以调用的外部能力。常见 Tool 包括:

  • 读取文件。
  • 搜索代码。
  • 执行 shell 命令。
  • 调用 HTTP API。
  • 控制浏览器。
  • 查询数据库。
  • 生成图片。

模型通常不会直接执行工具,而是向 Runtime 发出工具调用请求。Runtime 检查参数、权限和环境后执行,然后把结果作为 Observation 返回给模型。

工具调用的意义是把“语言推理”接到“真实世界操作”上。

Function Calling

Function Calling 是最常见的工具形式:开发者把一个函数声明给模型,包含函数名、描述和参数 schema。模型决定何时调用、传什么参数,运行时负责真正执行函数。

例子:

模型:我需要读取 package.json
Runtime:执行 read_file({ path: "package.json" })
Runtime:把文件内容返回给模型
模型:根据内容继续判断项目技术栈

它解决的是“模型如何用结构化方式请求执行动作”。

MCP

MCP,全称 Model Context Protocol,是一种把外部工具、数据源和工作流标准化接入 AI 应用的协议。

没有 MCP 时,每个 Agent 应用都要自己适配每个工具:

flowchart TD A["Agent A"] --> AG["GitHub adapter"] A --> AD["Database adapter"] A --> AB["Browser adapter"] B["Agent B"] --> BG["又写一遍 GitHub adapter"] B --> BD["又写一遍 Database adapter"] B --> BB["又写一遍 Browser adapter"]

有 MCP 后,结构变成:

flowchart LR H["Agent Host"] --> C["MCP Client"] C --> G["MCP Server:GitHub"] C --> D["MCP Server:Database"] C --> B["MCP Server:Browser"] G --> GT["Tools / Resources / Prompts"] D --> DT["Tools / Resources / Prompts"] B --> BT["Tools / Resources / Prompts"]

MCP Server 可以暴露三类常见能力:

  • Tools:可调用动作,比如查询数据库、写 issue、读文件。
  • Resources:可读取上下文,比如文档、表结构、配置。
  • Prompts:可复用提示或工作流模板。

所以 MCP 不是某一个具体工具,它更像 USB-C:定义了 Agent 应用和外部能力之间如何连接。

MCP Host / Client / Server

MCP 里常见三个角色:

flowchart LR H["Host:运行 Agent 的应用"] --> C["Client:连接某个 MCP Server"] C --> S["Server:暴露工具、资源或提示"]

一次 MCP 工具调用大概是:

sequenceDiagram participant A as Agent participant H as Host participant C as MCP Client participant S as Database MCP Server A->>H: 判断需要查数据库 H->>C: 发送 tools/call C->>S: 执行查询 S-->>C: 返回查询结果 C-->>H: 返回协议结果 H-->>A: 写回 Agent Context A->>A: 继续推理

重点是:模型不直接连数据库。模型提出意图,Host/Client/Server 负责按协议安全执行。

Skills

Skills 是给 Agent 的“可复用能力包”。它通常不是一个立即执行的工具,而是一组指导 Agent 如何完成某类任务的说明、脚本和参考资料。

一个 Skill 常见结构是:

skill-name/
  SKILL.md
  scripts/
  references/
  assets/

SKILL.md 里写什么时候使用这个技能、执行步骤、注意事项。scripts/ 里放稳定可复用的脚本。references/ 放需要时才读取的详细资料。assets/ 放模板、图片、字体等资源。

Tool 更像“按钮”:点一下执行某个动作。Skill 更像“操作手册”:告诉 Agent 做这类任务应该怎么走。

比如我给博客写的上传技能就属于 Skill:它告诉 Agent 如何从任意项目总结文档、写 frontmatter、扫描敏感信息、调用 Blog 上传 API、验证线上页面。

Agent Loop

Agent Loop 是 Agent 执行任务的核心循环。它通常长这样:

flowchart TD O["Observe:读取目标和上下文"] --> P["Think / Plan:判断下一步"] P --> A["Act:调用工具、生成文件或询问用户"] A --> R["Observe:读取工具结果"] R --> V["Reflect:检查是否完成或需要修正"] V -- "继续" --> O V -- "完成" --> F["Finish:交付结果"]

一个写项目文档的 Loop 例子:

sequenceDiagram participant U as 用户 participant A as Agent participant T as Tool participant B as Blog API U->>A: 帮我把这个项目整理成博客 A->>T: 读取 README T-->>A: 返回 README A->>T: 读取 main.py 和 services T-->>A: 返回关键代码 A->>T: 写入 docs/blog/project-notes.md A->>T: 扫描敏感信息 T-->>A: 无命中 A->>B: 上传 Markdown B-->>A: 返回线上 URL A->>T: 访问线上页面验证 T-->>A: 200 OK A-->>U: 告诉用户完成

Loop 的价值是允许 Agent 一边做一边校正,而不是一次性凭空输出。

Memory / State

Memory 和 State 都和“记住东西”有关,但侧重点不同。

State 通常是当前任务运行时状态:

  • 已读过哪些文件。
  • 当前计划做到哪一步。
  • 工具返回了什么结果。
  • 生成了哪些临时文件。

Memory 更偏长期记忆:

  • 用户常用技术栈。
  • 用户偏好的文档风格。
  • 项目固定部署方式。
  • 某个团队的接口规范。

很多系统会谨慎区分这两者。当前任务状态不一定应该长期保存;长期 Memory 也不应该无脑塞进每次任务。

Planner / Executor

复杂 Agent 里经常会拆出 Planner 和 Executor:

  • Planner:负责拆任务、排顺序、判断依赖。
  • Executor:负责执行具体步骤。

比如:

Planner:这个项目文档需要分成架构、接口、部署、风险四节
Executor:去读 README、main.py、Dockerfile,然后生成内容

小任务里模型自己就能同时做 Planner 和 Executor。大任务、多工具任务、多人协作任务里,拆开会更稳。

Handoff

Handoff 是把任务交给另一个更合适的 Agent 或专家。

比如一个主 Agent 负责统筹,但遇到 UI 设计时交给 Frontend Agent,遇到数据库慢查询时交给 DB Agent:

flowchart LR C["Coordinator Agent"] --> F["Frontend Agent"] C --> B["Backend Agent"] C --> S["Security Agent"] F --> R["局部结论"] B --> R S --> R R --> C

Handoff 的关键不是“多叫几个模型”,而是明确交接边界:输入是什么、期待输出是什么、谁负责最终合并。

Guardrails

Guardrails 是护栏。它限制 Agent 做不该做的事,或者在高风险动作前要求检查。

常见 Guardrails:

  • 不输出密钥、Cookie、Token。
  • 不访问内网 URL。
  • 不执行破坏性命令。
  • 高风险操作前请求确认。
  • 工具参数 schema 校验。
  • 输出格式必须符合 JSON schema。

Guardrails 不会让 Agent 变聪明,但会让 Agent 更可控。

RAG

RAG 是 Retrieval-Augmented Generation,检索增强生成。

它的思路是:模型不知道或不该凭记忆回答时,先去检索外部知识,再基于检索结果回答。

flowchart LR Q["User Question"] --> S["Search / Retrieve docs"] S --> C["Relevant chunks into context"] C --> M["Model answers with evidence"]

RAG 和 Agent 的关系是:RAG 可以作为 Agent Loop 中的一种工具步骤。不是所有 RAG 都是 Agent,也不是所有 Agent 都需要 RAG。

Workflow 和 Agent 的区别

Workflow 是固定流程,Agent 是动态决策。

Workflow 更像:

flowchart LR S1["Step 1"] --> S2["Step 2"] --> S3["Step 3"] --> D["Done"]

Agent 更像:

flowchart TD P["看情况决定下一步"] --> D{"当前需要什么?"} D -- "读文件" --> F["读取文件"] D -- "搜索资料" --> S["搜索"] D -- "信息不足" --> U["询问用户"] D -- "失败了" --> R["换方案重试"] F --> P S --> P U --> P R --> P

实际项目里两者经常混合。稳定、重复、低风险的部分适合 Workflow;开放、模糊、需要判断的部分适合 Agent。

它们怎么一起工作

拿“把一个项目总结成博客并上传”举例:

sequenceDiagram participant U as User participant A as Agent participant S as Skill participant T as Tools participant G as Guardrails participant B as Blog Upload API U->>A: 总结项目并上传到博客 A->>S: 加载 Blog 文档上传流程 S-->>A: 写作格式、检查项、上传方式 A->>T: 读取 README、依赖文件、核心代码 T-->>A: 返回项目事实 A->>T: 生成 Markdown 文档 A->>G: 检查 token / cookie / password G-->>A: 允许上传 A->>B: POST /api/admin/docs/upload B-->>A: 返回 slug 和 URL A->>T: 访问线上页面验证 T-->>A: 200 OK A-->>U: 返回线上 URL 和本地路径

在这条链路里:

  • Agent 负责判断和组织。
  • Skill 负责提供稳定流程。
  • Tool 负责执行动作。
  • MCP 负责标准化连接外部能力。
  • Loop 负责多步推进和纠错。
  • Memory/State 负责保留必要上下文。
  • Guardrails 负责控制风险。

最容易混的几个点

Agent 不是模型。

模型是 Agent 的核心组件,但 Agent 还包括运行时、工具、状态和控制逻辑。

MCP 不是 Agent。

MCP 是连接协议。它让 Agent 更容易使用外部工具和数据。

Skill 不是 Tool。

Tool 是可执行动作,Skill 是可复用方法论和资源包。Skill 里可以包含脚本,但 Skill 本身更像指导层。

Loop 不是死循环。

好的 Agent Loop 应该知道什么时候继续、什么时候停止、什么时候问用户、什么时候承认失败。

Memory 不是越多越好。

记住错误信息、过时偏好或敏感数据,都会让 Agent 变得更危险或更混乱。

一句话总结

Agent 系统可以理解成一套有目标、有工具、有上下文、有循环控制的执行系统。

如果说模型提供智能,Tools 提供行动能力,MCP 提供连接标准,Skills 提供经验复用,Loop 提供持续推进,那么 Guardrails 和 Memory/State 就负责让这个系统更可控、更连续。

真正好用的 Agent,不是名词堆得多,而是这些部件之间的边界清楚、交互顺畅、失败时知道如何收住。

参考资料

  • Model Context Protocol 官方介绍:https://modelcontextprotocol.io/docs/getting-started/intro
  • MCP Tools 规范:https://modelcontextprotocol.io/specification/2025-06-18/server/tools
  • OpenAI Agents SDK 指南:https://developers.openai.com/api/docs/guides/agents
  • OpenAI Agents SDK Agents 文档:https://openai.github.io/openai-agents-python/agents/
  • OpenAI Codex Skills 文档:https://developers.openai.com/codex/skills