通俗版 Claude Code 文档

结构照原 docs,内容改成真能照着做的人话版。

查看原始文档 目录顺序与官方保持一致

Extend with tools

Connect to external tools with MCP

Connect to external tools with MCP 这一页讲的,就是 Connect to external tools with MCP 这件事在 Claude Code 里到底怎么用。

页面信息

对应原页

Connect to external tools with MCP

页面性质

第三方中文解释页

使用建议

先看人话解释,再对照原页命令和代码

这页不是官方原文,而是顺着官方文档结构做的中文解释版。命令、参数、配置名这些硬东西尽量保留,解释部分则尽量讲成人能照着做的话。

如果你碰到特别敏感的配置、权限或企业环境差异,最好顺手点上面的“查看原始文档”再核一遍。

这一页先讲明白

这页主要讲 Connect to external tools with MCP:Configure MCP servers to extend your agent with external tools. Covers transport types, tool search for large tool sets, authentication, and error handling.

你可以把它当成"Extend with tools"这块里专门管这一摊事的说明书。

你可以把"Connect to external tools with MCP"理解成 Extend with tools 这一栏里的一把专门工具。这页不是让你背书,而是教你什么时候该把这把工具拿出来。

原文这页大多会按 Quickstart、Add an MCP server、In code、From a config file 这些环节往下讲。

翻成人话,大概就是:From a config file

第一,先别一上来全开全配。先按最小一步试通,确认没跑偏,再继续往下加。

第二,命令、配置名、参数名这些硬东西尽量保留原样。人话解释是帮你听懂,不是帮你改关键字。

第三,照着原文这几个环节挨个过:Quickstart -> Add an MCP server -> In code -> From a config file。像下地先看水路、再试机器、再正式开干,一步一步最稳。

终端里敲

原页关键片段:Quickstart

这一段不是只让你理解意思,下面这条命令就是现在要跑的。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "Use the docs MCP server to explain what hooks are in Claude Code",
  options: {
    mcpServers: {
      "claude-code-docs": {
        type: "http",
        url: "https://code.claude.com/docs/mcp"
      }
    },
    allowedTools: ["mcp__claude-code-docs__*"]
  }
})) {
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}
终端里敲

原页关键片段:In code

真到动手的时候了,下面这条直接敲一遍,看它回什么。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "List files in my project",
  options: {
    mcpServers: {
      filesystem: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-filesystem", "/Users/me/projects"]
      }
    },
    allowedTools: ["mcp__filesystem__*"]
  }
})) {
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}
改配置

原页关键片段:From a config file

这一段说完,最后还得写到配置里才算真的生效。

{
  "mcpServers": {
    "filesystem": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-filesystem", "/Users/me/projects"]
    }
  }
}
关键片段

原页关键片段:Grant access with allowedTools

先看下面这块原始片段,等会儿再回头看解释会顺得多。

const _ = {
  options: {
    mcpServers: {
      // your servers
    },
    allowedTools: [
      "mcp__github__*", // All tools from the github server
      "mcp__db__query", // Only the query tool from db server
      "mcp__slack__send_message" // Only send_message from slack server
    ]
  }
};
关键片段

原页关键片段:Discover available tools

"Discover available tools"这一段里最要紧的原始写法在下面,先看它怎么落地。

for await (const message of query({ prompt: "...", options })) {
  if (message.type === "system" && message.subtype === "init") {
    console.log("Available MCP tools:", message.mcp_servers);
  }
}
终端里敲

原页关键片段:stdio servers 1

看到这里,别光点头,下面这条命令先跑起来再说。

const _ = {
  options: {
    mcpServers: {
      github: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-github"],
        env: {
          GITHUB_TOKEN: process.env.GITHUB_TOKEN
        }
      }
    },
    allowedTools: ["mcp__github__list_issues", "mcp__github__search_issues"]
  }
};
改配置

原页关键片段:stdio servers 2

想把这条规矩固定住,就把下面这块老老实实写进去。

