From b260ee5e8333faefd74d8be78d722cd6a4d4b33d Mon Sep 17 00:00:00 2001 From: jif Date: Wed, 4 Nov 2026 21:10:15 +0000 Subject: [PATCH] Preserve project agent opt-ins across enabled legacy feature flags (#59496) ## Why An enabled legacy feature flag could prevent a project's `agents.enabled = true` from overriding a lower-priority legacy opt-out, leaving V1 agent tools unavailable. ## What changed Only stop scanning configuration layers at an explicit legacy feature opt-out. Enabled flags now allow the scan to continue, so project opt-ins can override lower-priority opt-outs while same-layer and higher-priority opt-outs remain effective. ## Testing Extend the model runtime selector regression test to cover enabled `features.collab` flags in project configuration and CLI overrides, and verify that explicit `false` values still disable V1 agent tools. GitOrigin-RevId: ca3dcf9dc6a642eb72e20929776fb74379715053 --- codex-rs/core/src/config/managed_features.rs | 6 ++-- .../tests/suite/model_runtime_selectors.rs | 30 +++++++++++++++++++ 2 files changed, 33 insertions(+), 3 deletions(-) diff --git a/codex-rs/core/src/config/managed_features.rs b/codex-rs/core/src/config/managed_features.rs index 7c04301444..1e3fe109db 100644 --- a/codex-rs/core/src/config/managed_features.rs +++ b/codex-rs/core/src/config/managed_features.rs @@ -23,9 +23,9 @@ pub(super) fn project_overrides_legacy_subagent_opt_out(layers: &ConfigLayerStac let mut project_enabled = false; for layer in layers.layers_high_to_low() { if let Some(features) = layer.config.get("features").and_then(toml::Value::as_table) - && features - .keys() - .any(|key| feature_for_key(key) == Some(Feature::Collab)) + && features.iter().any(|(key, enabled)| { + enabled.as_bool() == Some(false) && feature_for_key(key) == Some(Feature::Collab) + }) { return project_enabled; } diff --git a/codex-rs/core/tests/suite/model_runtime_selectors.rs b/codex-rs/core/tests/suite/model_runtime_selectors.rs index d25278e1f7..8034cde9be 100644 --- a/codex-rs/core/tests/suite/model_runtime_selectors.rs +++ b/codex-rs/core/tests/suite/model_runtime_selectors.rs @@ -447,6 +447,36 @@ async fn migrating_only_the_project_agent_setting_preserves_v1_tools() -> Result Some("multi_agent_v1"), ), (migrated, config(), None, Some("multi_agent_v1")), + ( + "[features]\nmulti_agent = true", + config().cli_overrides(vec![("features.collab".to_string(), true.into())]), + None, + Some("multi_agent_v1"), + ), + ( + migrated, + config().cli_overrides(vec![("features.collab".to_string(), true.into())]), + None, + Some("multi_agent_v1"), + ), + ( + "[agents]\nenabled = true\n[features]\ncollab = true", + config(), + None, + Some("multi_agent_v1"), + ), + ( + "[agents]\nenabled = true\n[features]\ncollab = false", + config(), + None, + None, + ), + ( + migrated, + config().cli_overrides(vec![("features.collab".to_string(), false.into())]), + None, + None, + ), ( migrated, config(),