diff --git a/litellm/model_prices_and_context_window_backup.json b/litellm/model_prices_and_context_window_backup.json index 49113c994e3..fc6e69a50f5 100644 --- a/litellm/model_prices_and_context_window_backup.json +++ b/litellm/model_prices_and_context_window_backup.json @@ -59501,8 +59501,8 @@ { "name": "claude-tool-search", "pattern": "claude-[a-z]+-(?:4[-._](?:[5-9]|[1-9]\\d)(?!\\d)|[5-9](?!\\d)(?:[-._]\\d{1,2}(?!\\d))?)", - "fill_missing_for_providers": ["anthropic", "azure_ai", "bedrock", "bedrock_converse", "vertex_ai-anthropic_models"], - "description": "Claude at version 4.5 or higher, in any id shape that contains claude--: minors 4.5 through 4.99, any later major-minor, and bare 5+ majors so a new family like claude-fable-5 matches. Two-digit majors are deliberately not matched so ids like claude-opus-41 (4.1) are not read as major 41. Anthropic shipped the tool search tool (tool_search_tool_regex, tool_search_tool_bm25) with Opus 4.5, Sonnet 4.5 and Haiku 4.5, and every newer Claude keeps it, so the flag follows the version instead of a per-model list. The Bedrock InvokeModel transformations read this flag to send the tool-search-tool-2025-10-19 beta, so a new Claude gets the beta with no code change.", + "fill_missing_for_providers": ["anthropic", "bedrock", "bedrock_converse", "vertex_ai-anthropic_models"], + "description": "Claude at version 4.5 or higher, in any id shape that contains claude--: minors 4.5 through 4.99, any later major-minor, and bare 5+ majors so a new family like claude-fable-5 matches. Two-digit majors are deliberately not matched so ids like claude-opus-41 (4.1) are not read as major 41. Anthropic's tool search docs list every Claude 4.5 and newer model as supported and Opus 4.1 and earlier as unsupported, so the flag follows the version instead of a per-model list. azure_ai is left out on purpose: Anthropic documents tool search as unavailable on Azure-hosted Foundry deployments, and the azure_ai/ key cannot tell those from Anthropic-hosted ones.", "model_info": { "supports_tool_search": true } diff --git a/model_prices_and_context_window.json b/model_prices_and_context_window.json index 49113c994e3..fc6e69a50f5 100644 --- a/model_prices_and_context_window.json +++ b/model_prices_and_context_window.json @@ -59501,8 +59501,8 @@ { "name": "claude-tool-search", "pattern": "claude-[a-z]+-(?:4[-._](?:[5-9]|[1-9]\\d)(?!\\d)|[5-9](?!\\d)(?:[-._]\\d{1,2}(?!\\d))?)", - "fill_missing_for_providers": ["anthropic", "azure_ai", "bedrock", "bedrock_converse", "vertex_ai-anthropic_models"], - "description": "Claude at version 4.5 or higher, in any id shape that contains claude--: minors 4.5 through 4.99, any later major-minor, and bare 5+ majors so a new family like claude-fable-5 matches. Two-digit majors are deliberately not matched so ids like claude-opus-41 (4.1) are not read as major 41. Anthropic shipped the tool search tool (tool_search_tool_regex, tool_search_tool_bm25) with Opus 4.5, Sonnet 4.5 and Haiku 4.5, and every newer Claude keeps it, so the flag follows the version instead of a per-model list. The Bedrock InvokeModel transformations read this flag to send the tool-search-tool-2025-10-19 beta, so a new Claude gets the beta with no code change.", + "fill_missing_for_providers": ["anthropic", "bedrock", "bedrock_converse", "vertex_ai-anthropic_models"], + "description": "Claude at version 4.5 or higher, in any id shape that contains claude--: minors 4.5 through 4.99, any later major-minor, and bare 5+ majors so a new family like claude-fable-5 matches. Two-digit majors are deliberately not matched so ids like claude-opus-41 (4.1) are not read as major 41. Anthropic's tool search docs list every Claude 4.5 and newer model as supported and Opus 4.1 and earlier as unsupported, so the flag follows the version instead of a per-model list. azure_ai is left out on purpose: Anthropic documents tool search as unavailable on Azure-hosted Foundry deployments, and the azure_ai/ key cannot tell those from Anthropic-hosted ones.", "model_info": { "supports_tool_search": true } diff --git a/tests/test_litellm/litellm_core_utils/test_fallback_generalizations.py b/tests/test_litellm/litellm_core_utils/test_fallback_generalizations.py index 37a44867857..f7793286c7a 100644 --- a/tests/test_litellm/litellm_core_utils/test_fallback_generalizations.py +++ b/tests/test_litellm/litellm_core_utils/test_fallback_generalizations.py @@ -1008,6 +1008,8 @@ def test_shipped_claude_thinking_rules_backfill_only_anthropic(shipped_cost_map) ("us.anthropic.claude-opus-4-5", "bedrock", True), ("claude-haiku-4-4", "anthropic", None), ("claude-haiku-4-6", "anthropic", True), + ("claude-opus-4.5", "anthropic", True), + ("claude-opus-4_5", "anthropic", True), ("claude-haiku-4-10", "anthropic", True), ("claude-haiku-5-0", "anthropic", True), ("claude-sonnet-5-1", "anthropic", True), @@ -1017,7 +1019,8 @@ def test_shipped_claude_thinking_rules_backfill_only_anthropic(shipped_cost_map) ) def test_shipped_tool_search_rule_version_boundaries(shipped_cost_map, model, provider, tool_search): """The claude-tool-search rule flags Claude 4.5 and newer in any family, bare major - or major-minor, and leaves 4.4 and date-suffixed 4.x ids without an opinion.""" + or major-minor with a dash, dot or underscore delimiter, and leaves 4.4 and + date-suffixed 4.x ids without an opinion.""" assert model not in litellm.model_cost info = litellm.get_model_info(model, custom_llm_provider=provider) assert info.get("supports_tool_search") is tool_search, model @@ -1025,17 +1028,23 @@ def test_shipped_tool_search_rule_version_boundaries(shipped_cost_map, model, pr def test_shipped_tool_search_rule_fills_mapped_claude_entries_without_flag(shipped_cost_map): """A mapped Claude 4.5+ entry with no supports_tool_search key gets it from the rule - on the Claude providers, a mapped pre-4.5 entry stays without one, and a reseller - copy of the same model is not touched.""" + on Anthropic direct, Vertex and Bedrock, a mapped pre-4.5 entry stays without one, + and Azure Foundry and reseller copies of the same model are not touched.""" for key, model, provider in ( ("claude-opus-4-7", "claude-opus-4-7", "anthropic"), - ("azure_ai/claude-opus-5", "claude-opus-5", "azure_ai"), + ("vertex_ai/claude-opus-5", "claude-opus-5", "vertex_ai"), ): assert "supports_tool_search" not in litellm.model_cost[key] assert litellm.get_model_info(model, custom_llm_provider=provider)["supports_tool_search"] is True assert "supports_tool_search" not in litellm.model_cost["claude-opus-4-1"] - assert litellm.get_model_info("claude-opus-4-1", custom_llm_provider="anthropic").get("supports_tool_search") is None + opus_4_1_info = litellm.get_model_info("claude-opus-4-1", custom_llm_provider="anthropic") + assert opus_4_1_info.get("supports_tool_search") is None + + assert "supports_tool_search" not in litellm.model_cost["azure_ai/claude-opus-5"] + azure_opus_5_info = litellm.get_model_info("claude-opus-5", custom_llm_provider="azure_ai") + assert azure_opus_5_info.get("supports_tool_search") is None assert match_fill_missing_generalizations("claude-opus-5", "bedrock")["supports_tool_search"] is True + assert "supports_tool_search" not in match_fill_missing_generalizations("claude-opus-5", "azure_ai") assert match_fill_missing_generalizations("claude-opus-5", "perplexity") is None