@@ -719,11 +719,11 @@ impl ModelRegistry {
719719 models = self . list_by_provider ( provider_id) ;
720720 }
721721 if models. is_empty ( ) {
722- // Codex models are not on models.dev (OAuth-only), so the bundled
723- // snapshot has no entries for them . Fall back to the canonical
724- // constant in claurst_core::codex_oauth so `/model` and the
725- // effective-model resolver still pick a real id for Codex users .
726- return codex_models_fallback ( provider_id, /* small = */ false ) ;
722+ // Codex and GitHub Copilot models may be absent from models.dev
723+ // (OAuth/subscription-backed providers) . Fall back to the curated
724+ // GPT agent model list so `/model` and the effective-model resolver
725+ // still pick real ids offline .
726+ return gpt_agent_models_fallback ( provider_id, /* small = */ false ) ;
727727 }
728728
729729 let priority_patterns = flagship_patterns_for ( provider_id) ;
@@ -769,8 +769,8 @@ impl ModelRegistry {
769769 models = self . list_by_provider ( provider_id) ;
770770 }
771771 if models. is_empty ( ) {
772- // See best_model_for_provider for the Codex rationale.
773- return codex_models_fallback ( provider_id, /* small = */ true ) ;
772+ // See best_model_for_provider for the GPT-agent fallback rationale.
773+ return gpt_agent_models_fallback ( provider_id, /* small = */ true ) ;
774774 }
775775
776776 let small_priority = small_patterns_for ( provider_id) ;
@@ -963,7 +963,7 @@ impl Default for ModelRegistry {
963963/// Earlier entries score higher.
964964fn flagship_patterns_for ( provider_id : & str ) -> & ' static [ & ' static str ] {
965965 match provider_id {
966- "anthropic" | "amazon-bedrock" | "github-copilot" | " azure" | "google-vertex" => & [
966+ "anthropic" | "amazon-bedrock" | "azure" | "google-vertex" => & [
967967 "claude-opus-4" ,
968968 "claude-sonnet-4" ,
969969 "claude-3-5-sonnet" ,
@@ -1006,7 +1006,7 @@ fn flagship_patterns_for(provider_id: &str) -> &'static [&'static str] {
10061006 ] ,
10071007 "zai" => & [ "glm-5.1" , "glm-5" , "glm-4.7" ] ,
10081008 "minimax" => & [ "minimax-m2" ] ,
1009- "codex" | "openai-codex" => & [
1009+ "codex" | "openai-codex" | "github-copilot" => & [
10101010 "gpt-5.6-sol" ,
10111011 "gpt-5.6-terra" ,
10121012 "gpt-5.6-luna" ,
@@ -1037,13 +1037,13 @@ fn flagship_patterns_for(provider_id: &str) -> &'static [&'static str] {
10371037}
10381038
10391039/// Substring patterns marking a model as the lightweight/cheap default.
1040- /// Codex is OAuth-only and absent from the models.dev bundled snapshot, so
1041- /// `list_by_provider("codex" )` always returns empty. This fallback returns
1042- /// the canonical default / small ids from
1040+ /// Codex and GitHub Copilot can be absent from the models.dev bundled snapshot,
1041+ /// so `list_by_provider(... )` may return empty. This fallback returns the
1042+ /// canonical GPT agent default / small ids from
10431043/// `claurst_core::codex_oauth::CODEX_MODELS` so `/model` and `/fast` keep
1044- /// working for Codex users .
1045- fn codex_models_fallback ( provider_id : & str , small : bool ) -> Option < String > {
1046- if !matches ! ( provider_id, "codex" | "openai-codex" ) {
1044+ /// working for subscription-backed GPT providers .
1045+ fn gpt_agent_models_fallback ( provider_id : & str , small : bool ) -> Option < String > {
1046+ if !matches ! ( provider_id, "codex" | "openai-codex" | "github-copilot" ) {
10471047 return None ;
10481048 }
10491049 if small {
@@ -1062,7 +1062,9 @@ fn codex_models_fallback(provider_id: &str, small: bool) -> Option<String> {
10621062fn small_patterns_for ( provider_id : & str ) -> & ' static [ & ' static str ] {
10631063 match provider_id {
10641064 "anthropic" => & [ "claude-haiku-4" , "claude-haiku-3-5" , "claude-haiku" ] ,
1065- "codex" | "openai" | "openai-codex" => & [ "gpt-5.6-luna" , "gpt-5.4-mini" , "gpt-5-mini" ] ,
1065+ "codex" | "openai" | "openai-codex" | "github-copilot" => {
1066+ & [ "gpt-5.6-luna" , "gpt-5.4-mini" , "gpt-5-mini" ]
1067+ }
10661068 _ => & [ "mini" , "haiku" , "flash" , "lite" , "small" , "nano" ] ,
10671069 }
10681070}
@@ -1221,6 +1223,14 @@ mod tests {
12211223 // The alias `openai-codex` must take the same path.
12221224 assert ! ( reg. best_model_for_provider( "openai-codex" ) . is_some( ) ) ;
12231225 assert ! ( reg. best_small_model_for_provider( "openai-codex" ) . is_some( ) ) ;
1226+ let copilot_best = reg
1227+ . best_model_for_provider ( "github-copilot" )
1228+ . expect ( "github-copilot best model must fall back to GPT agent default" ) ;
1229+ assert_eq ! ( copilot_best, claurst_core:: codex_oauth:: DEFAULT_CODEX_MODEL ) ;
1230+ let copilot_small = reg
1231+ . best_small_model_for_provider ( "github-copilot" )
1232+ . expect ( "github-copilot small model must fall back to a GPT agent small id" ) ;
1233+ assert_eq ! ( copilot_small, "gpt-5.6-luna" ) ;
12241234 // Unrelated providers continue to return None when absent.
12251235 assert ! ( reg
12261236 . best_model_for_provider( "definitely-not-a-provider" )
0 commit comments