fix(acp): allow custom model as default for non-local providers (#10438)
This commit is contained in:
@@ -214,14 +214,22 @@ impl GooseAcpAgent {
|
||||
.data(format!("Provider is not configured: {provider_id}")));
|
||||
}
|
||||
|
||||
if let Some(model_id) = model_id.as_deref() {
|
||||
let model_exists = entry.default_model == model_id
|
||||
|| entry.models.iter().any(|model| model.id == model_id)
|
||||
|| (provider_id == "local" && local_inference_model_exists(model_id)?);
|
||||
if !model_exists {
|
||||
return Err(agent_client_protocol::Error::invalid_params().data(format!(
|
||||
"Model '{model_id}' is not available for provider '{provider_id}'"
|
||||
)));
|
||||
// Custom/unlisted model entry is always allowed (#7255), matching the CLI
|
||||
// and in-session model-selection paths, so a model that is simply absent
|
||||
// from the provider's (often non-exhaustive) inventory must still be
|
||||
// accepted as the default here. Local inference is the exception: its
|
||||
// models cannot be fetched on demand, so they are validated against the
|
||||
// inventory or the on-disk registry.
|
||||
if provider_id == "local" {
|
||||
if let Some(model_id) = model_id.as_deref() {
|
||||
let model_exists = entry.default_model == model_id
|
||||
|| entry.models.iter().any(|model| model.id == model_id)
|
||||
|| local_inference_model_exists(model_id)?;
|
||||
if !model_exists {
|
||||
return Err(agent_client_protocol::Error::invalid_params().data(format!(
|
||||
"Model '{model_id}' is not available for provider '{provider_id}'"
|
||||
)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -901,6 +901,47 @@ fn test_custom_defaults_read() {
|
||||
});
|
||||
}
|
||||
|
||||
// Regression test for #10401: a custom model that is not present in a provider's
|
||||
// (non-exhaustive) inventory must still be accepted when saved as the default from
|
||||
// a brand-new chat, matching the CLI and in-session model-selection paths where
|
||||
// custom/unlisted model entry is always allowed (#7255).
|
||||
#[test]
|
||||
#[serial]
|
||||
fn test_custom_defaults_save_allows_unlisted_model() {
|
||||
let _env = env_lock::lock_env([("ANTHROPIC_API_KEY", Some("test-key"))]);
|
||||
let config_dir = write_acp_global_config(
|
||||
"GOOSE_MODEL: claude-3-5-haiku-latest\nGOOSE_PROVIDER: anthropic\n",
|
||||
);
|
||||
|
||||
run_test(async move {
|
||||
let openai = OpenAiFixture::new(vec![], Arc::new(EnforceSessionId::default())).await;
|
||||
let config = TestConnectionConfig {
|
||||
data_root: config_dir,
|
||||
..Default::default()
|
||||
};
|
||||
let conn = AcpServerConnection::new(config, openai).await;
|
||||
|
||||
let response = send_custom(
|
||||
conn.cx(),
|
||||
"_goose/unstable/defaults/save",
|
||||
serde_json::json!({
|
||||
"providerId": "anthropic",
|
||||
"modelId": "custom-unlisted-model",
|
||||
}),
|
||||
)
|
||||
.await
|
||||
.expect("saving an unlisted custom model as the default should succeed");
|
||||
|
||||
assert_eq!(
|
||||
response,
|
||||
serde_json::json!({
|
||||
"providerId": "anthropic",
|
||||
"modelId": "custom-unlisted-model",
|
||||
})
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[serial]
|
||||
fn test_custom_dictation_secret_save_delete() {
|
||||
|
||||
Reference in New Issue
Block a user