From abe2789bc91c2eebcc89e71901be5f8a578515a6 Mon Sep 17 00:00:00 2001 From: celia-oai Date: Fri, 24 Apr 2026 16:14:55 -0700 Subject: [PATCH 1/4] Fix Bedrock GPT-5.4 reasoning levels --- .../src/amazon_bedrock/catalog.rs | 28 +++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs index c6fc6aa07e4f..e37835326951 100644 --- a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs +++ b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs @@ -40,6 +40,8 @@ fn gpt_5_4_cmb_bedrock_model(priority: i32) -> ModelInfo { model.slug = GPT_5_4_CMB_MODEL_ID.to_string(); model.priority = priority; model.apply_patch_tool_type = Some(ApplyPatchToolType::Function); + model.default_reasoning_level = Some(ReasoningEffort::Medium); + model.supported_reasoning_levels = gpt_5_4_cmb_reasoning_levels(); model } @@ -96,6 +98,15 @@ fn bedrock_model(slug: &str, display_name: &str, priority: i32) -> ModelInfo { } } +fn gpt_5_4_cmb_reasoning_levels() -> Vec { + vec![ + reasoning_effort_preset(ReasoningEffort::Minimal), + reasoning_effort_preset(ReasoningEffort::Low), + reasoning_effort_preset(ReasoningEffort::Medium), + reasoning_effort_preset(ReasoningEffort::High), + ] +} + fn reasoning_effort_preset(effort: ReasoningEffort) -> ReasoningEffortPreset { ReasoningEffortPreset { effort, @@ -140,7 +151,24 @@ mod tests { gpt_5_4_model.slug = GPT_5_4_CMB_MODEL_ID.to_string(); gpt_5_4_model.priority = cmb_model.priority; gpt_5_4_model.apply_patch_tool_type = Some(ApplyPatchToolType::Function); + gpt_5_4_model.default_reasoning_level = Some(ReasoningEffort::Medium); + gpt_5_4_model.supported_reasoning_levels = gpt_5_4_cmb_reasoning_levels(); assert_eq!(*cmb_model, gpt_5_4_model); } + + #[test] + fn gpt_5_4_cmb_advertises_only_bedrock_supported_reasoning_levels() { + let catalog = static_model_catalog(); + let cmb_model = catalog + .models + .iter() + .find(|model| model.slug == GPT_5_4_CMB_MODEL_ID) + .expect("Bedrock catalog should include GPT-5.4 CMB"); + + assert_eq!( + cmb_model.supported_reasoning_levels, + gpt_5_4_cmb_reasoning_levels() + ); + } } From d2564951ebe987b8e83cc368efcf490b648b6612 Mon Sep 17 00:00:00 2001 From: celia-oai Date: Fri, 24 Apr 2026 16:27:09 -0700 Subject: [PATCH 2/4] Hardcode Bedrock GPT-5.4 CMB model metadata --- .../src/amazon_bedrock/catalog.rs | 107 ++++++++++++------ 1 file changed, 74 insertions(+), 33 deletions(-) diff --git a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs index e37835326951..66d550d426f0 100644 --- a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs +++ b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs @@ -1,6 +1,6 @@ -use codex_models_manager::bundled_models_response; -use codex_models_manager::model_info::model_info_from_slug; +use codex_models_manager::model_info::BASE_INSTRUCTIONS; use codex_protocol::config_types::ReasoningSummary; +use codex_protocol::config_types::Verbosity; use codex_protocol::openai_models::ApplyPatchToolType; use codex_protocol::openai_models::ConfigShellToolType; use codex_protocol::openai_models::InputModality; @@ -13,8 +13,9 @@ use codex_protocol::openai_models::TruncationPolicyConfig; use codex_protocol::openai_models::WebSearchToolType; const GPT_OSS_CONTEXT_WINDOW: i64 = 128_000; +const GPT_5_4_CONTEXT_WINDOW: i64 = 272_000; +const GPT_5_4_MAX_CONTEXT_WINDOW: i64 = 1_000_000; const GPT_5_4_CMB_MODEL_ID: &str = "openai.gpt-5.4-cmb"; -const GPT_5_4_MODEL_ID: &str = "gpt-5.4"; pub(crate) fn static_model_catalog() -> ModelsResponse { ModelsResponse { @@ -35,27 +36,39 @@ pub(crate) fn static_model_catalog() -> ModelsResponse { } fn gpt_5_4_cmb_bedrock_model(priority: i32) -> ModelInfo { - let mut model = bundled_gpt_5_4_model(); - - model.slug = GPT_5_4_CMB_MODEL_ID.to_string(); - model.priority = priority; - model.apply_patch_tool_type = Some(ApplyPatchToolType::Function); - model.default_reasoning_level = Some(ReasoningEffort::Medium); - model.supported_reasoning_levels = gpt_5_4_cmb_reasoning_levels(); - model -} - -fn bundled_gpt_5_4_model() -> ModelInfo { - if let Ok(response) = bundled_models_response() - && let Some(model) = response - .models - .into_iter() - .find(|model| model.slug == GPT_5_4_MODEL_ID) - { - return model; + ModelInfo { + slug: GPT_5_4_CMB_MODEL_ID.to_string(), + display_name: "gpt-5.4".to_string(), + description: Some("Strong model for everyday coding.".to_string()), + default_reasoning_level: Some(ReasoningEffort::Medium), + supported_reasoning_levels: gpt_5_4_cmb_reasoning_levels(), + shell_type: ConfigShellToolType::ShellCommand, + visibility: ModelVisibility::List, + supported_in_api: true, + priority, + additional_speed_tiers: vec!["fast".to_string()], + availability_nux: None, + upgrade: None, + base_instructions: BASE_INSTRUCTIONS.to_string(), + model_messages: None, + supports_reasoning_summaries: true, + default_reasoning_summary: ReasoningSummary::None, + support_verbosity: true, + default_verbosity: Some(Verbosity::Medium), + apply_patch_tool_type: Some(ApplyPatchToolType::Function), + web_search_tool_type: WebSearchToolType::TextAndImage, + truncation_policy: TruncationPolicyConfig::tokens(/*limit*/ 10_000), + supports_parallel_tool_calls: true, + supports_image_detail_original: true, + context_window: Some(GPT_5_4_CONTEXT_WINDOW), + max_context_window: Some(GPT_5_4_MAX_CONTEXT_WINDOW), + auto_compact_token_limit: None, + effective_context_window_percent: 95, + experimental_supported_tools: Vec::new(), + input_modalities: vec![InputModality::Text, InputModality::Image], + used_fallback_model_metadata: false, + supports_search_tool: true, } - - model_info_from_slug(GPT_5_4_MODEL_ID) } fn bedrock_model(slug: &str, display_name: &str, priority: i32) -> ModelInfo { @@ -76,7 +89,7 @@ fn bedrock_model(slug: &str, display_name: &str, priority: i32) -> ModelInfo { additional_speed_tiers: Vec::new(), availability_nux: None, upgrade: None, - base_instructions: codex_models_manager::model_info::BASE_INSTRUCTIONS.to_string(), + base_instructions: BASE_INSTRUCTIONS.to_string(), model_messages: None, supports_reasoning_summaries: true, default_reasoning_summary: ReasoningSummary::None, @@ -139,22 +152,50 @@ mod tests { } #[test] - fn gpt_5_4_cmb_uses_gpt_5_4_spec() { + fn gpt_5_4_cmb_uses_hardcoded_bedrock_spec() { let catalog = static_model_catalog(); let cmb_model = catalog .models .iter() .find(|model| model.slug == GPT_5_4_CMB_MODEL_ID) .expect("Bedrock catalog should include GPT-5.4 CMB"); - let mut gpt_5_4_model = bundled_gpt_5_4_model(); - gpt_5_4_model.slug = GPT_5_4_CMB_MODEL_ID.to_string(); - gpt_5_4_model.priority = cmb_model.priority; - gpt_5_4_model.apply_patch_tool_type = Some(ApplyPatchToolType::Function); - gpt_5_4_model.default_reasoning_level = Some(ReasoningEffort::Medium); - gpt_5_4_model.supported_reasoning_levels = gpt_5_4_cmb_reasoning_levels(); - - assert_eq!(*cmb_model, gpt_5_4_model); + assert_eq!( + *cmb_model, + ModelInfo { + slug: GPT_5_4_CMB_MODEL_ID.to_string(), + display_name: "gpt-5.4".to_string(), + description: Some("Strong model for everyday coding.".to_string()), + default_reasoning_level: Some(ReasoningEffort::Medium), + supported_reasoning_levels: gpt_5_4_cmb_reasoning_levels(), + shell_type: ConfigShellToolType::ShellCommand, + visibility: ModelVisibility::List, + supported_in_api: true, + priority: 0, + additional_speed_tiers: vec!["fast".to_string()], + availability_nux: None, + upgrade: None, + base_instructions: BASE_INSTRUCTIONS.to_string(), + model_messages: None, + supports_reasoning_summaries: true, + default_reasoning_summary: ReasoningSummary::None, + support_verbosity: true, + default_verbosity: Some(Verbosity::Medium), + apply_patch_tool_type: Some(ApplyPatchToolType::Function), + web_search_tool_type: WebSearchToolType::TextAndImage, + truncation_policy: TruncationPolicyConfig::tokens(/*limit*/ 10_000), + supports_parallel_tool_calls: true, + supports_image_detail_original: true, + context_window: Some(GPT_5_4_CONTEXT_WINDOW), + max_context_window: Some(GPT_5_4_MAX_CONTEXT_WINDOW), + auto_compact_token_limit: None, + effective_context_window_percent: 95, + experimental_supported_tools: Vec::new(), + input_modalities: vec![InputModality::Text, InputModality::Image], + used_fallback_model_metadata: false, + supports_search_tool: true, + } + ); } #[test] From f2811e27e619866ee5c22456c2b14227d24f341f Mon Sep 17 00:00:00 2001 From: celia-oai Date: Fri, 24 Apr 2026 16:29:53 -0700 Subject: [PATCH 3/4] Rename Bedrock OSS catalog helper --- codex-rs/model-provider/src/amazon_bedrock/catalog.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs index 66d550d426f0..fa8ffe79db16 100644 --- a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs +++ b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs @@ -21,12 +21,12 @@ pub(crate) fn static_model_catalog() -> ModelsResponse { ModelsResponse { models: vec![ gpt_5_4_cmb_bedrock_model(/*priority*/ 0), - bedrock_model( + bedrock_oss_model( "openai.gpt-oss-120b", "GPT OSS 120B on Bedrock", /*priority*/ 1, ), - bedrock_model( + bedrock_oss_model( "openai.gpt-oss-20b", "GPT OSS 20B on Bedrock", /*priority*/ 2, @@ -71,7 +71,7 @@ fn gpt_5_4_cmb_bedrock_model(priority: i32) -> ModelInfo { } } -fn bedrock_model(slug: &str, display_name: &str, priority: i32) -> ModelInfo { +fn bedrock_oss_model(slug: &str, display_name: &str, priority: i32) -> ModelInfo { ModelInfo { slug: slug.to_string(), display_name: display_name.to_string(), From 25fb97c046879d3d46f24522dd0a23b5176acce0 Mon Sep 17 00:00:00 2001 From: celia-oai Date: Fri, 24 Apr 2026 16:38:55 -0700 Subject: [PATCH 4/4] Remove redundant Bedrock CMB catalog test --- .../src/amazon_bedrock/catalog.rs | 47 ------------------- 1 file changed, 47 deletions(-) diff --git a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs index fa8ffe79db16..aa9e8bdead00 100644 --- a/codex-rs/model-provider/src/amazon_bedrock/catalog.rs +++ b/codex-rs/model-provider/src/amazon_bedrock/catalog.rs @@ -151,53 +151,6 @@ mod tests { assert_eq!(catalog.models[2].slug, "openai.gpt-oss-20b"); } - #[test] - fn gpt_5_4_cmb_uses_hardcoded_bedrock_spec() { - let catalog = static_model_catalog(); - let cmb_model = catalog - .models - .iter() - .find(|model| model.slug == GPT_5_4_CMB_MODEL_ID) - .expect("Bedrock catalog should include GPT-5.4 CMB"); - - assert_eq!( - *cmb_model, - ModelInfo { - slug: GPT_5_4_CMB_MODEL_ID.to_string(), - display_name: "gpt-5.4".to_string(), - description: Some("Strong model for everyday coding.".to_string()), - default_reasoning_level: Some(ReasoningEffort::Medium), - supported_reasoning_levels: gpt_5_4_cmb_reasoning_levels(), - shell_type: ConfigShellToolType::ShellCommand, - visibility: ModelVisibility::List, - supported_in_api: true, - priority: 0, - additional_speed_tiers: vec!["fast".to_string()], - availability_nux: None, - upgrade: None, - base_instructions: BASE_INSTRUCTIONS.to_string(), - model_messages: None, - supports_reasoning_summaries: true, - default_reasoning_summary: ReasoningSummary::None, - support_verbosity: true, - default_verbosity: Some(Verbosity::Medium), - apply_patch_tool_type: Some(ApplyPatchToolType::Function), - web_search_tool_type: WebSearchToolType::TextAndImage, - truncation_policy: TruncationPolicyConfig::tokens(/*limit*/ 10_000), - supports_parallel_tool_calls: true, - supports_image_detail_original: true, - context_window: Some(GPT_5_4_CONTEXT_WINDOW), - max_context_window: Some(GPT_5_4_MAX_CONTEXT_WINDOW), - auto_compact_token_limit: None, - effective_context_window_percent: 95, - experimental_supported_tools: Vec::new(), - input_modalities: vec![InputModality::Text, InputModality::Image], - used_fallback_model_metadata: false, - supports_search_tool: true, - } - ); - } - #[test] fn gpt_5_4_cmb_advertises_only_bedrock_supported_reasoning_levels() { let catalog = static_model_catalog();