第 5 章:进阶配置

MCP

通过模型上下文协议连接外部世界

1. MCP 是什么

1.1 定义与起源

MCP(Model Context Protocol,模型上下文协议)是 Anthropic 于 2024 年 11 月推出的开放协议,旨在标准化大语言模型(LLM)应用程序与外部数据源、工具之间的集成方式。官方将其比喻为"AI 世界的 USB-C 接口"——如同 USB-C 统一了各类电子设备的连接标准,MCP 试图统一 AI 应用与外部世界的通信方式。

在 MCP 出现之前,如果你想让 AI 访问某个数据源,需要为每个 AI 工具单独编写适配层:给 Claude 写一个插件,给 Cursor 写一个扩展,给 Windsurf 再写一个……复杂度是 N x M(N 个数据源 x M 个 AI 工具)。有了 MCP 之后,你只需要编写一次 MCP Server,所有支持 MCP 的客户端都能直接调用,复杂度降到了 N + M。

MCP 的设计深受 LSP(Language Server Protocol,语言服务器协议)的启发。LSP 标准化了如何在各种开发工具中添加编程语言支持,而 MCP 则标准化了如何将额外的上下文和工具集成到 AI 应用生态中。

1.2 设计哲学

MCP 基于以下核心设计原则:

原则含义
服务器应极其易于构建宿主应用处理复杂的编排职责,服务器专注于特定、明确定义的能力
服务器应高度可组合每个服务器提供隔离的聚焦功能,多个服务器可无缝组合
服务器不应读取整个对话服务器仅接收必要的上下文信息,完整对话历史保留在宿主
功能可逐步添加核心协议提供最低限度的必需功能,可根据需要协商额外能力

1.3 解决的问题

MCP 主要解决三个核心问题:

  1. 集成碎片化:每个 AI 工具都需要为每个数据源编写自定义集成代码
  2. 上下文传递困难:LLM 难以获取实时、私有、领域特定的数据
  3. 工具发现不一致:不同平台对"工具"的定义和调用方式各不相同

2. 核心架构

2.1 三层组件模型

MCP 采用客户端-宿主-服务器架构,其中每个宿主可以运行多个客户端实例:

+-------------------------------------------------------------+
|                        MCP Host                             |
|  (Claude Desktop / Claude Code / Cursor / Windsurf ...)     |
|                                                             |
|  +----------------+    +----------------+                   |
|  |  MCP Client 1  |    |  MCP Client 2  |  ...             |
|  |  (连接 Server A)|    |  (连接 Server B)|                  |
|  +-------+--------+    +-------+--------+                   |
+----------|-------------------|------------------------------+
           |                   |
           v                   v
    +-------------+      +-------------+
    | MCP Server A|      | MCP Server B|
    | (GitHub API)|      | (PostgreSQL)|
    +-------------+      +-------------+

宿主(Host):LLM 应用本身,作为容器和协调者。它创建并管理多个客户端实例,控制连接权限和生命周期,执行安全策略和同意要求,处理用户授权决策,协调 AI/LLM 集成和采样。

客户端(Client):由宿主创建,维护一个与特定服务器的一对一连接。每个客户端建立一个有状态的会话,处理协议协商和能力交换,双向路由协议消息,管理订阅和通知,在服务器之间维护安全边界。

服务器(Server):提供专门的上下文和能力。通过 MCP 原语暴露资源、工具和提示,独立运行并承担明确职责,通过客户端接口请求采样,必须遵守安全限制,可以是本地进程或远程服务。

2.2 协议规范:基于 JSON-RPC 2.0

MCP 基于 JSON-RPC 2.0 构建,提供了一种有状态的会话协议。它定义了三种核心消息类型:

消息类型特征用途
请求(Request)具有 idmethodparams,期望响应调用工具、列出资源、获取提示
响应(Response)匹配特定请求 id 的成功 resulterror返回操作结果
通知(Notification)无需响应的单向消息,无 id 字段状态变更、初始化完成信号

2.3 生命周期:从握手到关闭

MCP 定义了严格的三阶段连接生命周期:

阶段一:初始化(Initialization)

