Skip to content

OpenClaw 沙盒是可选功能,通过 agents.defaults.sandboxagents.list[].sandbox 控制工具是否在隔离环境执行。支持 Docker(默认)、SSH、OpenShell 三种后端。主模式 off/non-main/all,作用域 session/agent/shared,工作区访问 none/ro/rw。配置时需注意 Docker-out-of-Docker 路径映射限制、默认网络无出口、setupCommand 常见失败原因。使用 openclaw sandbox explain 检查当前有效配置。

OpenClaw 沙盒配置指南

OpenClaw 允许将 工具执行放到沙盒后端,减小出错时的爆炸半径。这是可选功能,由 agents.defaults.sandbox(全局)或 agents.list[].sandbox(单 agent)控制。沙盒关闭时,工具直接运行在宿主机。Gateway 始终在宿主机运行,工具执行在启用沙盒后才进入隔离环境。

这不是完美的安全边界,但当模型做出蠢事时,它能实质性地限制文件系统和进程的访问范围。

哪些内容被沙盒化

  • 工具执行(execreadwriteeditapply_patchprocess 等)。
  • 可选沙盒浏览器:agents.defaults.sandbox.browser
    • 默认自动启动(确保 CDP 可达),可通过 autoStartautoStartTimeoutMs 控制。
    • 默认使用专用 Docker 网络 openclaw-sandbox-browser,可用 browser.network 覆盖。
    • cdpSourceRange 可限制浏览器 CDP 入口的 CIDR 白名单。
    • noVNC 观察访问默认密码保护,OpenClaw 生成短生命期 token URL,密码在 URL fragment 中。
    • allowHostControl 允许沙盒会话显式控制宿主机浏览器。
    • 对于 target: "custom",可用 allowedControlUrlsallowedControlHostsallowedControlPorts 做白名单。

不沙盒化的内容:

  • Gateway 进程本身。
  • 任何通过 tools.elevated 明确允许在宿主机运行的工具。
    • Elevated exec 绕过沙盒,使用配置的 escapePath(默认 gateway,目标为 node 时用 node)。
    • 如果沙盒已关闭,tools.elevated 不改变执行方式(已在宿主机)。
  • 参见 Elevated Mode

模式:控制何时沙盒化

agents.defaults.sandbox.mode 取值:

  • "off":不使用沙盒。
  • "non-main"(默认你想让常规聊天留在宿主机时推荐):仅沙盒化 非主会话。注意判断依据是 session.mainKey(默认 "main"),而非 agent id。群组/频道会话用各自的 key,所以视为非主会话而被沙盒化。
  • "all":每个会话都进入沙盒。

作用域:控制创建多少容器

agents.defaults.sandbox.scope 取值:

  • "session"(默认):每个会话一个容器。
  • "agent":每个 agent 一个容器。
  • "shared":所有沙盒会话共享一个容器。

后端:选择沙盒运行时

agents.defaults.sandbox.backend 取值:

  • "docker"(沙盒开启时的默认值):本地 Docker 后端。
  • "ssh":通用 SSH 远程沙盒。
  • "openshell":OpenShell 托管沙盒。

SSH 专有配置在 agents.defaults.sandbox.ssh,OpenShell 专有配置在 plugins.entries.openshell.config

后端对比表

DockerSSHOpenShell
运行位置本地容器任意 SSH 可达主机OpenShell 托管沙盒
设置方式scripts/sandbox-setup.shSSH 密钥 + 目标主机启用 OpenShell 插件
工作区模型绑定挂载或复制远程权威(首次同步)mirrorremote
网络控制docker.network(默认无)取决于远程主机取决于 OpenShell
浏览器沙盒支持不支持暂不支持
绑定挂载docker.bindsN/AN/A
最适合本地开发、完全隔离把执行放到远程主机托管远程沙盒,支持可选双向同步

Docker 后端

沙盒默认关闭。开启沙盒且未选后端时自动使用 Docker。它通过 Docker 守护进程 socket(/var/run/docker.sock)在本地执行工具和沙盒浏览器。容器隔离取决于 Docker 命名空间。

