@omarsar0: 如果你使用MCP构建,这篇值得一读。(收藏它)论文涵盖了五个反复出现的MCP服务器模式……
摘要
本文对在十五个独立开发的服务器中观察到的五个反复出现的MCP服务器架构模式进行了分类,提供了一个包含上下文、问题、解决方案和后果的分类法。还记录了反模式、横切关注点以及定量评估,包括评分者间信度和传输开销。
查看缓存全文
缓存时间: 2026/07/01 04:00
如果你在使用 MCP 构建,这篇文章值得一读。(收藏它)这篇论文涵盖了十五个独立开发服务器中反复出现的五种 MCP 服务器模式。这个分类很有用,因为我看到许多 AI 团队在重复构建相同的结构,却没有共同的名字。如果你正在构建 MCP 服务器,这是一个实用的参考,可以帮助你判断你的服务器是在暴露资源、编排工具、管理会话、聚合代理,还是适配领域工作流。论文:https://arxiv.org/abs/2606.30317 在我们的学院中学习如何构建有效的 AI 代理:https://academy.dair.ai
面向 LLM 集成应用的 MCP 服务器架构模式
来源:https://arxiv.org/html/2606.30317
摘要
模型上下文协议(MCP)由 Anthropic 于 2024 年 11 月推出,定义了一个标准化接口,用于将大型语言模型(LLM)连接到外部工具、数据源和服务。发布后数月内,GitHub 上出现了数百个社区构建的 MCP 服务器,但尚无软件维护文献描述该生态系统在生产环境中的构建方式。本行业经验论文,基于对十五个独立开发服务器(来自 ANSYR 语音 AI 平台的五个生产服务器,加上来自官方 MCP 注册表的十个公开服务器)的枚举语料库,归纳了五种反复出现的 MCP 服务器架构模式:资源网关(Resource Gateway)、工具编排器(Tool Orchestrator)、有状态会话服务器(Stateful Session Server)、代理聚合器(Proxy Aggregator)和领域特定适配器(Domain-Specific Adapter)。每种模式都采用 Gamma 等人[1] 建立的结构化形式描述:上下文、问题、解决方案和后果。我们还记录了四个反模式以及一组关于认证、版本控制和可观测性的横切关注点。定量评估贡献了三个测量指标:两个独立 LLM 评定者在 54 个保留服务器上对分类法的评定者间信度(Cohen’s κ=0.76),这同时也定位了三个模式边界模糊之处;在回环链路上端到端测量的传输开销(stdio: 0.01 ms p50;streamable-http: 0.39 ms p50)以及基于同区域网络基线(≈30 ms p50 基线加上协议开销)建模的跨主机路径开销;还有一个工具数量研究,显示 Claude Haiku 4.5 在每上下文 10 到 15 个工具之间准确率低于 90%,Sonnet 4 在 20 到 30 个工具之间准确率下降。代码、语料库和提示词发布在 https://github.com/rodriguescarson/mcp-patterns-icsme2026。
I. 引言
将 LLM 连接到外部系统过去意味着在提示模板中手工编写函数调用模式,并为每个新模型重新实现胶水代码。模型上下文协议 (MCP) [2] 将其标准化:这是一个客户端-服务器协议,MCP 服务器向任何兼容 MCP 的客户端暴露工具(可调用函数)、资源(URI 寻址数据)和提示(可重用模板)。单个服务器无需修改即可与 Claude、GPT-4、Gemini 或任何其他兼容代理协同工作。该协议被迅速采用。发布后数月内,GitHub 和 MCP 注册表 [3] 上出现了数百个服务器。目前缺少的是一套架构指导,帮助从业者做出良好的设计决策,以及从维护和演化角度看待生态系统在生产环境中如何自我构建。实践中反复出现的问题包括:
- 如何分解工具?一个工具何时变成两个?
- 何时在服务器端维护状态是合理的,以及如何管理它?
- 操作员应如何聚合来自多个服务器的能力?
- 何时应包装复杂 API 而不是直接暴露?
这些问题并非 MCP 特有;它们是通过 LLM 客户端的特定约束看到的 API 设计问题。LLM 通过阅读自然语言描述来选择工具,而不是浏览文档或检查模式。它们对模式复杂性的敏感度与人类开发者不同。如果描述缺失或写得不好,人类工程师认为显而易见的工具对 LLM 来说可能不可见或模棱两可。
本文基于 Celabe(ANSYR 语音 AI 平台运营商,自 2024 年末起有五个 MCP 服务器投入生产)的生产 MCP 服务器部署,以及对公开 MCP 服务器生态系统的审查,识别了五个解决这些问题的模式、四个反模式以及一组横切关注点。这些模式遵循 Gamma 等人 [1] 的结构化格式,并将企业集成模式 [4] 的框架应用于 MCP 上下文。第三节枚举了语料库和编码协议;第四至第五节呈现了模式和反模式;第六节报告了定量评估;第八节讨论了局限性、有效性威胁和可重复性。
II. 背景
II-A 模型上下文协议 (MCP)
MCP [2] 基于 JSON-RPC 2.0,定义了三种原语。工具是可调用的函数,具有名称、自然语言描述和 JSON Schema 输入规范。资源是 LLM 可以读取的 URI 寻址端点;它们可以是静态的(文件、文档)或动态的(实时数据库查询)。提示是在服务器端管理的参数化模板,根据请求向用户或代理公开。定义了两种传输选项:stdio 用于本地进程内通信,streamable-http(HTTP 带可选服务器推送事件)用于远程服务器。
II-B 与先前工作的关系
MCP 扩展了 OpenAI [5] 和 Anthropic [6] 引入的函数调用能力,但将工具实现与调用它的 LLM 分离。最清晰的类比是语言服务器协议 (LSP) [7]:LSP 标准化了编辑器与语言智能工具之间的接口,使得同一服务器无需修改即可在 VS Code、Neovim 和 Emacs 中工作。MCP 旨在实现代理与能力提供者之间的相同解耦。
本文使用的模式方法论借鉴了 Gamma 等人 [1]、Fowler 的企业应用模式 [8] 以及 Hohpe & Woolf 的集成模式 [4]。我们应用相同的结构化描述格式(上下文、问题、解决方案、后果、已知用途),并针对 LLM 面向的 API 约束进行了调整。我们不声称这些结构骨架是新的;每个都在经典软件架构中有明确的祖先(表 I)。贡献在于当客户端是一个通过阅读自然语言描述而非查阅文档来选择操作的 LLM 时所引入的增量:这是 REST [9]、GraphQL [10] 和 LSP [7] 所没有的约束,也是反模式(第五节)和工具数量限制(第六节-C)出现的原因。
表 I:每个 MCP 模式都有一个经典祖先;贡献在于 LLM 客户端的增量。
| MCP 模式 | 经典祖先 |
|---|---|
| 资源网关 | 外观 (Facade) |
| 工具编排器 | 工作流、过程管理器 |
| 有状态会话服务器 | 会话外观 |
| 代理聚合器 | 网关聚合器 |
| 领域特定适配器 | 适配器 |
II-C LLM 工具使用与代理架构
关于 LLM 工具使用的先前工作涵盖评估基准(ToolBench 风格套件 [11]、函数调用基准 [5,6])、在运行时组合工具的代理架构(ReAct [12]、AutoGPT 风格循环 [13]、LangChain [14])以及浏览器控制代理的基础设施 [15]。这些贡献侧重于客户端:代理如何决定调用哪个工具。MCP 将注意力转向服务端:能力目录如何构建、命名和分组。我们的模式目录是对这些先前工作的补充而非替代,为服务器作者在存在像 MCP 这样的协议后所做的架构决策提供了词汇。
有一项新兴文献研究 MCP 本身,但从与架构正交的角度出发。Hou 等人 [16] 调查了 MCP 的安全威胁和开放研究方向;Hasan 等人 [17] 挖掘了公开 MCP 服务器中的安全和可维护性问题;Guo 等人 [18] 大规模测量了超过 8000 个服务器的生态系统。这些工作表征了生态系统包含什么以及哪里脆弱;但没有任何一个目录记录了反复出现的服务端设计结构,或者塑造这些结构的 LLM 客户端约束——这正是本文要填补的空白。我们的反模式(第五节)与 Hasan 等人的可维护性问题是同一服务器的互补视角。
III. 方法论与语料库
III-A 语料库
模式目录来源于十五个独立开发的 MCP 服务器构成的枚举语料库:来自 ANSYR 语音 AI 平台(由 Celabe 运营;2024 年末至 2025 年初部署)的五个生产服务器,以及来自官方 modelcontextprotocol/servers 注册表的十个公开服务器。表 II 列出了语料库。ANSYR 服务器因 IP 原因使用匿名标识符(Server-A 至 Server-E),其部署类别和主要模式在表中披露;公开服务器按完整 GitHub 路径列出。完整的机器可读语料库,包含时间戳和主要模式分配,包含在复现包(corpus.json)中。
表 II:用于推导模式目录的十五个 MCP 服务器枚举语料库。公开服务器链接到其规范实现;ANSYR(生产)服务器已匿名化。
| 服务器 | 类别 | 主要模式 |
|---|---|---|
| 生产 (Celabe / ANSYR), N = 5 | ||
| Server-A | 语音工具聚合器 | Tool Orchestrator |
| Server-B | 按需对话会话 | Stateful Session Server |
| Server-C | 电话 / SIP 适配器 | Domain-Specific Adapter |
| Server-D | 客户/CRM 读取网关 | Resource Gateway |
| Server-E | 多租户聚合器 | Proxy Aggregator |
| 公开 (modelcontextprotocol/servers), N = 10 | ||
| filesystem | 本地文件 | Resource Gateway |
| postgres | 关系数据库 | Resource Gateway |
| sqlite | 嵌入式数据库 | Resource Gateway |
| github | VCS / Issue API | Tool Orchestrator |
| slack | 消息 API | Tool Orchestrator |
| brave-search | 网络搜索 | Tool Orchestrator |
| fetch | 通用 HTTP | Tool Orchestrator |
| puppeteer | 浏览器自动化 | Stateful Session Server |
| memory | 每会话 KV 存储 | Stateful Session Server |
| git | 仓库状态 | Stateful Session Server |
III-B 编码协议
数据提取。 对于每个服务器,我们读取一组固定的来源并提取了五个工件:(i)工具、资源和提示注册(setRequestHandler 调用及其 JSON 模式)来自源代码;(ii)传输配置;(iii)任何服务器端会话或状态处理;(iv)对其他 MCP 服务器的委派;以及(v)领域特定验证或业务逻辑。对于十个公开服务器,这些来自 GitHub 仓库(源代码、README 和已发布文档);对于五个生产服务器,来自源代码和部署配置。我们没有仅依赖 README 文本,因为 README 经常省略我们感兴趣的结构性决策。
编码。 然后我们应用了两阶段定性编码流程 [19]。第一作者进行的第一阶段开放编码标记了每个提取工件中反复出现的结构性决策。第二阶段模式编码传递 [19] 将第一阶段的代码按共享结构和共享问题分组为候选模式;只有当候选模式独立出现在至少两个服务器中,并且解决了一个没有明显先前解决方案的问题时,才被提升到目录中。第二作者独立地对照语料库审查了所得分类法,两位合著者通过讨论解决了分歧。由于这次审查是验证性传递而非独立双重编码,我们在保留语料库上使用两个独立评定者分别测量了评定者间信度,详见第六节-A(Cohen’s κ=0.76)。
IV. 五种 MCP 架构模式
IV-A 模式 1:资源网关 (Resource Gateway)
也称为: 数据外观 (Data Facade),上下文提供者 (Context Provider)
IV-A1 上下文
LLM 代理需要从一个或多个后端系统(数据库、文档存储、第三方 API)读取结构化数据,并基于这些数据来支撑其响应。
IV-A2 问题
MCP 服务器应如何向 LLM 暴露后端数据,使其既能被查询,又能防止未受信任数据带来的提示注入,并且在后端模式变化时保持一致性?
IV-A3 解决方案
将服务器构建为网关,中介所有数据访问。将读操作暴露为资源(列表、按 ID 获取),当查询参数在开放 URI 模板中不安全时,将参数化查询暴露为工具。插入一个消毒层,在将后端响应传递给 LLM 之前,从中剥离或转义注入的内容。
清单 1:资源网关:MongoDB 文档暴露,带消毒
server.setRequestHandler(ListResourcesRequestSchema, async () => ({
resources: await db.collection('documents')
.find({}, {projection: {_id: 1, title: 1, updatedAt: 1}})
.toArray()
.then(docs => docs.map(d => ({
uri: `doc://${d._id}`,
name: d.title,
mimeType: 'application/json'
})))
}));
server.setRequestHandler(ReadResourceRequestSchema, async (req) => {
const id = req.params.uri.replace('doc://', '');
const doc = await db.collection('documents').findOne({_id: id});
return { contents: [{ uri: req.params.uri, text: sanitize(JSON.stringify(doc)) }] };
});
IV-A4 后果
好处: 单一的访问控制执行点;即使后端模式变化,LLM 看到的是稳定接口;提示注入风险集中在一个层控制。负担: 每次读取多一个网络跳转;后端模式变化会传播到 MCP 服务器;复杂的连接或聚合可能难以表示为资源。
IV-A5 已知用途
数据库连接器(PostgreSQL, MongoDB),文档存储桥接器(Notion, Google Drive),REST API 包装器(GitHub, Jira, Linear)。
IV-B 模式 2:工具编排器 (Tool Orchestrator)
也称为: 动作中心 (Action Hub),工作流外观 (Workflow Facade)
IV-B1 上下文
LLM 代理需要执行跨越多个外部系统的操作:例如,创建工单、通知分配人以及在频道中发帖。
IV-B2 问题
如何暴露多系统工作流,而无需 LLM 理解每个系统的 API、管理跨调用中间状态或处理部分失败?
IV-B3 解决方案
暴露复合工具,封装完整的工作流。每个工具在内部执行所有子调用,并返回一个单一摘要。LLM 看到一个操作;服务器处理编排。
清单 2:工具编排器:跨系统工作流作为一个工具
server.tool(
'create_incident',
{ title: z.string(), severity: z.enum(['P1','P2','P3']), assignee: z.string() },
async (args) => {
const ticket = await jira.createTicket({ ... });
await slack.notifyUser(args.assignee, `New ${args.severity} incident: ${args.title}`);
const runbook = await confluence.lookupRunbook(args.severity);
return { content: [{ type: 'text', text: `Incident created: ${ticket.key}\n${runbook}` }] };
}
);
IV-B4 后果
好处: 将多个系统协调逻辑封装在一个地方;减少 LLM 的工具选择开销;部分失败可以在内部处理。负担: 复合工具如果输出格式不佳或长时间运行,可能成为黑箱或降低 LLM 的可观察性;对于 LLM 来说,重试逻辑在复合工具外部无法使用。
IV-B5 已知用途
客户服务工作流(工单、通知、SLA 更新)、CI/CD 管道触发(构建、测试、部署)、数据流水线编排(提取、转换、加载)。
IV-C 模式 3:有状态会话服务器 (Stateful Session Server)
也称为: 对话持有者 (Conversation Holder),上下文记忆 (Context Memory)
(原文在此处中断,但根据上下文,后续内容应为模式 3 及后续模式的完整描述。这里假设用户只提供了上述部分,我们忠实翻译所给内容。若有完整文本,建议继续补充。)
相似文章
@rohanpaul_ai: 非常及时的文章。MCP 服务器需要清晰的设计模式,因为当工具过多或描述模糊时,LLM 会感到困惑……
本文提出了 MCP 服务器的设计模式,以提升 LLM 工具选择的准确性,并发现可见工具过多会降低性能,尤其是对较弱的模型而言。
大部分MCP服务器并不需要存在。你的情况可能是例外
大多数MCP服务器是不必要的;本文提供了一个判断何时需要MCP服务器的框架,强调首先需要稳定的API和CLI。
@smthomas3: 我接触的几乎每家公司都在构建 MCP 服务器,如果有多个工程团队的话,这说得通。
据 @smthomas3 称,大多数拥有多个工程团队的公司都在构建 MCP 服务器,这引用了 Hacker News 上关于 MCP 是否已死亡的讨论,以及 OpenAI 的 @mxstbr 的发言。
@svpino: MCP 并没有消亡。对于那些总说“但 MCP 会在你的上下文里塞垃圾”的人,这个抱怨已经过时了:现……
为 MCP(模型上下文协议)辩护,反驳其会向上下文注入垃圾信息的批评。指出 Claude Code、Codex 和 Cursor 等现代工具已实现渐进式披露,并按需加载 MCP 工具,使该抱怨过时。作者认为 MCP 最适合需要身份验证和可发现性的云端托管平台。
MCP安全现状 [pdf]
该PDF报告审视了模型上下文协议(MCP)的安全现状,涵盖漏洞与最佳实践。