From 8851148330e10fcfe0d2ac59f9b01a9914753dd8 Mon Sep 17 00:00:00 2001 From: "devin-ai-integration[bot]" <158243242+devin-ai-integration[bot]@users.noreply.github.com> Date: Sat, 12 Sep 2026 21:13:45 -0700 Subject: [PATCH] fix(router): preserve Azure Entra ID params in reusable credentials (#40889) CredentialLiteLLMParams omitted tenant_id, client_id, client_secret, azure_scope, azure_username and azure_password, so the strict dump used by credential reuse and Azure client init dropped them and the reused credential ended with no auth at all Co-authored-by: yassin Co-authored-by: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com> --- litellm/types/router.py | 6 ++++ tests/test_litellm/test_router.py | 35 +++++++++++++++++++ ui/litellm-dashboard/src/lib/http/schema.d.ts | 24 +++++++++++++ 3 files changed, 65 insertions(+) diff --git a/litellm/types/router.py b/litellm/types/router.py index fc09c40fe08..c7363502017 100644 --- a/litellm/types/router.py +++ b/litellm/types/router.py @@ -268,6 +268,12 @@ class CredentialLiteLLMParams(BaseModel): # callers see it, breaking Azure deployments configured with # ``azure_ad_token`` instead of a static ``api_key`` (#30235). azure_ad_token: str | None = None + tenant_id: str | None = None + client_id: str | None = None + client_secret: str | None = None + azure_scope: str | None = None + azure_username: str | None = None + azure_password: str | None = None ## VERTEX AI ## vertex_project: str | None = None vertex_location: str | None = None diff --git a/tests/test_litellm/test_router.py b/tests/test_litellm/test_router.py index f5e9b2091a0..b8a0d70f5bc 100644 --- a/tests/test_litellm/test_router.py +++ b/tests/test_litellm/test_router.py @@ -5625,6 +5625,41 @@ def test_get_deployment_credentials_with_provider_preserves_aws_auth_params(): assert credentials.get(key) == value, key +def test_get_deployment_credentials_preserves_azure_entra_id_params(): + entra_params = { + "tenant_id": "deployment-tenant", + "client_id": "deployment-client", + "client_secret": "deployment-client-secret", + "azure_scope": "https://cognitiveservices.azure.us/.default", + "azure_username": "deployment-user", + "azure_password": "deployment-password", + } + router = litellm.Router( + model_list=[ + { + "model_name": "azure-entra-model", + "litellm_params": { + "model": "azure/gpt-5.4", + "api_base": "https://example.openai.azure.com/", + "api_version": "2024-10-21", + **entra_params, + }, + "model_info": {"id": "azure-entra-model-id"}, + } + ], + ) + + credentials = router.get_deployment_credentials(model_id="azure-entra-model-id") + credentials_with_provider = router.get_deployment_credentials_with_provider(model_id="azure-entra-model-id") + + assert credentials is not None + assert credentials_with_provider is not None + assert "api_key" not in credentials + for key, value in entra_params.items(): + assert credentials.get(key) == value, key + assert credentials_with_provider.get(key) == value, key + + def _team_wildcard_model(api_key: str, model_id: str = "team-wildcard-id") -> dict: return { "model_name": f"model_name_team-1_{model_id}", diff --git a/ui/litellm-dashboard/src/lib/http/schema.d.ts b/ui/litellm-dashboard/src/lib/http/schema.d.ts index 3807286947d..7eadaa6c991 100644 --- a/ui/litellm-dashboard/src/lib/http/schema.d.ts +++ b/ui/litellm-dashboard/src/lib/http/schema.d.ts @@ -29639,6 +29639,12 @@ export interface components { aws_web_identity_token?: string | null; /** Azure Ad Token */ azure_ad_token?: string | null; + /** Azure Password */ + azure_password?: string | null; + /** Azure Scope */ + azure_scope?: string | null; + /** Azure Username */ + azure_username?: string | null; /** Bedrock Tags */ bedrock_tags?: unknown[] | null; /** Budget Duration */ @@ -29687,6 +29693,10 @@ export interface components { cache_read_input_token_cost_ultrafast?: number | null; /** Citation Cost Per Token */ citation_cost_per_token?: number | null; + /** Client Id */ + client_id?: string | null; + /** Client Secret */ + client_secret?: string | null; /** Complexity Router Config */ complexity_router_config?: { [key: string]: unknown; @@ -29900,6 +29910,8 @@ export interface components { tag_regex?: string[] | null; /** Tags */ tags?: string[] | null; + /** Tenant Id */ + tenant_id?: string | null; /** Tiered Pricing */ tiered_pricing?: { [key: string]: unknown; @@ -39841,6 +39853,12 @@ export interface components { aws_web_identity_token?: string | null; /** Azure Ad Token */ azure_ad_token?: string | null; + /** Azure Password */ + azure_password?: string | null; + /** Azure Scope */ + azure_scope?: string | null; + /** Azure Username */ + azure_username?: string | null; /** Bedrock Tags */ bedrock_tags?: unknown[] | null; /** Budget Duration */ @@ -39889,6 +39907,10 @@ export interface components { cache_read_input_token_cost_ultrafast?: number | null; /** Citation Cost Per Token */ citation_cost_per_token?: number | null; + /** Client Id */ + client_id?: string | null; + /** Client Secret */ + client_secret?: string | null; /** Complexity Router Config */ complexity_router_config?: { [key: string]: unknown; @@ -40102,6 +40124,8 @@ export interface components { tag_regex?: string[] | null; /** Tags */ tags?: string[] | null; + /** Tenant Id */ + tenant_id?: string | null; /** Tiered Pricing */ tiered_pricing?: { [key: string]: unknown;