模型上下文协议(MCP):简化AI与外部工具的集成

Step1-什么是MCP?如何创建自定义的MCP

什么是MCP?

**模型上下文协议(MCP)**是由Anthropic开发的开源标准,旨在通过标准化接口连接AI模型与外部工具、数据库和API。它类似于HTTP协议,但专注于AI应用的集成,提供了一个类似USB-C接口的通用连接方式,实现不同AI模型与不同工具之间的无缝通信。

MCP的主要组件

  • Host(主机):管理LLM应用,负责初始化和管理客户端。
  • Client(客户端):与服务器建立一对一的连接,负责消息路由和功能管理。
  • Server(服务器):提供工具和资源,支持数据检索和操作。
  • Base Protocol(基础协议):定义客户端和服务器之间的通信方式,使用JSON-RPC 2.0。

为什么使用MCP?

  • 标准化集成:MCP提供了一种结构化的方式来连接AI模型与外部工具,减少了定制化集成的需求。
  • 灵活性:支持不同AI模型和供应商之间的切换。
  • 安全性:保持数据在本地基础设施内,同时与AI进行交互。
  • 可扩展性:支持多种传输方式,如stdio、WebSockets、HTTP SSE等。

MCP示例项目:GitHub PR审查服务器

项目概述

该项目使用MCP连接Claude Desktop与GitHub和Notion,实现自动化的代码审查和文档管理。

步骤概述

  1. 环境设置

    • 安装Python 3.10+。
    • 设置uv包管理器,创建虚拟环境。
  2. 安装依赖

    • 使用uvpip安装必要的Python包,如mcp[cli]requestsnotion-client
  3. 环境变量设置

    • 创建.env文件,存储GitHub和Notion的API密钥。
  4. GitHub集成

    • 编写github_integration.py文件,实现从GitHub获取PR变更的功能。
  5. MCP服务器实现

    • 创建pr_analyzer.py文件,定义MCP工具,实现PR分析和Notion文档创建。
  6. 运行MCP服务器

    • 使用python pr_analyzer.py命令启动服务器。

示例代码

GitHub集成代码
python 复制代码
import os
import requests
from dotenv import load_dotenv

load_dotenv()
GITHUB_TOKEN = os.getenv('GITHUB_TOKEN')

def fetch_pr_changes(repo_owner: str, repo_name: str, pr_number: int) -> dict:
    # Fetch PR metadata and file changes
    pr_url = f"https://api.github.com/repos/{repo_owner}/{repo_name}/pulls/{pr_number}"
    files_url = f"{pr_url}/files"
    headers = {'Authorization': f'token {GITHUB_TOKEN}'}
    
    try:
        pr_response = requests.get(pr_url, headers=headers)
        pr_response.raise_for_status()
        pr_data = pr_response.json()
        
        files_response = requests.get(files_url, headers=headers)
        files_response.raise_for_status()
        files_data = files_response.json()
        
        # Combine PR metadata with file changes
        changes = []
        for file in files_data:
            change = {
                'filename': file['filename'],
                'status': file['status'],
                'additions': file['additions'],
                'deletions': file['deletions'],
                'changes': file['changes'],
                'patch': file.get('patch', ''),
                'raw_url': file.get('raw_url', ''),
                'contents_url': file.get('contents_url', '')
            }
            changes.append(change)
        
        pr_info = {
            'title': pr_data['title'],
            'description': pr_data['body'],
            'author': pr_data['user']['login'],
            'created_at': pr_data['created_at'],
            'updated_at': pr_data['updated_at'],
            'state': pr_data['state'],
            'total_changes': len(changes),
            'changes': changes
        }
        
        return pr_info
        
    except Exception as e:
        print(f"Error fetching PR changes: {str(e)}")
        return None
MCP服务器代码
python 复制代码
import sys
from mcp.server.fastmcp import FastMCP
from github_integration import fetch_pr_changes
from notion_client import Client
from dotenv import load_dotenv

