MCP(Model Context Protocol,模型上下文协议)是 2024 年底由 Anthropic 提出的开放标准,用来给大模型统一接入数据源与工具。在 MCP 出现之前,每个 AI 应用都要为数据库、文件系统、第三方 API 各写一套私有适配;MCP 用一套客户端-服务器协议把这些能力标准化,让同一个 MCP Server 能被任意支持 MCP 的客户端复用。本文从协议动机讲到动手搭建一个 MCP Server,并给出生产落地的工程建议。
一、为什么需要 MCP:N×M 的集成困境
假设你有 5 个大模型客户端(Claude Desktop、VS Code 插件、自研 Agent)和 8 个数据源(MySQL、PostgreSQL、文件系统、GitHub、Slack、内部 API……)。如果每种客户端都直接对接每个数据源,你需要写 5×8 = 40 套集成代码,而且任何一端升级都要同步改全部。这就是 AI 应用早期的”N×M 集成地狱”。
MCP 的解法是引入一层标准协议:数据源侧实现一次 MCP Server,客户端侧实现一次 MCP Client,二者通过统一的原语通信。集成复杂度从 N×M 降到 N+M。它和当年 LSP(语言服务器协议)统一编辑器与编程语言插件的思路如出一辙——把”能力提供方”和”能力消费方”解耦。
二、MCP 的三层架构:Host / Client / Server
理解 MCP 只需记住三个角色:
- Host(宿主):用户直接使用的 AI 应用,例如 Claude Desktop、Cursor、或你自己的 Agent 进程。它负责发起对话、调度模型。
- Client(客户端):Host 内部为每个 Server 启动的一个连接实例,遵循一对一关系——一个 Client 只连一个 Server,负责收发 JSON-RPC 消息。
- Server(服务端):暴露能力的进程,可以是本地脚本(stdio 传输)或远程 HTTP 服务,提供工具、资源、提示模板三类原语。
协议本身跑在 JSON-RPC 2.0 之上,对传输层不挑——本地用标准输入输出(stdio),远程用 Streamable HTTP(基于 SSE 双向流)。这意味着同一个 Server 既能给桌面客户端用,也能挂到云端给 SaaS 用,只需换传输方式。
三、三个核心原语:Resources / Tools / Prompts
MCP Server 能对外提供三类能力,这是它和单纯”函数调用”最大的区别:
1. Resources(资源):可被读取的上下文
资源是只读的、由应用侧主动拉取的数据,类似”给模型的参考资料”。例如一个 file:// 资源返回某份文档内容,一个 db://orders/recent 资源返回最近订单。资源用 URI 寻址,模型不直接”调用”它,而是由 Host 在合适时机注入上下文。
2. Tools(工具):可被模型执行的操作
工具是可写、可副作用的操作,例如”查询天气””执行 SQL””发 Slack 消息”。每个工具带名称、描述和 JSON Schema 形参,模型根据描述决定是否调用、填什么参数。工具是 MCP 最常用、也最容易踩安全红线的部分。
3. Prompts(提示模板):可复用的交互流程
提示模板是预定义的对话骨架,例如”把这段代码转成带单测的版本”。用户点一下就能把结构化提示灌进对话,适合把团队最佳实践固化成一键动作。
四、动手搭一个 MCP Server(Python + FastMCP)
官方 Python SDK 提供了 FastMCP 高层封装,几行代码就能暴露工具。下面这个示例注册了一个查询订单的工具和一个配置资源:
from mcp.server.fastmcp import FastMCP
mcp = FastMCP("demo-server")
@mcp.tool()
def query_orders(days: int) -> str:
"""查询最近 N 天的订单总量(演示用)"""
# 真实场景这里查数据库;注意:不要在工具里直接拼接 SQL
return f"近 {days} 天订单共 1280 笔"
@mcp.resource("config://app")
def app_config() -> str:
return "env=prod region=cn-hangzhou"
if __name__ == "__main__":
mcp.run() # 默认 stdio 传输
装好依赖 pip install mcp 后,python server.py 就会以 stdio 方式启动并等待客户端连接。@mcp.tool() 装饰的函数会自动生成 JSON Schema,模型看到的只有函数名、描述与参数,调用时 SDK 负责序列化往返。
五、客户端如何接入:配置即连接
桌面客户端(如 Claude Desktop)只需在配置文件里声明 Server 的启动命令,Host 会自行拉起子进程并维护 Client 连接。一个本地 stdio Server 的配置如下:
{
"mcpServers": {
"demo": {
"command": "python",
"args": ["/abs/path/server.py"]
}
}
}
如果你用 TypeScript SDK 自建客户端,流程是”建传输→连 Client→列工具”:
import { Client } from "@modelcontextprotocol/sdk/client/index.js";
import { StdioClientTransport } from "@modelcontextprotocol/sdk/client/stdio.js";
const transport = new StdioClientTransport({ command: "python", args: ["server.py"] });
const client = new Client({ name: "my-client", version: "1.0.0" });
await client.connect(transport);
const tools = await client.listTools();
远程部署时改用 Streamable HTTP 传输,客户端用 POST 发 JSON-RPC,服务端以 SSE 回推事件流:
curl -X POST http://localhost:8000/mcp \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-d '{"jsonrpc":"2.0","id":1,"method":"tools/list","params":{}}'
六、MCP 与 Function Calling、LangChain Tools 有何不同
很多人会问:模型本来就有 Function Calling,LangChain 也有 Tool 抽象,MCP 多此一举吗?关键在”标准化”与”复用”两个词。Function Calling 是厂商私有格式,换模型要改适配;LangChain Tools 绑定框架,换框架要重写;MCP 是开放协议,Server 一次编写、任意客户端复用。
| 维度 | Function Calling | LangChain Tools | MCP |
| 标准化程度 | 厂商私有 | 框架私有 | 开放标准 |
| 复用范围 | 绑定单一模型 | 绑定单一框架 | 跨客户端复用 |
| 传输方式 | 模型 HTTP 接口 | 进程内调用 | stdio / HTTP |
| 生态 | 各自实现 | 社区集成 | 统一注册表 |
实践中三者并不互斥:很多 Agent 框架(如 LangChain)已经能直接把 MCP Server 包装成自己的 Tool 来用,见 LangChain Agent 实战:工具调用与自主编排。MCP 解决的是”能力怎么被统一暴露”,上层编排仍可用你熟悉的框架。
七、传输层怎么选:stdio 还是 Streamable HTTP
| 维度 | Stdio | Streamable HTTP |
| 部署位置 | 本地子进程 | 远程服务 |
| 适用场景 | 桌面 / 单机 | 多用户 / SaaS |
| 鉴权 | 进程级,无需网络 | 需令牌与 HTTPS |
| 运维 | 随客户端启停 | 独立部署可水平扩展 |
个人工具、本地文件检索优先 stdio,零运维;要把能力开放给团队或多租户,就上 Streamable HTTP,但务必加鉴权、限流与日志,避免成为新的攻击面。关于服务入口的缓冲与代理配置,可参考 Nginx 反向代理实战:从配置到性能调优。
八、生产落地:安全清单
MCP 把”执行权”交给了模型,安全是头等大事。上线前至少过一遍下面的清单:
| 风险 | 缓解措施 |
| 工具被诱导执行危险操作 | 写操作加人工确认;危险工具(删库、发消息)默认关闭 |
| Server 返回污染内容 | 对资源内容做校验与长度上限,防止提示注入 |
| 远程 Server 未鉴权 | Streamable HTTP 必须 HTTPS + 令牌,按租户隔离 |
| 工具描述被劫持 | Server 来源可信白名单,不从公网随意拉第三方 Server |
| 凭据泄露 | 密钥走环境变量 / 密钥管理,禁止硬编码进工具代码 |
特别提醒:模型看到的”工具描述”本身就可能成为提示注入入口——恶意 Server 可以在描述里藏指令诱导模型。只接入可信来源的 Server,是 MCP 落地的最低防线。关于 AI 应用的安全攻防,可延伸阅读 大模型提示注入攻防:AI 应用安全实战。
九、生态与选型
官方维护了一个 MCP Server 注册表(如 GitHub 上的 modelcontextprotocol/servers),社区已贡献数据库、浏览器、文件系统、Git、Slack 等大量现成 Server。选型时遵循两条原则:优先用官方/高星社区 Server,少自己造轮子;对核心业务数据源(订单库、用户库),宁可自研一个最小 Server 并严格收窄权限,也不要直接挂一个权限过大的通用 Server。若你想把私有知识库也暴露成工具,可结合 2026 年搭建私有 AI 知识库:Dify + Ollama 本地部署 的思路,把检索能力包成 MCP 资源。
十、小结
MCP 的本质是用”开放协议”取代”私有集成”,把 AI 应用连接外部世界的能力标准化、可复用化。对开发者而言,它意味着少写几十套适配、多专注业务逻辑;对团队而言,它意味着工具能力可以像组件一样沉淀和共享。上手路径很清晰:先用 FastMCP 写一个小 Server 跑通 stdio,再按需迁移到 Streamable HTTP 服务化,全程把安全清单当成上线门槛。当你的 Agent 需要记忆与编排时,MCP 还能和 AI 智能体记忆系统、Agent 评测 组合成完整闭环。MCP 不会取代你的 Agent 框架,而是让框架之下那层”能力插座”终于统一了。




