BrainBank
AI 课堂/最佳实践Claude Code Deep Dive

WebSearchTool:联网搜索

2026/8/2 14:40:09 · 来源

#claude-code#best-practices#tool-use#agent-workflow#web-search#webfetchtool

深入剖析 Claude Code 的 WebSearchTool:搜索 schema、Provider 环境限制、权限模型、与 WebFetchTool 的经典组合工作流,以及开发者最常见的三个误解。

这个工具到底做什么

WebSearchTool 负责让 Claude Code 查询互联网的最新信息。
它解决的核心问题不是“打开某个网页”,而是:

当主线程需要知道当前世界上最近发生了什么、某个产品最新文档是什么、某个问题有哪些公开资料时,如何安全地发起联网搜索。

所以它和 WebFetchTool 的区别一定要先记清:

  • WebSearchTool:找信息源
  • WebFetchTool:读指定页面

在真实使用里,这两个工具经常是一前一后配合。

它的 schema 很简单,但能力很强

tools/WebSearchTool/WebSearchTool.ts

const inputSchema = z.strictObject({
  query: z.string().min(2).describe('The search query to use'),
  allowed_domains: z.array(z.string()).optional(),
  blocked_domains: z.array(z.string()).optional(),
})

看起来只有 3 个字段,但已经涵盖了最关键的搜索控制:

  • 搜什么
  • 只搜哪些域名
  • 排除哪些域名

这意味着 Claude Code 的联网搜索不是“随便搜一下”,而是支持受约束的搜索。

它不是 Bash 调搜索引擎,而是接 Anthropic 的 Web Search 能力

源码里最关键的一段是这部分工具 schema 构造:

function makeToolSchema(input: Input): BetaWebSearchTool20250305 {
  return {
    type: 'web_search_20250305',
    name: 'web_search',
    allowed_domains: input.allowed_domains,
    blocked_domains: input.blocked_domains,
    max_uses: 8,
  }
}

这说明 WebSearchTool 不是自己去模拟浏览器,也不是 shell 调第三方搜索接口。
它实际上是把官方的 Web Search server tool 接进了 Claude Code 的工具系统。

换句话说,它做的是:

由 Claude Code 主线程触发,再由底层支持 Web Search 的模型能力去执行搜索

一张图看搜索链路

模型需要最新信息 > WebSearchTool > 构造 web_search schema > queryModelWithStreaming

触发 server tool: web_search > 返回搜索命中与说明文本 > 解析结果块 > 主线程继续引用结果

它的核心调用方式很值得研究

call() 里这段代码最能说明它的本质:

const queryStream = queryModelWithStreaming({
  messages: [userMessage],
  systemPrompt: asSystemPrompt([
    'You are an assistant for performing a web search tool use',
  ]),
  tools: [],
  options: {
    extraToolSchemas: [toolSchema],
    querySource: 'web_search_tool',
    ...
  },
})

这里有几个关键点:

  1. 它自己重新发起了一次模型调用
  2. 这次调用的目的不是普通回答,而是执行搜索
  3. 搜索工具是通过 extraToolSchemas 注入进去的

这说明 WebSearchTool 其实是一个包装型工具

  • 外层是 Claude Code 的标准工具
  • 内层再发起一次支持 web search 的模型请求

它为什么不是直接把结果返回,而是要先解析内容块

源码里有一段非常关键的解析逻辑:

function makeOutputFromSearchResponse(
  result: BetaContentBlock[],
  query: string,
  durationSeconds: number,
): Output

注释写得很直白:返回内容不是一个单纯数组,而是一串混合块:

  • server_tool_use
  • web_search_tool_result
  • text
  • citation 相关块

所以 WebSearchTool 的一个核心工作就是:

把底层返回的搜索结果块重新整理成 Claude Code 更容易消费的结构

它的输出其实是“搜索结果 + 说明文本”的混合体

输出 schema 里有一段非常重要:

results: z
  .array(z.union([searchResultSchema(), z.string()]))
  .describe('Search results and/or text commentary from the model')