初始化是客户端与服务器的第一次交互,必须在任何其他操作之前完成。

步骤 1:客户端发送 initialize 请求

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "initialize",
  "params": {
    "protocolVersion": "2025-03-26",
    "capabilities": {
      "roots": { "listChanged": true },
      "sampling": {}
    },
    "clientInfo": {
      "name": "ClaudeCode",
      "version": "2.1.0"
    }
  }
}

步骤 2:服务器响应其能力和信息

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "protocolVersion": "2025-03-26",
    "capabilities": {
      "logging": {},
      "prompts": { "listChanged": true },
      "resources": { "subscribe": true, "listChanged": true },
      "tools": { "listChanged": true }
    },
    "serverInfo": {
      "name": "github-server",
      "version": "1.0.0"
    },
    "instructions": "Optional instructions for the client"
  }
}

步骤 3:客户端发送 initialized 通知确认就绪

{
  "jsonrpc": "2.0",
  "method": "notifications/initialized"
}

阶段二:运行(Operation)

双方根据协商的能力交换消息。客户端可以请求工具列表、调用工具、读取资源、获取提示;服务器可以发送能力变更通知。

阶段三:关闭(Shutdown)

  • stdio 传输:客户端关闭输入流,等待服务器退出,必要时发送 SIGTERMSIGKILL
  • HTTP 传输:关闭关联的 HTTP 连接

2.4 能力协商

MCP 使用基于能力的协商系统,客户端和服务器在初始化期间显式声明支持的功能:

类别能力描述
客户端roots提供文件系统根目录的能力
客户端sampling支持 LLM 采样请求
服务器prompts提供提示模板
服务器resources提供可读资源
服务器tools暴露可调用的工具
服务器logging发送结构化日志消息
服务器completions支持参数自动补全

2.5 三种核心原语

MCP Server 通过三种原语暴露功能:

原语类型用途示例
Tools(工具)可执行执行操作、副作用查询数据库、发送消息、创建文件
Resources(资源)只读提供数据、上下文文件内容、API 返回、配置信息
Prompts(提示)模板预定义对话模板代码审查模板、日报生成模板

Tools 是 AI 可以调用的"函数",执行某个动作并返回结果。Resources 是 AI 可以读取的"数据源"。Prompts 是帮助 AI 更快理解任务的"模板"。

2.6 传输方式

MCP 支持两种传输方式:

传输方式适用场景特点
stdio本地进程通信通过标准输入输出传输,适合本地工具,安全性高
HTTP / SSE远程服务通信基于 HTTP 或 Server-Sent Events,适合云端服务,需处理认证

3. 内置 MCP Server 列表

MCP 生态已发展出数百个 Server,覆盖开发、数据、通信、自动化等多个领域。以下是官方和社区维护的核心 Server:

3.1 官方参考实现

Server功能安装方式
Everything参考测试服务器,包含 prompts、resources、tools 完整示例npx -y @modelcontextprotocol/server-everything
FetchWeb 内容获取和转换,优化 LLM 使用效率npx -y @modelcontextprotocol/server-fetch
Filesystem安全文件操作,支持可配置访问控制npx -y @modelcontextprotocol/server-filesystem /allowed/path
Git读取、搜索和操作 Git 仓库uvx mcp-server-git
Memory基于知识图谱的持久化记忆系统npx -y @modelcontextprotocol/server-memory
Sequential Thinking动态反思式问题求解npx -y @modelcontextprotocol/server-sequentialthinking
Time时间和时区转换npx -y @modelcontextprotocol/server-time

3.2 常用第三方 Server