{
  "mcpServers": {
    "github": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-github"],
      "env": {
        "GITHUB_TOKEN": "${GITHUB_TOKEN}"
      }
    }
  }
}
终端里敲

原页关键片段:HTTP/SSE servers 1

先别急着往下翻,下面这条命令跑完,心里才有底。

const _ = {
  options: {
    mcpServers: {
      "remote-api": {
        type: "sse",
        url: "https://api.example.com/mcp/sse",
        headers: {
          Authorization: `Bearer ${process.env.API_TOKEN}`
        }
      }
    },
    allowedTools: ["mcp__remote-api__*"]
  }
};
改配置

原页关键片段:HTTP/SSE servers 2

这会儿轮到改配置了,字段名和关键字别自己乱换。

{
  "mcpServers": {
    "remote-api": {
      "type": "sse",
      "url": "https://api.example.com/mcp/sse",
      "headers": {
        "Authorization": "Bearer ${API_TOKEN}"
      }
    }
  }
}
终端里敲

原页关键片段:Pass credentials via environment variables 1

这一段不是只让你理解意思,下面这条命令就是现在要跑的。

const _ = {
  options: {
    mcpServers: {
      github: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-github"],
        env: {
          GITHUB_TOKEN: process.env.GITHUB_TOKEN
        }
      }
    },
    allowedTools: ["mcp__github__list_issues"]
  }
};
改配置

原页关键片段:Pass credentials via environment variables 2

这一段说完,最后还得写到配置里才算真的生效。

{
  "mcpServers": {
    "github": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-github"],
      "env": {
        "GITHUB_TOKEN": "${GITHUB_TOKEN}"
      }
    }
  }
}
终端里敲

原页关键片段:HTTP headers for remote servers 1

看到这里,别光点头,下面这条命令先跑起来再说。

const _ = {
  options: {
    mcpServers: {
      "secure-api": {
        type: "http",
        url: "https://api.example.com/mcp",
        headers: {
          Authorization: `Bearer ${process.env.API_TOKEN}`
        }
      }
    },
    allowedTools: ["mcp__secure-api__*"]
  }
};

预留广告位

正文中段响应式广告 等你后面真接 AdSense,这里再放正式广告。

Documentation Index

这里不是让你背"Documentation Index"这个词,而是让你看它真干活时怎么使。

这里还牵扯作用域,意思就是这条规则到底管当前项目、你个人,还是只管这一趟会话。

Quickstart

别把这段只当成标题看,它其实是在给"Quickstart"划边界。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

终端里敲

Quickstart

这一段不是只让你理解意思,下面这条命令就是现在要跑的。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "Use the docs MCP server to explain what hooks are in Claude Code",
  options: {
    mcpServers: {
      "claude-code-docs": {
        type: "http",
        url: "https://code.claude.com/docs/mcp"
      }
    },
    allowedTools: ["mcp__claude-code-docs__*"]
  }
})) {
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}

Add an MCP server

看到这里,就把"Add an MCP server"当成一件真要上手的活来看。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

In code

这里不是让你背"In code"这个词,而是让你看它真干活时怎么使。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

终端里敲

In code

真到动手的时候了,下面这条直接敲一遍,看它回什么。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "List files in my project",
  options: {
    mcpServers: {
      filesystem: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-filesystem", "/Users/me/projects"]
      }
    },
    allowedTools: ["mcp__filesystem__*"]
  }
})) {
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}

From a config file

这一段是在教你把 a .mcp.json file at your project root. The file is picked up when the project setting source is enabled, which it is for default query() options. If you set settingSources explicitly, include "project" for this file to load: 真正建出来。文件放哪儿、字段怎么写、建完怎么验,都得跟着看。

这里还牵扯作用域,意思就是这条规则到底管当前项目、你个人,还是只管这一趟会话。

改配置

From a config file

这一段说完,最后还得写到配置里才算真的生效。

{
  "mcpServers": {
    "filesystem": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-filesystem", "/Users/me/projects"]
    }
  }
}

Allow MCP tools