这意味着返回结果不是纯搜索命中列表,而可能同时包含:

  • 一组搜索 hits
  • 一段文字说明

换句话说,WebSearchTool 并不是只把链接丢回来,而是允许模型在搜索结果外再补一些中间解释。

这也是它比普通搜索 API 更像 Agent 工具的地方

普通搜索 API 常常返回:

  • 标题
  • URL
  • 摘要

而 Claude Code 的 WebSearchTool 还会处理:

  • 工具调用块
  • 文本解释块
  • 引用与来源要求

这让它更适合直接接入主循环,而不是只当一个数据源。

prompt 里对“来源”要求非常严格

tools/WebSearchTool/prompt.ts

CRITICAL REQUIREMENT - You MUST follow this:
  - After answering the user's question, you MUST include a "Sources:" section at the end of your response
  - In the Sources section, list all relevant URLs from the search results as markdown hyperlinks

这说明 Anthropic 对这个工具的产品要求很明确:

  • 只要用了联网搜索
  • 最终回答里就应该带来源

这对可信度和可验证性非常重要。

一张图看它和回答生成的关系

WebSearchTool > 拿到最新搜索结果 > 主线程生成回答 > 附 Sources 链接 从产品角度看,这也是 Claude Code 比“模型偷偷搜一下然后不告诉你来源”更成熟的地方。

它还会强制提醒“用当前年份搜索”

getWebSearchPrompt() 里还有一条很有意思的约束:

IMPORTANT - Use the correct year in search queries:
  - The current month is ${currentMonthYear}. You MUST use this year when searching for recent information

这说明 Anthropic 已经意识到一个非常真实的问题:

如果模型搜“latest React docs”却没带当前年份,很可能召回到旧内容

所以 prompt 明确要求它在搜“最新信息”时带上当前年份。
这是一个很典型的产品化修补动作。

它并不是在所有环境里都能开

isEnabled() 里可以看到它会检查 provider 和 model:

if (provider === 'firstParty') return true
if (provider === 'vertex') {
  const supportsWebSearch =
    model.includes('claude-opus-4') ||
    model.includes('claude-sonnet-4') ||
    model.includes('claude-haiku-4')
  return supportsWebSearch
}
if (provider === 'foundry') return true
return false

这说明 WebSearchTool 不是“所有 Claude Code 运行环境都能用”的固定能力。
它会受到:

  • API provider
  • 模型能力
  • 平台支持情况

的共同影响。

这也是为什么这类工具要单独做 isEnabled()

它的权限模型和 WebFetch 不一样

WebSearchTool 的权限逻辑更粗一点:

async checkPermissions(_input): Promise<PermissionResult> {
  return {
    behavior: 'passthrough',
    message: 'WebSearchTool requires permission.',
    suggestions: [
      {
        type: 'addRules',
        rules: [{ toolName: WEB_SEARCH_TOOL_NAME }],
        behavior: 'allow',
        destination: 'localSettings',
      },
    ],
  }
}

这说明它更偏“工具级权限”,不像 WebFetchTool 细化到域名级规则。
原因也很好理解:

  • WebSearchTool 处理的是泛化搜索
  • WebFetchTool 处理的是具体 URL 访问

后者在安全边界上天然更细。

它和 WebFetchTool 是最经典的一前一后组合

这两者的配合关系几乎可以画成固定模板: WebSearchTool > 找出候选来源 > 挑选可信 URL > WebFetchTool > 抓取并提炼页面正文

这个链路特别适合:

  • 最新文档查询
  • 新闻或最近公告
  • 对比多个资料来源
  • 从搜索命中里继续深挖单个页面

一次典型使用路径

比如用户问:

Claude Code 官方命令页最近怎么写 /usage 的?

主线程常见路径会是:

  1. WebSearchTool 搜官方文档或特定域名
  2. 找到命令文档页
  3. 再交给 WebFetchTool 抓正文
  4. 最后组织回答并附上来源

这就是为什么 WebSearchTool 更像“找入口”,而不是“直接完成研究”。