类别Server功能安装方式
代码托管GitHub仓库管理、PR、Issue、代码搜索远程 HTTP Server,需 GitHub PAT
代码托管GitLabGitLab API、项目管理npx -y @modelcontextprotocol/server-gitlab
数据库PostgreSQL只读数据库访问、Schema 检查npx -y @modelcontextprotocol/server-postgres <dsn>
数据库SQLite数据库交互和商业智能npx -y @modelcontextprotocol/server-sqlite
数据库MySQLSQL 查询执行社区实现
浏览器Puppeteer浏览器自动化和网页抓取npx -y @modelcontextprotocol/server-puppeteer
通信Slack频道管理和消息功能远程 HTTP Server,OAuth 认证
通信Email (Gmail)邮件发送和搜索OAuth 2.0 认证
搜索Brave SearchWeb 和本地搜索需 Brave Search API Key
监控Sentry检索和分析 Sentry 问题远程 HTTP Server
地图Google Maps位置服务、路线、地点详情需 Google Maps API Key
网盘Google Drive文件访问和搜索OAuth 2.0 认证
文档Notion页面、数据库、块操作远程 HTTP Server,OAuth 认证
设计Figma设计文件访问社区实现
支付Stripe支付操作和管理远程 HTTP Server

3.3 Server 生态发现

社区维护的 Server 目录:

4. 在 Claude Code 中安装与配置 MCP Server

4.1 三种安装方式

Claude Code 支持三种方式添加 MCP Server:

方式一:远程 HTTP Server(推荐)

适合连接云端服务,是最广泛支持的传输方式:

# 基本语法
claude mcp add --transport http <name> <url>

# 连接 Notion
claude mcp add --transport http notion https://mcp.notion.com/mcp

# 带 Bearer Token 的认证
claude mcp add --transport http secure-api https://api.example.com/mcp \
  --header "Authorization: Bearer your-token"

方式二:远程 SSE Server

# 基本语法
claude mcp add --transport sse <name> <url>

# 连接 Asana
claude mcp add --transport sse asana https://mcp.asana.com/sse

方式三:本地 stdio Server

适合需要直接系统访问或自定义脚本的工具:

# 基本语法
claude mcp add [options] <name> -- <command> [args...]

# 连接 Airtable
claude mcp add --transport stdio --env AIRTABLE_API_KEY=YOUR_KEY airtable \
  -- npx -y airtable-mcp-server

# 连接 PostgreSQL 数据库
claude mcp add --transport stdio db -- npx -y @modelcontextprotocol/server-postgres \
  "postgresql://user:pass@localhost:5432/mydb"

# 连接文件系统(限制访问目录)
claude mcp add --transport stdio fs -- npx -y @modelcontextprotocol/server-filesystem \
  /Users/lionad/projects /Users/lionad/documents

4.2 三种配置作用域

Claude Code 支持三个配置作用域:

作用域加载范围团队共享存储位置
Local(默认)仅当前项目~/.claude.json
Project仅当前项目是(通过版本控制).mcp.json(项目根目录)
User所有项目~/.claude.json
# Local 作用域(默认)
claude mcp add --transport http stripe https://mcp.stripe.com

# Project 作用域(团队共享)
claude mcp add --transport http paypal --scope project https://mcp.paypal.com/mcp

# User 作用域(跨项目)
claude mcp add --transport http hubspot --scope user https://mcp.hubspot.com/anthropic

Project 作用域的配置文件 .mcp.json 示例:

{
  "mcpServers": {
    "shared-server": {
      "command": "/path/to/server",
      "args": [],
      "env": {}
    }
  }
}

4.3 管理命令

# 列出所有配置的 Server
claude mcp list

# 查看特定 Server 详情
claude mcp get github

# 移除 Server
claude mcp remove github

# 重置项目作用域的批准选择
claude mcp reset-project-choices

# 在 Claude Code 内检查 Server 状态
/mcp

4.4 环境变量扩展

.mcp.json 支持环境变量扩展,方便团队共享配置同时保护敏感信息:

{
  "mcpServers": {
    "api-server": {
      "type": "http",
      "url": "${API_BASE_URL:-https://api.example.com}/mcp",
      "headers": {
        "Authorization": "Bearer ${API_KEY}"
      }
    }
  }
}

支持的语法:

  • ${VAR} — 展开为环境变量 VAR 的值
  • ${VAR:-default} — 若 VAR 已设置则使用其值,否则使用默认值

4.5 常用 Server 配置示例

GitHub

# 使用 GitHub Personal Access Token
claude mcp add --transport http github https://api.githubcopilot.com/mcp/ \
  --header "Authorization: Bearer YOUR_GITHUB_PAT"

