所属分卷:卷五「Anthropic Agent 设计研究」
建议前读:11. 子代理与任务系统 或 28. Direct Connect、Server 与 Upstream Proxy
agent 的 isolation 到底隔离了什么?是文件副本、运行目录、权限,还是整个会话身份?
Claude Code 的隔离不是一个单一开关,而是三层不同语义的组合:worktree 隔离工作副本,remote 隔离执行环境,cwd override 则只重定向本地文件与 shell 的默认工作目录。
这一章专门解释 AgentTool 里与隔离相关的执行路径:
isolation: "worktree"isolation: "remote"cwd
以及它们和 transcript、resume、cleanup 的关系。
worktree的目标是隔离文件修改,不是隔离上下文。remote的目标是把 agent 放进另一套远端运行环境,而且天然是 background 任务。cwdoverride 不是 worktree 的弱版本,它不会复制仓库,只会重定向本地执行目录。
- AgentTool 隔离分支:src/tools/AgentTool/AgentTool.tsx
- worktree 工具:src/utils/worktree.ts
- remote agent task:src/tasks/RemoteAgentTask/RemoteAgentTask.tsx
flowchart TD
A["AgentTool input"] --> B{"isolation"}
B -- none --> C{"cwd override?"}
B -- worktree --> D["createAgentWorktree"]
B -- remote --> E["teleportToRemote + registerRemoteAgentTask"]
C -- 否 --> F["沿用父 cwd"]
C -- 是 --> G["runWithCwdOverride"]
D --> H["在隔离副本中执行"]
H --> I{"是否有改动"}
I -- 无改动 --> J["removeAgentWorktree"]
I -- 有改动 --> K["保留 worktreePath/worktreeBranch"]
多 agent 一旦进入真实工程工作流,就会立刻遇到冲突问题:
- 两个 agent 同时写同一工作副本
- agent 的临时修改污染主线程
- 长任务需要更干净的执行环境
Anthropic 的回答不是“让 agent 小心一点”,而是把隔离作为一等执行参数。
createAgentWorktree() 和 hasWorktreeChanges() 体现了 worktree 路径的核心语义:
- 给 agent 一个独立工作副本
- 尽量复用主仓库的大目录与设置
- 完成后根据是否发生修改决定清理还是保留
尤其值得注意的是“有改动就保留、无改动就清理”的策略。它说明 Anthropic 不是把 worktree 当临时目录,而是把它当成可交付工作结果的载体。
src/utils/worktree.ts 不只支持 git worktree,还支持 hook-based worktree。文档上最值得记住的是:
- git 路径下系统能检测是否有改动,并自动清理
- hook-based 路径下系统更保守,往往倾向保留
这体现了一种 fail-closed 思路:检测不到可靠状态时,不主动删除用户可能需要的工作副本。
fork child 如果跑在 worktree 里,buildWorktreeNotice() 会明确告诉它:
- 上下文继承自父线程
- 文件路径要映射到新的 worktree root
- 编辑前要重新读文件
这说明 Anthropic 明确认定:上下文不是 live filesystem snapshot。即使给了 worktree,agent 也必须重新验证文件状态。
cwd 的语义更简单也更窄:
- 不复制 repo
- 不创建隔离 worktree
- 只是把本地执行的默认目录切换到某个绝对路径
在源码里它通过 runWithCwdOverride() 包裹执行。也就是说,cwd 更像一次局部执行重定向,而不是完整隔离策略。
remote 路径会走 teleportToRemote() 与 registerRemoteAgentTask()。这条路径有几个很清晰的产品假设:
- 远端执行天然不是同步 REPL 交互
- 它应该表现为 task
- 结果要通过 remote task notification 回来
因此 remote 不是“另一个本地模式”,而是一条明确的异步远端执行协议。
cleanupWorktreeIfNeeded() 其实体现了一个很强的不变量:
- 清理必须发生在通知之前
- 通知里要能告诉调用者 worktree 是否被保留
这说明 Anthropic 把“后续如何继续处理该 agent 的产物”视为 agent 结果的一部分,而不是外围 housekeeping。
resumeAgent.ts 会把 worktreePath 持久化在 metadata 里,并在恢复时检查该目录是否还存在。这说明:
- 隔离不是一次性 spawn 配置
- 它属于 agent 身份的一部分
如果 worktree 不存在,系统会回退到父 cwd,而不是直接崩溃。这体现了工程上更实用的恢复优先策略。
这一套设计说明 Anthropic 在谈“agent 隔离”时,并不是只关心 sandbox 安全。它更关心的是:
- 多 agent 协作时的工作副本冲突
- 长任务的结果可持续性
- resume 时的环境连续性
也就是说,隔离在这里既是安全问题,也是软件工程协作问题。
Claude Code 的 worktree、remote 和 cwd 三条路径展示了非常工程化的 agent 隔离观:不是抽象地说“把 agent 隔离起来”,而是明确区分工作副本隔离、执行环境隔离和工作目录重定向三种不同机制。