AI 技术

MCP (Model Context Protocol):AI 应用的统一接口标准

深入理解 Anthropic 推出的 MCP 协议,如何让 AI 模型与外部工具无缝集成

MCP (Model Context Protocol):AI 应用的统一接口标准

Model Context Protocol (MCP) 是 Anthropic 推出的开放协议,旨在标准化 AI 模型与外部工具、数据源的交互方式。它就像是 AI 世界的 USB 接口——一个统一的标准,让不同的工具和服务能够轻松连接。

什么是 MCP?

MCP 是一个客户端-服务器协议,定义了 AI 应用如何:

  • 访问数据:数据库、文件系统、API
  • 调用工具:执行命令、操作服务
  • 获取上下文:实时信息、用户数据

核心概念

┌─────────────┐         ┌─────────────┐         ┌─────────────┐
│             │         │             │         │             │
│  AI Client  │ ◄─MCP──► │ MCP Server  │ ◄─────► │  Resources  │
│  (Claude)   │         │  (GitHub)   │         │  (Repos)    │
│             │         │             │         │             │
└─────────────┘         └─────────────┘         └─────────────┘

为什么需要 MCP?

问题:碎片化的集成

在 MCP 之前,每个 AI 应用都需要:

// 为每个服务编写自定义集成
const githubClient = new GitHubClient(token);
const slackClient = new SlackClient(token);
const notionClient = new NotionClient(token);
// ... 数十个不同的客户端

解决方案:统一协议

使用 MCP:

// 统一的 MCP 客户端
const mcpClient = new MCPClient();

// 连接任何 MCP 服务器
await mcpClient.connect('github');
await mcpClient.connect('slack');
await mcpClient.connect('notion');

MCP 架构

三层架构

  1. Resources(资源)

    • 数据源:文件、数据库记录、API 响应
    • 只读访问
    • 支持订阅更新
  2. Tools(工具)

    • 可执行操作:创建、更新、删除
    • 带参数的函数调用
    • 返回结构化结果
  3. Prompts(提示)

    • 预定义的提示模板
    • 可重用的对话模式
    • 支持参数化

通信流程

1. Client 发现 Server 能力
   Client → Server: list_resources()
   Server → Client: [resource1, resource2, ...]

2. Client 请求资源
   Client → Server: read_resource(uri)
   Server → Client: { content, metadata }

3. Client 调用工具
   Client → Server: call_tool(name, params)
   Server → Client: { result, status }

实现 MCP 服务器

基础服务器

import { Server } from '@modelcontextprotocol/sdk/server/index.js';
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';

// 创建服务器
const server = new Server(
  {
    name: 'my-mcp-server',
    version: '1.0.0',
  },
  {
    capabilities: {
      resources: {},
      tools: {},
    },
  }
);

// 定义资源
server.setRequestHandler('resources/list', async () => {
  return {
    resources: [
      {
        uri: 'file:///data/users.json',
        name: 'Users Database',
        mimeType: 'application/json',
      },
    ],
  };
});

// 读取资源
server.setRequestHandler('resources/read', async (request) => {
  const { uri } = request.params;

  if (uri === 'file:///data/users.json') {
    const users = await loadUsers();
    return {
      contents: [
        {
          uri,
          mimeType: 'application/json',
          text: JSON.stringify(users, null, 2),
        },
      ],
    };
  }

  throw new Error('Resource not found');
});

// 定义工具
server.setRequestHandler('tools/list', async () => {
  return {
    tools: [
      {
        name: 'create_user',
        description: 'Create a new user',
        inputSchema: {
          type: 'object',
          properties: {
            name: { type: 'string' },
            email: { type: 'string' },
          },
          required: ['name', 'email'],
        },
      },
    ],
  };
});

// 执行工具
server.setRequestHandler('tools/call', async (request) => {
  const { name, arguments: args } = request.params;

  if (name === 'create_user') {
    const user = await createUser(args.name, args.email);
    return {
      content: [
        {
          type: 'text',
          text: `User created: ${user.id}`,
        },
      ],
    };
  }

  throw new Error('Tool not found');
});

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

GitHub MCP 服务器示例

// GitHub MCP Server
class GitHubMCPServer {
  constructor(private token: string) {}

  // 资源:仓库列表
  async listRepositories() {
    const repos = await this.fetchRepos();
    return repos.map(repo => ({
      uri: `github://repos/${repo.full_name}`,
      name: repo.name,
      description: repo.description,
    }));
  }

  // 资源:文件内容
  async readFile(owner: string, repo: string, path: string) {
    const content = await this.fetchFileContent(owner, repo, path);
    return {
      uri: `github://repos/${owner}/${repo}/contents/${path}`,
      mimeType: 'text/plain',
      text: content,
    };
  }

  // 工具:创建 Issue
  async createIssue(owner: string, repo: string, title: string, body: string) {
    const issue = await this.githubAPI.createIssue({
      owner,
      repo,
      title,
      body,
    });
    return {
      issueNumber: issue.number,
      url: issue.html_url,
    };
  }

  // 工具:创建 PR
  async createPullRequest(params: PRParams) {
    const pr = await this.githubAPI.createPR(params);
    return {
      prNumber: pr.number,
      url: pr.html_url,
    };
  }
}

使用 MCP 服务器

在 Claude Code 中配置

{
  "mcpServers": {
    "github": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-github"],
      "env": {
        "GITHUB_TOKEN": "your_token_here"
      }
    },
    "postgres": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-postgres"],
      "env": {
        "DATABASE_URL": "postgresql://localhost/mydb"
      }
    },
    "filesystem": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-filesystem", "/path/to/allowed/directory"]
    }
  }
}

