ls、read_file、write_file、edit_file、glob 和 grep 等工具向代理暴露文件系统接口。这些工具通过一个可插拔的后端运行。read_file 工具原生支持二进制文件(图像、PDF、音频、视频),并在所有后端中返回一个包含类型化 content 和 mimeType 的 ReadResult。
沙盒和 LocalShellBackend 还提供了一个 execute 工具。
本页将解释如何:
快速入门
这里有一些预构建的文件系统后端,您可以快速地将其与您的深度代理一起使用:内置后端
StateBackend
- 通过
StateBackend将文件存储在当前线程的 LangGraph 代理状态中。 - 通过检查点在同一线程的多个代理轮次中持久化。文件不跨线程共享。
- 用于代理写入中间结果的草稿本。
- 自动淘汰大型工具输出,代理随后可以分块读回。
FilesystemBackend(本地磁盘)
FilesystemBackend 在可配置的根目录下读写真实文件。
- 在可配置的
root_dir下读写真实文件。 - 您可以选择性地设置
virtual_mode=True以在root_dir下沙盒化和规范化路径。 - 使用安全的路径解析,尽可能防止不安全的符号链接遍历,可以使用 ripgrep 进行快速
grep。
- 您机器上的本地项目
- CI 沙盒
- 挂载的持久卷
LocalShellBackend(本地 Shell)
- 扩展
FilesystemBackend,增加了用于在宿主机上运行 Shell 命令的execute工具。 - 使用
subprocess.run(shell=True)直接在您的机器上运行命令,没有沙盒化。 - 支持
timeout(默认 120 秒)、max_output_bytes(默认 100,000)、env和inherit_env用于环境变量。 - Shell 命令使用
root_dir作为工作目录,但可以访问系统上的任何路径。
- 本地编码助手和开发工具
- 当您信任代理时,在开发过程中快速迭代
StoreBackend(LangGraph 存储)
部署到 LangSmith 部署 时,请省略
store 参数。平台会自动为您的代理配置一个存储。StoreBackend将文件存储在运行时提供的 LangGraphBaseStore中,从而实现跨线程的持久存储。
- 当您已经在使用配置好的 LangGraph 存储运行时(例如,Redis、Postgres 或
BaseStore背后的云实现)。 - 当您通过 LangSmith 部署 部署代理时(系统会自动为您的代理配置一个存储)。
命名空间工厂
命名空间工厂控制StoreBackend 读写数据的位置。它接收一个 LangGraph Runtime 并返回一个用作存储命名空间的字符串元组。使用命名空间工厂可以在用户、租户或助手之间隔离数据。
在构造 StoreBackend 时,将命名空间工厂传递给 namespace 参数:
Runtime 提供:
-
rt.context— 用户通过 LangGraph 的上下文模式 传递的上下文(例如,user_id) -
rt.serverInfo— 在 LangGraph Server 上运行时的服务器特定元数据(助手 ID、图 ID、认证用户) -
rt.executionInfo— 执行标识信息(线程 ID、运行 ID、检查点 ID)
Runtime 参数在 deepagents>=1.9.1 中可用。早期的 1.9.x 版本传递的是 BackendContext — 请参阅下面的从 BackendContext 迁移。rt.serverInfo 和 rt.executionInfo 需要 deepagents>=1.9.0。(user_id, thread_id) 用于按用户按对话隔离,或者添加后缀如 "filesystem" 以在同一范围使用多个存储命名空间时进行区分。
命名空间组件必须仅包含字母数字字符、连字符、下划线、点、@、+、冒号和波浪号。为防止 glob 注入,拒绝使用通配符(*、?)。
ContextHubBackend
开始之前:
ContextHubBackend 需要在 LangSmith 中设置一个上下文中心仓库。如果您不熟悉代理仓库和技能仓库,请先阅读上下文中心概念页面。ContextHubBackend 将您的代理文件系统存储在 LangSmith 上下文中心仓库中。它可以使用独立仓库或链接到技能仓库的代理仓库。
仓库结构: 在上下文中心,一个_代理仓库_保存代理的顶层指令和配置(例如,AGENTS.md、tools.json)。它可以链接到一个或多个_技能仓库_,每个技能仓库打包为一个可重用的能力(例如,包含电子邮件格式化或代码审查指令的 SKILL.md)。当您传递 ContextHubBackend("my-agent") 时,后端将代理仓库挂载到文件系统根目录;链接的技能仓库显示为 /skills/ 下的子目录。
这意味着您代理的上下文故意分布在多个仓库中:每个代理一个仓库,每个技能单独的仓库。这种分离使得技能可以独立于多个代理进行版本控制、共享和重用。如果这感觉过于分散,请参阅链接仓库了解其原理。
使用 owner/name 或 name 格式的仓库标识符构造它。
使用
ContextHubBackend 前请设置 LANGSMITH_API_KEY。- 首次使用时延迟拉取中心仓库树,然后从内存缓存提供读取服务。
- 将写入和编辑作为中心提交进行持久化,并在成功提交后更新缓存。
- 使用乐观父提交写入(
parent_commit):每次推送都针对已知的最新提交哈希。
- 如果仓库不存在,首次拉取视为空;第一次成功写入可以创建仓库。
- 如果另一个写入者先推进了仓库,您过期的父提交写入可能会失败。在冲突时重新拉取并重试。
upload_files()接受 UTF-8 文本。非 UTF-8 文件按路径以invalid_path拒绝。
- LangSmith 原生的持久文件系统持久化,无需单独连接 LangGraph
BaseStore。 - 受益于中心提交历史记录的文件系统更改的工作流。
CompositeBackend(路由器)
CompositeBackend根据路径前缀将文件操作路由到不同的后端。- 在列表和搜索结果中保留原始路径前缀。
- 当您希望为代理同时提供线程作用域和跨线程存储时,
CompositeBackend允许您同时提供StateBackend和StoreBackend - 当您有多个信息源想要作为单个文件系统的一部分提供给代理时。
- 例如,您将长期记忆存储在一个存储中的
/memories/下,并且您还有一个自定义后端,其中包含可通过 /docs/ 访问的文档。
- 例如,您将长期记忆存储在一个存储中的
指定一个后端
- 将后端实例传递给
createDeepAgent({ backend: ... })。文件系统中间件将其用于所有工具操作。 - 后端必须实现
AnyBackendProtocol(BackendProtocolV1或BackendProtocolV2)— 例如,new StateBackend()、new FilesystemBackend({ rootDir: "." })、new StoreBackend()。 - 如果省略,默认为
new StateBackend()。
在 1.9.0 版本之前,只支持
BackendProtocol,现在称为 BackendProtocolV1。V1 后端在运行时通过 adaptBackendProtocol() 自动适配到 V2。要继续使用现有的 V1 后端,无需更改代码。要更新到 v2,请参阅将现有后端更新到 v2。路由到不同的后端
将命名空间的各个部分路由到不同的后端。通常用于跨线程持久化/memories/*,并保持其他所有内容为线程作用域。
/workspace/plan.md→StateBackend(线程作用域)/memories/agent.md→/deepagents/myagent下的FilesystemBackendls、glob、grep聚合结果并显示原始路径前缀。
- 更长的前缀优先(例如,路由
"/memories/projects/"可以覆盖"/memories/")。 - 对于 StoreBackend 路由,请确保存储已通过
create_deep_agent(model=..., store=...)提供或由平台配置。 - Deep Agents 将内部数据(卸载的工具结果、对话历史记录)写入默认后端。使用
StateBackend作为默认后端,以保持这些工件临时性,避免将它们写入磁盘或持久存储。有关完整示例,请参阅 FilesystemBackend 提示。
自定义后端
实现自定义后端以将 Deep Agents 连接到数据库、对象存储和远程文件系统等存储系统。有关示例,请参阅社区构建的后端。实现后端协议
实现BackendProtocol(BackendProtocolV2)并提供以下方法:
要同时支持
execute 工具(运行 Shell 命令),请实现 SandboxBackendProtocol,它用 execute 方法扩展了 BackendProtocolV2。
所有方法必须返回带有可选 error 字段的结构化 Result 对象 — 不要在文件缺失或模式无效时抛出异常。
示例:S3 风格后端骨架
示例:S3 风格后端骨架
此骨架将文件系统路径映射到对象键。用您的存储客户端的列表、读取、搜索、上传和读-修改-写操作填充每个方法。
权限
使用权限声明式地控制代理可以读取或写入哪些文件和目录。权限适用于内置的文件系统工具,并在调用后端之前进行评估。 有关完整的选项集,包括规则排序、子代理权限和组合后端交互,请参阅权限指南。添加策略钩子
对于基于路径的允许/拒绝规则之外的自定义验证逻辑(速率限制、审计日志、内容检查),通过子类化或包装后端来强制执行企业规则。 阻止对选定前缀下的写入/编辑(子类化):多模态和二进制文件
多模态文件支持(PDF、音频、视频)需要
deepagents>=1.9.0。read() 遇到二进制文件(根据文件扩展名确定 MIME 类型)时,它返回一个包含 Uint8Array 内容和相应 mimeType 的 ReadResult。文本文件返回 string 内容。
支持的 MIME 类型
读取二进制文件
FileData 格式
FileData 是用于在状态和存储后端中存储文件内容的类型。
fileFormat: "v1" 传递给后端构造函数(例如,new StoreBackend({ fileFormat: "v1" }))。
从后端工厂迁移
以前,StateBackend 和 StoreBackend 等后端需要一个接收运行时对象的工厂函数,因为它们需要运行时上下文(状态、存储)才能运行。后端现在通过 LangGraph 的 get_config()、get_store() 和 get_runtime() 辅助函数在内部解析此上下文,因此您可以直接传递实例。
发生了什么变化
已弃用的 API
工厂模式在运行时仍然有效,并会发出弃用警告。在下一个主要版本之前更新您的代码以使用直接实例。
迁移示例
从 BackendContext 迁移
在 deepagents>=0.5.2(Python)和 deepagents>=1.9.1(TypeScript)中,命名空间工厂直接接收 LangGraph Runtime,而不是 BackendContext 包装器。旧的 BackendContext 形式仍然通过向后兼容的 .runtime 和 .state 访问器工作,但这些访问器会发出弃用警告,并将在 deepagents>=0.7 中移除。
发生了什么变化:
- 工厂参数现在是
Runtime,而不是BackendContext。 - 删除
.runtime访问器 — 例如,ctx.runtime.context.user_id变为rt.server_info.user.identity。 ctx.state没有直接替代。命名空间信息在运行期间应是只读且稳定的,而状态是可变的且逐步变化的 — 从状态派生命名空间有风险,导致数据最终位于不一致的键下。如果您有一个需要读取代理状态的用例,请提交问题。
协议参考
后端必须实现BackendProtocol。
必需方法:
ls(path: str) -> LsResult- 返回至少包含
path的条目。可用时包括is_dir、size、modified_at。按path排序以获得确定性输出。
- 返回至少包含
read(file_path: str, offset: int = 0, limit: int = 2000) -> ReadResult- 成功时返回文件数据。文件缺失时,返回
ReadResult(error="Error: File '/x' not found")。
- 成功时返回文件数据。文件缺失时,返回
grep(pattern: str, path: Optional[str] = None, glob: Optional[str] = None) -> GrepResult- 返回结构化匹配项。出错时,返回
GrepResult(error="...")(不要引发异常)。
- 返回结构化匹配项。出错时,返回
glob(pattern: str, path: Optional[str] = None) -> GlobResult- 返回匹配的文件作为
FileInfo条目(如果没有则返回空列表)。
- 返回匹配的文件作为
write(file_path: str, content: str) -> WriteResult- 仅创建语义。冲突时,返回
WriteResult(error=...)。成功时,设置path,对于状态后端设置files_update={...};外部后端应使用files_update=None。
- 仅创建语义。冲突时,返回
edit(file_path: str, old_string: str, new_string: str, replace_all: bool = False) -> EditResult- 除非
replace_all=True,否则强制old_string唯一。如果未找到,返回错误。成功时包括occurrences。
- 除非
LsResult(error, entries)—entries成功时为list[FileInfo],失败时为None。ReadResult(error, file_data)—file_data成功时为FileData字典,失败时为None。GrepResult(error, matches)—matches成功时为list[GrepMatch],失败时为None。GlobResult(error, matches)—matches成功时为list[FileInfo],失败时为None。WriteResult(error, path, files_update)EditResult(error, path, files_update, occurrences)FileInfo字段:path(必需),可选is_dir、size、modified_at。GrepMatch字段:path、line、text。FileData字段:content(str),encoding("utf-8"或"base64"),created_at,modified_at。 :::
BackendProtocolV2。所有查询方法都返回带有 { error?: string, ...data } 的结构化 Result 对象。
必需方法
-
ls(path: string) → LsResult- 列出指定目录中的文件和目录(非递归)。目录在其路径末尾有
/,并且is_dir=true。可用时包括is_dir、size、modified_at。
- 列出指定目录中的文件和目录(非递归)。目录在其路径末尾有
-
read(filePath: string, offset?: number, limit?: number) → ReadResult- 读取文件内容。对于文本文件,内容按行偏移/限制分页(默认偏移 0,限制 500)。对于二进制文件,返回完整的原始
Uint8Array内容,并设置mimeType字段。文件缺失时,返回{ error: "File '/x' not found" }。
- 读取文件内容。对于文本文件,内容按行偏移/限制分页(默认偏移 0,限制 500)。对于二进制文件,返回完整的原始
-
readRaw(filePath: string) → ReadRawResult- 以原始
FileData形式读取文件内容。返回包含时间戳的完整文件数据。
- 以原始
-
grep(pattern: string, path?: string | null, glob?: string | null) → GrepResult- 在文件内容中搜索字面文本模式。二进制文件(根据 MIME 类型确定)被跳过。失败时,返回
{ error: "..." }。
- 在文件内容中搜索字面文本模式。二进制文件(根据 MIME 类型确定)被跳过。失败时,返回
-
glob(pattern: string, path?: string) → GlobResult- 返回匹配 glob 模式的文件作为
FileInfo条目。
- 返回匹配 glob 模式的文件作为
-
write(filePath: string, content: string) → WriteResult- 仅创建语义。冲突时,返回
{ error: "..." }。成功时,设置path,对于状态后端设置filesUpdate={...};外部后端应使用filesUpdate=null。
- 仅创建语义。冲突时,返回
-
edit(filePath: string, oldString: string, newString: string, replaceAll?: boolean) → EditResult- 除非
replaceAll=true,否则强制oldString唯一。如果未找到,返回错误。成功时包括occurrences。
- 除非
可选方法
uploadFiles(files: Array<[string, Uint8Array]>) → FileUploadResponse[]— 上传多个文件(用于沙盒后端)。downloadFiles(paths: string[]) → FileDownloadResponse[]— 下载多个文件(用于沙盒后端)。
结果类型
支持类型
FileInfo—path(必需),可选is_dir、size、modified_at。GrepMatch—path、line(1-indexed)、text。FileData— 带时间戳的文件内容。请参阅 FileData 格式。
沙盒扩展
SandboxBackendProtocolV2 用以下内容扩展了 BackendProtocolV2:
execute(command: string) → ExecuteResponse— 在沙盒中运行 Shell 命令。readonly id: string— 沙盒实例的唯一标识符。
将现有后端更新到 V2
迁移指南
迁移指南
Connect these docs to Claude, VSCode, and more via MCP for real-time answers.

