主题
解释器
在 Deep Agents 内运行轻量级代码,以组合工具、编排子智能体并转换结构化数据
解释器为智能体在智能体循环内提供一个可编程的内存中工作区。智能体编写代码来完成任务,运行时执行它并只返回相关结果。中间结果不会成为模型上下文的一部分。
沙箱是以代码优先的方式作用于环境(例如运行命令、安装依赖和编辑文件),而解释器则是以代码优先的方式组合工具、保留状态,并决定哪些信息应返回给模型。
WARNING
解释器处于beta 阶段。API 和生命周期行为可能在不同版本之间发生变化。
NOTE
解释器需要 langchain-quickjs>=0.2.0 以及 Python 3.11 或更高版本。
为什么使用解释器?
大多数智能体工作在模型推理和工具调用之间交替进行。模型可以在一轮中发起多个工具调用,但该批次在发出那一刻就固定了。没有另一次模型轮次,就无法循环、根据结果分支、重试失败,或将一次调用的输出馈入下一次调用,而且每个结果都会返回模型上下文。模型还决定要发起多少次调用,因此要求它在数百个条目上分派工作并不可靠,它往往只覆盖样本而非每一个条目。
解释器将这种编排移入代码,让模型只推理要做什么,而不是每一个中间步骤。
Programmatic tool calling (PTC)
从解释器代码调用选定的工具,包括循环、重试、分支和并行批次。
Dynamic subagents
从代码分派子智能体,以对大型输入进行扇出、验证和递归工作流。
Stateful work
将中间值保留在运行时状态中,而不会使模型上下文过载。
Deterministic transforms
对结构化数据进行排序、分组、解析、验证、评分和聚合,而无需另一次模型轮次。
选择一种模式
对智能体循环内的代码使用解释器:组合工具、保留状态,并控制什么返回给模型。
对作用于环境的代码使用沙箱:shell 命令、包安装、测试、文件系统编辑和操作系统级执行。
| 需求 | 使用 |
|---|---|
| 一两个简单的外部调用 | 普通工具调用 |
| 纯内存中的 JavaScript:循环、分支、重试或数据转换(无外部工具) | 解释器 |
| 从代码编排的许多外部工具调用(需要 PTC) | 使用程序化工具调用(PTC) 的解释器 |
| 许多独立的工作单元、多个视角,或对大型输入的递归分析 | 使用动态子智能体的解释器 |
| Shell 命令、包安装、测试或完整的操作系统文件系统访问 | 沙箱 |
快速开始
安装 QuickJS middleware 包,然后使用 create_deep_agent 上的 middleware 参数传入解释器 middleware。
bash
pip install -U "deepagents[quickjs]"bash
uv add "deepagents[quickjs]"python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="google_genai:gemini-3.6-flash",
middleware=[CodeInterpreterMiddleware()],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="openai:gpt-5.5",
middleware=[CodeInterpreterMiddleware()],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="anthropic:claude-sonnet-5",
middleware=[CodeInterpreterMiddleware()],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="openrouter:z-ai/glm-5.2",
middleware=[CodeInterpreterMiddleware()],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="fireworks:accounts/fireworks/models/glm-5p2",
middleware=[CodeInterpreterMiddleware()],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="baseten:zai-org/GLM-5.2",
middleware=[CodeInterpreterMiddleware()],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="ollama:north-mini-code-1.0",
middleware=[CodeInterpreterMiddleware()],
)解释器如何工作
该 middleware 向智能体添加一个 eval 工具。在有帮助时,智能体编写 JavaScript 并调用 eval;你并不直接调用解释器。该工具在 QuickJS 上下文中运行代码,其中的变量可以在 eval 调用之间保留,具体取决于持久化 mode。它捕获 console.log、console.warn 和 console.error,并返回最后一个表达式的结果。
智能体可以编写这样的代码:
ts
const rows = [
{ team: "alpha", score: 8 },
{ team: "beta", score: 13 },
{ team: "alpha", score: 21 },
];
const totals = rows.reduce((acc, row) => {
acc[row.team] = (acc[row.team] ?? 0) + row.score;
console.log(`${row.team} score: ${acc[row.team]}`);
return acc;
}, {});
totals;默认情况下(mode="thread"),解释器状态在同一线程的各轮次之间持久保留。mode 选项和快照生命周期请参阅持久化。
代码运行在 QuickJS 之上,这是一个轻量级的 JavaScript 运行时。默认情况下,解释器代码无法访问宿主机文件系统、网络、shell、包管理器或时钟。它可以计算、持有状态并写入 console.log、console.warn 或 console.error,仅此而已。
两个显式的桥接扩展了这一范围:
- 工具,通过程序化工具调用(PTC)。在
tools命名空间下将工具的白名单提供为异步函数。这些可以是智能体自己的工具,也可以是你定义并传入的独立工具。 - 子智能体,通过动态子智能体。当智能体配置了子智能体时,解释器会暴露一个
task()全局函数,用于从代码中分派它们。
程序化工具调用在你启用它之前是关闭的。只要智能体有子智能体,通过 task() 进行的子智能体分派就默认开启,你可以将其关闭。没有其他内容跨越 QuickJS 边界。
程序化工具调用(PTC)
程序化工具调用(PTC)将选定的智能体工具在解释器内以全局 tools 命名空间暴露。智能体无需要求模型发起一次工具调用、等待结果,然后决定下一次调用,而是可以编写代码,在循环、分支、重试或并行批次中调用工具。
当中间结果只是下一步的输入时,这很有帮助:解释器在有任何内容返回给模型之前对它们进行过滤或聚合,使多步工作流保持 token 高效。它与模型无关,由 middleware 实现,而非特定服务商的工具调用 API。
该 middleware 将每个白名单中的工具作为异步函数暴露在 tools 下。智能体用 await 调用它,在代码中处理结果,模型只看到最终的解释器输出,而不是每一个中间值。工具名称会转换为 camelCase,而输入对象仍遵循工具的 schema,因此名为 web_search 的工具会变成 tools.webSearch(...):
ts
const result: string = await tools.webSearch({
query: "deepagents interpreters",
});启用 PTC
使用显式的白名单启用 PTC:
python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="google_genai:gemini-3.6-flash",
middleware=[CodeInterpreterMiddleware(ptc=["web_search"])],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="openai:gpt-5.5",
middleware=[CodeInterpreterMiddleware(ptc=["web_search"])],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="anthropic:claude-sonnet-5",
middleware=[CodeInterpreterMiddleware(ptc=["web_search"])],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="openrouter:z-ai/glm-5.2",
middleware=[CodeInterpreterMiddleware(ptc=["web_search"])],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="fireworks:accounts/fireworks/models/glm-5p2",
middleware=[CodeInterpreterMiddleware(ptc=["web_search"])],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="baseten:zai-org/GLM-5.2",
middleware=[CodeInterpreterMiddleware(ptc=["web_search"])],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="ollama:north-mini-code-1.0",
middleware=[CodeInterpreterMiddleware(ptc=["web_search"])],
)启用 PTC 后,智能体可以从解释器代码中调用白名单中的工具。此示例并行搜索多个主题,并在返回给模型之前合并结果:
ts
const topics = ["retrieval", "memory", "evaluation"];
const results = await Promise.all(
topics.map((topic) =>
tools.webSearch({ query: `${topic} best practices 2025` }),
),
);
results.join("\n\n");WARNING
PTC 调用目前通过解释器桥接执行,不经过常规工具调用路径。因此,interrupt_on 批准工作流不会针对每次 PTC 发起的工具调用强制执行。
动态子智能体
下面的概述涵盖何时使用动态子智能体以及一个最小的 task() 模式。配置、编排示例、工作流触发器和安全注意事项请参阅动态子智能体。
动态子智能体让解释器使用内置的 task() 全局函数从代码中分派已配置的子智能体。跨越许多独立单元的任务(例如审查目录中的每个文件或对一批工单进行分类)会变成一个扇出工作并综合结果的循环。
在以下情况使用动态子智能体:
- 扇出并综合:并行地在许多条目上运行同类工作,然后合并结果。
- 验证:将发现发送给独立的验证者子智能体,只保留已确认的结果。
- 递归工作流:在解释器变量中保留一个工作集,选择切片,调用子智能体,并改进结果。
ts
const paths = ["src/auth.ts", "src/routes/api.ts"];
const reviews = await Promise.all(
paths.map((path) =>
task({
description: `Review ${path} for authentication issues`,
subagentType: "reviewer",
}),
),
);
reviews.join("\n\n");持久化
使用 CodeInterpreterMiddleware 上的 mode 参数控制跨轮次状态:
"thread"(默认):状态在eval调用之间以及智能体轮次之间持久保留。middleware 在每个智能体轮次之后对解释器状态进行快照,并在下一轮次之前恢复它。"turn":状态在一个智能体轮次内的多次eval调用之间持久保留,然后在下一轮次重置。"call":每次eval调用都在全新的 REPL 中运行,不从前面的调用继承任何内容。
使用 mode="thread" 时,快照是解释器内存中 JavaScript 状态的序列化副本,包括智能体完成运行代码时存在的全局变量、变量、函数和导入的模块。跨对话轮次,其生命周期为:
- 一个轮次开始,middleware 为该线程恢复最新的解释器快照。
- 智能体调用
eval一次或多次。这些调用共享一个实时上下文;middleware 不在它们之间进行快照。 - 轮次结束,middleware 将更新后的快照写入图状态。
- 下一轮次从该快照恢复,而不是从一个空运行时恢复。
NOTE
快照只保留可序列化的数据。函数、类和其他不可序列化的运行时对象在恢复后会变成无法访问的残留物。访问其中一个会抛出类似 Value for 'fn' was not restored because it is not serializable (type: function). 的错误。
快照保留的是解释器内存,而非外部世界的影响。如果解释器代码通过 PTC 调用了一个工具,恢复先前的解释器快照不会撤销该工具调用的副作用。它只会恢复记录或处理了结果的解释器变量。
跨轮次持久化不需要检查点器:
python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="google_genai:gemini-3.6-flash",
middleware=[
CodeInterpreterMiddleware(
mode="thread", # Default
)
],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="openai:gpt-5.5",
middleware=[
CodeInterpreterMiddleware(
mode="thread", # Default
)
],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="anthropic:claude-sonnet-5",
middleware=[
CodeInterpreterMiddleware(
mode="thread", # Default
)
],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="openrouter:z-ai/glm-5.2",
middleware=[
CodeInterpreterMiddleware(
mode="thread", # Default
)
],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="fireworks:accounts/fireworks/models/glm-5p2",
middleware=[
CodeInterpreterMiddleware(
mode="thread", # Default
)
],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="baseten:zai-org/GLM-5.2",
middleware=[
CodeInterpreterMiddleware(
mode="thread", # Default
)
],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
agent = create_deep_agent(
model="ollama:north-mini-code-1.0",
middleware=[
CodeInterpreterMiddleware(
mode="thread", # Default
)
],
)由于解释器快照存储在图状态中,检查点器 也会在检查点历史中捕获它们。当你需要持久化线程或 时间旅行 时,请添加一个:
python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
from langgraph.checkpoint.memory import MemorySaver
agent = create_deep_agent(
model="google_genai:gemini-3.6-flash",
checkpointer=MemorySaver(),
middleware=[CodeInterpreterMiddleware(mode="thread")],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
from langgraph.checkpoint.memory import MemorySaver
agent = create_deep_agent(
model="openai:gpt-5.5",
checkpointer=MemorySaver(),
middleware=[CodeInterpreterMiddleware(mode="thread")],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
from langgraph.checkpoint.memory import MemorySaver
agent = create_deep_agent(
model="anthropic:claude-sonnet-5",
checkpointer=MemorySaver(),
middleware=[CodeInterpreterMiddleware(mode="thread")],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
from langgraph.checkpoint.memory import MemorySaver
agent = create_deep_agent(
model="openrouter:z-ai/glm-5.2",
checkpointer=MemorySaver(),
middleware=[CodeInterpreterMiddleware(mode="thread")],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
from langgraph.checkpoint.memory import MemorySaver
agent = create_deep_agent(
model="fireworks:accounts/fireworks/models/glm-5p2",
checkpointer=MemorySaver(),
middleware=[CodeInterpreterMiddleware(mode="thread")],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
from langgraph.checkpoint.memory import MemorySaver
agent = create_deep_agent(
model="baseten:zai-org/GLM-5.2",
checkpointer=MemorySaver(),
middleware=[CodeInterpreterMiddleware(mode="thread")],
)python
from deepagents import create_deep_agent
from langchain_quickjs import CodeInterpreterMiddleware
from langgraph.checkpoint.memory import MemorySaver
agent = create_deep_agent(
model="ollama:north-mini-code-1.0",
checkpointer=MemorySaver(),
middleware=[CodeInterpreterMiddleware(mode="thread")],
)设置 mode="turn" 可仅在单个轮次内持久化解释器状态,或设置 mode="call" 使每次 eval 都获得一个全新的 REPL。
安全性
解释器使用 QuickJS 以严格的默认隔离运行不受信任的 JavaScript。请将其视为作用域受限的解释器运行时,而不是完整的生产沙箱后端。
你通过 PTC 暴露的每个工具都是解释器代码可以使用的外部能力。请将 PTC 允许列表视为权限边界:只暴露智能体所需的工具,并避免桥接那些能够访问敏感系统、花费资金、修改数据或调用不受限制网络的宽泛工具,除非这种行为是有意为之。
| 能力 | 默认是否可用 | 如何暴露它 |
|---|---|---|
| JavaScript 执行 | 是 | 添加解释器中间件 |
顶层 await | 是 | 在解释器代码中使用 promise |
console.log、warn、error 捕获 | 是 | 使用 capture_console=False 禁用 |
| 智能体工具 | 否 | 添加 PTC 允许列表 |
| 文件系统访问 | 否 | 通过 PTC 允许列表添加 内置文件系统工具 |
| 网络访问 | 否 | 通过 PTC 暴露特定的网络工具 |
| 挂钟时间或日期时间访问 | 否 | 如有需要,暴露一个显式的时间工具 |
| Shell 命令、包安装、测试、操作系统级执行 | 否 | 使用 沙箱后端 |
NOTE
代码执行的工作原理
解释器代码运行在嵌入式 QuickJS 上下文中,而不是单独的 VM 或进程。在 Python 中,该运行时由 quickjs-rs 提供,它在 安全指南 中记录了这种同进程执行边界。
请将解释器视为能力受限的执行层,而不是主机内存隔离边界。对于不受信任或半受信任的代码,请在隔离的工作进程或容器中运行智能体,并保持 PTC 允许列表尽可能窄。
配置
CodeInterpreterMiddleware 接受以下选项:
| Kwarg | 默认值 | 用途 |
|---|---|---|
memory_limit | 64 * 1024 * 1024 (64 MB) | 限制每个线程的 QuickJS 堆内存。 |
timeout | 5.0 | 每次 eval 调用的超时限制(秒)。 |
tool_name | "eval" | 暴露给模型的解释器工具名称。 |
capture_console | True | 在工具响应中捕获 console.log、console.warn 和 console.error。设置为 False 可丢弃控制台输出。 |
max_result_chars | 4000 | 将返回给模型的结果、错误和 stdout 文本截断到最大字符数。 |
ptc | None | 以 tools.* 形式在解释器内暴露的工具名称或 BaseTool 实例的允许列表。省略以禁用。参见 启用 PTC。 |
max_ptc_calls | 256 | 每次 eval 允许的最大 tools.* 调用次数。仅在受信任环境中设置为 None。参见 程序化工具调用(PTC) 和 安全。 |
subagents | True | 当智能体有子智能体时,暴露内置的 task() 全局函数。设置为 False 可要求通过常规 task 工具进行分派。参见 动态子智能体。 |
mode | "thread" | 控制解释器持久性:"thread"(跨轮次)、"turn"(在单个轮次内)或 "call"(每次 eval 都使用全新的 REPL)。参见 持久性。 |
max_snapshot_bytes | None | 丢弃大于此字节限制的快照。默认为 memory_limit。参见 持久性。 |