要将宿主机 GPU 暴露给 Docker 沙盒,设置 agents.defaults.sandbox.docker.gpus(或每个 agent 的 sandbox.docker.gpus),值传递给 Docker 的 --gpus 参数,如 "all""device=GPU-uuid",需要宿主机安装 NVIDIA Container Toolkit 等兼容运行时。

WARNING

Docker-out-of-Docker(DooD)约束

如果 OpenClaw Gateway 本身运行在 Docker 容器中,它会通过宿主 Docker socket 管理同级别的沙盒容器(DooD)。此时存在路径映射约束:

  • 配置必须用宿主机路径openclaw.json 中的 workspace 配置必须写宿主机绝对路径(例如 /home/user/.openclaw/workspaces),不是 Gateway 容器内的路径。OpenClaw 请求 Docker 创建沙盒时,daemon 以宿主机 OS 命名空间评估路径。
  • FS bridge 必须镜像:OpenClaw Gateway 原生进程也向 workspace 目录写入心跳和 bridge 文件。由于 Gateway 在其容器环境中解析同一个字符串(宿主机路径),Gateway 部署必须包含相同的卷映射,即 -v /home/user/.openclaw:/home/user/.openclaw
  • Codex 代码模式:当 OpenClaw 沙盒活跃时,Codex 会禁用自身的 app-server 原生 Code Mode、用户 MCP 服务器和 app 后端插件执行,因为这些原生功能由 Gateway-host app-server 进程运行而非 OpenClaw 沙盒。普通 exec/process 工具不可用时,通过 sandbox_execsandbox_process 等沙盒工具暴露 Shell 访问。不要将宿主机 Docker socket 挂载到 agent 沙盒容器或自定义 Codex 沙盒中。

Ubuntu/AppArmor 问题:当你故意在没有启用 OpenClaw 沙盒的情况下运行原生 Codex workspace-write,且服务用户不允许创建非特权用户命名空间时,workspace-write 可能失败。当 Docker 沙盒出站被禁用(network: "none",默认),Codex 也需要非特权网络命名空间。常见错误:bwrap: setting up uid map: Permission deniedbwrap: loopback: Failed RTM_NEWADDR: Operation not permitted。运行 openclaw doctor,如果报告 Codex bwrap 命名空间探测失败,建议使用 AppArmor profile 授予所需命名空间。kernel.apparmor_restrict_unprivileged_userns=0 是全局回退,有安全权衡,仅在可接受该主机姿态时使用。

如果你内部映射路径时没用绝对宿主机路径一致,OpenClaw 原生会抛出 EACCES 权限错误,因为容器环境内无法找到该完全限定路径字符串。

SSH 后端

当你想在任意 SSH 可达主机上沙盒化 exec、文件工具和媒体读取时,使用 backend: "ssh"

json5
{
  agents: {
    defaults: {
      sandbox: {
        mode: "all",
        backend: "ssh",
        scope: "session",
        workspaceAccess: "rw",
        ssh: {
          target: "user@gateway-host:22",
          workspaceRoot: "/tmp/openclaw-sandboxes",
          strictHostKeyChecking: true,
          updateHostKeys: true,
          identityFile: "~/.ssh/id_ed25519",
          certificateFile: "~/.ssh/id_ed25519-cert.pub",
          knownHostsFile: "~/.ssh/known_hosts",
          // identityData / certificateData / knownHostsData 替代本地文件
        },
      },
    },
  },
}

工作原理

- OpenClaw 在 `sandbox.ssh.workspaceRoot` 下创建每个作用域的远程根目录。
- 首次使用(创建或重建后),OpenClaw 从本地工作区一次性同步到远程。
- 之后 `exec`、`read`、`write`、`edit`、`apply_patch`、媒体读取、入站媒体暂存都直接通过 SSH 操作远程工作区。
- OpenClaw **不**自动将远程变更同步回本地。

认证材料

