MCP实战:从零搭建笔记搜索Server,接入Claude Code与Cursor
最近“MCP”基本是 AI 开发圈子里出现频率最高的三个字母。你在用 Claude Code、Cursor或者任何号称“能自己干活”的智能体客户端时大概率都见过配置文件里有个叫mcpServers的字段。这个 MCPModel Context Protocol模型上下文协议说白了就是给大模型接外部工具和数据的开放标准。我习惯把它理解成“USB 接口”——大模型是一台只有键盘和屏幕的电脑MCP 是那个接口而搭建 MCP就是做一件插在这个接口上的外设。这篇文章不打算停留在概念层面。我会先讲清楚 MCP 到底在解决什么问题、它的核心架构长什么样然后从零开始手把手搭一个真正能用的笔记搜索 MCP Server再把它接进 Claude Code 和 Cursor 里跑通。后半部分我还整理了连不上、超时、工具不生效这些高频故障的排查思路以及蓝湖、Figma、Chrome DevTools、Playwright 等热门现成方案怎么选怎么用。适合人群会写一点 TypeScript 或者 JavaScript对 MCP 还停留在“似乎很火但不知道从哪下手”的开发者。1. MCP 到底解决了什么问题先别急着写代码1.1 一个真实场景让 AI 自己去翻你的一千个笔记文件假设你是一个知识管理重度用户本地存了一千多个 Markdown 笔记有博客草稿、会议记录、读书摘录。你想让一个 AI 助手帮你“找出来上个月聊过某某方案的所有笔记”并且基于这些笔记做个总结。没有 MCP 的时候这事非常别扭。你大概只有两条路第一条把所有笔记全文塞进上下文里让模型自己翻一千个文件加起来几百万 token既不现实也贵得离谱第二条给模型写一个专用 API 接口做一套搜索服务再单独写一套“如何调用这个服务”的提示词塞给模型。第二条路看起来很合理但问题在于只要有十个工具你就得维护十套接口格式和十份使用说明。更麻烦的是每次新增工具都要改客户端的集成代码。这种“点对点连接”的方式在工具少的时候没问题一旦系统多起来就是一张越来越乱的蜘蛛网。MCP 要解决的正是这种“每个 AI 都要和每个工具单独适配”的杂乱状态。1.2 MCP 和“直接调一个 API”有什么区别很多人第一次接触 MCP 会问我写个 HTTP 接口给 AI 调用不也一样吗效果上有点像但本质有区别。直接调 API是“你告诉 AI 有个接口长什么样、怎么调”用 MCP是“AI 通过协议自动发现你的工具自己决定什么时候调用”。MCP 的连接过程大体是客户端启动后去连 MCP ServerServer 把自己暴露的 Tools、Resources、Prompts 清单告诉客户端客户端再把清单交给大模型。模型在推理过程中发现“我需要搜笔记”于是主动发起一次工具调用Server 执行完毕后把结果返回给模型。这意味着你不需要在每次交互前把工具的使用手册写进提示词里。工具的“说明书”是协议的一部分由 Server 动态提供。工具越多这个优势越明显。而且 MCP 是开放标准不是某一家公司的私有协议Claude、Cursor、以及越来越多的 IDE 和 Agent 框架都原生支持。1.3 为什么建议亲手搭一个 Server而不是只跑现成的现在网上的 MCP Server 一大堆官方也好、社区也好几乎什么都有文件系统、数据库、浏览器控制、设计稿读取。那为什么还要自己动手搭我的体会是搭建一个 Server 是理解这套协议最快的方式。协议规范文档写得再清楚也不如亲手注册一个工具、看着它在客户端里被调用一次来得深刻。而且实际业务里总有现成方案覆盖不到的需求你公司的内部系统、你自己的笔记、某个特殊格式的数据文件这些通常都需要定制一个轻量 Server。另外自己搭一遍之后再去看蓝湖 MCP、Chrome DevTools MCP 的源码和配置会轻松很多。因为不管哪个现成方案核心骨架都一样建立连接、注册工具、处理请求。后面你会看到整个 Server 的核心代码其实很短。2. 动手前必须对齐的协议骨架Client、Server、Transport 和三种原语2.1 角色划分谁主动谁被动MCP 的架构很清晰就两个角色加一个连接层。客户端Client是主动发起连接的一方负责跟大模型交互也负责把模型的意图转成对工具的具体调用。常见的客户端包括 Claude Desktop、Claude Code、Cursor、各种支持 MCP 的 IDE 插件。Server 是被动等待请求的一方负责具体干活读文件、查数据库、操作浏览器、调外部 API 都行。一个 Client 可以同时连接多个 Server这也是“USB 接口”类比里最贴切的一点——你可以在同一台电脑上插很多外设。连接层Transport是双方通信的方式。MCP 规范里传输层是可替换的目前最常用的是两种Stdio 和 Streamable HTTP。下面细说。2.2 Stdio 和 Streamable HTTP本地与远程怎么选Stdio 传输是最简单也最常见的模式。客户端直接在本地启动一个子进程把 MCP Server 作为子进程跑起来双方通过标准输入stdin和标准输出stdout传递 JSON-RPC 消息。Stdio 的好处是零网络开销、启动快、不需要管端口和鉴权非常适合“只在这台机器上用”的场景。我在第 3 节要搭的笔记搜索服务就是这种模式。要注意的是Stdio 模式下 Server 进程的生命周期跟客户端绑定客户端退出Server 进程也会被收掉所以它不适合做常驻后台服务。Streamable HTTP 是另一类模式。Server 作为一个 HTTP 服务常驻客户端通过 HTTP 请求连接支持远程访问。适合把 Server 部署在一台服务器上让多个客户端共享一套工具。以前还有个 SSE 模式现在 SDK 基本都往 Streamable HTTP 收敛了。如果你看到老教程里写sse注意区分版本别照抄。简单给个选择建议场景推荐传输方式原因本机个人工具比如访问笔记、本地文件Stdio配置简单无网络开销团队共享工具比如统一查询内部文档Streamable HTTP部署在一处处处可用需要常驻后台、定时任务的工具Streamable HTTP进程不被客户端生命周期影响2.3 Tools、Resources、Prompts 三种原语分别是什么MCP 规范定义了三种核心原语新手很容易混淆。Tools 是“让模型执行动作”的能力读写文件、发消息、执行命令都属于这一类。它们通常有输入参数执行后返回结构化结果。模型是否调用某个 Tool是由模型根据描述自主决定的。这是最重要的原语80% 的 MCP Server 都只实现了 Tools。Resources 是“只读数据”的暴露方式。比如你想让 AI 能读取一份固定文档、查一个配置项可以把它们声明成 Resource。客户端会把 Resource 的 URI 和描述呈现给模型模型决定要不要读取对应内容。简单理解Tools 是动词Resources 是名词。Prompts 是一段可复用的提示词模板。Server 可以提供一些提示词模板用户选一个模板里的变量会被填充最后变成对话上下文。它不像 Tools 那样由模型自动触发更多是用户主动使用。这三者不是必选项。搭一个工具型 Server通常只需要实现 Tools。如果你的 Server 只是想把一批静态数据暴露给 AI那用 Resources 更合适。理解这些之后就可以上手写代码了。3. 从零搭一个笔记搜索 MCP Server完整工程示例3.1 环境准备与项目初始化我先交代一下环境Node.js 版本至少 18 以上。我用的是 JavaScript 而不是 TypeScript目的是让示例代码最小化、能直接跑不引入编译步骤。如果你想用 TypeScript原理完全一致加一层构建配置就行。项目初始化很简单一条命令搭起来mkdir notes-mcp cd notes-mcp npm init -y npm install modelcontextprotocol/sdk zod然后修改package.json加上type: module。这会让 Node 把.js文件按 ESM 模块处理代码里可以直接用import语法。这个 Server 要解决什么需求我的笔记目录里全是 Markdown 文件我希望 AI 能帮我回答“我笔记里提到过的某个话题有哪些相关内容”。所以我需要三个能力列出笔记目录里所有文件、读取某篇笔记全文、按关键字搜索笔记内容。对应的我会注册三个 Tools。需要解释一下为什么用zod。MCP 的 Tool 输入格式本质是 JSON Schema但手写 JSON Schema 很啰嗦而且校验逻辑要自己写。官方 SDK 支持用zod定义参数SDK 会自动把 zod 描述转成 JSON Schema并在调用前完成参数校验。这对保证工具安全性很有价值后面我会专门说。3.2 写核心逻辑Server 代码完整版在项目目录里创建一个server.js完整代码如下import { McpServer } from modelcontextprotocol/sdk/server/mcp.js; import { StdioServerTransport } from modelcontextprotocol/sdk/server/stdio.js; import { z } from zod; import { readdir, readFile } from node:fs/promises; import path from node:path; // 笔记目录通过环境变量传入避免把路径写死 const NOTES_DIR process.env.NOTES_DIR || path.join(process.cwd(), notes); const server new McpServer({ name: notes-server, version: 1.0.0 }); // 工具 1列出所有笔记文件 server.registerTool( list_notes, { description: 列出笔记目录中的所有 Markdown 文件名不返回内容, inputSchema: { type: object, properties: {} } }, async () { const files await readdir(NOTES_DIR); const markdownFiles files.filter((f) f.endsWith(.md)); const text markdownFiles.length ? markdownFiles.join(\n) : 笔记目录为空; return { content: [{ type: text, text }] }; } ); // 工具 2读取指定笔记的全文 server.registerTool( read_note, { description: 读取一篇笔记的完整内容文件名必须是 .md 文件, inputSchema: { type: object, properties: { filename: { type: string, description: 笔记文件名例如 daily.md } }, required: [filename] } }, async ({ filename }) { // 关键安全点防止路径穿越只允许访问 NOTES_DIR 内的文件 const filePath path.resolve(NOTES_DIR, filename); if (!filePath.startsWith(path.resolve(NOTES_DIR))) { return { content: [{ type: text, text: 拒绝访问文件名非法 }] }; } const content await readFile(filePath, utf-8); return { content: [{ type: text, text: content }] }; } ); // 工具 3按关键字搜索笔记内容 server.registerTool( search_notes, { description: 在所有笔记中搜索指定关键字返回命中的文件名、行号和匹配片段, inputSchema: { type: object, properties: { keyword: { type: string, description: 要搜索的关键字 } }, required: [keyword] } }, async ({ keyword }) { const files await readdir(NOTES_DIR); const hits []; for (const file of files) { if (!file.endsWith(.md)) continue; const content await readFile(path.join(NOTES_DIR, file), utf-8); const lines content.split(\n); lines.forEach((line, idx) { if (line.includes(keyword)) { hits.push(${file}:${idx 1}: ${line.trim()}); } }); } const text hits.length ? hits.join(\n) : 没有命中; return { content: [{ type: text, text }] }; } ); // 使用 Stdio 传输启动服务 const transport new StdioServerTransport(); await server.connect(transport);这段代码核心就三个动作创建McpServer实例、用registerTool注册工具、通过StdioServerTransport启动连接。有几个细节值得留意。content数组是 MCP 统一的结果包装格式AI 拿到的就是这个content所以你返回的文本要尽量结构化、易读。比如搜索结果是文件名:行号:内容片段本身就是在帮模型降低解析成本。另外read_note里做了路径穿越防护path.resolve先算出绝对路径再用startsWith校验它必须以NOTES_DIR为前缀。这种安全问题在本地工具里经常被忽略但一旦你把配置文件指到别的目录或者未来这个 Server 被暴露成远程服务这就是大漏洞。3.3 准备测试目录和笔记文件光有代码还不行得造点测试数据。在项目目录下建一个notes文件夹放几个 Markdown 文件。比如notes/ ├── daily.md ├── project-alpha.md └── reading.md随便写点内容注意让“关键字”出现在多个文件里方便测试搜索工具时观察多文件命中效果。例如在daily.md里写“今天讨论了 MCP 的传输层方案”在project-alpha.md里写“计划用 MCP 连接内部知识库”这样后面搜索“MCP”时就有两条命中结果。3.4 手动验证 Server 能不能跑在接到客户端之前可以先手动验证 Server 进程能正常启动、能响应消息。最简单的办法是直接运行 NodeNOTES_DIR/path/to/notes node server.js如果代码没问题进程不会输出任何东西也不会退出。注意这个“安静”是正常的。因为 stdout 被协议占用了任何多余打印都会破坏协议这也是新手最容易踩的坑我在第 5 节详细说。想要更直观地调试官方提供了一个可视化工具 MCP Inspector一条命令就能启动npx modelcontextprotocol/inspector node server.js它会起一个本地调试面板让你手动连接 Server、查看工具列表、逐条调用工具并看到返回结果。强烈建议第一次写 MCP Server 时用这个工具过一遍确认三个工具都注册成功并且返回正常再往客户端里接。4. 接入 Claude Code 和 Cursor配置与首次调通的全过程4.1 Claude Code 的两种配置方式Claude Code 是 Anthropic 官方出品的终端 AI 编程助手也是目前对 MCP 支持最成熟的客户端之一。配置方式有两种二选一即可。第一种是用命令行添加对新手最友好claude mcp add notes-server -- node /绝对路径/server.js执行后 Claude Code 会把notes-server这个 MCP Server 记录到配置里。注意--后面的内容会被当作启动命令所以路径必须是绝对路径不能写相对路径否则客户端在另一个工作目录启动时会找不到文件。如果你希望每个项目的配置不一样可以创建项目级配置文件.mcp.json放在项目根目录。Claude Code 启动时会自动读取{ mcpServers: { notes-server: { command: node, args: [/绝对路径/server.js], env: { NOTES_DIR: /绝对路径/notes } } } }我推荐用配置文件方式因为它把env也一并管理了比如NOTES_DIR这种运行时参数可以直接写进去。要注意的是JSON 里不能用注释也不能有多余逗号很多配置死活加载不上就卡在这。4.2 Cursor 的 MCP 入口和配置文件位置Cursor 对 MCP 的支持也很完整但入口藏得稍微深一点。新版里你可以在设置Settings里搜 MCP会有一个 MCP 管理面板可以在里面手动添加服务器。也可以用命令面板CtrlShiftP输入 “MCP: Open Configuration File” 直接打开配置文件。Cursor 的项目级配置文件路径是.cursor/mcp.json内容和上面.mcp.json完全一致。我个人的经验是项目级配置好过全局配置因为不同项目要挂的 Server 不一样全局配置会把无关工具暴露给所有项目既增加模型误调用概率也拖慢启动速度。配置完之后回到对话界面正常情况下 MCP 状态面板里会显示notes-server已经连接。如果显示失败或者超时不要急着反复重连先去看第 5 节的排查思路。4.3 第一次真正调用让 AI 用工具而不是“自己猜”配置通了之后验证效果的最好方式就是直接问一个需要工具才能回答的问题。比如对 Claude Code 说“搜索一下笔记里关于 MCP 传输层的内容并总结我最近写了什么。”模型内部会先发起search_notes工具调用拿到命中结果后再可能调用read_note读取某篇笔记全文最后做总结。整个流程里模型是自主决策的你不需要告诉它“你的笔记在哪个目录、文件叫什么名字”。这正是 MCP 的核心价值能力发现是协议自动完成的。如果你第一次尝试时发现模型只是凭印象回答没有触发任何工具先确认两件事第一MCP 面板里 Server 状态是不是正常第二工具描述是否足够清晰。时刻记住模型选择调用哪个工具主要依据就是你写的description字段。比如我的search_notes描述里明确写了“返回命中的文件名、行号和匹配片段”模型就知道这个工具适合做关键字检索而不是全文读取。5. 碰上“连不上”“超时”先别慌一套可复用的排查流程5.1 症状与根因对照表MCP 的问题看起来千奇百怪但根因其实高度集中。我整理了一份对照表基本覆盖了 90% 的情况。症状最常见根因解决动作启动即失败客户端提示找不到命令启动命令路径写错或环境变量没有继承用绝对路径确认 node 在 PATH 里客户端一直转圈然后报超时Server 启动慢或启动过程卡住去掉启动期间的阻塞逻辑再三确认没有多余输出连接成功但工具列表是空的注册代码没执行到或注册抛异常看 Server 日志确认 registerTool 执行完工具调用后客户端说格式错误返回结构不符合 MCP 规范检查 content 包装是否正确所有工具都能用但模型总是不调描述不清或工具太泛把 description 写具体参数约束收紧5.2 超时问题timed out after 30 seconds是怎么来的很多人会遇到这样的报错客户端提示 MCP Server 连接超时甚至是 JSON-RPC 超时。这类问题在 Codex、Claude Code 等客户端里都出现过关键词通常是timed out after 30 seconds或者类似表述。根因往往是Server 进程本身启动太慢或者 Client 发起的首次请求没有得到及时响应。比如代码里在创建 Server 之前做了一个耗时的数据加载像连接数据库、缓存预热、读取一个大文件那客户端等不到响应自然就超时了。另一个常见原因是 Server 刚启动时需要在 Stdio 模式下完成一次“握手”过程如果启动代码里不小心在前几行就打印了日志协议握手会被这段杂音打乱。解决办法有两条线。短期来说把启动时的大数据加载改成懒加载也就是真正收到工具调用请求时才去初始化数据或者干脆把这些耗时任务丢到后台异步执行。长期来说给 Server 加启动日志放到 stderr 或者文件里方便定位到底卡在哪一步。5.3 日志乱入Stdio 传输模式下的头号大坑我要单独强调一个非常隐蔽、几乎每个新手都会踩的坑在 Stdio 模式下千万别往 stdout 打印任何东西。MCP 客户端和 Server 之间通过 stdin 和 stdout 传 JSON-RPC 消息。如果你在代码里写了console.log(server started)这段文本会直接混进协议通道客户端的解析器拿到一句不是合法 JSON 的文本轻则丢掉这条消息重则整个连接直接断掉。很多“连接成功但工具列表为空”的诡异问题源头就是这么一行日志。正确做法是把日志写到 stderr或者写到一个独立的日志文件里。stderr 在 Stdio 传输下通常被客户端转发到自己的日志面板不影响协议通道写到文件则更可控适合做长期的日志审计。如果你需要自定义日志管理可以引入debug这类库或者干脆自己封装一个writeLog函数把时间戳、工具名、入参、出参都记到文件里。我自己习惯在 Server 里加一个环境变量LOG_FILE指向日志文件的绝对路径import { appendFile } from node:fs/promises; async function writeLog(message) { if (!process.env.LOG_FILE) return; await appendFile(process.env.LOG_FILE, [${new Date().toISOString()}] ${message}\n); }之后在每个工具调用的开头和结尾都调一次writeLog排查问题时直接看日志文件比在客户端里瞎猜高效得多。5.4 环境变量和配置文件的“看不见的差别”还有一类问题特别迷惑人同一个 Server在自己终端手动跑没问题接到客户端里就报错。这时要优先怀疑环境变量。客户端启动 MCP Server 的方式和你在终端里手动跑是不一样的它可能不会加载你的.bashrc或.zshrc所以PATH可能不是你熟悉的那一份。如果是用npx启动的 Server客户端很可能找不到 npx 的路径。稳妥做法是直接用绝对路径唤醒启动命令比如{ command: /usr/local/bin/node, args: [/绝对路径/server.js] }可以用which node查 node 的可执行文件路径。Windows 环境下路径写法还有各种盘符和反斜杠的坑建议全部用正斜杠并且尽量用配置文件里env字段传路径参数因为很多问题本质上就是“当前工作目录不对”。6. 现成的高口碑 MCP 方案怎么选蓝湖、Figma、浏览器自动化6.1 设计稿类蓝湖 MCP 和 Figma MCP 的正确用法设计稿场景是 MCP 最火的应用之一因为设计稿转代码一直是前端团队的痛点。蓝湖 MCP 是国内团队接入比较多的方案搭建方向大致是在蓝湖上获取一个服务链接或者令牌然后配置到 Client 端。接入后AI 可以在对话里读取设计稿的图层结构、标注信息、元素尺寸相当于把设计数据变成了模型可以直接查询的资源。想切图时模型可以按图层 ID 取出对应的切图资源省去你手动打开设计工具一个个拖的时间。Figma MCP 同理通过官方 MCP Server 接入后AI 能读取 Figma 文件的节点结构、样式属性、文本内容。但关于“Figma MCP 能不能直接切图”这个问题我实际用下来是这样的能不能导出切片资源取决于你的 Figma 账号类型和 Access Token 权限。免费版账号的 token 通常只能读取文件结构想要完整的切图导出能力一般需要付费工作区账号才能开通对应的 API 权限。换句话说不是 MCP 插件不支持而是上游图档权限卡住了。我的建议很直接如果你只是用免费版 Figma 做个人项目不要指望 AI 直接给你导出全套切图但让它给你分析图层结构、提取设计规范、把标注说明整理成开发文档是完全够用的。如果团队已经在用付费版那就放开手脚把导出切片也交给 MCP。6.2 浏览器自动化类Chrome DevTools MCP 与 Playwright MCP浏览器自动化是另一大热点。Chrome DevTools MCP 的思路是通过 Chrome DevTools Protocol 连接本地 Chrome 实例让 AI 能读取当前页面的 DOM、网络请求、控制台日志做一些页面调试。接入它需要在配置里指定一个调试端口并且提前用命令行启动 Chrome 时带上--remote-debugging-port参数。Playwright MCP 则更“全能”一点。它是微软官方出的浏览器自动化库的 MCP 封装支持启动浏览器、跳转页面、点击元素、输入文本、截图、抓取网络请求等。如果说 Chrome DevTools MCP 更像“诊断工具”Playwright MCP 更像是“能替你做事的助理”。这里必须提醒一句浏览器自动化工具的权限极强它可以让 AI 读取你正在浏览的网页内容更可以替你在打开的页面上做操作。如果你在本地用问题不大如果配置到团队共享 Server务必给 Server 设访问控制别让你自己的浏览器被别人远程操纵。我习惯的做法是只在特定的浏览器 profile 上用而且连接完成就立即关闭调试端口。6.3 垂直行业的 MCP从安全测试到设计工具链除了上面两个大众方向很多垂直领域也有现成 MCP。安全测试方向有 Yakit MCP、BurpSuite MCP能把流量分析、漏洞扫描能力暴露给 Agent逆向分析有 IDA Pro MCP可以在反汇编窗口里通过自然语言下指令设计工具链还有只读类的 MCP用于读设计稿数据。还有像查票类的 12306 MCP、API 调试类的 Apipost MCP 等等。这些垂直方案的搭建思路都是同一套拿到 Server 的启动方式或 HTTP endpoint按第 3 节那种配置格式填进去。我的判断标准有三个官方出品或社区活跃度高不高、是否支持鉴权至少不能让任何人都能调、文档里是否给了明确的权限边界说明。满足这三条的基本可以放心用。7. 把 MCP 做得更好用命名、权限、架构上的实用建议7.1 工具命名和描述是模型决策的“说明书”模型选择哪个工具靠的是工具名和描述。我在第 3 节写工具时名称都用了明确的动词list_notes、read_note、search_notes。模型看到一个工具叫search_notes、描述是“按关键字搜索笔记内容”马上就知道它该在这个场景被调用。反过来如果你的工具叫process_data、描述写“处理数据”模型根本不知道它处理什么数据、输入输出是什么、适合什么场景几乎不会被正确调用。所以工具描述要写清楚三件事这个工具做什么、输入参数代表什么、返回结果是什么格式。参数也尽量收紧能用枚举就用枚举能限定类型就限定类型模型不太擅长猜参数。7.2 最小权限原则Server 不需要的能力就别开MCP Server 的能力边界一定要控制。一个只读笔记的 Server不需要写入权限一个查数据库的 Server用只读账号就够了一个需要访问本机 Chrome 的 Server不应该拿到整个操作系统的文件访问权。权限问题的底线在于MCP 工具的调用者是大模型是概率系统这意味着你写的任何工具都可能被以你预期之外的方式调用。我见过有人把本机文件删除能力暴露给 AI理由是“AI 不会乱删”。这种想法非常危险。正确姿势是Server 只注册完成任务所需的最少工具集路径只限定在指定目录文件操作尽量用只读模式远程 Server 必须加 API Key 或 OAuth。7.3 MCP 和 RAG 怎么分工别再混为一谈最后说一个高频概念混淆MCP 和 RAG 的区别。RAG检索增强生成解决的是“模型不知道”的问题核心是内容召回。你把文档切块、向量化、检索然后把命中片段拼进上下文里让模型基于这些内容作答。MCP 解决的是“模型做不了”的问题核心是能力接入。模型本来不能读写文件、不能查数据库、不能操作浏览器通过 MCP它获得了这些能力。两者不是替代关系更多是互补。一个典型的结合场景把向量检索做成 MCP 的一个 Tool模型先调用这个 Tool 从知识库里召回候选文档再结合全局上下文做回答。这样既让模型获得了“搜索”能力又保证了回答内容来自真实的知识库。所以别再问“该用 RAG 还是 MCP 了”你要先想清楚“我是缺知识还是缺能力”搭建 MCP 这件事门槛其实比我一开始想象的低得多。一个能用的 Server核心代码不过几十行。真正难的部分在工程化怎么命名工具、怎么控制权限、怎么管理日志、怎么选传输方式。这些没有标准答案但只要你亲手搭过一遍再回头看那些现成 MCP 的源码心里就门儿清了。我强烈建议你今晚就用第 3 节的代码跑一个本地笔记 Server拿自己的文件当测试数据然后跟 Claude Code 或者 Cursor 连上试试让 AI 帮你搜索和总结。跑通的那一刻你对 MCP 的理解会上一个台阶。
上一篇/下一篇内容由系统自动关联
返回资讯列表 →