logo

从零实现MCP服务:基于Node.js的文件统计工具开发全流程

作者:蛮不讲李2026.07.20 18:29浏览量:0

简介:本文将手把手教你实现一个基于Model Context Protocol(MCP)的标准化服务,通过开发文件统计工具掌握协议交互机制。适合Node.js开发者、AI工具链开发者及需要扩展模型能力的技术团队,完整实现包含工具开发、服务部署、可视化调试全流程。

一、协议解析与开发目标

MCP(Model Context Protocol)是用于构建模型与外部工具安全交互的标准化协议,通过结构化接口实现代码执行、数据库查询、API调用等能力接入。本文将实现一个文件统计服务mcp-file-counter,具备以下核心功能:

  • 递归统计指定目录下的文件总数
  • 支持通过忽略列表排除特定子目录
  • 通过Inspector工具实现可视化调试
  • 符合MCP协议的标准化交互接口

该服务可作为模型工具链的基础组件,例如在文档分析场景中统计文件数量,或在数据处理流程中作为前置校验步骤。

二、开发环境准备

2.1 基础环境要求

  • Node.js 18+(推荐LTS版本)
  • 包管理工具:pnpm(推荐)或npm
  • 代码编辑器:VS Code(推荐安装TypeScript插件)

2.2 快速初始化

  1. # 创建项目目录
  2. mkdir mcp-file-counter && cd mcp-file-counter
  3. # 初始化项目(使用pnpm)
  4. pnpm init -y
  5. # 安装核心依赖
  6. pnpm add @modelcontextprotocol/sdk
  7. pnpm add -D typescript tsx @types/node @modelcontextprotocol/inspector

2.3 项目结构规范

  1. ├── src/ # 源代码目录
  2. ├── server.ts # 服务入口
  3. └── tools/ # 工具实现
  4. └── fileCount.ts # 文件统计逻辑
  5. ├── tsconfig.json # TypeScript配置
  6. └── package.json # 项目依赖

三、TypeScript配置详解

在项目根目录创建tsconfig.json,关键配置说明:

  1. {
  2. "compilerOptions": {
  3. "target": "ES2022", // 使用最新ECMAScript特性
  4. "module": "NodeNext", // 支持ES模块导入
  5. "moduleResolution": "NodeNext",
  6. "outDir": "dist", // 编译输出目录
  7. "rootDir": "src", // 源代码根目录
  8. "strict": true, // 启用严格类型检查
  9. "esModuleInterop": true, // 支持CommonJS/ES模块混用
  10. "skipLibCheck": true // 跳过声明文件检查
  11. }
  12. }

四、核心工具实现

4.1 文件统计逻辑

src/tools/fileCount.ts中实现递归遍历算法:

  1. import fs from 'node:fs/promises';
  2. import path from 'node:path';
  3. export async function countFiles(
  4. root: string,
  5. ignore: string[] = []
  6. ): Promise<number> {
  7. const visited = new Set<string>();
  8. const ignoreSet = new Set(ignore.map(s => s.trim()).filter(Boolean));
  9. async function walk(dir: string): Promise<number> {
  10. const dirents = await fs.readdir(dir, { withFileTypes: true });
  11. let count = 0;
  12. for (const dirent of dirents) {
  13. const fullPath = path.join(dir, dirent.name);
  14. const relativePath = path.relative(root, fullPath);
  15. // 跳过符号链接和已访问路径
  16. if (dirent.isSymbolicLink() || visited.has(fullPath)) {
  17. continue;
  18. }
  19. visited.add(fullPath);
  20. // 处理忽略规则
  21. if (ignoreSet.has(relativePath) ||
  22. ignoreSet.has(dirent.name)) {
  23. continue;
  24. }
  25. if (dirent.isDirectory()) {
  26. count += await walk(fullPath);
  27. } else if (dirent.isFile()) {
  28. count++;
  29. }
  30. }
  31. return count;
  32. }
  33. return walk(path.resolve(root));
  34. }

