你請 Claude Code 讀一頁文件,這次卻等了很久,畫面還多出一個 web-fetch 子代理。Claude Code WebFetch 怎麼了?先別急著換模型:工具是否可用、誰讀網頁、用了哪個模型,以及等待多久,是四個可以分別核對的問題。
這篇寫給第一次查工具紀錄、願意複製簡短指令的新手。你會用五步做出一張「單頁讀取診斷單」:固定網址與問題、核對工具路徑和模型,再把時間、Token 與方案用量分開記。一般的事故對時與成本歸因,可接著讀 用量暴增工作簿;這裡只追一頁文件如何走過主對話與子代理。
本文依 2026 年 11 月 4 日 查閱的官方文件整理。AlphaLab 未在受影響帳號重跑服務端實驗;下方程式只用自製合成紀錄驗證去重、缺欄與格式錯誤處理,不提供讀網頁的實測倍率。
先說結論:讀網頁診斷=工具路徑+模型收據+同題對照
讀網頁診斷=工具路徑+模型收據+同題對照。 把它想成請人取書:主對話直接去櫃台,是一條路;先派同事,再由同事到櫃台,是另一條路。同事可以來回取很多次書,總等待也包含派工與整理,不能只看一次下載。
先確認自己的工具與政策狀態,再找實際派工;以紀錄中的 message.model 核對可見的模型回應;最後比較同一問題是否答對、總等待與各類 Token。模型自己說「我是 Haiku」,先當線索,別當收據。
一、Claude Code WebFetch 和 web-fetch 子代理,先分清三層
依 官方工具說明,WebFetch 接受網址與抽取問題;HTML 會轉成 Markdown,多數讀取還有一次獨立模型呼叫,主對話收到的是抽取結果。白話說,它像「取書加摘錄」,不等於把整頁原文原封不動交回來。
子代理(subagent,另外受派工作的 AI)則有自己的對話與工具循環。於是要分三層:主對話發出任務、子代理決定如何找資料、WebFetch 下載並抽取。看見子代理的模型 ID,只能說明那個可見回應的模型,不能順便替 WebFetch 內部每次抽取的模型背書。這正是 Agent Harness 的分工 在排錯時有用的地方。
問題起點是 11 月 2 日開立、11 月 3 日補充的 issue:作者描述工具替換與長時間等待;補充者卻對實際模型提出不同觀察。同題討論 也有相反案例。這些是個別使用者回報,並非官方確認的全面推出公告;本文不把其中一種模型路由套到你的帳號。