配置后可直接使用自然语言操作:

Review PR #456 and suggest improvements
Create a new issue for the bug we just found
Show me all open PRs assigned to me

PostgreSQL

claude mcp add --transport stdio db -- npx -y @bytebase/dbhub \
  --dsn "postgresql://readonly:pass@prod.db.com:5432/analytics"

配置后可直接查询:

What's our total revenue this month?
Show me the schema for the orders table
Find customers who haven't made a purchase in 90 days

Sentry

claude mcp add --transport http sentry https://mcp.sentry.dev/mcp

配置后可调试生产问题:

What are the most common errors in the last 24 hours?
Show me the stack trace for error ID abc123
Which deployment introduced these new errors?

4.6 高级功能

动态工具更新:Claude Code 支持 MCP list_changed 通知,Server 可动态更新可用工具而无需重新连接。

自动重连:HTTP/SSE Server 断开后,Claude Code 会自动以指数退避重连(最多 5 次,从 1 秒开始翻倍)。

输出限制:默认最大输出 25000 tokens,可通过环境变量调整:

export MAX_MCP_OUTPUT_TOKENS=50000
claude

工具搜索:默认启用工具延迟加载,只有 Claude 实际使用的工具才会进入上下文,减少对上下文窗口的占用。

5. 自定义 MCP Server:从零开发

5.1 环境准备

# 创建项目目录
mkdir mcp-weather-server && cd mcp-weather-server

# 初始化(使用 Bun 或 npm)
bun init -y
# 或 npm init -y

# 安装 MCP TypeScript SDK 和 Zod
bun add @modelcontextprotocol/sdk zod
# 或 npm install @modelcontextprotocol/sdk zod

TypeScript 配置要点:

{
  "compilerOptions": {
    "target": "ES2022",
    "module": "ESNext",
    "moduleResolution": "bundler",
    "esModuleInterop": true,
    "strict": true
  }
}

5.2 创建 Server 骨架

// src/index.ts
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
import { z } from "zod";

// 创建服务器实例
const server = new McpServer({
  name: "weather-service",
  version: "1.0.0",
});

// 注册工具(Tools)
server.tool(
  "get_weather",
  "获取指定城市的当前天气信息",
  {
    city: z.string().describe("城市名称,如:北京、上海"),
  },
  async ({ city }) => {
    // 工具实现见下文
    return { content: [{ type: "text", text: `查询 ${city} 的天气...` }] };
  }
);

// 启动服务器
const transport = new StdioServerTransport();
await server.connect(transport);

console.error("MCP Weather Server 已启动,等待连接...");

5.3 实现工具(Tools)

// 天气查询工具实现
server.tool(
  "get_weather",
  "获取指定城市的当前天气信息",
  {
    city: z.string().describe("城市名称,如:北京、上海"),
  },
  async ({ city }) => {
    const API_KEY = process.env.OPENWEATHER_API_KEY;
    const url = `https://api.openweathermap.org/data/2.5/weather?q=${encodeURIComponent(city)}&appid=${API_KEY}&units=metric&lang=zh_cn`;

    try {
      const response = await fetch(url);
      if (!response.ok) {
        throw new Error(`API 请求失败:${response.status}`);
      }

      const data = await response.json();

      return {
        content: [
          {
            type: "text",
            text: JSON.stringify({
              city: data.name,
              temperature: `${data.main.temp}°C`,
              feels_like: `${data.main.feels_like}°C`,
              description: data.weather[0].description,
              humidity: `${data.main.humidity}%`,
              wind_speed: `${data.wind.speed} m/s`,
            }, null, 2),
          },
        ],
      };
    } catch (error) {
      return {
        content: [
          {
            type: "text",
            text: `查询失败:${error instanceof Error ? error.message : '未知错误'}`,
          },
        ],
        isError: true,
      };
    }
  }
);

5.4 添加资源(Resources)

// 提供服务器状态信息
server.resource(
  "server-status",
  "status://server",
  async (uri) => ({
    contents: [
      {
        uri: uri.href,
        text: JSON.stringify({
          name: "Weather Service",
          version: "1.0.0",
          status: "running",
          timestamp: new Date().toISOString(),
        }, null, 2),
      },
    ],
  })
);

