{"record":{"id":"2a95e3d5b2048e99","repo":"BerriAI/litellm","slug":"azure-anthropic-requests-require-an-api-base-set","errorCode":null,"errorMessage":"Azure Anthropic requests require an api_base. Set `api_base` or the AZURE_AI_API_BASE env var.","messagePattern":"Azure Anthropic requests require an api_base\\. Set `api_base` or the AZURE_AI_API_BASE env var\\.","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"litellm/main.py","lineNumber":1570,"sourceCode":"            messages=messages,\n            api_base=api_base,\n            api_key=api_key,\n            model_response=model_response,\n            logging_obj=logging,\n            optional_params=optional_params,\n            litellm_params=litellm_params,\n            timeout=timeout,\n            acompletion=acompletion,\n            stream=stream,\n            headers=headers or litellm.headers,\n        )\n\n    # Check if this is a Claude model - route to Azure Anthropic handler\n    elif \"claude\" in model.lower():\n        # Use Azure Anthropic handler for Claude models\n        api_base = AzureFoundryModelInfo.get_api_base(api_base)\n        if api_base is None:\n            raise ValueError(\n                \"Azure Anthropic requests require an api_base. Set `api_base` or the AZURE_AI_API_BASE env var.\"\n            )\n        api_key = AzureFoundryModelInfo.get_api_key(api_key)\n\n        # Ensure the URL ends with /v1/messages for Anthropic\n        if api_base:\n            api_base = api_base.rstrip(\"/\")\n            if not api_base.endswith(\"/v1/messages\"):\n                if \"/anthropic\" in api_base:\n                    parts: Final = api_base.split(\"/anthropic\", 1)\n                    api_base = parts[0] + \"/anthropic\"\n                else:\n                    api_base = api_base + \"/anthropic\"\n                api_base = api_base + \"/v1/messages\"\n\n        response = azure_anthropic_chat_completions.completion(\n            model=model,\n            messages=messages,","sourceCodeStart":1552,"sourceCodeEnd":1588,"githubUrl":"https://github.com/BerriAI/litellm/blob/77b7c6c40c0c5aa5fbcb1d6a1825ac39ca8829b8/litellm/main.py#L1552-L1588","documentation":"ValueError raised when a Claude model under the azure_ai provider routes to the Azure Anthropic handler (the code even normalizes the URL toward .../anthropic and /v1/messages) but AzureFoundryModelInfo.get_api_base finds no endpoint via api_base, litellm.api_base, or AZURE_AI_API_BASE. Claude-on-Foundry deployments are addressed by their deployment URL, so litellm aborts before calling.","triggerScenarios":"completion(model='azure_ai/<claude-deployment>', ...) with none of api_base kwarg / litellm.api_base / AZURE_AI_API_BASE set; or only AZURE_API_BASE exported, which this path does not consult.","commonSituations":"Migrating from Azure OpenAI to a Claude model on Azure AI Foundry and reusing the old env setup; the deployment URL (which ends in /deployments/<name>) never configured in the new environment.","solutions":["Pass api_base set to your Foundry Claude deployment URL (the code will append /v1/messages as needed)","Or export AZURE_AI_API_BASE with that URL","Verify the URL contains the anthropic/deployment segment you expect; the handler splits on '/anthropic' when normalizing","Confirm auth (api_key/AZURE_AI_API_KEY) is also set once the base is fixed"],"exampleFix":"# before\nresp = litellm.completion(model='azure_ai/claude-3-5-sonnet', messages=m)  # ValueError\n\n# after\nimport os\nos.environ['AZURE_AI_API_BASE'] = 'https://<resource>.services.ai.azure.com/api/projects/<proj>/deployments/claude-3-5-sonnet'\nos.environ['AZURE_AI_API_KEY'] = '...'\nresp = litellm.completion(model='azure_ai/claude-3-5-sonnet', messages=m)","handlingStrategy":"validation","validationCode":"import os\nneeds_foundry = model.startswith('azure_ai/') and 'claude' in model.lower()\nif needs_foundry and not (api_base or os.getenv('AZURE_AI_API_BASE')):\n    raise SystemExit('Claude on azure_ai needs api_base or AZURE_AI_API_BASE')","typeGuard":"def azure_anthropic_ready(model: str, api_base: str | None) -> bool:\n    return 'claude' not in model.lower() or bool(api_base or os.getenv('AZURE_AI_API_BASE'))","tryCatchPattern":"try:\n    resp = litellm.completion(model='azure_ai/claude-3-5-sonnet', messages=m)\nexcept ValueError as e:\n    if 'Azure Anthropic requests require an api_base' in str(e):\n        raise RuntimeError('Configure the Foundry Claude deployment URL via api_base/AZURE_AI_API_BASE') from e\n    raise","preventionTips":["Keep the Foundry Claude deployment URL in version-controlled config, not shell history","Verify the URL reaches the anthropic deployment; the handler appends /v1/messages itself","When migrating providers, audit env var names -- azure_ai uses AZURE_AI_* not AZURE_*","Add a startup check for every azure_ai model string in your config"],"tags":["azure-ai","anthropic","claude","api-base","env-var","litellm"],"backgroundTag":"missing-api-base","analyzedSha":"77b7c6c40c0c5aa5fbcb1d6a1825ac39ca8829b8","analyzedAt":"2026-08-18T11:44:31.656Z","schemaVersion":2},"datasetVersion":"2026-08-21T18:17:14.833Z"}