Skip to content

Commit 531ce76

Browse files
authored
fix: pretty-print the sandbox config in the TUI/exec modes (#1376)
Now that #1373 simplified the sandbox config, we can print something much simpler in the TUI (and in `codex exec`) to summarize the sandbox config. Before: ![Screenshot 2025-06-24 at 5 45 52 PM](https://github.com/user-attachments/assets/b7633efb-a619-43e1-9abe-7bb0be2d0ec0) With this change: ![Screenshot 2025-06-24 at 5 46 44 PM](https://github.com/user-attachments/assets/8d099bdd-a429-4796-a08d-70931d984e4f) For reference, my `config.toml` contains: ``` [sandbox] mode = "workspace-write" writable_roots = ["/tmp", "/Users/mbolin/.pyenv/shims"] ``` Fixes #1248
1 parent 63363a5 commit 531ce76

File tree

8 files changed

+60
-14
lines changed

8 files changed

+60
-14
lines changed

codex-rs/common/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,3 +16,4 @@ serde = { version = "1", optional = true }
1616
# Separate feature so that `clap` is not a mandatory dependency.
1717
cli = ["clap", "toml", "serde"]
1818
elapsed = []
19+
sandbox_summary = []

codex-rs/common/src/lib.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,8 @@ mod config_override;
1212

1313
#[cfg(feature = "cli")]
1414
pub use config_override::CliConfigOverrides;
15+
16+
mod sandbox_summary;
17+
18+
#[cfg(feature = "sandbox_summary")]
19+
pub use sandbox_summary::summarize_sandbox_policy;
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
use codex_core::protocol::SandboxPolicy;
2+
3+
pub fn summarize_sandbox_policy(sandbox_policy: &SandboxPolicy) -> String {
4+
match sandbox_policy {
5+
SandboxPolicy::DangerFullAccess => "danger-full-access".to_string(),
6+
SandboxPolicy::ReadOnly => "read-only".to_string(),
7+
SandboxPolicy::WorkspaceWrite {
8+
writable_roots,
9+
network_access,
10+
} => {
11+
let mut summary = "workspace-write".to_string();
12+
if !writable_roots.is_empty() {
13+
summary.push_str(&format!(
14+
" [{}]",
15+
writable_roots
16+
.iter()
17+
.map(|p| p.to_string_lossy())
18+
.collect::<Vec<_>>()
19+
.join(", ")
20+
));
21+
}
22+
if *network_access {
23+
summary.push_str(" (network access enabled)");
24+
}
25+
summary
26+
}
27+
}
28+
}

codex-rs/core/src/protocol.rs

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -183,17 +183,8 @@ impl SandboxPolicy {
183183
/// the current working directory and the per-user tmp dir on macOS. It does
184184
/// not allow network access.
185185
pub fn new_workspace_write_policy() -> Self {
186-
let mut writable_roots = vec![];
187-
188-
// Also include the per-user tmp dir on macOS.
189-
if cfg!(target_os = "macos") {
190-
if let Some(tmpdir) = std::env::var_os("TMPDIR") {
191-
writable_roots.push(PathBuf::from(tmpdir));
192-
}
193-
}
194-
195186
SandboxPolicy::WorkspaceWrite {
196-
writable_roots,
187+
writable_roots: vec![],
197188
network_access: false,
198189
}
199190
}
@@ -229,6 +220,17 @@ impl SandboxPolicy {
229220
SandboxPolicy::WorkspaceWrite { writable_roots, .. } => {
230221
let mut roots = writable_roots.clone();
231222
roots.push(cwd.to_path_buf());
223+
224+
// Also include the per-user tmp dir on macOS.
225+
// Note this is added dynamically rather than storing it in
226+
// writable_roots because writable_roots contains only static
227+
// values deserialized from the config file.
228+
if cfg!(target_os = "macos") {
229+
if let Some(tmpdir) = std::env::var_os("TMPDIR") {
230+
roots.push(PathBuf::from(tmpdir));
231+
}
232+
}
233+
232234
roots
233235
}
234236
}

codex-rs/exec/Cargo.toml

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,11 @@ anyhow = "1"
1919
chrono = "0.4.40"
2020
clap = { version = "4", features = ["derive"] }
2121
codex-core = { path = "../core" }
22-
codex-common = { path = "../common", features = ["cli", "elapsed"] }
22+
codex-common = { path = "../common", features = [
23+
"cli",
24+
"elapsed",
25+
"sandbox_summary",
26+
] }
2327
codex-linux-sandbox = { path = "../linux-sandbox" }
2428
mcp-types = { path = "../mcp-types" }
2529
owo-colors = "4.2.0"

codex-rs/exec/src/event_processor.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
use codex_common::elapsed::format_elapsed;
2+
use codex_common::summarize_sandbox_policy;
23
use codex_core::WireApi;
34
use codex_core::config::Config;
45
use codex_core::model_supports_reasoning_summaries;
@@ -134,7 +135,7 @@ impl EventProcessor {
134135
("model", config.model.clone()),
135136
("provider", config.model_provider_id.clone()),
136137
("approval", format!("{:?}", config.approval_policy)),
137-
("sandbox", format!("{:?}", config.sandbox_policy)),
138+
("sandbox", summarize_sandbox_policy(&config.sandbox_policy)),
138139
];
139140
if config.model_provider.wire_api == WireApi::Responses
140141
&& model_supports_reasoning_summaries(&config.model)

codex-rs/tui/Cargo.toml

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,11 @@ base64 = "0.22.1"
2020
clap = { version = "4", features = ["derive"] }
2121
codex-ansi-escape = { path = "../ansi-escape" }
2222
codex-core = { path = "../core" }
23-
codex-common = { path = "../common", features = ["cli", "elapsed"] }
23+
codex-common = { path = "../common", features = [
24+
"cli",
25+
"elapsed",
26+
"sandbox_summary",
27+
] }
2428
codex-linux-sandbox = { path = "../linux-sandbox" }
2529
codex-login = { path = "../login" }
2630
color-eyre = "0.6.3"

codex-rs/tui/src/history_cell.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ use crate::text_formatting::format_and_truncate_tool_result;
66
use base64::Engine;
77
use codex_ansi_escape::ansi_escape_line;
88
use codex_common::elapsed::format_duration;
9+
use codex_common::summarize_sandbox_policy;
910
use codex_core::WireApi;
1011
use codex_core::config::Config;
1112
use codex_core::model_supports_reasoning_summaries;
@@ -152,7 +153,7 @@ impl HistoryCell {
152153
("model", config.model.clone()),
153154
("provider", config.model_provider_id.clone()),
154155
("approval", format!("{:?}", config.approval_policy)),
155-
("sandbox", format!("{:?}", config.sandbox_policy)),
156+
("sandbox", summarize_sandbox_policy(&config.sandbox_policy)),
156157
];
157158
if config.model_provider.wire_api == WireApi::Responses
158159
&& model_supports_reasoning_summaries(&config.model)

0 commit comments

Comments
 (0)