Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
36 changes: 30 additions & 6 deletions docs/cli/configuration/sandbox.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -34,14 +34,36 @@ Under the hood, Sandbox uses Seatbelt profiles on macOS, bubblewrap with seccomp
| **File writes** | Deny all except **CWD** (current working directory). Additional paths can be allowed. `denyWrite` overrides `allowWrite`. | `sandbox.filesystem.allowWrite`, `sandbox.filesystem.denyWrite` |
| **Network** | Deny all except `*.factory.ai` (always allowed by default). Additional domains must be explicitly allowed. | `sandbox.network.allowedDomains` |

## Sandbox modes

The `sandbox.mode` setting selects how isolation is applied:

- **`per-command`** (default) -- only Droid-initiated shell commands and tool operations are sandboxed.
- **`whole-process`** (Linux only) -- the entire Droid process is launched inside the OS sandbox, extending isolation to the main process, MCP stdio transports, and subagents.

## What's included

**Per-command sandbox mode** (default when enabled):
**Per-command sandbox mode** (`mode: "per-command"`, default when enabled):

- **File tools** (Read, Edit, Create, LS, Grep, Glob, ApplyPatch) -- `checkFileAccess()` before every operation, enforcing `denyRead` for reads and `allowWrite`/`denyWrite` for writes
- **Execute tool** -- shell commands wrapped in OS sandbox (Seatbelt/bubblewrap) with network routed through SRT's filtering proxy for domain-level control
- **FetchUrl** -- `checkNetworkAccess()` against `allowedDomains`
- **Note** -- main Droid process, MCPs and subagent are not isolated yet.
- **MCP tools** -- fail closed (denied) under an active sandbox. MCP tool behavior is opaque (a server can read/write files, reach the network, etc.) and the protocol exposes no per-tool effect metadata, so MCP tools cannot be mapped to an enforceable sandbox policy and are blocked by the default-deny tool policy below.
- **Note** -- the main Droid process and subagents are not isolated in this mode. Use `whole-process` mode to isolate them.

**Whole-process sandbox mode** (`mode: "whole-process"`, Linux only):

- At startup the entire Droid process is re-executed inside the OS sandbox, so the main process, MCP stdio transports, and subagent lifecycles all run within the configured filesystem and network boundaries
- Network requests made directly by the Droid process (not only those from the Execute tool) are filtered against `allowedDomains`, with interactive domain prompts in TUI mode
- **Fails closed** -- if the secure runtime cannot be established at startup (unsupported platform, missing sandbox support, or a failed isolation check), Droid refuses to start rather than running unsandboxed
- Default access policies, filesystem and network configuration, and allow-always persistence behave the same as per-command mode

**Tool policy (default-deny):**

- Every registered tool declares sandbox side-effect metadata (`filesystem-read`, `filesystem-write`, `network`, `process`, `external-service`, `persistent-settings`)
- When sandbox is enabled, a tool is allowed only if every declared side effect maps to a sandbox policy handler (file access, network, or per-command Execute). Tools with an unannotated, unknown, or unhandled side effect are denied
- Tools whose effects cannot be enforced locally -- such as MCP tools and connectors (`external-service`) -- have no handler and therefore fail closed
- Tool-policy denials are **non-promptable**: user approval cannot bypass missing policy coverage, and these denials are not configurable via `allowWrite`/`allowedDomains`

**Interactive permission prompts (TUI mode):**