这一段主要是在把"Allow MCP tools"讲实,不是只摆个标题给你看。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

Tool naming convention

看到这里,就把"Tool naming convention"当成一件真要上手的活来看。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

Grant access with allowedTools

这一段是在说怎么用 allowedTools 去做 specify which MCP tools Claude can use:。看这种内容,光知道名字没用,还是得落到手上。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

关键片段

Grant access with allowedTools

先看下面这块原始片段,等会儿再回头看解释会顺得多。

const _ = {
  options: {
    mcpServers: {
      // your servers
    },
    allowedTools: [
      "mcp__github__*", // All tools from the github server
      "mcp__db__query", // Only the query tool from db server
      "mcp__slack__send_message" // Only send_message from slack server
    ]
  }
};

Discover available tools

这一块主要是在说"Discover available tools"真到手上该怎么用,哪里最容易踩坑。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

关键片段

Discover available tools

"Discover available tools"这一段里最要紧的原始写法在下面,先看它怎么落地。

for await (const message of query({ prompt: "...", options })) {
  if (message.type === "system" && message.subtype === "init") {
    console.log("Available MCP tools:", message.mcp_servers);
  }
}

Transport types

这里不是让你背"Transport types"这个词,而是让你看它真干活时怎么使。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

stdio servers

这一块主要是在说"stdio servers"真到手上该怎么用,哪里最容易踩坑。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

终端里敲

stdio servers 1

看到这里,别光点头,下面这条命令先跑起来再说。

const _ = {
  options: {
    mcpServers: {
      github: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-github"],
        env: {
          GITHUB_TOKEN: process.env.GITHUB_TOKEN
        }
      }
    },
    allowedTools: ["mcp__github__list_issues", "mcp__github__search_issues"]
  }
};
改配置

stdio servers 2

想把这条规矩固定住,就把下面这块老老实实写进去。

{
  "mcpServers": {
    "github": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-github"],
      "env": {
        "GITHUB_TOKEN": "${GITHUB_TOKEN}"
      }
    }
  }
}

HTTP/SSE servers

这一段主要是在把"HTTP/SSE servers"讲实,不是只摆个标题给你看。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

终端里敲

HTTP/SSE servers 1

先别急着往下翻,下面这条命令跑完,心里才有底。

const _ = {
  options: {
    mcpServers: {
      "remote-api": {
        type: "sse",
        url: "https://api.example.com/mcp/sse",
        headers: {
          Authorization: `Bearer ${process.env.API_TOKEN}`
        }
      }
    },
    allowedTools: ["mcp__remote-api__*"]
  }
};
改配置

HTTP/SSE servers 2

这会儿轮到改配置了,字段名和关键字别自己乱换。

{
  "mcpServers": {
    "remote-api": {
      "type": "sse",
      "url": "https://api.example.com/mcp/sse",
      "headers": {
        "Authorization": "Bearer ${API_TOKEN}"
      }
    }
  }
}

SDK MCP servers

这一段主要是在把"SDK MCP servers"讲实,不是只摆个标题给你看。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

MCP tool search

这一段更像在讲判断条件,什么时候该上,什么时候先别急。把触发条件看清,比背标题更重要。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

Authentication

这一段主要是在把"Authentication"讲实,不是只摆个标题给你看。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

Pass credentials via environment variables

这一段是在说怎么用 the env field to pass API keys, tokens, and other credentials 去做 the MCP server:。看这种内容,光知道名字没用,还是得落到手上。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

终端里敲

Pass credentials via environment variables 1

这一段不是只让你理解意思,下面这条命令就是现在要跑的。

const _ = {
  options: {
    mcpServers: {
      github: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-github"],
        env: {
          GITHUB_TOKEN: process.env.GITHUB_TOKEN
        }
      }
    },
    allowedTools: ["mcp__github__list_issues"]
  }
};
改配置

Pass credentials via environment variables 2

这一段说完,最后还得写到配置里才算真的生效。

{
  "mcpServers": {
    "github": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-github"],
      "env": {
        "GITHUB_TOKEN": "${GITHUB_TOKEN}"
      }
    }
  }
}