- `identityFile`, `certificateFile`, `knownHostsFile`:使用本地文件,经 OpenSSH 配置传递。
- `identityData`, `certificateData`, `knownHostsData`:使用内联字符串或 SecretRef。OpenClaw 通过 secrets 运行时解析,写入临时文件(权限 `0600`),SSH 会话结束时删除。
- 如果同一项同时设置了 `*File` 和 `*Data`,对于该 SSH 会话,`*Data` 优先。

远程权威模型的后果

这是**远程权威**模型。初始同步后,远程 SSH 工作区成为真正的沙盒状态。

- 同步之后在 OpenClaw 外部对宿主机做的编辑不会在远程可见,除非重建沙盒。
- `openclaw sandbox recreate` 删除该作用域的远程根目录,下次使用时重新从本地同步。
- SSH 后端不支持浏览器沙盒。
- `sandbox.docker.*` 设置不适用。

OpenShell 后端

使用 backend: "openshell" 在 OpenShell 托管的远程环境沙盒化工具。完整设置、配置参考和工作区模式比较见 OpenShell 页面

OpenShell 复用 SSH 后端的核心传输和远程文件系统桥,增加了 OpenShell 生命周期(sandbox create/get/deletesandbox ssh-config)和可选的 mirror 工作区模式。

json5
{
  agents: {
    defaults: {
      sandbox: {
        mode: "all",
        backend: "openshell",
        scope: "session",
        workspaceAccess: "rw",
      },
    },
  },
  plugins: {
    entries: {
      openshell: {
        enabled: true,
        config: {
          from: "openclaw",
          mode: "remote", // mirror | remote
          remoteWorkspaceDir: "/sandbox",
          remoteAgentWorkspaceDir: "/agent",
        },
      },
    },
  },
}

OpenShell 模式:

  • mirror(默认):本地工作区为权威。OpenClaw 在 exec 前同步本地文件到 OpenShell,exec 后同步回来。
  • remote:沙盒创建后 OpenShell 工作区为权威。OpenClaw 从本地工作区一次性同步,之后文件工具和 exec 直接操作远程沙盒,不同步回来。

远程传输细节

- OpenClaw 调用 `openshell sandbox ssh-config <name>` 获取沙盒 SSH 配置。
- Core 将 SSH 配置写入临时文件,打开 SSH 会话,复用与 `backend: "ssh"` 相同的远程文件系统桥。
- 在 `mirror` 模式下,生命周期的区别是 exec 前后同步。

当前 OpenShell 限制

- 尚不支持沙盒浏览器
- `sandbox.docker.binds` 在 OpenShell 后端不适用
- `sandbox.docker.*` 仍然只对 Docker 后端有效

工作区模式

OpenShell 的两种工作区模型。

  • mirror(本地权威):设置 plugins.entries.openshell.config.mode: "mirror"。行为:exec 前本地→远程同步,exec 后远程→本地同步。文件工具通过沙盒桥操作,但本地工作区在轮次之间保持权威。适用场景:你在 OpenClaw 外部编辑文件并希望自动体现在沙盒中;希望 OpenShell 沙盒尽量像 Docker 后端;希望宿主机工作区在每次 exec 后反映沙盒写入。代价:每次 exec 前后额外同步。
  • remote(OpenShell 权威):设置 mode: "remote"。行为:沙盒首次创建时从本地工作区一次性同步,之后 execreadwriteeditapply_patch 直接操作远程 OpenShell 工作区。OpenClaw 自动将远程变更同步回本地。提示时的媒体读取仍通过沙盒桥工作。重要后果:如果在同步后你在宿主机编辑文件,远程沙盒不会自动看到;沙盒重建时,远程工作区重新从本地同步。适用场景:沙盒主要存在于远程 OpenShell 侧;希望降低每轮同步开销;不希望本地编辑悄悄覆盖远程状态。

选择 mirror 如果你把沙盒看作临时执行环境,选择 remote 如果你把沙盒看作真正的工作区。