Expand Down Expand Up @@ -80,19 +102,21 @@ Under the hood, Sandbox uses Seatbelt profiles on macOS, bubblewrap with seccomp
{
"sandbox": {
"enabled": true,
// Isolation scope: "per-command" (default) or "whole-process" (Linux only)
"mode": "per-command",
"filesystem": {
// Additional writable paths beyond CWD (which is always writable)
"allowWrite": ["/tmp/build-output", "~/.config"],
// Deny writes to specific subpaths even if parent is in allowWrite
"denyWrite": ["/tmp/build-output/cache/locks", "~/.config/secrets"],
// Block reads to specific paths (everything else is readable)
"denyRead": ["~/.aws/credentials", "~/.ssh/id_rsa"],
"denyRead": ["~/.aws/credentials", "~/.ssh/id_rsa"]
},
"network": {
// Only these domains are reachable (*.factory.ai always included)
"allowedDomains": ["github.com", "*.npmjs.org"],
},
},
"allowedDomains": ["github.com", "*.npmjs.org"]
}
}
}
```

Expand Down
36 changes: 30 additions & 6 deletions docs/jp/cli/configuration/sandbox.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -34,14 +34,36 @@ OSレベルのサンドボックス化では、ユーザーがDroidのファイ
| **ファイル書き込み** | **CWD**(現在の作業ディレクトリ)以外はすべて拒否。追加のパスは許可できます。`denyWrite` は `allowWrite` より優先されます。 | `sandbox.filesystem.allowWrite`, `sandbox.filesystem.denyWrite` |
| **ネットワーク** | `*.factory.ai`(デフォルトで常に許可)以外はすべて拒否。追加のドメインは明示的に許可する必要があります。 | `sandbox.network.allowedDomains` |

## サンドボックスモード

`sandbox.mode` 設定で、分離の適用方法を選択します:

- **`per-command`**(デフォルト) -- Droid が開始するシェルコマンドとツール操作のみがサンドボックス化されます。
- **`whole-process`**(Linux のみ) -- Droid プロセス全体が OS サンドボックス内で起動され、メインプロセス、MCP の stdio トランスポート、サブエージェントにまで分離が拡張されます。

## 含まれる機能

**コマンド単位のサンドボックスモード**(有効時のデフォルト):
**コマンド単位のサンドボックスモード**(`mode: "per-command"`、有効時のデフォルト):

- **ファイルツール**(Read、Edit、Create、LS、Grep、Glob、ApplyPatch) -- すべての操作の前に `checkFileAccess()` を実行し、読み取りには `denyRead`、書き込みには `allowWrite` / `denyWrite` を適用
- **Execute ツール** -- シェルコマンドを OS サンドボックス(Seatbelt / bubblewrap)でラップし、ネットワークはドメインレベル制御のために SRT のフィルタリングプロキシ経由でルーティング
- **FetchUrl** -- `allowedDomains` に対して `checkNetworkAccess()` を実行
- **注記** -- メインのDroidプロセス、MCP、サブエージェントはまだ分離されていません。
- **MCP ツール** -- サンドボックス有効時は fail closed(拒否)になります。MCP ツールの挙動は不透明で(サーバーがファイルの読み書きやネットワークアクセスなどを行う可能性があります)、プロトコルはツールごとの効果メタデータを公開しないため、強制可能なサンドボックスポリシーにマッピングできず、後述のデフォルト拒否ツールポリシーによってブロックされます。
- **注記** -- このモードではメインのDroidプロセスとサブエージェントは分離されません。これらを分離するには `whole-process` モードを使用してください。

**プロセス全体のサンドボックスモード**(`mode: "whole-process"`、Linux のみ):

- 起動時に Droid プロセス全体が OS サンドボックス内で再実行されるため、メインプロセス、MCP の stdio トランスポート、サブエージェントのライフサイクルがすべて、設定されたファイルシステムおよびネットワーク境界の範囲内で実行されます
- Droid プロセスが直接行うネットワークリクエスト(Execute ツールからのものだけでなく)も `allowedDomains` に対してフィルタリングされ、TUI モードでは対話型のドメインプロンプトが表示されます
- **Fails closed** -- 起動時にセキュアなランタイムを確立できない場合(非対応プラットフォーム、サンドボックスサポートの欠如、または分離チェックの失敗)、Droid はサンドボックスなしで実行するのではなく起動を拒否します
- デフォルトのアクセスポリシー、ファイルシステムおよびネットワーク設定、「常に許可」の永続化は、コマンド単位モードと同じ挙動です

**ツールポリシー(デフォルト拒否):**

- 登録されたすべてのツールは、サンドボックスの副作用メタデータ(`filesystem-read`、`filesystem-write`、`network`、`process`、`external-service`、`persistent-settings`)を宣言します
- サンドボックス有効時、宣言されたすべての副作用がサンドボックスポリシーハンドラ(ファイルアクセス、ネットワーク、またはコマンド単位の Execute)にマッピングされる場合にのみ、ツールが許可されます。注釈のない副作用、不明な副作用、または未処理の副作用を持つツールは拒否されます
- ローカルで強制できない効果を持つツール(MCP ツールやコネクタ(`external-service`)など)はハンドラを持たないため、fail closed になります
- ツールポリシーによる拒否は**プロンプト不可**です。ユーザーの承認でポリシーカバレッジの欠如を回避することはできず、これらの拒否は `allowWrite` / `allowedDomains` では設定できません

**対話型の権限プロンプト(TUIモード):**

Expand Down Expand Up @@ -80,19 +102,21 @@ OSレベルのサンドボックス化では、ユーザーがDroidのファイ
{
"sandbox": {
"enabled": true,
// 分離のスコープ: "per-command"(デフォルト)または "whole-process"(Linux のみ)
"mode": "per-command",
"filesystem": {
// CWD(常に書き込み可)に加えて書き込み可能にするパス
"allowWrite": ["/tmp/build-output", "~/.config"],
// 親が allowWrite にあっても特定のサブパスへの書き込みを拒否
"denyWrite": ["/tmp/build-output/cache/locks", "~/.config/secrets"],
// 特定のパスへの読み取りをブロック(それ以外は読み取り可)
"denyRead": ["~/.aws/credentials", "~/.ssh/id_rsa"],
"denyRead": ["~/.aws/credentials", "~/.ssh/id_rsa"]
},
"network": {
// 到達可能なドメインはこれらのみ(*.factory.ai は常に含まれる)
"allowedDomains": ["github.com", "*.npmjs.org"],
},
},
"allowedDomains": ["github.com", "*.npmjs.org"]
}
}
}
```

Expand Down
Loading