// 提供 API 文档
server.resource(
  "api-docs",
  "docs://api",
  async (uri) => ({
    contents: [
      {
        uri: uri.href,
        text: `
# Weather MCP Server API

## Tools
- get_weather(city: string): 获取指定城市天气

## Resources
- status://server - 服务器状态
- docs://api - API 文档
        `.trim(),
      },
    ],
  })
);

5.5 添加提示模板(Prompts)

// 预定义的天气报告模板
server.prompt(
  "weather_report",
  "生成一份格式化的天气报告",
  {
    city: z.string().describe("城市名称"),
    include_tips: z.boolean().optional().describe("是否包含穿衣建议"),
  },
  ({ city, include_tips }) => ({
    messages: [
      {
        role: "user",
        content: {
          type: "text",
          text: `请为${city}生成一份天气报告。${include_tips ? "同时提供穿衣建议。" : ""}`,
        },
      },
    ],
  })
);

5.6 完整入口文件

// src/index.ts(完整版)
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
import { z } from "zod";

const server = new McpServer({
  name: "weather-service",
  version: "1.0.0",
});

// ===== Tools =====
server.tool("get_weather", /* ... */);

// ===== Resources =====
server.resource("server-status", /* ... */);
server.resource("api-docs", /* ... */);

// ===== Prompts =====
server.prompt("weather_report", /* ... */);

// ===== 错误处理 =====
process.stdin.on("error", (err) => {
  console.error("标准输入错误:", err);
  process.exit(1);
});

process.stdout.on("error", (err) => {
  console.error("标准输出错误:", err);
  process.exit(1);
});

// 优雅退出
process.on("SIGINT", async () => {
  await server.close();
  process.exit(0);
});

// 启动
const transport = new StdioServerTransport();
await server.connect(transport);
console.error("MCP Weather Server 已启动,等待连接...");

5.7 配置 Claude Code 使用自定义 Server

# 使用绝对路径配置
claude mcp add --transport stdio weather -- bun run /absolute/path/to/mcp-weather-server/src/index.ts

或在 .mcp.json 中配置:

{
  "mcpServers": {
    "weather": {
      "command": "bun",
      "args": ["run", "/absolute/path/to/mcp-weather-server/src/index.ts"],
      "env": {
        "OPENWEATHER_API_KEY": "your-api-key"
      }
    }
  }
}

5.8 生产环境部署选项

部署方式适用场景优点缺点
本地 stdio个人使用、开发测试简单、安全无法共享
HTTP/SSE团队共享、多用户可远程访问需处理认证
Serverless生产环境自动扩缩容冷启动延迟

生产环境注意事项:

// 认证检查
const apiKey = request.headers.get("Authorization");
if (apiKey !== `Bearer ${process.env.API_KEY}`) {
  return new Response("Unauthorized", { status: 401 });
}

// 日志记录
import pino from "pino";
const logger = pino();

server.tool("get_weather", /* ... */, async ({ city }) => {
  logger.info({ city }, "查询天气");
  // ...
});

6. MCP 与 Function Call 的区别和关系

6.1 核心区别

维度Function CallMCP
本质模型内置能力(如 OpenAI 的 JSON 格式指令)跨模型协议标准(独立于具体模型)
定位单模型调用外部工具的实现方式多模型调用工具的通信规范
发起方由大模型主动生成调用指令由标准化客户端/服务器架构传递指令
依赖关系深度绑定特定模型模型无关(兼容 Claude/GPT/通义等)
工具热插拔需重新部署模型工具可动态注册/卸载
跨设备调用限于本地环境支持远程/云工具调用

6.2 简单比喻

  • Function Call = 手机的语音助手(只能控制本机 App)
  • MCP = 蓝牙协议(让任何手机连接任何耳机)

6.3 协同工作模式

二者实际可形成互补的上下游关系:

用户请求 → 大模型生成 Function Call → 转换为 MCP 请求 → 调用工具 → 结果返回模型

