core: construct test permission profiles directly

This commit is contained in:
Michael Bolin
2026-05-15 10:58:53 -07:00
parent 6db97e90f3
commit 18c34e0760
2 changed files with 37 additions and 47 deletions

View File

@@ -5,13 +5,8 @@ use codex_network_proxy::NetworkDomainPermission;
use codex_protocol::models::ManagedFileSystemPermissions;
use codex_protocol::models::PermissionProfile;
use codex_protocol::permissions::NetworkSandboxPolicy;
use codex_protocol::protocol::SandboxPolicy;
use pretty_assertions::assert_eq;
fn permission_profile_for_sandbox_policy(sandbox_policy: &SandboxPolicy) -> PermissionProfile {
PermissionProfile::from_legacy_sandbox_policy(sandbox_policy)
}
fn domain_permissions(
entries: impl IntoIterator<Item = (&'static str, NetworkDomainPermissionToml)>,
) -> NetworkDomainPermissionsToml {
@@ -62,7 +57,7 @@ fn requirements_allowed_domains_are_a_baseline_for_user_allowlist() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_read_only_policy()),
&PermissionProfile::read_only(),
)
.expect("config should stay within the managed allowlist");
@@ -97,7 +92,7 @@ fn requirements_allowed_domains_do_not_override_user_denies_for_same_pattern() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&PermissionProfile::workspace_write(),
)
.expect("managed allowlist should not erase a user deny");
@@ -129,7 +124,7 @@ fn requirements_allowlist_expansion_keeps_user_entries_mutable() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&PermissionProfile::workspace_write(),
)
.expect("managed baseline should still allow user edits");
@@ -207,7 +202,7 @@ fn danger_full_access_keeps_managed_allowlist_and_denylist_fixed() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&PermissionProfile::Disabled,
)
.expect("yolo mode should pin the effective policy to the managed baseline");
@@ -241,7 +236,7 @@ fn managed_allowed_domains_only_disables_default_mode_allowlist_expansion() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&PermissionProfile::workspace_write(),
)
.expect("managed baseline should still load");
@@ -270,7 +265,7 @@ fn managed_allowed_domains_only_ignores_user_allowlist_and_hard_denies_misses()
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&PermissionProfile::workspace_write(),
)
.expect("managed-only allowlist should still load");
@@ -300,7 +295,7 @@ fn managed_allowed_domains_only_without_managed_allowlist_blocks_all_user_domain
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&PermissionProfile::workspace_write(),
)
.expect("managed-only mode should treat missing managed allowlist as empty");
@@ -324,7 +319,7 @@ fn managed_allowed_domains_only_blocks_all_user_domains_in_full_access_without_m
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&PermissionProfile::Disabled,
)
.expect("managed-only mode should treat missing managed allowlist as empty");
@@ -351,7 +346,7 @@ fn deny_only_requirements_do_not_create_allow_constraints_in_full_access() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&PermissionProfile::Disabled,
)
.expect("deny-only requirements should not constrain the allowlist");
@@ -384,7 +379,7 @@ fn allow_only_requirements_do_not_create_deny_constraints_in_full_access() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&PermissionProfile::Disabled,
)
.expect("allow-only requirements should not constrain the denylist");
@@ -417,7 +412,7 @@ fn requirements_denied_domains_are_a_baseline_for_default_mode() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&PermissionProfile::workspace_write(),
)
.expect("default mode should merge managed and user deny entries");
@@ -452,7 +447,7 @@ fn requirements_denylist_expansion_keeps_user_entries_mutable() {
let spec = NetworkProxySpec::from_config_and_constraints(
config,
Some(requirements),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&PermissionProfile::workspace_write(),
)
.expect("managed baseline should still allow user edits");

View File

@@ -172,10 +172,6 @@ use std::time::Duration as StdDuration;
mod guardian_tests;
fn permission_profile_for_sandbox_policy(sandbox_policy: &SandboxPolicy) -> PermissionProfile {
PermissionProfile::from_legacy_sandbox_policy(sandbox_policy)
}
struct InstructionsTestCase {
slug: &'static str,
expects_apply_patch_description: bool,
@@ -670,10 +666,11 @@ fn validated_network_policy_amendment_host_rejects_mismatch() {
#[tokio::test]
async fn start_managed_network_proxy_applies_execpolicy_network_rules() -> anyhow::Result<()> {
let permission_profile = PermissionProfile::workspace_write();
let spec = crate::config::NetworkProxySpec::from_config_and_constraints(
NetworkProxyConfig::default(),
/*requirements*/ None,
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&permission_profile,
)?;
let mut exec_policy = Policy::empty();
exec_policy.add_network_rule(
@@ -686,7 +683,7 @@ async fn start_managed_network_proxy_applies_execpolicy_network_rules() -> anyho
let (started_proxy, _) = Session::start_managed_network_proxy(
&spec,
&exec_policy,
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&permission_profile,
/*network_policy_decider*/ None,
/*blocked_request_observer*/ None,
/*managed_network_requirements_enabled*/ false,
@@ -705,6 +702,7 @@ async fn start_managed_network_proxy_applies_execpolicy_network_rules() -> anyho
#[tokio::test]
async fn start_managed_network_proxy_ignores_invalid_execpolicy_network_rules() -> anyhow::Result<()>
{
let permission_profile = PermissionProfile::workspace_write();
let spec = crate::config::NetworkProxySpec::from_config_and_constraints(
NetworkProxyConfig::default(),
Some(NetworkConstraints {
@@ -717,7 +715,7 @@ async fn start_managed_network_proxy_ignores_invalid_execpolicy_network_rules()
managed_allowed_domains_only: Some(true),
..Default::default()
}),
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&permission_profile,
)?;
let mut exec_policy = Policy::empty();
exec_policy.add_network_rule(
@@ -730,7 +728,7 @@ async fn start_managed_network_proxy_ignores_invalid_execpolicy_network_rules()
let (started_proxy, _) = Session::start_managed_network_proxy(
&spec,
&exec_policy,
&permission_profile_for_sandbox_policy(&SandboxPolicy::new_workspace_write_policy()),
&permission_profile,
/*network_policy_decider*/ None,
/*blocked_request_observer*/ None,
/*managed_network_requirements_enabled*/ false,
@@ -748,13 +746,14 @@ async fn start_managed_network_proxy_ignores_invalid_execpolicy_network_rules()
#[tokio::test]
async fn managed_network_proxy_decider_survives_full_access_start() -> anyhow::Result<()> {
let full_access_permission_profile = PermissionProfile::Disabled;
let spec = crate::config::NetworkProxySpec::from_config_and_constraints(
NetworkProxyConfig::default(),
Some(NetworkConstraints {
enabled: Some(true),
..Default::default()
}),
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&full_access_permission_profile,
)?;
let exec_policy = Policy::empty();
let decider_calls = Arc::new(std::sync::atomic::AtomicUsize::new(0));
@@ -769,7 +768,7 @@ async fn managed_network_proxy_decider_survives_full_access_start() -> anyhow::R
let (started_proxy, _) = Session::start_managed_network_proxy(
&spec,
&exec_policy,
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&full_access_permission_profile,
Some(network_policy_decider),
/*blocked_request_observer*/ None,
/*managed_network_requirements_enabled*/ true,
@@ -777,9 +776,7 @@ async fn managed_network_proxy_decider_survives_full_access_start() -> anyhow::R
)
.await?;
let spec = spec.recompute_for_permission_profile(&permission_profile_for_sandbox_policy(
&SandboxPolicy::new_workspace_write_policy(),
))?;
let spec = spec.recompute_for_permission_profile(&PermissionProfile::workspace_write())?;
spec.apply_to_started_proxy(&started_proxy).await?;
let current_cfg = started_proxy.proxy().current_cfg().await?;
assert_eq!(current_cfg.network.allowed_domains(), None);
@@ -818,6 +815,7 @@ async fn managed_network_proxy_decider_survives_full_access_start() -> anyhow::R
#[tokio::test]
async fn new_turn_refreshes_managed_network_proxy_for_sandbox_change() -> anyhow::Result<()> {
let (mut session, _turn_context) = make_session_and_context().await;
let initial_permission_profile = PermissionProfile::workspace_write();
let initial_policy = SandboxPolicy::new_workspace_write_policy();
let mut network_config = NetworkProxyConfig::default();
@@ -836,12 +834,12 @@ async fn new_turn_refreshes_managed_network_proxy_for_sandbox_change() -> anyhow
let spec = crate::config::NetworkProxySpec::from_config_and_constraints(
network_config,
Some(requirements),
&permission_profile_for_sandbox_policy(&initial_policy),
&initial_permission_profile,
)?;
let (started_proxy, _) = Session::start_managed_network_proxy(
&spec,
&Policy::empty(),
&permission_profile_for_sandbox_policy(&initial_policy),
&initial_permission_profile,
/*network_policy_decider*/ None,
/*blocked_request_observer*/ None,
/*managed_network_requirements_enabled*/ false,
@@ -870,9 +868,7 @@ async fn new_turn_refreshes_managed_network_proxy_for_sandbox_change() -> anyhow
state.session_configuration.original_config_do_not_use = Arc::new(config);
state
.session_configuration
.set_permission_profile_for_tests(PermissionProfile::from_legacy_sandbox_policy(
&initial_policy,
))
.set_permission_profile_for_tests(initial_permission_profile)
.expect("test setup should allow permission profile");
}
session.services.network_proxy = Some(started_proxy);
@@ -913,7 +909,7 @@ async fn danger_full_access_turns_do_not_expose_managed_network_proxy() -> anyho
enabled: Some(true),
..Default::default()
}),
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&PermissionProfile::Disabled,
)?;
let session = make_session_with_config(move |config| {
@@ -979,7 +975,7 @@ async fn danger_full_access_tool_attempts_do_not_enforce_managed_network() -> an
enabled: Some(true),
..Default::default()
}),
&permission_profile_for_sandbox_policy(&SandboxPolicy::DangerFullAccess),
&PermissionProfile::Disabled,
)?;
let session = make_session_with_config(move |config| {
@@ -1047,6 +1043,7 @@ async fn danger_full_access_tool_attempts_do_not_enforce_managed_network() -> an
#[tokio::test]
async fn workspace_write_turns_continue_to_expose_managed_network_proxy() -> anyhow::Result<()> {
let permission_profile = PermissionProfile::workspace_write();
let sandbox_policy = SandboxPolicy::new_workspace_write_policy();
let network_spec = crate::config::NetworkProxySpec::from_config_and_constraints(
NetworkProxyConfig::default(),
@@ -1054,7 +1051,7 @@ async fn workspace_write_turns_continue_to_expose_managed_network_proxy() -> any
enabled: Some(true),
..Default::default()
}),
&permission_profile_for_sandbox_policy(&sandbox_policy),
&permission_profile,
)?;
let session = make_session_with_config(move |config| {
@@ -1074,6 +1071,7 @@ async fn workspace_write_turns_continue_to_expose_managed_network_proxy() -> any
#[tokio::test]
async fn user_shell_commands_do_not_inherit_managed_network_proxy() -> anyhow::Result<()> {
let permission_profile = PermissionProfile::workspace_write();
let sandbox_policy = SandboxPolicy::new_workspace_write_policy();
let network_spec = crate::config::NetworkProxySpec::from_config_and_constraints(
NetworkProxyConfig::default(),
@@ -1081,7 +1079,7 @@ async fn user_shell_commands_do_not_inherit_managed_network_proxy() -> anyhow::R
enabled: Some(true),
..Default::default()
}),
&permission_profile_for_sandbox_policy(&sandbox_policy),
&permission_profile,
)?;
let (session, rx) = make_session_with_config_and_rx(move |config| {
@@ -2127,13 +2125,14 @@ async fn session_configured_reports_permission_profile_for_external_sandbox() ->
let sandbox_policy = SandboxPolicy::ExternalSandbox {
network_access: codex_protocol::protocol::NetworkAccess::Restricted,
};
let expected_sandbox_policy = sandbox_policy.clone();
let permission_profile = PermissionProfile::External {
network: NetworkSandboxPolicy::Restricted,
};
let expected_permission_profile = permission_profile.clone();
let mut builder = test_codex().with_config(move |config| {
config
.permissions
.set_permission_profile(PermissionProfile::from_legacy_sandbox_policy(
&sandbox_policy,
))
.set_permission_profile(permission_profile.clone())
.expect("set permission profile");
config
.set_legacy_sandbox_policy(sandbox_policy)
@@ -2142,10 +2141,6 @@ async fn session_configured_reports_permission_profile_for_external_sandbox() ->
let test = builder.build(&server).await?;
let expected_permission_profile =
codex_protocol::models::PermissionProfile::from_legacy_sandbox_policy(
&expected_sandbox_policy,
);
assert_eq!(
test.session_configured.permission_profile, expected_permission_profile,
"ExternalSandbox is represented explicitly instead of as a lossy root-write profile"