当前位置:首页 >> 主机教程

常见SEO服务器虚拟化与云从零开始的MCP开发

发布时间:2025-12-15 16:39:24 作者:熊猫主机教程网
简介 租云计算服务器 前言:我们迎来万能插头? 在 AI 提效上,我们小组的每个人都有自己的独特方式,作为一个沉醉在业务开发+业务样式改版的终端开发,再加上我的 CSS 功底基本上样式就是靠试,每次在 UI 还原部分都是很是痛苦。这样,在团队内部同学完成了 Done 插件转React 代码并完成 OneDay Web 端落地后,我就

租云计算服务器

前言:我们迎来万能插头?

在 AI 提效上,我们小组的每个人都有自己的独特方式,作为一个沉醉在业务开发+业务样式改版的终端开发,再加上我的 CSS 功底基本上样式就是靠试,每次在 UI 还原部分都是很是痛苦。这样,在团队内部同学完成了 Done 插件转React 代码并完成 OneDay Web 端落地后,我就在想,是否可以在插件端实现一样的能力,就这样 MCP 的能力自然就进入我的视野了。

先看一下效果:

「链接」

这个小玩具是通过 MCP 协议进行开发的,并且集成在了 OneDay插件中。这篇文章,主要记录了自己在开发 MCP 插件的过程中的学习路径,以及是如何从零用 AI 开发一个小插件的。最后,也是趁着业务大改版的机会,将这个插件结合在我的开发流程中。

MCP 协议简介:AI 的"万能插头"

2024 年 11 月,Anthropic 推出了 Model Context Protocol (MCP),这一开放协议旨在解决 LLM 与外部工具集成的标准化问题。MCP 提供了一种统一的方式,使 AI 模型能够与各种数据源和工具进行交互,被官方形象地称为 AI 应用的"USB-C 端口"。

MCP 的本质与价值

MCP的核心价值在于提供一种标准化的方式,让 AI 模型与外部世界进行交互。在 MCP 出现之前,开发者需要为每个 AI 集成创建定制化的解决方案,这导致了严重的碎片化问题。

MCP 解决了这些问题,它提供了以下关键价值:

统一集成标准:一个协议对接所有集成,降低开发难度实时数据更新:支持动态数据交互而非静态连接自动工具发现:支持动态工具发现和上下文处理隐私保护:数据和工具不需上传远端,保护数据隐私开发效率:显著减少开发时间,提高系统可靠性

核心能力

根据 MCP 协议规范,服务器可以提供三种核心对象:

支持程度

目前 MCP 这一概念的火热也让众多 IDE 和框架积极投身在这一领域,其中Claude桌面应用和Continue提供了最全面的MCP支持,包括资源、提示模板和工具集成,使其能够深度整合本地工具和数据源。众多代码编辑器和IDE(如Cursor、Zed、Windsurf Editor和Theia IDE)通过MCP增强了开发工作流程,提供如智能代码生成、AI辅助编码等功能。

