Skills: 自定义工具开发

最后更新:2026-08-31

内置工具不够用?自己造——MCP 协议让 Skill 的能力没有边界。


1. MCP 协议基础

(1) 什么是 MCP

Model Context Protocol 是 AI 工具的标准协议:

TEXT 📖 仅展示
MCP 架构
┌──────────┐    MCP 协议    ┌──────────────┐
│ AI 客户端 │ ←──────────→ │ MCP 服务器    │
│ (Claude)  │               │ (自定义工具)  │
└──────────┘               └──────────────┘
                                  ↕
                            ┌──────────────┐
                            │ 外部服务      │
                            │ (DB/API/文件) │
                            └──────────────┘

(2) 工具类型

类型 说明 示例
资源工具 提供数据读取 数据库查询、文件系统
动作工具 执行操作 发送邮件、创建工单
提示工具 提供模板 报告模板、审查清单

2. 开发自定义工具

(1) 需求分析

TEXT 📖 仅展示
自定义工具开发流程
1. 识别内置工具无法满足的需求
2. 确定工具的输入/输出
3. 选择实现方式(Node.js / Python)
4. 实现工具逻辑
5. 配置 MCP 服务器
6. 在 Skill 中绑定使用

(2) 最小实现

TYPESCRIPT
// mcp-server-example/index.ts
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";

const server = new McpServer({ name: "db-query", version: "1.0.0" });

server.tool("query_database", { sql: { type: "string" } }, async ({ sql }) => {
  const result = await executeQuery(sql);
  return { content: [{ type: "text", text: JSON.stringify(result) }] };
});

const transport = new StdioServerTransport();
await server.connect(transport);

(3) 配置接入

JSON
{
  "mcpServers": {
    "db-query": {
      "command": "node",
      "args": ["./mcp-servers/db-query/index.js"],
      "env": {
        "DATABASE_URL": "postgresql://localhost/mydb"
      }
    }
  }
}

3. 工具设计原则

(1) 单一职责

每个工具只做一件事:

✅ 好设计 ❌ 坏设计
query_database do_database_stuff
send_email communicate
search_logs find_stuff

(2) 输入验证

TYPESCRIPT
server.tool("query_database", {
  sql: {
    type: "string",
    description: "SQL 查询语句(仅允许 SELECT)",
    validate: (sql: string) => {
      if (/^\s*(DROP|DELETE|UPDATE|INSERT|ALTER)/i.test(sql)) {
        throw new Error("Only SELECT queries are allowed");
      }
    }
  }
}, handler);

(3) 错误处理

TYPESCRIPT
async ({ sql }) => {
  try {
    const result = await executeQuery(sql);
    return { content: [{ type: "text", text: JSON.stringify(result) }] };
  } catch (error) {
    return {
      content: [{ type: "text", text: `Query failed: ${error.message}` }],
      isError: true
    };
  }
};

4. 工具调试与发布

(1) 本地调试

BASH
# 直接运行 MCP 服务器测试
node ./mcp-servers/db-query/index.js

# 发送测试请求
echo '{"method":"tools/list"}' | node ./mcp-servers/db-query/index.js

(2) 日志记录

TYPESCRIPT
// 添加日志中间件
server.tool("query_database", { sql: { type: "string" } }, async ({ sql }) => {
  console.error(`[DB-QUERY] SQL: ${sql}`);
  const start = Date.now();
  const result = await executeQuery(sql);
  console.error(`[DB-QUERY] Duration: ${Date.now() - start}ms`);
  return { content: [{ type: "text", text: JSON.stringify(result) }] };
});

(3) 发布与分发

TEXT 📖 仅展示
发布方式
├── npm 包:npm publish @your-org/mcp-server-xxx
├── Docker:docker build + docker push
├── Git 仓库:直接 clone 使用
└── 配置模板:提供 JSON 配置模板

5. 自定义工具实战

▶ 示例:日志搜索工具

Alice 开发了一个日志搜索 MCP 工具:

YAML
---
name: log-analyzer
description: "日志分析:搜索、过滤、统计"
tools:
  - Read
  - search_logs  # 自定义 MCP 工具
---

Bob 说:"自定义工具的价值在于连接 AI 和你的专属系统——通用工具够不到的地方,定制工具来补。"


❓ 常见问题

Q 必须用 TypeScript 开发 MCP 工具吗?
A 不是。MCP 协议是 JSON-RPC,任何语言都能实现。官方 SDK 提供 TypeScript 和 Python 版本。
Q 自定义工具有安全风险吗?
A 有。务必在工具内部做输入验证和权限控制,不要把安全责任完全交给 Skill 提示词。
Q 一个 MCP 服务器可以提供多个工具吗?
A 可以。但建议每个服务器不超过 5 个工具,保持职责聚焦。

📖 小节


📝 作业

  1. 基础题(难度⭐):使用 MCP SDK 创建一个最简单的 Hello World 工具并接入 Skill。
  2. 进阶题(难度⭐⭐):开发一个数据库查询 MCP 工具,包含输入验证和错误处理。
  3. 挑战题(难度⭐⭐⭐):开发一个完整的日志分析 MCP 工具,支持搜索、过滤和统计,并编写调试和发布文档。
Web-Tutorial.com

Web-Tutorial 技术团队

由多位开发者共同维护的编程教程平台。每篇教程由对应领域的开发者编写和审核,确保内容准确可靠。如发现任何问题,欢迎向我们反馈。

100%

🙏 帮我们做得更好

我们是刚上线的编程教程站,几个人的小团队,精力有限。页面虽经检查,难免还有疏漏——链接失效、排版错乱、内容有误、语言生硬……

如果您发现了,麻烦告诉我们,我们会在收到反馈后第一时间进行修复,再次感谢您的光临 🙏