OpenShell 生命周期

OpenShell 沙盒仍通过常规沙盒生命周期管理:

  • openclaw sandbox list 显示 OpenShell 运行时及 Docker 运行时。
  • openclaw sandbox recreate 删除当前运行时,下次使用时重新创建。
  • prune 逻辑也感知后端。

对于 remote 模式,recreate 尤其重要:它删除该作用域的远程权威工作区,下次使用时从本地重新同步。对于 mirror 模式,recreate 主要重置远程执行环境(因为本地工作区始终权威)。

工作区访问

agents.defaults.sandbox.workspaceAccess 控制沙盒能看到的工作区内容:

  • "none"(默认):沙盒工作区为 ~/.openclaw/sandboxes
  • "ro":将 agent 工作区只读挂载到容器内 /agent(禁用 write/edit/apply_patch)。
  • "rw":将 agent 工作区读写挂载到 /workspace

使用 OpenShell 后端时,mirror 模式仍以本地工作区为 exec 轮次间的权威;remote 模式以远程工作区为权威(初始同步后)。workspaceAccess 的只读/无限制设置仍然生效。

入站媒体会被复制到沙盒工作区的 media/inbound/*

技能须知read 工具以沙盒为根。workspaceAccess: "none" 时,OpenClaw 把符合条件的技能镜像到沙盒工作区的 .../skills 下以便读取。"rw" 时,工作区技能可从 /workspace/skills 读取。

自定义绑定挂载

agents.defaults.sandbox.docker.binds:将宿主机目录挂载到容器。格式 host:container:mode(例如 "/home/user/source:/source:rw")。

全局和 per-agent 的挂载会合并(不替换)。在 scope: "shared" 下,per-agent 挂载被忽略。

agents.defaults.sandbox.browser.binds:仅挂载到沙盒浏览器容器。设置后(含 [])替换浏览器容器中默认的 agents.defaults.sandbox.docker.binds;未设置时回退到 docker.binds(向后兼容)。

示例(只读源码 + 额外数据目录):

json5
{
  agents: {
    defaults: {
      sandbox: {
        docker: {
          binds: ["/home/user/source:/source:ro", "/var/data/myapp:/data:ro"],
        },
      },
    },
    list: [
      {
        id: "build",
        sandbox: {
          docker: {
            binds: ["/mnt/cache:/cache:rw"],
          },
        },
      },
    ],
  },
}

WARNING

绑定挂载安全

  • 挂载绕过沙盒文件系统,直接暴露宿主机路径(:ro:rw 模式)。
  • OpenClaw 阻止危险绑定源,例如 docker.sock/etc/proc/sys/dev 及可能暴露它们的父挂载。
  • 同时阻止常见家目录凭据根:~/.aws~/.cargo~/.config~/.docker~/.gnupg~/.netrc~/.npm~/.ssh
  • 绑定验证不是简单字符串匹配。OpenClaw 规范化源路径,再通过最深已存在的祖先路径解析,然后重新检查被阻止路径和允许根目录。这意味着即使最终叶子不存在,符号链接父目录溢出也会被拒绝。
  • 允许的源根目录也以相同方式规范化,因此看起来在符号链接解析前允许的路径也会被拒绝。
  • 敏感挂载(secrets、SSH 密钥、服务凭据)应使用 :ro,除非绝对必要。
  • 可搭配 workspaceAccess: "ro" 使用(只读工作区),挂载模式独立。
  • 参见 Sandbox vs Tool Policy vs Elevated 了解挂载与工具策略、elevated exec 的交互。

镜像与设置

默认 Docker 镜像:openclaw-sandbox:bookworm-slim

INFO

源码检出 vs npm 安装

scripts/sandbox-setup.shscripts/sandbox-common-setup.shscripts/sandbox-browser-setup.sh 仅在从 源码仓库 运行时可用。它们不包含在 npm 包中。

如果你通过 npm install -g openclaw 安装,请直接使用下面内联的 docker build 命令。

构建默认镜像

从源码检出:
```bash
scripts/sandbox-setup.sh
```
从 npm 安装(不需要源码):
```bash
docker build -t openclaw-sandbox:bookworm-slim - <<'DOCKERFILE'
FROM debian:bookworm-slim
ENV DEBIAN_FRONTEND=noninteractive
RUN apt-get update && apt-get install -y --no-install-recommends \
  bash ca-certificates curl git jq python3 ripgrep \
  && rm -rf /var/lib/apt/lists/*
RUN useradd --create-home --shell /bin/bash sandbox
USER sandbox
WORKDIR /home/sandbox
CMD ["sleep", "infinity"]
DOCKERFILE
```
默认镜像**不包含 Node**。如果技能需要 Node 或其他运行时,要么烘焙自定义镜像,要么通过 `sandbox.docker.setupCommand` 安装(需要网络出口 + 可写根目录 + root 用户)。

OpenClaw 不会在 `openclaw-sandbox:bookworm-slim` 缺失时静默替换为 `debian:bookworm-slim`。目标为此默认镜像的沙盒运行会快速失败并提示构建指令,直到你构建它为止,因为捆绑镜像携带了沙盒写/编辑辅助工具所需的 `python3`。

可选:构建通用镜像

如需更完整的沙盒镜像(含 `curl`、`jq`、`nodejs`、`python3`、`git`):

从源码检出:
```bash
scripts/sandbox-common-setup.sh
```
从 npm 安装:先构建默认镜像(如上),然后使用仓库中的 `scripts/docker/sandbox/Dockerfile.common` 在其基础上构建。

然后设置 `agents.defaults.sandbox.docker.image` 为 `openclaw-sandbox-common:bookworm-slim`。

可选:构建沙盒浏览器镜像

从源码检出:
```bash
scripts/sandbox-browser-setup.sh
```
从 npm 安装:使用仓库中的 `scripts/docker/sandbox/Dockerfile.browser` 构建。

默认情况下,Docker 沙盒容器无网络。可通过 agents.defaults.sandbox.docker.network 覆盖。

沙盒浏览器 Chromium 默认参数

捆绑的沙盒浏览器镜像对容器化工作负载应用保守的 Chromium 启动默认值:
- `--remote-debugging-address=127.0.0.1`
- `--remote-debugging-port=<从 OPENCLAW_BROWSER_CDP_PORT 派生>`
- `--user-data-dir=${HOME}/.chrome`
- `--no-first-run`、`--no-default-browser-check`
- `--disable-3d-apis`、`--disable-gpu`、`--disable-dev-shm-usage`
- `--disable-background-networking`、`--disable-extensions`
- `--disable-features=TranslateUI`、`--disable-breakpad`、`--disable-crash-reporter`
- `--disable-software-rasterizer`、`--no-zygote`
- `--metrics-recording-only`、`--renderer-process-limit=2`
- 当 `noSandbox` 启用时使用 `--no-sandbox`。
- 图形硬编码标记(`--disable-3d-apis`、`--disable-software-rasterizer`、`--disable-gpu`)是可选的,在容器缺少 GPU 支持时有用。设置 `OPENCLAW_BROWSER_DISABLE_GRAPHICS_FLAGS=0` 如果你的工作负载需要 WebGL 等。
- `--disable-extensions` 默认启用,可设置 `OPENCLAW_BROWSER_DISABLE_EXTENSIONS=0` 关闭。
- `--renderer-process-limit=2` 由 `OPENCLAW_BROWSER_RENDERER_PROCESS_LIMIT=<N>` 控制,`0` 则保留 Chromium 默认。

如果需要不同运行时配置,使用自定义浏览器镜像并提供自己的入口点。对本地(非容器)Chromium 配置,使用 `browser.extraArgs` 追加启动标志。

网络安全默认值

- `network: "host"` 被阻止。
- `network: "container:&lt;id&gt;"` 默认被阻止(命名空间加入风险)。
- 应急覆盖:`agents.defaults.sandbox.docker.dangerouslyAllowContainerNamespaceJoin: true`。

Docker 安装和容器化 Gateway 部署见 Docker。对于 Docker Gateway 部署,scripts/docker/setup.sh 可引导沙盒配置。设置 OPENCLAW_SANDBOX=1(或 true/yes/on)启用该路径。可用 OPENCLAW_DOCKER_SOCKET 覆盖 socket 位置。完整设置与 env 参考见 Docker

setupCommand:一次性容器设置

setupCommand 在沙盒容器创建后运行一次(不是每次运行),通过 sh -lc 在容器内执行。

路径:

  • 全局:agents.defaults.sandbox.docker.setupCommand
  • 每个 agent:agents.list[].sandbox.docker.setupCommand

常见陷阱

- 默认 `docker.network` 为 `"none"`(无出口),包安装会失败。
- `docker.network: "container:&lt;id&gt;"` 需要设置 `dangerouslyAllowContainerNamespaceJoin: true`,仅应急使用。
- `readOnlyRoot: true` 阻止写入;应设为 `readOnlyRoot: false` 或烘焙自定义镜像。
- `user` 必须为 root 才能安装包(省略或设为 `"0:0"`)。
- 沙盒 exec **不继承**宿主机的 `process.env`。技能 API key 应通过 `agents.defaults.sandbox.docker.env` 或自定义镜像注入。
- `docker.env` 中的值作为显式 Docker 容器环境变量传递,任何有 Docker daemon 访问权限的人可通过 `docker inspect` 查看。如果此元数据暴露不可接受,请使用自定义镜像、挂载的 secret 文件或其他密钥交付路径。

工具策略与逃生出口

工具允许/拒绝策略在沙盒规则前仍然有效。如果工具被全局或 per-agent 拒绝,沙盒无法恢复它。

tools.elevated 是明确的逃生出口:在宿主机上运行 exec(默认使用 gateway,目标为 node 时用 node)。/exec 指令仅对授权发送者生效并跨会话持久化;要完全禁用 exec,使用工具策略拒绝(见 Sandbox vs Tool Policy vs Elevated)。

调试:

  • 使用 openclaw sandbox explain 检查生效的沙盒模式、工具策略及修复配置键。
  • 参见 Sandbox vs Tool Policy vs Elevated 了解“为什么被阻止”的思维模型。

多 Agent 覆盖

每个 agent 可覆盖 sandbox + tools:agents.list[].sandboxagents.list[].tools 以及 agents.list[].tools.sandbox.tools(沙盒工具策略)。参见 Multi-Agent Sandbox & Tools 了解优先级。

最简启用示例

json5
{
  agents: {
    defaults: {
      sandbox: {
        mode: "non-main",
        scope: "session",
        workspaceAccess: "none",
      },
    },
  },
}

常见问题

沙盒模式下工具为什么无法联网?

默认 Docker 沙盒容器无网络(network: "none")。如需联网,设置 agents.defaults.sandbox.docker.networkbridgehost 或其他自定义网络。注意 network: "host" 默认被阻止。另外,如果使用 setupCommand 安装包,也需要网络出口。

SSH 沙盒后端需要什么配置?

需要配置 agents.defaults.sandbox.ssh.targetuser@host:port)、workspaceRoot(远程工作区根目录)、认证材料(identityFileidentityData 等),以及 strictHostKeyCheckingknownHostsFile 等。远程主机需运行 SSH 服务并允许密钥登录。首次使用时 OpenClaw 会从本地工作区同步一次,后续操作直接通过 SSH 执行。

如何检查当前沙盒配置和可能的问题?

运行 openclaw sandbox explain 查看当前生效的沙盒模式、作用域、后端、工具策略等信息。若遇到 Docker 沙盒容器启动失败(如 EACCES 权限错误),检查 DooD 路径映射是否正确(workspace 配置需用宿主机绝对路径,Gateway 容器需相同卷映射)。也可以运行 openclaw doctor 检查 AppArmor 命名空间等问题。

相关文档