HTTP headers for remote servers

这一块主要是在说"HTTP headers for remote servers"真到手上该怎么用,哪里最容易踩坑。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

终端里敲

HTTP headers for remote servers 1

看到这里,别光点头,下面这条命令先跑起来再说。

const _ = {
  options: {
    mcpServers: {
      "secure-api": {
        type: "http",
        url: "https://api.example.com/mcp",
        headers: {
          Authorization: `Bearer ${process.env.API_TOKEN}`
        }
      }
    },
    allowedTools: ["mcp__secure-api__*"]
  }
};
改配置

HTTP headers for remote servers 2

想把这条规矩固定住,就把下面这块老老实实写进去。

{
  "mcpServers": {
    "secure-api": {
      "type": "http",
      "url": "https://api.example.com/mcp",
      "headers": {
        "Authorization": "Bearer ${API_TOKEN}"
      }
    }
  }
}

OAuth2 authentication

别把这段只当成标题看,它其实是在给"OAuth2 authentication"划边界。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

终端里敲

OAuth2 authentication

这一段不是只让你理解意思,下面这条命令就是现在要跑的。

// After completing OAuth flow in your app
const accessToken = await getAccessTokenFromOAuthFlow();

const options = {
  mcpServers: {
    "oauth-api": {
      type: "http",
      url: "https://api.example.com/mcp",
      headers: {
        Authorization: `Bearer ${accessToken}`
      }
    }
  },
  allowedTools: ["mcp__oauth-api__*"]
};

Examples

看到这里,就把"Examples"当成一件真要上手的活来看。

List issues from a repository

遇到这种内容,别急着大拆大改,先按它给的路子把问题缩小。

这里还牵扯作用域,意思就是这条规则到底管当前项目、你个人,还是只管这一趟会话。

关键片段

List issues from a repository 1

"List issues from a repository"这一段里最要紧的原始写法在下面,先看它怎么落地。

export GITHUB_TOKEN=ghp_xxxxxxxxxxxxxxxxxxxx
终端里敲

List issues from a repository 2

看到这里,别光点头,下面这条命令先跑起来再说。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "List the 3 most recent issues in anthropics/claude-code",
  options: {
    mcpServers: {
      github: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-github"],
        env: {
          GITHUB_TOKEN: process.env.GITHUB_TOKEN
        }
      }
    },
    allowedTools: ["mcp__github__list_issues"]
  }
})) {
  // Verify MCP server connected successfully
  if (message.type === "system" && message.subtype === "init") {
    console.log("MCP servers:", message.mcp_servers);
  }

  // Log when Claude calls an MCP tool
  if (message.type === "assistant") {
    for (const block of message.message.content) {
      if (block.type === "tool_use" && block.name.startsWith("mcp__")) {
        console.log("MCP tool called:", block.name);
      }
    }
  }

  // Print the final result
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}

Query a database

这段看着像个标题,其实是在说"Query a database"管到哪儿。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

终端里敲

Query a database

先别急着往下翻,下面这条命令跑完,心里才有底。

import { query } from "@anthropic-ai/claude-agent-sdk";

// Connection string from environment variable
const connectionString = process.env.DATABASE_URL;

for await (const message of query({
  // Natural language query - Claude writes the SQL
  prompt: "How many users signed up last week? Break it down by day.",
  options: {
    mcpServers: {
      postgres: {
        command: "npx",
        // Pass connection string as argument to the server
        args: ["-y", "@modelcontextprotocol/server-postgres", connectionString]
      }
    },
    // Allow only read queries, not writes
    allowedTools: ["mcp__postgres__query"]
  }
})) {
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}

Error handling

看到这里,就把"Error handling"当成一件真要上手的活来看。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

终端里敲

Error handling