在官网的示例中(https://modelcontextprotocol.io/examples),可以发现,越来越多的公司、组织开始积极拥抱 MCP,目前通过 MCP 可以进行本地文件、云端文件的修改,Git 相关仓库的阅读与更改,基于Puppeteer 进行浏览器自动化和网页抓取,甚至通过EverArt的相关服务可以进行图像生成。

一些更抽象的 MCP 服务可以在这里看一看(https://github.com/punkpeye/awesome-mcp-servers)

真的是大一统么?

文档上说的很好,MCP 是AI 届的USB-C,使用了 MCP 就意味着你的协议可以在所有的 AI 应用上使用了。

但是,强如 USB-C 现在也没有办法做到真正的大一统,不同厂商之间还是存在着不同。

所以,MCP 可能统一,但是 MCP统一不太可能。

现在针对不同的 AI 终端每个 MCP 支持的能力也是不尽相同的,本文说的只是在 OneDay VSC 插件上的开发体验;

前置学习一下

看完前面的 MCP 具体协议相关的文档之后,理解能力比较强的老师可能已经知道 MCP 是在干啥了,像我这种 AI 知识早就还给 CV、ML 老师了的同学来说,还是不是很清楚 MCP 具体是咋被调用的。

为了搞清楚MCP 的运作方式,我准备学习一下开源的工具以及 SDK 是如何运作的,作为一个练习时长2 坤年的终端开发,我选择的开源仓库是 Roo 和 MCP Typescript 的 SDK。

如何使用MCP TS进行开发

在 MCP 官网上,赫然写着Building MCP with LLMs(https://modelcontextprotocol.io/tutorials/building-mcp-with-llms),但是本着尊重 AI 的劳动成果的原则还是要学习一下里面具体的内容的。

这部分不太详细展开,具体的 MCP 开发还是参考官网的文档好了。

Client

负责与 MCP 服务器建立连接并发送请求,主要的方法有:

connect(transport):连接到服务器request(request, schema, options):发送请求并等待响应close():关闭连接import{Client} from"@modelcontextprotocol/sdk/client/index.js";

McpServer

提供一个高级 API 来创建 MCP 服务器,主要的方法有:

tool(name, schema, handler):注册一个工具resource(name, template, handler):注册一个资源connect(transport):连接到传输层import{ McpServer }from"@modelcontextprotocol/sdk/server/mcp.js";constserver =newMcpServer({name:"我的MCP服务",version:"1.0.0"});

Server

一个低级类,也是本文采用的一个类,低级开发用低级类(bushi

setRequestHandler(schema, handler):为特定请求类型设置处理程序connect(transport):连接到传输层import{Server} from"@modelcontextprotocol/sdk/server/index.js";

传输接口(Transport)

MCP 支持多种传输方式,用于与客户端通信,主要是通过:stdio 传输(命令行应用)和SSE 传输(Web服务器)。

import{ StdioServerTransport }from"@modelcontextprotocol/sdk/server/stdio.js";consttransport =newStdioServerTransport();awaitserver.connect(transport);import{ SSEServerTransport }from"@modelcontextprotocol/sdk/server/sse.js";importexpressfrom"express";constapp = express(); app.get("/sse",async(req, res) => {consttransport =newSSEServerTransport("/messages", res);awaitserver.connect(transport); }); app.post("/messages",async(req, res) => {awaittransport.handlePostMessage(req, res); }); app.listen(3000);

具体的开发流程如下

Roo 如何调用MCP

Roo 是谁,Cline 优化版罢了

大体上了解了 MCP SDK中的使用方式,那么问题又来了: MCP 集成在客户端上,客户端是如何判断是否需要调用 MCP 以及使用哪个 MCP 的?

打开 Roo 的源码,AI 总结启动...

可以看出来主要流程有意图识别、工具识别、工具调用这三个主要的步骤。

意图识别

Roo Code使用大型语言模型(LLM)来理解用户的自然语言输入并识别用户的意图。当用户提出一个请求时,LLM会分析请求并决定使用哪些工具来完成任务。

系统提示构建:通过 generatePrompt 函数构建完整的系统提示,包括 MCP 服务器和工具信息。

这使 LLM 能够了解可用的 MCP 服务器及其功能。

这使 LLM 能够了解可用的 MCP 服务器及其功能// src/core/prompts/system.ts// 通过 generatePrompt 函数构建完整的系统提示,包括 MCP 服务器和工具信息。// 这使 LLM 能够了解可用的 MCP 服务器及其功能asyncfunctiongeneratePrompt(context: vscode.ExtensionContext, cwd:string, supportsComputerUse:boolean, mode: Mode, mcpHub?: McpHub,// MCP 集线器实例,负责管理所有 MCP 服务器连接diffStrategy?: DiffStrategy, browserViewportSize?:string,// ... 其他参数):Promise<string>{// ... 前面的代码// 异步获取两个部分:模式部分和 MCP 服务器部分const[modesSection, mcpServersSection] =awaitPromise.all([ getModesSection(context),// 仅当当前模式包含 mcp 组时才加载 MCP 服务器部分modeConfig.groups.some((groupEntry) =>getGroupName(groupEntry) ==="mcp") ? getMcpServersSection(mcpHub, effectiveDiffStrategy, enableMcpServerCreation) :Promise.resolve(""), ])// 构建完整的系统提示,包括多个部分constbasePrompt =`${roleDefinition}${getSharedToolUseSection()}${getToolDescriptionsForMode(//这里会包含 MCP 相关工具的描述 mode, cwd, supportsComputerUse, effectiveDiffStrategy, browserViewportSize, mcpHub, customModeConfigs, experiments, )}${getToolUseGuidelinesSection()}${mcpServersSection}// 这部分包含所有可用的 MCP 服务器及其工具信息 // ... 其他部分 `returnbasePrompt }

MCP 服务器信息生成:getMcpServersSection 方法收集并格式化已连接的 MCP 服务器信息:提供服务器名称、可用工具及其参数架构,让 LLM 知道如何使用它们。

// src/core/prompts/sections/mcp-servers.tsexportasyncfunctiongetMcpServersSection(mcpHub?: McpHub, diffStrategy?: DiffStrategy, enableMcpServerCreation?:boolean,):Promise<string>{if(!mcpHub) {return""}// 构建已连接服务器的信息字符串constconnectedServers = mcpHub.getServers().length >0?`${mcpHub .getServers() .filter((server) => server.status ==="connected")//只显示已连接的服务器 .map((server) => {//为每个服务器生成其工具列表信息consttools = server.tools ?.map((tool) => {//为每个工具包含输入模式(如果有)constschemaStr = tool.inputSchema ?` Input Schema:${JSON.stringify(tool.inputSchema,null,2).split("\n").join("\n ")}`:""return`-${tool.name}:${tool.description}\n${schemaStr}`}) .join("\n\n") // ... 生成资源模板和直接资源信息 ... // 解析服务器配置以显示命令信息 const config = JSON.parse(server.config) // 返回完整的服务器描述,包括工具、资源模板和直接资源 return ( `${server.name} (\`${config.command}${config.args ?`${config.args.join(" ")}`:""}\`)`+ (tools ?`\n\n Available Tools\n${tools}`:"") + (templates ?`\n\n Resource Templates\n${templates}`:"") + (resources ?`\n\n Direct Resources\n${resources}`:"") ) }) .join("\n\n")}` : "(No MCP servers currently connected)" // 如果没有连接服务器,显示此消息 // ... 返回完整部分,包括 MCP 服务器介绍和创建指南 ... }

工具描述提供:getUseMcpToolDescription 函数定义了 MCP 工具的使用方法和参数格式。包含使用示例,帮助 LLM 生成正确格式的工具调用。

//src/core/prompts/tools/use-mcp-tool.tsexportfunction getUseMcpToolDescription(args: ToolArgs): string |undefined{//如果没有 MCP 集线器,不需要此工具描述if(!args.mcpHub) {returnundefined}//返回标准化的工具描述,包括参数说明和使用示例return`use_mcp_toolDescription: Request to use a tool provided by a connected MCP server. Each MCP server can provide multiple toolswithdifferent capabilities. Tools have defined input schemas that specify required and optional parameters. Parameters: - server_name: (required) The nameofthe MCP server providing the tool - tool_name: (required) The nameofthe tool to execute -arguments: (required) AJSONobject containing the tools input parameters, following the tools input schemaUsage:<use_mcp_tool><server_name>server name here