具体协作流程:

  1. 模型通过 Function Call 解析用户意图
  2. 将函数调用参数转换为 MCP 标准报文
  3. MCP 客户端分发给对应工具服务器
  4. 结果通过 MCP 返回模型生成回答

优势:保留 Function Call 的意图解析能力,获得 MCP 的工具生态扩展性。

6.4 技术演进趋势

  • Function Call 将作为模型原生基础能力持续进化
  • MCP 正在成为企业 AI 基础设施的事实标准协议
  • 二者边界逐渐模糊,最终形成"模型解析 → 协议传输 → 工具执行"分层架构
  • OpenAI 等厂商已支持 Function Call 转 MCP 网关

7. 实际案例

7.1 案例一:连接 PostgreSQL 数据库

场景:让 Claude 用自然语言查询数据库。

配置

claude mcp add --transport stdio postgres -- npx -y \
  @modelcontextprotocol/server-postgres \
  "postgresql://readonly:pass@localhost:5432/analytics"

使用

> 本月总收入是多少?
[Claude 自动调用 MCP 工具查询数据库]

> 显示 orders 表的 Schema
[Claude 自动调用 schema 查询工具]

> 找出 90 天内未购买的客户
[Claude 生成并执行 SQL 查询]

最佳实践

  1. 使用只读账号连接生产数据库
  2. 提供数据库 Schema 文件帮助 AI 理解表结构
  3. 准备示例查询文件提升生成质量

7.2 案例二:操作 GitHub

场景:在 Claude Code 中直接管理代码仓库。

配置

claude mcp add --transport http github https://api.githubcopilot.com/mcp/ \
  --header "Authorization: Bearer YOUR_GITHUB_PAT"

使用

> Review PR #456 并给出改进建议
[Claude 读取 PR  diff、评论、CI 状态,生成审查报告]

> 为刚发现的 bug 创建一个新 Issue
[Claude 自动创建 Issue,包含复现步骤和堆栈跟踪]

> 显示分配给我的所有开放 PR
[Claude 查询并列出 PR 列表]

> 实现 JIRA 工单 ENG-4521 描述的功能并在 GitHub 创建 PR
[Claude 读取工单 → 编写代码 → 提交 → 创建 PR]

7.3 案例三:读取 Slack 消息

场景:将 Slack 消息作为上下文输入 Claude。

配置

claude mcp add --transport http slack https://mcp.slack.com/mcp

Slack 官方远程 Server 使用 OAuth 认证,尊重现有权限。

使用

> 总结 #engineering 频道今天的讨论
[Claude 读取频道消息并生成摘要]

> 根据 Slack 中发布的新 Figma 设计更新邮件模板
[Claude 读取 Slack 中的设计链接 → 获取 Figma 内容 → 更新代码]

> 给参与讨论的 10 位用户发送反馈会议邀请
[Claude 提取用户列表 → 生成邮件草稿]

7.4 案例四:多 MCP 串联工作流

场景:将多个 MCP Server 串联完成复杂任务。

用户: "实现 JIRA 工单 ENG-4521 的功能,基于我们的设计规范,
       然后创建 PR 并通知团队"

Claude 的执行流程:
1. [JIRA MCP] 读取 ENG-4521 的详细描述
2. [Figma MCP] 获取相关设计稿
3. [Git MCP] 检查当前分支状态
4. [Filesystem MCP] 读取项目代码规范
5. 编写代码实现功能
6. [Git MCP] 提交代码
7. [GitHub MCP] 创建 PR
8. [Slack MCP] 在 #engineering 频道通知团队

8. 安全考量

8.1 核心安全风险

MCP 引入了全新的攻击面:AI 代理基于自然语言动态执行工具,访问敏感系统。OWASP 已发布专门的 MCP 安全速查表,识别出以下关键风险:

风险描述
Tool Poisoning(工具投毒)恶意指令隐藏在工具描述、参数 Schema 或返回值中,操纵 LLM 行为
Rug Pull 攻击Server 在初始用户批准后更改工具定义,将可信工具变为恶意工具
Tool Shadowing恶意 Server 的工具描述操纵代理对其他可信 Server 工具的行为
Confused Deputy(混淆代理)MCP Server 使用自身(往往过于宽泛的)权限执行操作,而非请求用户的权限
数据外泄通过提示注入将敏感数据编码到看似正常的工具调用中
供应链攻击从公共注册表安装不受信任或已被攻破的 MCP Server 包
沙箱逃逸本地 MCP Server 以完整主机权限运行,导致文件系统遍历或任意代码执行

8.2 安全最佳实践

1. 最小权限原则

  • 为每个 MCP Server 授予其功能所需的最低权限
  • 使用按 Server 隔离的凭证,绝不跨 Server 共享 Token
  • 请求窄范围的 OAuth 作用域(如 mail.readonly 而非 mail.full_access
  • 优先使用短期临时 Token 而非长期 PAT

2. 工具描述完整性校验

  • 批准前检查所有工具描述、参数名、类型和返回 Schema
  • 整个工具 Schema 视为潜在的注入面
  • 使用加密哈希固定工具定义,变更时告警(防止 rug pull)
  • 使用 mcp-scan 等工具自动检测投毒描述和跨 Server 阴影

3. 沙箱隔离

  • 在沙箱环境(容器、chroot、应用沙箱)中运行本地 MCP Server
  • 将文件系统访问限制为仅所需目录
  • 除非明确需要,否则禁用网络访问
  • 将敏感 Server(支付、认证、PII)与普通 Server 分离

4. 敏感操作人工确认

  • 对破坏性、财务或数据共享操作要求显式用户确认
  • 向用户显示完整的工具调用参数,而非仅摘要名称
  • 切勿自动批准工具调用,尤其在多 Server 设置中

5. 输入输出验证

  • 将所有输入视为不受信任(源自可能被恶意上下文影响的 LLM 输出)
  • 防范注入攻击(SQL、OS 命令、路径遍历)
  • 在返回 LLM 上下文前验证和清理工具输出
  • 切勿传递原始 Shell 命令或未经清理的文件路径

6. 传输层安全

  • 对所有远程 MCP Server 端点强制执行认证
  • 使用 OAuth 2.0 with PKCE 进行远程 Server 授权
  • 始终对远程传输使用 TLS
  • 将 MCP HTTP/SSE Server 绑定到特定接口(如 127.0.0.1),而非 0.0.0.0
  • 使用操作系统原生安全凭证存储(macOS Keychain、Windows Credential Manager)

7. 监控、日志与审计

  • 记录所有 MCP 工具调用,包含完整参数、用户上下文和时间戳
  • 将 MCP 日志输入 SIEM 进行异常检测
  • 对异常模式告警:新工具被调用、管理员级查询、异常调用频率
  • 从日志中脱敏密钥和 PII

8. 供应链安全

  • 仅从可信、已验证的来源安装 MCP Server
  • 安装前审查 Server 源代码和工具定义
  • 使用校验和或代码签名验证包完整性
  • 仔细检查包名再安装——拼写仿冒(typosquatting)是常见攻击向量

8.3 Claude Code 的安全机制

Claude Code 内置了多层安全保护:

  • 项目作用域 Server 需批准.mcp.json 中配置的 Server 首次使用时需要用户批准
  • 作用域隔离:Local/Project/User 三层作用域确保配置不会意外泄露
  • Denylist 优先managed-mcp.json 中的拒绝列表绝对优先于允许列表
  • 输出限制:默认 25000 tokens 的输出上限防止上下文被淹没
  • 工具搜索:延迟加载工具定义,减少上下文暴露面

企业级管理配置示例:

// /Library/Application Support/ClaudeCode/managed-mcp.json (macOS)
{
  "mcpServers": {
    "github": {
      "type": "http",
      "url": "https://api.githubcopilot.com/mcp/"
    },
    "sentry": {
      "type": "http",
      "url": "https://mcp.sentry.dev/mcp"
    }
  },
  "deniedMcpServers": [
    { "serverUrl": "https://*.untrusted.com/*" },
    { "serverCommand": ["npx", "-y", "unapproved-package"] }
  ]
}

9. 参考来源