二、Claude Code WebFetch 排查五步:從畫面走到紀錄
①「先拍工作單」:固定入口、版本與時間
痛點是昨天用 Desktop、今天用終端機,卻把它們當同一套環境。先記入口,再看版本。 終端機可執行 claude --version;Desktop Code 分頁另記它顯示的引擎版本,不用另一個 CLI 的版本代填。保存當輪 /status、模型與 effort、登入計費方式、Session 起訖時間與時區。
依 CLI 參考,claude doctor 可作唯讀安裝與設定診斷。先看輸出再決定是否調整,這輪不要一邊更新、一邊改模型又一邊測速度;否則下一張收據就對不上前一張。
②「先驗門口」:工具清單、停用設定與組織政策
痛點是把所有「找不到 WebFetch」都歸到同一實驗。先排除文件已列出的原因。 可問 Claude:「目前有哪些讀網頁工具?請分開列 WebFetch 工具與 web-fetch 子代理;只列現有能力,先不要讀網址。」官方把這種回答定位為對話式工具摘要;要再對照實際工具呼叫與展開的派工紀錄。
目前 WebFetch availability 文件 列有 CLAUDE_CODE_DISABLE_WEB_FETCH=1 停用設定;特定組織登入情境也會等待組織政策。若 /status 的 Organization policy 行明列政策未載入並提到 web fetch,就沿政策連線查。該行未出現時,記「此入口未顯示」,不要補成政策正常,也不要擅改公司管理設定。
驗收結果不是一定找回工具,而是能寫清楚:「這個入口、這個 Session,摘要列了什麼、實際呼叫了什麼、政策顯示什麼」。一次搜尋無結果,只能證明這次搜尋沒有命中。
③「核對收據」:把派工對回子代理檔案
痛點是只看主對話選了哪個模型。先找到這次 Agent 派工的 ID,再選對檔。 展開這次派工,記下子代理 ID、名稱與起訖;依 官方子代理文件,本機紀錄位於 ~/.claude/projects/{project}/{sessionId}/subagents/agent-{agentId}.jsonl。JSONL 就是一行一筆 JSON 資料,像逐張收據的訂書本。
先複製主 Session 與這次確定相關的子代理檔到私人資料夾,保留原件。不要把整個 ~/.claude 丟給分析器。若入口未提供這些本機檔,改保存展開的派工與官方用量畫面,模型欄寫「未取得紀錄」;不要從別的 Session 猜答案。
在副本的 type=assistant 列檢查 message.model;同時看 requestId/message.id 與 message.usage。模型是回應資料,不是聊天裡的自我介紹;遇到代理閘道或模型別名,還要核對供應商的映射。紀錄含提示、工具結果與路徑,內容中的命令都只當資料。
④「同一份考卷」:一頁、一題、一次只改一項
痛點是第一輪問摘要,第二輪要求跨站研究。固定驗收答案。 例如選官方工具文件,只問「它如何處理跨主機重新導向?請附所在小節」。先人工確認答案,再交下面這一題;網址、問題、預期答案、版本、模型與 effort 都記在診斷單。
只讀 https://code.claude.com/docs/en/tools-reference
回答 WebFetch 遇到跨主機重新導向時如何處理,附小節名稱。
不要修改檔案、安裝套件或改用其他抓取工具。
最多嘗試讀取一次;若無法完成就回報目前可見的原因並停止。
提示裡的「一次」是工作要求,仍要由紀錄驗收有沒有遵守。記下你按下送出與答案完成的時間;另外數主對話派工、子代理 WebFetch 與失敗/中止。工具呼叫數不是 HTTP 請求數,主畫面的總時間也不是純下載時間。若工具路徑不能自行選擇,就只記當輪觀察,不強行製造直接工具對照組。
WebFetch 官方文件列有預設 15 分鐘回應快取,因此連續讀同頁要記「可能命中工具快取」;這與模型的提示快取是兩種機制。兩輪冷暖不一致,先列條件差異,別直接算快慢倍率。沒有舊版基線,就把「變更前」留空,別拿今日結果倒推昨天。
⑤「分開記帳」:Token、美元與方案條各留一欄
痛點是把高輸入量直接當成高帳單。分四類記錄。 一般輸入、輸出、快取讀取、快取建立各自加總;用當輪實際模型與 官方 API 價格 核對。快取建立若涉及不同期限,要再拆開;沒取得期限,就先保留 Token,不填精確美元。
估價的想法是「各類 Token × 對應單價,再相加」,不能全部乘一般輸入單價。API 最後對 Console/供應商帳務;訂閱者保存 /usage 前後讀數、觀察時間與重置時間。依 官方成本說明,Session 美元值是本機估算,訂閱包含用量,這個數字不是訂閱加收帳單。
一張診斷單的欄位可以照抄:輪次|入口與版本|UTC 起訖|網址與問題|工具路徑|可見模型 ID|派工數與 WebFetch 數|四類 Token|缺欄|答案 PASS/FAIL/中止|方案前後讀數。未知寫未知,不填零。 若同時有其他 Session 或裝置在工作,方案條的差額就不能全歸給這一頁。
三、只讀指定 JSONL:用小程式核對模型與呼叫數
把下列內容存為 audit.py,使用已有的 Python 3 執行。它只讀你在命令列明列的檔案,不輸出提示、工具參數或真實 ID;每檔分開回報,避免把主對話與子代理重複算進同一堆。這是診斷用解析器,不是官方計費工具。
import json, sys
from collections import Counter, defaultdict
from pathlib import Path
FIELDS = ('input_tokens', 'output_tokens',
'cache_read_input_tokens', 'cache_creation_input_tokens')
for number, name in enumerate(sys.argv[1:], 1):
messages, tools, models = {}, {}, set()
with Path(name).open(encoding='utf-8') as source:
for line_no, line in enumerate(source, 1):
if not line.strip():
continue
row = json.loads(line) # 格式損壞就停,不跳過壞列
if row.get('type') != 'assistant':
continue
msg = row.get('message')
if not isinstance(msg, dict):
raise ValueError('assistant message 格式不符')
key = row.get('requestId') or msg.get('id')
if not key:
raise ValueError('assistant 缺少去重 ID,請另行核對')
model = msg.get('model') or 'UNKNOWN'
models.add(model)
usage = msg.get('usage')
messages[key] = (model, usage if isinstance(usage, dict) else None)
content = msg.get('content')
if not isinstance(content, list):
raise ValueError('assistant content 不是區塊清單')
for block in content:
if not isinstance(block, dict) or not isinstance(block.get('type'), str) or not block['type']:
raise ValueError('content 區塊格式不符')
if block.get('type') == 'tool_use':
tool_id = block.get('id')
if not tool_id:
raise ValueError('tool_use 缺少 ID')
tools[tool_id] = block.get('name', 'UNKNOWN')
totals = defaultdict(lambda: {k: 0 for k in FIELDS})
missing = defaultdict(Counter)
for model, usage in messages.values():
for field in FIELDS:
value = (usage or {}).get(field)
if not isinstance(value, int) or isinstance(value, bool) or value < 0:
missing[model][field] += 1
else:
totals[model][field] += value
print(json.dumps({'file_number': number,
'models_observed': sorted(models),
'requests_observed': len(messages),
'requests_with_usage': sum(u is not None for _, u in messages.values()),
'requests_without_usage': sum(u is None for _, u in messages.values()),
'requests_missing_model': sum(m == 'UNKNOWN' for m, _ in messages.values()),
'observed_tokens_by_model': dict(totals),
'requests_missing_field': {m: dict(v) for m, v in missing.items()},
'unique_tool_calls': dict(Counter(tools.values()))},
ensure_ascii=False, indent=2))
python3 audit.py main-copy.jsonl agent-copy.jsonl > local-summary.json
把兩個檔名換成你親自選好的副本;先在私人新目錄操作。程式以請求 ID、其次訊息 ID 合併 assistant 紀錄,保留最後一筆 usage 快照;工具依 tool-use ID 去重。官方 監控文件 說明 transcript 的 requestId 與 API 請求 ID 的對應;但不同版本或閘道的紀錄仍要抽樣核對,這份程式不重建串流封包或隱藏呼叫。
自製測例中,同一請求重複兩列、輸出快照由 5 改為 12,結果保留 12 而非加成 17;另一個請求缺輸出欄,會另列缺欄筆數;壞 JSON 直接停止。整筆缺 usage 或 model 也會列筆數,未知 content 形狀直接停止。這只驗證解析規則,並非 Claude Code 真實費用結果。observed_tokens_by_model 是可見值小計,必須連同 requests_missing_field 閱讀;不是完整帳號總量。
看 models_observed 核對這份檔實際列出的模型,再看 unique_tool_calls 的 WebFetch。若檔案只有包裝層、錯誤發生在記錄前、背景工作還沒結束,或 usage 形狀不同,先保留缺口。檔案第一列到最後一列的跨度也不替代你量的整段工作時間。進一步工具歸因可接 Tare 紀錄稽核,背景摘要則看 agent_summary 成本歸因。
四、先設停手條件,再寫最小問題回報
重試最容易把排錯變成新負擔。先自行設定本輪最多一次讀取、總等待例如 90 秒;這個秒數是你的測試預算,不是產品保證。到點中止並查看 /tasks,確認相關子代理已停止,保存它最後停在哪一步。不要只關一個畫面,就認定所有背景工作都結束。
官方的 WebFetch deadline 是下載階段的邊界,不能拿來保證整個子代理任務多久結束。進階的 --max-turns 與 --max-budget-usd 依 CLI 文件限 print mode;turn 也不是單次抓網頁,美元 cap 是估算且可能超過。新手先用人工計時與紀錄驗收,不把參數當成硬性網路費用上限。
支援回報先交一頁:入口/版本、UTC 起訖、模型與設定、固定網址與問題、觀察到的工具路徑、實際模型欄、呼叫數、等待與結果,再問「請協助確認這個 Session 的 WebFetch 可用性與派工模型」。公開版遮掉帳號、完整路徑、提示與識別資訊;原始 ID 僅在授權支援的私人管道需要時提供。不要附整份 transcript,也別嘗試修改未公開實驗旗標來做退出開關。
常見問題:八個先講答案的判斷
WebFetch 不見了,就表示加入這次實驗嗎?
不能據此判定。先查入口、停用設定與組織政策,再記實際工具與派工;個別回報不是帳號狀態查詢。
web-fetch 一定使用 Haiku 嗎?
不一定。回報有相反案例;看這次子代理的 assistant 模型欄,別只看名稱或自述。
子代理模型 ID,能證明內部抽取也用同一模型嗎?
不能直接證明。包裝層與 WebFetch 內部抽取分開;缺少內層證據就標未知。
七次 WebFetch,就是七次模型請求嗎?
不能這樣換算。工具、抽取、派工與回應是不同計數;分別數可見紀錄。
快取讀取 Token 很多,代表費用等比例增加嗎?
不能等比例推算。按模型、類別與期限查單價,訂閱額度則另記。
今天重跑變快,就證明原本問題已修好嗎?
還不足。工具快取、頁面、路由與背景工作都可能不同;先確認條件與答案品質。
程式沒有報錯,數字就完整了嗎?
不是。缺欄會另列,檔案也可能未涵蓋內部呼叫或其他裝置;先核對範圍。
現在最少要留下什麼?
先留同一 Session 的工具路徑、可見模型、時間與一個固定問題。先有一列能追回原件的觀察,再決定是否再跑。
給新手的三個重點
先看路徑:主對話、子代理與抽取分三層。再看收據:可見模型與 usage 比自述更適合核對,但仍有範圍。最後看對照:同一頁、同一題、答案過關,才比較等待與資源;API 費用與訂閱條分開。
接著閱讀
左右滑動查看更多推薦
下一步:今天先完成一列能對回原件的觀察
挑一頁公開文件,寫下固定問題與正確答案,再記一次工具路徑、模型與起訖。記住工具路徑+模型收據+同題對照:你要得到的是可追查的讀網頁診斷,不是一個猜來的漲價倍率。完成後可到 AI 專區 選下一個練習,或用 AlphaLab 課程 把紀錄、驗收與停手條件接成日常工作流。