class PRAnalyzer:
    def __init__(self):
        load_dotenv()
        
        self.mcp = FastMCP("github_pr_analysis")
        print("MCP Server initialized", file=sys.stderr)
        
        self._init_notion()
        self._register_tools()
    
    def _init_notion(self):
        self.notion_api_key = os.getenv("NOTION_API_KEY")
        self.notion_page_id = os.getenv("NOTION_PAGE_ID")
        
        if not self.notion_api_key or not self.notion_page_id:
            raise ValueError("Missing Notion API key or page ID")
        
        self.notion = Client(auth=self.notion_api_key)
        print(f"Notion client initialized successfully", file=sys.stderr)
    
    def _register_tools(self):
        @self.mcp.tool()
        async def fetch_pr(repo_owner: str, repo_name: str, pr_number: int) -> dict:
            pr_info = fetch_pr_changes(repo_owner, repo_name, pr_number)
            return pr_info
        
        @self.mcp.tool()
        async def create_notion_page(title: str, content: str) -> str:
            self.notion.pages.create(
                parent={"type": "page_id", "page_id": self.notion_page_id},
                properties={"title": {"title": [{"text": {"content": title}}]}},
                children=[{
                    "object": "block",
                    "type": "paragraph",
                    "paragraph": {
                        "rich_text": [{
                            "type": "text",
                            "text": {"content": content}
                        }]
                    }
                }]
            )
            return f"Notion page '{title}' created successfully!"
    
    def run(self):
        try:
            print("Running MCP Server for GitHub PR Analysis...", file=sys.stderr)
            self.mcp.run(transport="stdio")
        except Exception as e:
            print(f"Fatal Error in MCP Server: {str(e)}", file=sys.stderr)
            sys.exit(1)

if __name__ == "__main__":
    analyzer = PRAnalyzer()
    analyzer.run()

运行MCP服务器

使用以下命令启动服务器:

bash 复制代码
python pr_analyzer.py

启动后,打开Claude Desktop应用,通过MCP与GitHub和Notion进行交互,实现自动化的PR审查和文档管理。


Step2-配置支持MCP的Agent

Agent概述

Agent是指能够与MCP服务器交互的智能实体,通常由大型语言模型(LLM)驱动。通过MCP,Agent可以访问外部工具和数据源,执行复杂任务。

配置Agent

要配置支持MCP的Agent,需要完成以下步骤:

  1. 设置开发环境

    • 确保Python 3.8或更高版本已安装。
    • 安装必要的依赖,如openai-agentsmcp[cli]
  2. 定义MCP服务器配置

    • 创建一个配置文件(例如mcp_agent.config.yaml),定义MCP服务器的设置,包括服务器类型(stdio或SSE)和工具列表。
  3. 初始化Agent

    • 使用Agent框架(如OpenAI Agents SDK)创建一个Agent实例。
    • 将MCP服务器配置传递给Agent,以便其可以访问和使用MCP工具。
  4. 集成MCP工具

    • 在Agent中注册MCP工具,确保Agent可以调用这些工具执行任务。
  5. 运行Agent

    • 启动Agent,并通过MCP服务器与外部工具进行交互。

示例代码

以下是使用OpenAI Agents SDK配置支持MCP的Agent的示例代码:

python 复制代码
import asyncio
from openai_agents import Agent, MCPServerStdio

# 初始化MCP服务器
local_server = MCPServerStdio(
    params={
        "command": "npx",
        "args": ["-y", "@modelcontextprotocol/server-filesystem", "./local_files"],
    },
    cache_tools_list=True
)

# 创建Agent实例
async def run_agent_with_mcp_servers():
    async with local_server:
        agent = Agent(
            name="MultiToolAgent",
            instructions="Use available tools to accomplish tasks.",
            mcp_servers=[local_server]
        )
        
        # 运行Agent
        result = await agent.run("Complete the requested task using appropriate tools.")
        return result

# 执行Agent
asyncio.run(run_agent_with_mcp_servers())

调试和监控

  • 日志检查:监视MCP服务器日志以捕获工具执行过程中的错误。
  • 追踪功能:使用SDK的内置追踪功能监控工具调用,并优化性能。

扩展和优化

  • 多Agent架构:考虑使用多个Agent来分担工具调用负担,提高系统的可扩展性。
  • 缓存机制:在远程SSE服务器中使用缓存来减少延迟,提高响应速度。

通过这些步骤和示例,你可以成功配置支持MCP的Agent,并将其与外部工具和数据源进行集成。

相关推荐
西电研梦7 分钟前
难度偏低,25西电人工智能学院821、833、834考研录取情况
人工智能·考研·面试·西安电子科技大学·考研录取
uhakadotcom11 分钟前
CVE-2025-30208:Vite 开发服务器安全漏洞解析
后端·面试·github
FirstMrRight40 分钟前
策略模式随笔~
后端·设计模式
Asthenia041244 分钟前
面试官试图狠狠从三大垃圾回收算法拷打到七大GC器
后端
佟格湾1 小时前
聊透多线程编程-线程池-7.C# 三个Timer类
开发语言·后端·c#·多线程编程·多线程
海风极客1 小时前
为什么列式存储更适合OLAP?
后端·面试
顾云澜1 小时前
Apache Superset本地部署结合内网穿透实现无公网IP远程查看数据
开发语言·后端·golang
小陈同学呦1 小时前
聊聊CSS选择器
前端·css·面试
写bug写bug1 小时前
Java并发编程:本质上只有一种创建线程的方法
java·后端
Asthenia04121 小时前
数据通信技术复习笔记:频带传输与数字调制详解
后端