最容易误解它的地方

误解一:WebSearchTool 就是搜索引擎 API 包装

不完全对。
它还包括:

  • 模型发起的 server tool 调用
  • 内容块解析
  • 来源约束
  • 环境与 provider 判定

误解二:有了 WebSearchTool 就不需要 WebFetchTool

也不对。
搜索结果通常只是入口,真正看正文往往还得 WebFetchTool

误解三:它总能搜到最新内容

它只是提供联网搜索能力,不等于结果一定完美。
所以 Anthropic 还专门在 prompt 里要求:

  • 使用当前年份
  • 回答时列来源

这些都是为了降低“搜到旧资料”或“说不清来源”的风险。

小结

如果用一句话总结:

WebSearchTool 是 Claude Code 的联网检索入口,它通过官方 web search schema 发起搜索,再把底层搜索结果块整理成主循环可消费的结构化结果。

它真正重要的地方,不只是“能搜”,而是:

能把搜索结果、来源约束、模型环境和后续网页深读串成一条完整的联网工作流。

学习地图

学习路线

第一阶段:理解工具定位

  • WebSearchTool 的核心职责("找信息源" vs "读指定页面")
  • 搜索 schema 的 3 个字段含义及受约束搜索原理

第二阶段:底层机制

  • server tool web_search_20250305 调用流程
  • 模型二次发起搜索请求 + 内容块解析链路
  • 返回结果的混合结构(search hits、补充说明、citation)

第三阶段:环境 & 权限

  • isEnabled() 的环境判定(provider + model 白名单)
  • WebSearchTool vs WebFetchTool 的权限粒度差异
  • Prompt 中的强制约束(当前年份、来源引用)

第四阶段:实战组合工作流

  • WebSearchTool → WebFetchTool 的标准链路
  • 如何构造查询、限制域名解析结果
  • Sources 引用规范与可信度保障

第五阶段:避坑指南

  • "它不是搜索引擎 API 包装"
  • "有了搜索仍需抓取"
  • "搜索结果 ≠ 一定最新"三项误区

动手实践——分步指南

WebSearchTool 实战指南

  1. 确认运行环境支持:使用支持 web search 的 provider(firstParty / vertex with Opus-4/Sonnet-4/Haiku-4 / foundry),调用 isEnabled() 通过即表示可用。

  2. 检查权限配置:在 Claude Code 的设置中放行 WebSearchTool,确保 systemPrompt 约束生效(来源引用 + 当前年份标注)。

  3. 发起受约束搜索:构造 query(≥ 2 字符)、allowed_domains、blocked_domains,调用 WebSearchTool。示例——只搜官方文档域:

    • query: "Claude Code /usage command latest documentation"
    • allowed_domains: ["docs.anthropic.com"]
  4. 解析搜索结果块:区分返回中的 search hits、模型补充说明文本、citation 块。确认输出含 "Sources:" 段落。

  5. 链式搭配 WebFetchTool:从搜索命中中挑选可信 URL,传入 WebFetchTool 抓取完整正文,避免只依赖摘要片段。

  6. 引用来源回答:整理最终答案时,必须附上 Sources 链接(按搜索结果中的 URL 以 Markdown 超链接形式列出),确保可验证性。

三大推荐资源

  1. 1
    Claude Code Tool Use Overview

    Anthropic 官方文档,涵盖 Claude Code 工具集概览、搜索类工具的启用条件与使用模式。

    https://docs.anthropic.com/en/docs/claude-code/tools-overview

  2. 2
    Anthropic API Tool Use Guide

    Claude API 工具调用规范文档,包括 web search schema(web_search_20250305)的字段说明与调用示例。

    https://docs.anthropic.com/en/docs/build-with-claude/tool-use

  3. 3
    claude-code (anthropics/claude-code GitHub)

    Claude Code 开源仓库,包含 WebSearchTool、WebFetchTool 等工具源码与环境检测逻辑。

    https://github.com/anthropics/claude-code

链接由 AI 推荐——使用前建议快速核实。