MCP 协议¶
一句话:MCP(Model Context Protocol)是 Anthropic 提出的开放标准,用 host/client/server 三端架构把"工具/资源"与"模型"解耦,让一个工具 server 可被任意 host 复用——比 Function Calling 更通用、更标准化。
概念¶
Function Calling 解决的是"一个应用内的某个模型怎么调本应用的几个工具",工具元数据是应用自己声明、强绑定的。当工具变多、要跨多个模型/应用复用,或要接入企业内大量系统时,每个应用重复声明、各自对接的代价就很高。
MCP(Model Context Protocol) 把这件事标准化、解耦化:它定义了一个客户端-服务器协议,工具/资源/提示被封装成独立的 MCP Server,任何支持 MCP 的 Host(如 Claude Desktop、IDE、Agent 平台)都能通过一个 Client 接入并复用这些能力。三端职责:
| 角色 | 职责 | 例子 |
|---|---|---|
| Host(宿主) | 承载 LLM、决定何时用工具、管理用户会话与授权 | Claude Desktop、Cursor、自研 Agent 平台 |
| Client(客户端) | Host 内的协议适配器,与某个 Server 维持 1:1 连接,转发请求/结果 | Host 为每个接入的 Server 创建一个 Client |
| Server(服务端) | 暴露工具(Tools)、资源(Resources)、提示(Prompts)的独立进程/服务 | 数据库 MCP Server、GitHub MCP Server、企业订单系统 MCP Server |
核心差异在于复用与标准化:一个 MCP Server 写一次,多个 Host 都能用;工具声明从"应用内硬编码"升级为"标准化协议暴露"。蒋磊案例(报告 §5.3)正是用 MCP 打通企业内部 10+ 系统接口——把分散的内部系统封装成统一协议,Agent 接入成本从"N 个系统各对接"变成"接 N 个标准 Server"。
原理¶
MCP 的关键设计点:
- 统一三类能力:Tools(可执行函数,类似 Function Calling)、Resources(只读数据/上下文,如文件、数据库行)、Prompts(可复用的提示模板)。工具只是其中一类。
- 传输与生命周期标准化:定义了连接初始化、能力协商(server 声明自己提供哪些 tools/resources/prompts)、调用、断线等标准消息格式(通常基于 JSON-RPC over stdio/SSE)。
- 解耦带来复用:Server 不关心是哪个模型、哪个 Host 在调用;Host 也不需要为每个工具重写声明——通过能力协商动态发现。
可以理解为:Function Calling 是"模型 ↔ 应用内工具"的调用约定,MCP 是"任意模型/Host ↔ 任意工具服务"的通用总线。Function Calling 解决"能不能调",MCP 进一步解决"能不能标准化复用"。
// 概念示意:Host 端通过 Client 接入 MCP Server 并暴露为模型工具
public class McpIntegration {
public Agent build() {
// 1. 为每个 MCP Server 创建一个 Client(1:1 连接)
McpClient orderClient = McpClient.connect("order-mcp-server");
McpClient ticketClient = McpClient.connect("ticket-mcp-server");
McpClient searchClient = McpClient.connect("enterprise-search-mcp");
// 2. 能力协商:动态发现各 Server 提供的 tools/resources/prompts
List<ToolDescriptor> tools = Stream.of(orderClient, ticketClient, searchClient)
.flatMap(c -> c.listTools().stream())
.toList(); // 10+ 系统接口统一收口
// 3. Host 把这些标准工具注册给模型,模型决策后由 Client 转发执行
return AiServices.builder(Agent.class)
.chatLanguageModel(model)
.tools(new McpToolProvider(tools, Map.of(
"order-mcp-server", orderClient,
"ticket-mcp-server", ticketClient,
"enterprise-search-mcp", searchClient
)))
.build();
}
}
/** 执行时:按工具归属的 Server,通过对应 Client 转发调用 */
public class McpToolProvider implements ToolProvider {
public String call(String toolName, JsonNode args) {
McpClient client = route(toolName); // 找到工具所在 Server 的 Client
return client.invokeTool(toolName, args); // 标准协议转发
}
}
# 概念示意:MCP Host 端接入多个 Server 并统一暴露给模型
from mcp import ClientSession, StdioServerParameters
from mcp.client.stdio import stdio_client
async def build_agent():
servers = {
"order": "order-mcp-server",
"ticket": "ticket-mcp-server",
"search": "enterprise-search-mcp", # 10+ 系统接口
}
tools_by_server = {}
for name, cmd in servers.items():
params = StdioServerParameters(command=cmd)
async with stdio_client(params) as (read, write):
async with ClientSession(read, write) as session:
await session.initialize() # 能力协商
# 动态发现该 Server 提供的 tools/resources/prompts
tools_by_server[name] = await session.list_tools()
# Host 把所有 Server 的工具统一注册给模型,按归属转发执行
return Agent(
model=model,
tools=all_tools(tools_by_server),
dispatcher=McpDispatcher(tools_by_server), # 按 tool -> server 路由
)
class McpDispatcher:
async def invoke(self, tool_name: str, args: dict) -> str:
server = self.route(tool_name) # 找到工具所在 Server
async with self.session(server) as s:
return await s.call_tool(tool_name, args) # 标准协议转发
实战要点¶
- MCP 的价值在"复用 + 标准化",不在"比 Function Calling 强":单应用、少量工具,Function Calling 足够;要跨系统、跨 Host 复用大量工具时,MCP 才显出优势(如蒋磊打通 10+ 接口)。
- Server 颗粒度按系统/领域划分:一个内部系统封装成一个 MCP Server(订单 Server、工单 Server、知识库 Server),Host 通过能力协商聚合,避免一个巨型 Server。
- 授权与安全是 MCP 上线重点:Server 暴露了内部系统能力,必须配套鉴权、越权控制、审计日志,否则相当于把内部接口开放给模型直接调。
- 能力协商让工具可热插拔:Server 升级新增工具,Host 通过重新协商自动发现,不必改 Host 代码——这是解耦带来的运维收益。
- 不要把 MCP 当噱头堆砌:报告把 MCP 列为"前沿基线要素",但也点名"无对应项目支撑的术语堆砌"是红旗——能讲清 host/client/server 职责、复用优势、落地过的系统数才有说服力。
本节相关题目¶
| 难度 | 题目 | 链接 |
|---|---|---|
| 基础 | Function Calling vs MCP 各解决什么问题 | → 题库 |
| 进阶 | MCP host/client/server 职责、工具复用优势 | → 题库 |
| 深度 | Agent 平台如何用 MCP 收口企业系统接入 | → 题库 |