| name | mcp-builder |
| description | Use this skill when creating Model Context Protocol (MCP) servers, adding tools to extend Claude's capabilities, or integrating external APIs as MCP tools. |
MCP Builder Skill
You have expertise in building Model Context Protocol servers to extend Claude's capabilities.
When to Use
This skill activates for:
- Creating new MCP servers
- Adding tools to existing servers
- Integrating external APIs as MCP tools
- Configuring MCP servers in Claude Desktop/Code
- Debugging MCP server issues
MCP Server Quickstart
Project Setup
mkdir my-mcp-server && cd my-mcp-server
npm init -y
npm install @modelcontextprotocol/sdk zod
npm install -D typescript @types/node
Minimal Server Template
import { Server } from '@modelcontextprotocol/sdk/server/index.js';
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
import { CallToolRequestSchema, ListToolsRequestSchema } from '@modelcontextprotocol/sdk/types.js';
const server = new Server({ name: 'my-server', version: '1.0.0' }, { capabilities: { tools: {} } });
server.setRequestHandler(ListToolsRequestSchema, async () => ({
tools: [
{
name: 'my_tool',
description: 'What this tool does and when Claude should use it',
inputSchema: {
type: 'object',
properties: {
param: { type: 'string', description: 'Parameter description' },
},
required: ['param'],
},
},
],
}));
server.setRequestHandler(CallToolRequestSchema, async request => {
if (request.params.name === 'my_tool') {
const { param } = request.params.arguments as { param: string };
return {
content: [{ type: 'text', text: `Result for: ${param}` }],
};
}
throw new Error(`Unknown tool: ${request.params.name}`);
});
const transport = new StdioServerTransport();
await server.connect(transport);
package.json
{
"name": "my-mcp-server",
"version": "1.0.0",
"type": "module",
"bin": { "my-mcp-server": "./dist/index.js" },
"scripts": {
"build": "tsc",
"start": "node dist/index.js"
}
}
tsconfig.json
{
"compilerOptions": {
"target": "ES2022",
"module": "NodeNext",
"moduleResolution": "NodeNext",
"outDir": "./dist",
"strict": true,
"esModuleInterop": true
},
"include": ["src/**/*"]
}
Tool Design Patterns
API Wrapper Tool
{
name: "api_search",
description: "Search the [Service] API. Use when user asks to find [things].",
inputSchema: {
type: "object",
properties: {
query: { type: "string", description: "Search query" },
limit: { type: "number", description: "Max results (1-100)", default: 10 }
},
required: ["query"]
}
}
Database Query Tool
{
name: "db_query",
description: "Execute a read-only SQL query against the database.",
inputSchema: {
type: "object",
properties: {
query: { type: "string", description: "SELECT query (read-only)" },
params: { type: "array", items: { type: "string" }, description: "Query parameters" }
},
required: ["query"]
}
}
File Operation Tool
{
name: "file_read",
description: "Read contents of a file within the allowed directory.",
inputSchema: {
type: "object",
properties: {
path: { type: "string", description: "Relative file path" }
},
required: ["path"]
}
}
Input Validation
import { z } from 'zod';
const SearchSchema = z.object({
query: z.string().min(1).max(500),
limit: z.number().min(1).max(100).default(10),
filters: z
.object({
type: z.enum(['all', 'recent', 'popular']).optional(),
})
.optional(),
});
const validated = SearchSchema.parse(request.params.arguments);
Error Handling
import { McpError, ErrorCode } from '@modelcontextprotocol/sdk/types.js';
throw new McpError(ErrorCode.InvalidParams, 'Query cannot be empty');
throw new McpError(ErrorCode.InvalidRequest, 'Resource not found');
throw new McpError(ErrorCode.InternalError, 'API request failed');
Configuration
Claude Desktop (~/.claude/claude_desktop_config.json)
{
"mcpServers": {
"my-server": {
"command": "node",
"args": ["/path/to/dist/index.js"],
"env": {
"API_KEY": "your-key"
}
}
}
}
Published Package
{
"mcpServers": {
"my-server": {
"command": "npx",
"args": ["-y", "@yourorg/my-mcp-server"],
"env": { "API_KEY": "your-key" }
}
}
}
Best Practices
- Clear Descriptions - Help Claude understand when to use each tool
- Validate Everything - Use Zod for input validation
- Handle Errors Gracefully - Return meaningful error messages
- Environment Variables - Never hardcode secrets
- Rate Limiting - Protect against excessive API calls
- Logging - Log to stderr for debugging (stdout is for MCP protocol)
Common Integrations
| Service | Package | Use Case |
|---|
| GitHub | @octokit/rest | Repository operations |
| Slack | @slack/web-api | Team communication |
| Notion | @notionhq/client | Workspace management |
| Stripe | stripe | Payment operations |
| Supabase | @supabase/supabase-js | Database & auth |
| OpenAI | openai | AI operations |