Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion ARCHITECTURE.md
Original file line number Diff line number Diff line change
Expand Up @@ -336,7 +336,7 @@ Each translation is isolated in its own file, making it easy to test and modify
| `/v1/chat/completions` | Gemini | `llms/gemini/chat/transformation.py` |
| `/v1/chat/completions` | Vertex AI | `llms/vertex_ai/gemini/transformation.py` |
| `/v1/chat/completions` | OpenAI | `llms/openai/chat/gpt_transformation.py` |
| `/v1/messages` (passthrough) | Anthropic | `llms/anthropic/experimental_pass_through/messages/transformation.py` |
| `/v1/messages` (passthrough) | Anthropic | `llms/anthropic/pass_through/messages/transformation.py` |
| `/v1/messages` (passthrough) | Bedrock | `llms/bedrock/messages/invoke_transformations/anthropic_claude3_transformation.py` |
| `/v1/messages` (passthrough) | Vertex AI | `llms/vertex_ai/vertex_ai_partner_models/anthropic/experimental_pass_through/transformation.py` |
| Passthrough endpoints | All | `proxy/pass_through_endpoints/llm_provider_handlers/` |
Expand Down
2 changes: 1 addition & 1 deletion litellm/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -1691,7 +1691,7 @@ def set_global_gitlab_config(config: Dict[str, Any]) -> None:
SagemakerNovaConfig as SagemakerNovaConfig,
)
from .llms.cohere.chat.transformation import CohereChatConfig as CohereChatConfig
from .llms.anthropic.experimental_pass_through.messages.transformation import (
from .llms.anthropic.pass_through.messages.transformation import (

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Former module import breaks

If an existing SDK integration imports AnthropicMessagesConfig from litellm.llms.anthropic.experimental_pass_through.messages.transformation, it now gets ModuleNotFoundError: the package was moved without keeping the old import path. This violates the repository directive to avoid backwards-incompatible changes without a user-controlled flag. Keep the former path working during migration.

Rule Used: What: avoid backwards-incompatible changes without user-controlled flags Why: This breaks current behaviour for users using existing functionality Example of BAD: this PR (#22164) introduced run_post_custom... (source)

AnthropicMessagesConfig as AnthropicMessagesConfig,
)
from .llms.bedrock.messages.invoke_transformations.anthropic_claude3_transformation import (
Expand Down
2 changes: 1 addition & 1 deletion litellm/_lazy_imports_registry.py
Original file line number Diff line number Diff line change
Expand Up @@ -742,7 +742,7 @@
),
"CohereChatConfig": (".llms.cohere.chat.transformation", "CohereChatConfig"),
"AnthropicMessagesConfig": (
".llms.anthropic.experimental_pass_through.messages.transformation",
".llms.anthropic.pass_through.messages.transformation",
"AnthropicMessagesConfig",
),
"BedrockClaudePlatformMessagesConfig": (
Expand Down
8 changes: 4 additions & 4 deletions litellm/caching/caching_handler.py
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@

if TYPE_CHECKING:
from litellm.litellm_core_utils.litellm_logging import Logging as LiteLLMLoggingObj
from litellm.llms.anthropic.experimental_pass_through.messages.response_cache import (
from litellm.llms.anthropic.pass_through.messages.response_cache import (
AnthropicMessagesStreamCacheWriter,
)
from litellm.types.utils import PromptTokensDetailsWrapper
Expand Down Expand Up @@ -127,7 +127,7 @@ def _should_defer_streaming_cache_hit_callbacks(*, cached_result: object) -> boo
spend and callback records. A plain (non-stream) replay logs here, since nothing
else will.
"""
from litellm.llms.anthropic.experimental_pass_through.messages.response_cache import (
from litellm.llms.anthropic.pass_through.messages.response_cache import (
CachedAnthropicMessagesStreamIterator,
)
from litellm.responses.streaming_iterator import BaseResponsesAPIStreamingIterator
Expand Down Expand Up @@ -930,7 +930,7 @@ def _convert_cached_result_to_model_response(
elif (
call_type == CallTypes.anthropic_messages.value or call_type == CallTypes.aanthropic_messages.value
) and isinstance(cached_result, dict):
from litellm.llms.anthropic.experimental_pass_through.messages.response_cache import (
from litellm.llms.anthropic.pass_through.messages.response_cache import (
convert_cached_anthropic_messages_result,
)

Expand Down Expand Up @@ -1150,7 +1150,7 @@ def wrap_streaming_result_for_cache(
return result
if not isinstance(result, AsyncIterator):
return result
from litellm.llms.anthropic.experimental_pass_through.messages.response_cache import (
from litellm.llms.anthropic.pass_through.messages.response_cache import (
AnthropicMessagesStreamCacheWriter,
)

Expand Down
2 changes: 1 addition & 1 deletion litellm/integrations/shadow_eval_logger.py
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,7 @@ def _chat_request_from_anthropic_messages(
because the logged optional_params switch dialect per provider path (the bridge's
inner completion rewrites them to chat shape mid-flight); the adapter translates
them alongside the messages, and sampling params copy through untranslated."""
from litellm.llms.anthropic.experimental_pass_through.adapters.transformation import (
from litellm.llms.anthropic.pass_through.adapters.transformation import (
LiteLLMAnthropicMessagesAdapter,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ Claude Code (Anthropic's official CLI) sends web search requests using Anthropic

Native tools are converted to LiteLLM standard format **before** sending to the provider:

1. **Conversion Point** (`litellm/llms/anthropic/experimental_pass_through/messages/handler.py`):
1. **Conversion Point** (`litellm/llms/anthropic/pass_through/messages/handler.py`):
- In `anthropic_messages()` function (lines 60-127)
- Runs BEFORE the API request is made
- Detects native web search tools using `is_web_search_tool()`
Expand Down
4 changes: 2 additions & 2 deletions litellm/llms/anthropic/chat/guardrail_translation/handler.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@

from litellm._logging import verbose_proxy_logger
from litellm.llms.anthropic.chat.transformation import AnthropicConfig
from litellm.llms.anthropic.experimental_pass_through.adapters.transformation import (
from litellm.llms.anthropic.pass_through.adapters.transformation import (
LiteLLMAnthropicMessagesAdapter,
is_provider_native_tool_dict,
)
Expand Down Expand Up @@ -365,7 +365,7 @@ def build_stream_error_items(
def _standalone_block_chunks(self, exc: "ModifyResponseException") -> list[bytes]:
import uuid

from litellm.llms.anthropic.experimental_pass_through.messages.fake_stream_iterator import (
from litellm.llms.anthropic.pass_through.messages.fake_stream_iterator import (
FakeAnthropicMessagesStreamIterator,
)
from litellm.llms.base_llm.guardrail_translation.utils import (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,15 +11,15 @@
import litellm
from litellm._logging import verbose_logger
from litellm.litellm_core_utils.asyncify import run_async_function
from litellm.llms.anthropic.experimental_pass_through.adapters.transformation import (
from litellm.llms.anthropic.pass_through.adapters.transformation import (
AnthropicAdapter,
)
from litellm.llms.anthropic.experimental_pass_through.context_management import (
from litellm.llms.anthropic.pass_through.context_management import (
AnthropicContextManagementError,
PolyfillResult,
apply_context_management,
)
from litellm.llms.anthropic.experimental_pass_through.utils import (
from litellm.llms.anthropic.pass_through.utils import (
is_reasoning_auto_summary_enabled,
litellm_logging_obj_from_kwargs,
local_model_name,
Expand Down Expand Up @@ -102,7 +102,7 @@ async def _prepare_context_managed_request(
user_api_key_auth: "UserAPIKeyAuth | None" = None,
) -> PolyfillResult | None:
"""Apply client compaction history, then optional context_management polyfill."""
from litellm.llms.anthropic.experimental_pass_through.context_management.editors.compact import (
from litellm.llms.anthropic.pass_through.context_management.editors.compact import (
apply_client_compaction_block_history,
)

Expand Down Expand Up @@ -179,7 +179,7 @@ def _polyfill_will_run(
if edits is None:
return False

from litellm.llms.anthropic.experimental_pass_through.context_management.constants import (
from litellm.llms.anthropic.pass_through.context_management.constants import (
COMPACT_EDIT_TYPE,
)

Expand All @@ -205,7 +205,7 @@ def _spec_has_non_compact_edits(
if edits is None:
return False

from litellm.llms.anthropic.experimental_pass_through.context_management.constants import (
from litellm.llms.anthropic.pass_through.context_management.constants import (
COMPACT_EDIT_TYPE,
)

Expand Down Expand Up @@ -240,7 +240,7 @@ def _normalize_spec_edits(
if _context_management_explicitly_dropped(additional_drop_params):
return None

from litellm.llms.anthropic.experimental_pass_through.context_management.dispatcher import (
from litellm.llms.anthropic.pass_through.context_management.dispatcher import (
_normalize_spec,
)

Expand Down Expand Up @@ -437,7 +437,7 @@ def _normalize_reasoning_effort(
Handles both string ("max") and dict ({"effort": "max", "summary": ...})
formats. Uses model registry to check supports_xhigh/supports_minimal.
"""
from litellm.llms.anthropic.experimental_pass_through.utils import (
from litellm.llms.anthropic.pass_through.utils import (
normalize_reasoning_effort_value,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ def __init__(self, completion_stream: _ChunkStream):
@staticmethod
def _is_combined(chunk: "ModelResponseStream") -> bool:
"""True if ``chunk`` carries response content AND a finish_reason."""
from litellm.llms.anthropic.experimental_pass_through.messages.utils import (
from litellm.llms.anthropic.pass_through.messages.utils import (
openai_chat_refusal_text,
)

Expand Down Expand Up @@ -1029,7 +1029,7 @@ def _with_refusal_stop_details(
delta: Final = processed_chunk["delta"]
if delta.get("stop_reason") == "max_tokens":
return processed_chunk
from litellm.llms.anthropic.experimental_pass_through.messages.utils import (
from litellm.llms.anthropic.pass_through.messages.utils import (
refusal_stop_details,
)

Expand Down Expand Up @@ -1083,7 +1083,7 @@ def _delta_has_content(processed_chunk: Mapping[str, object]) -> bool:
@staticmethod
def _is_blank_delta(chunk: "ModelResponseStream") -> bool:
from litellm.llms.anthropic.common_utils import is_empty_unsigned_thinking_block
from litellm.llms.anthropic.experimental_pass_through.messages.utils import (
from litellm.llms.anthropic.pass_through.messages.utils import (
openai_chat_refusal_text,
)

Expand Down Expand Up @@ -1120,7 +1120,7 @@ def _should_start_new_content_block(self, chunk: "ModelResponseStream") -> bool:
- Different content types in the response
- Specific markers in the content
"""
from litellm.llms.anthropic.experimental_pass_through.messages.utils import (
from litellm.llms.anthropic.pass_through.messages.utils import (
openai_chat_refusal_text,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
from pydantic import JsonValue, TypeAdapter

import litellm
from litellm.llms.anthropic.experimental_pass_through.utils import (
from litellm.llms.anthropic.pass_through.utils import (
is_reasoning_auto_summary_enabled,
prompt_cache_key_from_user_id,
)
Expand Down Expand Up @@ -134,14 +134,14 @@ def create_tool_name_mapping(
normalize_anthropic_tool_use_id,
strip_encrypted_reasoning_blocks_from_anthropic_messages,
)
from litellm.llms.anthropic.experimental_pass_through.context_management import (
from litellm.llms.anthropic.pass_through.context_management import (
PolyfillResult,
)
from litellm.llms.anthropic.experimental_pass_through.messages.mid_conversation_system import (
from litellm.llms.anthropic.pass_through.messages.mid_conversation_system import (
convert_mid_conversation_system_turns,
is_system_role_message,
)
from litellm.llms.anthropic.experimental_pass_through.messages.utils import (
from litellm.llms.anthropic.pass_through.messages.utils import (
openai_chat_refusal_text,
refusal_stop_details,
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -798,7 +798,7 @@ def _count_effective_tokens(
threshold check matches the downstream ``input_tokens`` metric.
"""
# Local import to avoid pulling the adapter at module load time.
from litellm.llms.anthropic.experimental_pass_through.adapters.transformation import (
from litellm.llms.anthropic.pass_through.adapters.transformation import (
LiteLLMAnthropicMessagesAdapter,
)

Expand Down Expand Up @@ -955,7 +955,7 @@ def _build_summary_messages(
system prompt); the conversation history is translated to OpenAI shape;
the summarization prompt is appended as a final user turn.
"""
from litellm.llms.anthropic.experimental_pass_through.adapters.transformation import (
from litellm.llms.anthropic.pass_through.adapters.transformation import (
LiteLLMAnthropicMessagesAdapter,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -336,7 +336,7 @@ async def _settle_task(task: asyncio.Task | None) -> None:
await task

async def aclose(self) -> None:
from litellm.llms.anthropic.experimental_pass_through.messages.streaming_iterator import (
from litellm.llms.anthropic.pass_through.messages.streaming_iterator import (
aclose_if_supported,
)

Expand Down Expand Up @@ -379,7 +379,7 @@ async def _process_agentic_hooks(self) -> None:
if hasattr(result, "__aiter__"):
self._follow_up_iterator = result.__aiter__()
elif isinstance(result, dict):
from litellm.llms.anthropic.experimental_pass_through.messages.fake_stream_iterator import (
from litellm.llms.anthropic.pass_through.messages.fake_stream_iterator import (
FakeAnthropicMessagesStreamIterator,
)
from litellm.types.llms.anthropic_messages.anthropic_response import (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -215,7 +215,7 @@ async def _try_websearch_short_circuit(
if response is not None:
anthropic_response = cast(AnthropicMessagesResponse, response)
if stream:
from litellm.llms.anthropic.experimental_pass_through.messages.fake_stream_iterator import (
from litellm.llms.anthropic.pass_through.messages.fake_stream_iterator import (
FakeAnthropicMessagesStreamIterator,
)

Expand Down Expand Up @@ -531,7 +531,7 @@ def anthropic_messages_handler(
# reference the provider cannot resolve. Popped from kwargs so it never reaches the provider.
skip_mcp_handler: Final = kwargs.pop("_skip_mcp_handler", False)
if not skip_mcp_handler and tools:
from litellm.llms.anthropic.experimental_pass_through.messages.mcp_handler import (
from litellm.llms.anthropic.pass_through.messages.mcp_handler import (
anthropic_messages_with_mcp,
)
from litellm.responses.mcp.litellm_proxy_mcp_handler import (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ async def handle(
custom_llm_provider: str | None,
**kwargs,
) -> AnthropicMessagesResponse | AsyncIterator:
from litellm.llms.anthropic.experimental_pass_through.messages.fake_stream_iterator import (
from litellm.llms.anthropic.pass_through.messages.fake_stream_iterator import (
FakeAnthropicMessagesStreamIterator,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -180,7 +180,7 @@ async def anthropic_messages_with_mcp(
)

if stream:
from litellm.llms.anthropic.experimental_pass_through.messages.fake_stream_iterator import (
from litellm.llms.anthropic.pass_through.messages.fake_stream_iterator import (
FakeAnthropicMessagesStreamIterator,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
import litellm
from litellm._logging import verbose_logger
from litellm.caching.caching_handler import create_cache_write_task
from litellm.llms.anthropic.experimental_pass_through.messages.streaming_iterator import (
from litellm.llms.anthropic.pass_through.messages.streaming_iterator import (
AnthropicMessagesStreamingResponse,
BaseAnthropicMessagesStreamingIterator,
_is_message_stop_chunk,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
from litellm.litellm_core_utils.litellm_logging import Logging as LiteLLMLoggingObj
from litellm.litellm_core_utils.logging_worker import GLOBAL_LOGGING_WORKER
from litellm.llms.anthropic.common_utils import ANTHROPIC_ERROR_STATUS_CODE_MAP
from litellm.llms.anthropic.experimental_pass_through.messages.utils import INCOMPLETE_STREAM_ERROR_MESSAGE
from litellm.llms.anthropic.pass_through.messages.utils import INCOMPLETE_STREAM_ERROR_MESSAGE
from litellm.proxy.pass_through_endpoints.success_handler import (
PassThroughEndpointLogging,
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -590,7 +590,7 @@ def get_async_streaming_response_iterator(
litellm_logging_obj: LiteLLMLoggingObj,
) -> AsyncIterator:
"""Helper function to handle Anthropic streaming responses using the existing logging handlers"""
from litellm.llms.anthropic.experimental_pass_through.messages.streaming_iterator import (
from litellm.llms.anthropic.pass_through.messages.streaming_iterator import (
BaseAnthropicMessagesStreamingIterator,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ def _build_responses_kwargs(
if isinstance(reasoning, dict):
effort: Final[object] = reasoning.get("effort")
if isinstance(effort, str):
from litellm.llms.anthropic.experimental_pass_through.utils import (
from litellm.llms.anthropic.pass_through.utils import (
normalize_reasoning_effort_value,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
from litellm.litellm_core_utils.prompt_templates.common_utils import (
encrypted_reasoning_signature,
)
from litellm.llms.anthropic.experimental_pass_through.messages.utils import (
from litellm.llms.anthropic.pass_through.messages.utils import (
INCOMPLETE_STREAM_ERROR_MESSAGE,
refusal_stop_details,
responses_output_refusal_text,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,11 +20,11 @@
from litellm.litellm_core_utils.reasoning_effort_utils import (
reasoning_effort_from_thinking_budget,
)
from litellm.llms.anthropic.experimental_pass_through.messages.utils import (
from litellm.llms.anthropic.pass_through.messages.utils import (
refusal_stop_details,
responses_output_refusal_text,
)
from litellm.llms.anthropic.experimental_pass_through.utils import (
from litellm.llms.anthropic.pass_through.utils import (
is_reasoning_auto_summary_enabled,
prompt_cache_key_from_user_id,
)
Expand Down Expand Up @@ -69,7 +69,7 @@ def translate_responses_api_usage_to_anthropic_usage(
if raw_usage is None:
return AnthropicUsage(input_tokens=0, output_tokens=0)

from litellm.llms.anthropic.experimental_pass_through.adapters.transformation import (
from litellm.llms.anthropic.pass_through.adapters.transformation import (
LiteLLMAnthropicMessagesAdapter,
)
from litellm.responses.utils import ResponseAPILoggingUtils
Expand Down
2 changes: 1 addition & 1 deletion litellm/llms/anthropic/prompt_cache_prediction.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
from litellm.llms.anthropic.common_utils import AnthropicModelInfo, is_anthropic_oauth_key
from litellm.llms.anthropic.count_tokens.handler import AnthropicCountTokensHandler
from litellm.llms.anthropic.count_tokens.transformation import COUNT_TOKEN_OPTION_NAMES
from litellm.llms.anthropic.experimental_pass_through.messages.transformation import (
from litellm.llms.anthropic.pass_through.messages.transformation import (
DEFAULT_ANTHROPIC_API_VERSION,
AnthropicMessagesConfig,
)
Expand Down
2 changes: 1 addition & 1 deletion litellm/llms/azure_ai/anthropic/messages_transformation.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

from typing import Any, Final

from litellm.llms.anthropic.experimental_pass_through.messages.transformation import (
from litellm.llms.anthropic.pass_through.messages.transformation import (
AnthropicMessagesConfig,
)
from litellm.llms.azure.common_utils import BaseAzureLLM
Expand Down
2 changes: 1 addition & 1 deletion litellm/llms/bedrock/chat/converse_transformation.py
Original file line number Diff line number Diff line change
Expand Up @@ -1831,7 +1831,7 @@ def _filter_context_management_for_bedrock_converse(
anthropic_beta_list: list,
) -> None:
"""Keep only compact_20260112 edits for Bedrock; add beta header or drop field."""
from litellm.llms.anthropic.experimental_pass_through.context_management.constants import (
from litellm.llms.anthropic.pass_through.context_management.constants import (
COMPACT_EDIT_TYPE,
)
from litellm.types.llms.anthropic import ANTHROPIC_BETA_HEADER_VALUES
Expand Down
Loading
Loading