在代码中使用

import { MCPClient } from '@modelcontextprotocol/sdk/client/index.js';

// 创建客户端
const client = new MCPClient({
  name: 'my-app',
  version: '1.0.0',
});

// 连接到服务器
await client.connect(transport);

// 列出可用资源
const { resources } = await client.request({
  method: 'resources/list',
});

// 读取资源
const { contents } = await client.request({
  method: 'resources/read',
  params: {
    uri: 'github://repos/user/repo/contents/README.md',
  },
});

// 调用工具
const result = await client.request({
  method: 'tools/call',
  params: {
    name: 'create_issue',
    arguments: {
      owner: 'user',
      repo: 'repo',
      title: 'Bug Report',
      body: 'Found a bug...',
    },
  },
});

官方 MCP 服务器

Anthropic 提供了多个官方服务器:

1. GitHub Server

npx @modelcontextprotocol/server-github

功能:

  • 读取仓库、文件、Issues、PRs
  • 创建 Issues、PRs、Comments
  • 搜索代码和仓库

2. PostgreSQL Server

npx @modelcontextprotocol/server-postgres

功能:

  • 查询数据库
  • 执行 SQL
  • 获取表结构

3. Filesystem Server

npx @modelcontextprotocol/server-filesystem /allowed/path

功能:

  • 读取文件
  • 写入文件
  • 列出目录

4. Slack Server

npx @modelcontextprotocol/server-slack

功能:

  • 读取消息
  • 发送消息
  • 管理频道

实战案例

案例 1:自动化代码审查

// 使用 GitHub MCP 服务器
async function reviewPullRequest(prNumber: number) {
  // 1. 获取 PR 信息
  const pr = await mcp.readResource(`github://pr/${prNumber}`);

  // 2. 获取变更的文件
  const files = await mcp.readResource(`github://pr/${prNumber}/files`);

  // 3. 让 AI 审查代码
  const review = await claude.analyze(files);

  // 4. 创建审查评论
  await mcp.callTool('create_review', {
    prNumber,
    body: review,
    event: 'COMMENT',
  });
}

案例 2:数据库查询助手

// 使用 PostgreSQL MCP 服务器
async function queryDatabase(question: string) {
  // 1. 获取数据库结构
  const schema = await mcp.readResource('postgres://schema');

  // 2. 让 AI 生成 SQL
  const sql = await claude.generateSQL(question, schema);

  // 3. 执行查询
  const result = await mcp.callTool('execute_query', { sql });

  // 4. 格式化结果
  return formatResults(result);
}

案例 3:文档生成器

// 使用 Filesystem MCP 服务器
async function generateDocs(projectPath: string) {
  // 1. 读取所有源文件
  const files = await mcp.readResource(`file://${projectPath}/**/*.ts`);

  // 2. 让 AI 生成文档
  const docs = await claude.generateDocs(files);

  // 3. 写入文档文件
  await mcp.callTool('write_file', {
    path: `${projectPath}/docs/API.md`,
    content: docs,
  });
}

最佳实践

1. 安全性

// ✅ 好:验证输入
server.setRequestHandler('tools/call', async (request) => {
  const { name, arguments: args } = request.params;

  // 验证参数
  if (!isValidInput(args)) {
    throw new Error('Invalid input');
  }

  // 检查权限
  if (!hasPermission(request.context.user, name)) {
    throw new Error('Permission denied');
  }

  return await executeTool(name, args);
});

// ❌ 不好:直接执行
server.setRequestHandler('tools/call', async (request) => {
  return await executeTool(request.params.name, request.params.arguments);
});

2. 错误处理

// ✅ 好:详细的错误信息
try {
  const result = await performOperation();
  return { success: true, data: result };
} catch (error) {
  return {
    success: false,
    error: {
      code: 'OPERATION_FAILED',
      message: error.message,
      details: error.stack,
    },
  };
}

3. 性能优化

// ✅ 好:缓存和批处理
class OptimizedMCPServer {
  private cache = new Map();

  async readResource(uri: string) {
    // 检查缓存
    if (this.cache.has(uri)) {
      return this.cache.get(uri);
    }

    // 获取数据
    const data = await fetchData(uri);

    // 缓存结果
    this.cache.set(uri, data);

    return data;
  }

  async batchReadResources(uris: string[]) {
    // 批量获取,减少网络请求
    return await Promise.all(uris.map(uri => this.readResource(uri)));
  }
}

MCP 生态系统

社区服务器

  • Notion MCP Server:访问 Notion 数据库和页面
  • Google Drive MCP Server:读写 Google Drive 文件
  • Jira MCP Server:管理 Jira Issues 和项目
  • MongoDB MCP Server:查询 MongoDB 数据库

开发工具

  • MCP Inspector:调试 MCP 服务器
  • MCP Playground:测试 MCP 集成
  • MCP SDK:多语言 SDK(TypeScript、Python、Go)

未来展望

MCP 正在快速发展,未来将支持:

  • 流式传输:实时数据流
  • 双向通信:服务器主动推送
  • 多模态支持:图片、音频、视频
  • 联邦学习:分布式 AI 训练

总结

MCP 是 AI 应用集成的未来:

  • ✅ 统一的接口标准
  • ✅ 简化集成复杂度
  • ✅ 提高可维护性
  • ✅ 促进生态发展

如果你正在构建 AI 应用,MCP 是不可或缺的工具!

参考资源


开始使用 MCP,构建更强大的 AI 应用!