Claude Code 源码研究:一个 while(true) 循环让大模型自己干活
2026 年 3 月 31 日,Anthropic 因为一次 npm 发布事故,把 Claude Code 的完整 TypeScript 源码泄露到了公网。50 万行代码、1900 个源文件,一览无余。
韩国开发者 Sigrid Jin 将这批源码整理并上传至 GitHub(https://github.com/instructkr/claude-code),随后又基于原始架构做了 Python clean-room 移植 。

这是一次罕见的机会,我们终于可以打开一个顶级 AI Agent 的引擎盖,看看里面到底装了什么——
01
Claude Code 是什么
Claude Code 是 Anthropic 做的一个终端 AI 助手。注意,不是网页聊天框,是你打开终端、敲命令行用的那种工具。
你在终端里对它说”帮我把项目里所有 console.log 换成 logger.info”,它就会自己去搜代码、读文件、改文件、跑测试——全程像一个真人在操作你的电脑。你不需要手把手告诉它每一步做什么,它自己规划、自己执行、自己验证。
虽然它目前主要用于编程场景,但其底层架构并不局限于写代码。读文件、执行命令、搜索网页、调用外部服务——这套机制可以驱动 AI 完成任何需要”多步操作”的复杂任务。编程只是它最先落地的场景。

这就是所谓的 AI Agent。和普通聊天机器人的区别在于:聊天机器人只能说,Agent 能做。
02
一个“死循环”撑起的自主决策
Claude Code 的核心引擎叫 Agent Loop,实现在一个叫
query.ts 的文件里,从第 303 行写到第 1729 行,一千四百行代码。
但把所有细节剥掉,骨架只有一句话:
while (true) {
调用 API,把用户需求和工具列表发给 Claude 模型
收到模型回复
if (回复里没有工具调用请求) → 退出循环
else → 执行模型要求的工具,把结果塞回对话历史,继续循环
}
就这。一个 while(true) 无限循环,一个 needsFollowUp 布尔标志。
每一轮循环做的事情是:把当前的完整对话历史(包括用户的原始需求、之前每一轮 AI 的回复、每一次工具执行的结果)打包发给 Claude 模型的 API。
模型返回的内容里,可能包含三种东西:文字(text)——要对用户说的话;思考(thinking)——内部推理过程;以及工具调用请求(tool_use)——”请帮我执行这个操作”。
关键判断就在这里:如果回复中包含任何 tool_use,循环继续;如果一个 tool_use 都没有,循环结束。
源码里的实现非常直白:
if (msgToolUseBlocks.length > 0) {
needsFollowUp = true
}
以及:
if (!needsFollowUp) {
return { reason: ‘completed’ }
}
没有复杂的状态机,没有花哨的流程编排。循环继不继续,完全取决于模型自己的输出里有没有工具调用请求。
为什么”没有 tool_use”就意味着结束
这不是 Claude Code 团队拍脑袋定的规则,而是 Anthropic Messages API 的 Tool Use 协议本身的语义。
当 Claude 模型觉得还需要获取信息或执行操作才能完成任务——它在回复里放一个 tool_use block,意思是”我需要这个操作的结果才能继续”。
当模型觉得信息已经足够,可以给出最终答案——它只返回文字,不再请求任何工具。
换句话说,退出循环不是代码的决策,是模型的决策。 Claude Code 只是忠实地执行了这个决策。
这是整个架构中最精妙的地方:一个看似简单的布尔判断,把”任务是否完成”这个极其复杂的判断,完全委托给了大模型的推理能力。代码不需要理解任务是什么,不需要定义”完成”长什么样——模型自己知道。
上下文的雪球效应
每一轮循环结束后,本轮模型的回复和工具执行结果都会被追加到消息历史中。下一轮发给 API 的消息,比上一轮多了一段……
像滚雪球一样,模型在每一轮都能看到自己之前做了什么、得到了什么结果,从而做出连贯的下一步决策。这也是 Agent 能”记住”自己在做什么的根本原因——不是因为它有记忆,而是因为每次决策时,所有历史都摆在它面前。
代价当然也很明显:token 消耗逐轮递增。Claude Code 为此实现了一整套上下文压缩机制——自动摘要、渐进折叠、紧急压缩——来应对雪球越滚越大的问题。
但这是工程细节,不影响核心架构的理解。
03
不是代码,而是模型在选择工具
Claude Code 内置了大约 40 个工具:Bash(执行命令)、FileRead(读文件)、FileEdit(改文件)、Grep(搜索代码)、WebFetch(抓网页)、AgentTool(派生子 Agent)……覆盖了从日常开发到系统运维的绝大多数操作场景。
一个自然的问题是:模型怎么知道该用哪个工具?
答案可能再次出乎意料:Claude Code 的代码里没有任何工具选择逻辑。没有 if-else,没有决策树,没有规则引擎。选哪个工具、传什么参数,百分之百是 Claude 模型自己在推理过程中决定的。
40 本”说明书”
Claude Code 做的事情,是给每个工具写了一份详细的自然语言说明——像产品说明书一样。每次调 API,这 40 份说明书会被一起塞进请求里。
以 BashTool 为例,它的说明长达数百行,不只告诉模型”这个工具能执行 shell 命令”,还包括:
-
什么时候该用它:”执行构建、测试、安装依赖”
-
什么时候不该用它:”不要用 cat 读文件,用 FileRead;不要用 sed 改文件,用 FileEdit”
-
安全红线:”不要 force push 到 main 分支”
-
超时限制、参数格式、沙箱规则……
模型读完这 40 份说明书,结合用户的需求和当前的上下文,自己判断下一步该用哪个工具。
这就像你给一个经验丰富的工程师一份工具清单和操作手册。你不需要告诉他”现在请用扳手拧第三颗螺丝”——你只要把手册给他,他自然知道什么场景用什么工具。
“软引导”而非”硬编码”
Claude Code 无法强制模型的选择,但可以通过说明书的措辞来施加影响。
BashTool 的说明里有这么一段:
IMPORTANT: Avoid using this tool to run cat, head, tail, sed, awk, or echo commands. Instead, use the appropriate dedicated tool…
这不是代码层面的限制——就算模型非要用 Bash 执行 cat,代码也会照样运行。但这段自然语言描述会影响模型的推理过程,让它更倾向于选择专用工具。
这是一种通过语言塑造行为的引导方式。不是铁栅栏,是路标。模型有完全的自由意志,但精心撰写的说明书会让它大概率做出更合理的选择。
某种意义上,Claude Code 团队最重要的工作之一,不是写循环逻辑,而是写好这 40 份说明书。工具说明的质量,直接决定了模型行为的质量。
04
一个执行轨迹实例
把上面的原理串起来,看一个具体的例子。用户输入:”帮我把项目里所有 console.log 替换成 logger.info,确保能正常运行。”
Agent 的执行轨迹如下:
-
第 1 轮:模型读到需求,决定先摸清状况。返回两个工具调用——用 Grep 搜索所有包含 console.log 的文件,用 FileRead 看 package.json 了解项目结构。
-
第 2 轮:模型看到 Grep 结果(5 个文件命中),再发一个 Grep,搜索项目里有没有现成的 logger 模块。
-
第 3 轮:发现项目已有 src/utils/logger.ts。模型一口气返回 5 个 FileEdit 调用,逐个文件替换。
-
第 4 轮:5 个文件全部编辑成功。模型返回一个 Bash 调用:npm test。
-
第 5 轮:测试全部通过。模型只返回一段文字:”全部完成,替换了 5 个文件,所有测试通过。”没有 tool_use。循环结束。
五轮循环,从搜索到发现到修改到验证,每一轮调用的工具种类和数量都不同,全部由模型根据当时的上下文自主决定。没有任何预设的流程图,没有人告诉它”第一步搜索、第二步确认、第三步修改”——它自己推理出了这个序列。
05
架构的简洁之美
读完 Claude Code 的源码,最大的感受不是”这代码真复杂”,而是这个架构选择真大胆。
把”任务完成了吗”这个判断交给模型,把”该用哪个工具”这个选择交给模型,把”下一步做什么”这个规划交给模型——Claude Code 的代码本身,几乎不做任何业务决策。它只做三件事:传话、跑腿、反馈结果。
这是一个深刻的架构哲学:当模型足够强时,最好的 Agent 框架不是替模型做决定,而是给模型最好的决策环境。
40 份精心撰写的工具说明书,就是这个”决策环境”的核心。不是用代码约束模型的行为,而是用语言塑造模型的认知。
这让我想到一个更大的命题。过去我们构建软件系统,核心工作是编写逻辑——if-else、状态机、流程引擎。而在 Agent 的世界里,核心工作变成了编写描述——用自然语言告诉 AI 它有什么能力、什么该做、什么不该做。
代码从”控制流”变成了”信息流”。工程师从”逻辑的编写者”变成了”上下文的策展人”。
这大概就是 AI Agent 真正带来的范式转移。不在于 while(true) 有多精巧,而在于我们开始用一种全新的方式构建软件——不是编程让机器执行,而是描述让智能体理解。
今天它在写代码,明天它可以在做任何事。循环是同一个循环,说明书换一套就行。


夜雨聆风