关键实现细节

  1. 使用Set数据结构实现路径去重
  2. 通过path.relative()获取相对路径进行忽略匹配
  3. 递归处理子目录时传递完整路径
  4. 符号链接自动跳过防止循环引用

4.2 工具测试用例

  1. // 测试代码示例
  2. (async () => {
  3. const count = await countFiles('./src', ['node_modules', 'dist']);
  4. console.log(`Total files: ${count}`);
  5. })();

五、MCP服务开发

5.1 服务入口实现

src/server.ts中创建标准MCP服务:

  1. import { createServer } from '@modelcontextprotocol/sdk';
  2. import { countFiles } from './tools/fileCount';
  3. const server = createServer({
  4. tools: {
  5. count_files: {
  6. description: 'Count files in directory with ignore patterns',
  7. params: {
  8. type: 'object',
  9. properties: {
  10. path: { type: 'string' },
  11. ignore: { type: 'array', items: { type: 'string' } }
  12. },
  13. required: ['path']
  14. },
  15. async execute(params) {
  16. return {
  17. count: await countFiles(params.path, params.ignore)
  18. };
  19. }
  20. }
  21. }
  22. });
  23. server.listen(3000, () => {
  24. console.log('MCP Server running on port 3000');
  25. });

5.2 协议交互流程

  1. 客户端发送标准化请求:

    1. {
    2. "tool": "count_files",
    3. "params": {
    4. "path": "/var/log",
    5. "ignore": ["archives", "temp"]
    6. }
    7. }
  2. 服务端返回结构化响应:

    1. {
    2. "result": {
    3. "count": 142
    4. }
    5. }

六、可视化调试

6.1 启动Inspector

  1. npx @modelcontextprotocol/inspector --port 3000

6.2 调试界面操作

  1. 在工具列表中选择count_files
  2. 填写测试参数:
    • path: ./src
    • ignore: ['node_modules']
  3. 点击执行按钮查看实时结果
  4. 使用”History”功能复用历史请求

七、部署优化建议

7.1 性能优化

  • 添加文件缓存机制(如LRU缓存)
  • 实现并发请求控制
  • 对大目录采用流式处理

7.2 安全增强

  • 添加路径遍历防护
  • 实现请求速率限制
  • 添加JWT认证中间件

7.3 监控方案

  1. // 扩展Server实现
  2. import { createPrometheusExporter } from '@modelcontextprotocol/monitoring';
  3. const exporter = createPrometheusExporter({ port: 9090 });
  4. server.use(exporter.middleware());

八、常见问题排查

8.1 服务启动失败

  • 检查端口冲突:lsof -i :3000
  • 验证Node版本:node -v
  • 查看详细日志:添加DEBUG=mcp*环境变量

8.2 文件统计不准确

  • 检查忽略路径格式(相对路径 vs 绝对路径)
  • 验证目录读写权限
  • 使用fs.stat()验证文件类型

8.3 协议交互异常

  • 验证请求体结构是否符合JSON Schema
  • 检查工具名称是否匹配
  • 使用Postman等工具直接测试API

九、扩展开发方向

  1. 多文件系统支持:扩展实现S3/HDFS等存储系统的统计
  2. 高级过滤功能:添加文件扩展名过滤、大小范围过滤
  3. 批量处理接口:设计目录列表批量统计接口
  4. 元数据收集:返回文件修改时间等附加信息

总结

本文完整实现了从协议理解到服务开发的全流程,通过文件统计工具的实践掌握了MCP的核心开发模式。开发者可以基于此架构快速扩展其他工具服务,如数据库查询、API调用等。建议后续研究协议的流式响应机制和批量处理优化,进一步提升服务能力。完整代码已上传至某代码托管平台(示例表述),可搜索”mcp-file-counter”获取参考实现。

发表评论

活动