这一段不是只让你理解意思,下面这条命令就是现在要跑的。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "Process data",
  options: {
    mcpServers: {
      "data-processor": dataServer
    }
  }
})) {
  if (message.type === "system" && message.subtype === "init") {
    const failedServers = message.mcp_servers.filter((s) => s.status !== "connected");

    if (failedServers.length > 0) {
      console.warn("Failed to connect:", failedServers);
    }
  }

  if (message.type === "result" && message.subtype === "error_during_execution") {
    console.error("Execution failed");
  }
}

Troubleshooting

这里讲的是怎么找毛病,先查明白哪一步出错,再决定怎么修。

Server shows “failed” status

这一块主要是在说"Server shows “failed” status"真到手上该怎么用,哪里最容易踩坑。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

关键片段

Server shows “failed” status

"Server shows “failed” status"这一段里最要紧的原始写法在下面,先看它怎么落地。

if (message.type === "system" && message.subtype === "init") {
  for (const server of message.mcp_servers) {
    if (server.status === "failed") {
      console.error(`Server ${server.name} failed to connect`);
    }
  }
}

Tools not being called

这一段更像在讲判断条件,什么时候该上,什么时候先别急。把触发条件看清,比背标题更重要。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

关键片段

Tools not being called

这一段要真抓重点,通常就抓下面这块原文。

const _ = {
  options: {
    mcpServers: {
      // your servers
    },
    allowedTools: ["mcp__servername__*"] // Required for Claude to use the tools
  }
};

Connection timeouts

这里主要是在交代"Connection timeouts"这一块会碰到哪些事。

如果你打算把外接能力往里挂,这里提到的 hooks、MCP、skills、memory 都要分清各自负责哪一摊。

Related resources

这一段主要是在把"Related resources"讲实,不是只摆个标题给你看。

看这段时要特别盯工具和权限边界,别为了省事一把全开。

照着做一遍

如果你不想来回翻,就先照这几步顺着做。

每做完一步就看一下结果,再决定要不要继续往下。

终端里敲

第 1 步:Quickstart

这一段不是只让你理解意思,下面这条命令就是现在要跑的。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "Use the docs MCP server to explain what hooks are in Claude Code",
  options: {
    mcpServers: {
      "claude-code-docs": {
        type: "http",
        url: "https://code.claude.com/docs/mcp"
      }
    },
    allowedTools: ["mcp__claude-code-docs__*"]
  }
})) {
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}
终端里敲

第 2 步:In code

真到动手的时候了,下面这条直接敲一遍,看它回什么。

import { query } from "@anthropic-ai/claude-agent-sdk";

for await (const message of query({
  prompt: "List files in my project",
  options: {
    mcpServers: {
      filesystem: {
        command: "npx",
        args: ["-y", "@modelcontextprotocol/server-filesystem", "/Users/me/projects"]
      }
    },
    allowedTools: ["mcp__filesystem__*"]
  }
})) {
  if (message.type === "result" && message.subtype === "success") {
    console.log(message.result);
  }
}
改配置

第 3 步:From a config file

这一段说完,最后还得写到配置里才算真的生效。

{
  "mcpServers": {
    "filesystem": {
      "command": "npx",
      "args": ["-y", "@modelcontextprotocol/server-filesystem", "/Users/me/projects"]
    }
  }
}
关键片段

第 4 步:Grant access with allowedTools

先看下面这块原始片段,等会儿再回头看解释会顺得多。

const _ = {
  options: {
    mcpServers: {
      // your servers
    },
    allowedTools: [
      "mcp__github__*", // All tools from the github server
      "mcp__db__query", // Only the query tool from db server
      "mcp__slack__send_message" // Only send_message from slack server
    ]
  }
};

一眼看懂这一页

先把这页到底在讲什么看明白,再去碰具体命令和配置,最不容易绕晕。

Connect to external tools with MCP
   |
   v
这是 Extend with tools 里的一摊要紧活
   |
   v
先弄懂,再下手

文末提醒

这站会按官方 docs 的导航和内容变化继续重生成,原站加页、删页、改页时,这里会跟着更新。

人话解释会尽量顺着原页往下讲,但命令、参数名、配置名这些硬东西还是保留原样,免得你抄过去跑不起来。