mirror of
https://github.com/BerriAI/litellm.git
synced 2026-09-12 23:01:41 +00:00
fix(bedrock): drop client_metadata for every converse model
This commit is contained in:
parent
c05aef159f
commit
53da9bca8e
3 changed files with 15 additions and 89 deletions
|
|
@ -86,7 +86,6 @@ from litellm.utils import (
|
|||
from ..common_utils import (
|
||||
BedrockError,
|
||||
BedrockModelInfo,
|
||||
bedrock_arn_hides_model_family,
|
||||
bedrock_converse_supports_parallel_tool_use_config,
|
||||
bedrock_model_accepts_cache_points,
|
||||
get_anthropic_beta_from_headers,
|
||||
|
|
@ -1335,14 +1334,7 @@ class AmazonConverseConfig(BaseConfig):
|
|||
)
|
||||
|
||||
additional_request_params.pop("parallel_tool_calls", None)
|
||||
|
||||
drops_client_metadata: Final = base_model.startswith("anthropic") or bedrock_arn_hides_model_family(model)
|
||||
if drops_client_metadata and additional_request_params.pop("client_metadata", None) is not None:
|
||||
litellm.verbose_logger.debug(
|
||||
"Bedrock Converse: dropping `client_metadata` for model=%s, Anthropic rejects it with "
|
||||
"'client_metadata: Extra inputs are not permitted'",
|
||||
model,
|
||||
)
|
||||
additional_request_params.pop("client_metadata", None)
|
||||
|
||||
# Only set the topK value in for models that support it
|
||||
additional_request_params.update(self._handle_top_k_value(model, inference_params, drop_params))
|
||||
|
|
|
|||
|
|
@ -809,15 +809,6 @@ def get_bedrock_base_model(model: str) -> str:
|
|||
return model
|
||||
|
||||
|
||||
def bedrock_arn_hides_model_family(model: str) -> bool:
|
||||
"""
|
||||
True for an ARN-addressed model whose base name carries no ``provider.model``
|
||||
id, such as an application inference profile or a provisioned throughput ARN.
|
||||
Callers that gate behavior on the model family cannot resolve one here.
|
||||
"""
|
||||
return "arn:" in model.lower() and "." not in get_bedrock_base_model(model)
|
||||
|
||||
|
||||
def bedrock_converse_supports_parallel_tool_use_config(model: str) -> bool:
|
||||
return any(
|
||||
(litellm.model_cost.get(candidate) or {}).get("supports_parallel_tool_use_config") is True
|
||||
|
|
|
|||
|
|
@ -979,16 +979,19 @@ def test_config_blocks_do_not_leak_into_inference_config():
|
|||
assert data["serviceTier"] == {"type": "priority"}
|
||||
|
||||
|
||||
@pytest.mark.parametrize("model", ["anthropic.claude-opus-4-8", "us.anthropic.claude-opus-4-8"])
|
||||
def test_client_metadata_stripped_for_anthropic_converse_request(model):
|
||||
"""``client_metadata`` sent by codex must not reach Anthropic as a passthrough model field.
|
||||
|
||||
Converse forwards ``additionalModelRequestFields`` verbatim to the model, and Anthropic
|
||||
rejects the request with "client_metadata: Extra inputs are not permitted".
|
||||
"""
|
||||
config = AmazonConverseConfig()
|
||||
|
||||
data = config._transform_request_helper(
|
||||
@pytest.mark.parametrize(
|
||||
"model",
|
||||
[
|
||||
"anthropic.claude-opus-4-8",
|
||||
"us.anthropic.claude-opus-4-8",
|
||||
"amazon.nova-pro-v1:0",
|
||||
"us.meta.llama4-maverick-17b-instruct-v1:0",
|
||||
"arn:aws:bedrock:us-east-1:123456789012:application-inference-profile/abcdef123456",
|
||||
"arn:aws:bedrock:us-east-1:123456789012:inference-profile/us.amazon.nova-pro-v1:0",
|
||||
],
|
||||
)
|
||||
def test_client_metadata_stripped_from_converse_request(model):
|
||||
data = AmazonConverseConfig()._transform_request_helper(
|
||||
model=model,
|
||||
system_content_blocks=[],
|
||||
optional_params={
|
||||
|
|
@ -999,71 +1002,11 @@ def test_client_metadata_stripped_for_anthropic_converse_request(model):
|
|||
messages=None,
|
||||
)
|
||||
|
||||
fields = data.get("additionalModelRequestFields", {})
|
||||
fields = data["additionalModelRequestFields"]
|
||||
assert "client_metadata" not in fields
|
||||
assert fields["anthropic_beta"] == ["computer-use-2025-01-24"]
|
||||
|
||||
|
||||
def test_client_metadata_kept_for_non_anthropic_converse_request():
|
||||
"""Only Anthropic is known to reject ``client_metadata``, so other families keep the passthrough."""
|
||||
config = AmazonConverseConfig()
|
||||
|
||||
data = config._transform_request_helper(
|
||||
model="amazon.nova-pro-v1:0",
|
||||
system_content_blocks=[],
|
||||
optional_params={
|
||||
"maxTokens": 16,
|
||||
"client_metadata": {"originator": "codex_cli_rs"},
|
||||
},
|
||||
messages=None,
|
||||
)
|
||||
|
||||
assert data["additionalModelRequestFields"]["client_metadata"] == {"originator": "codex_cli_rs"}
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"model",
|
||||
[
|
||||
"arn:aws:bedrock:us-east-1:123456789012:application-inference-profile/abcdef123456",
|
||||
"arn:aws:bedrock:us-east-1:123456789012:provisioned-model/abcdef123456",
|
||||
],
|
||||
)
|
||||
def test_client_metadata_stripped_for_arn_models_converse(model):
|
||||
"""An ARN hides which family serves the request, and pointing one at Claude is how
|
||||
teams route codex traffic, so the field has to go there too or the 400 comes back."""
|
||||
config = AmazonConverseConfig()
|
||||
|
||||
data = config._transform_request_helper(
|
||||
model=model,
|
||||
system_content_blocks=[],
|
||||
optional_params={
|
||||
"maxTokens": 16,
|
||||
"client_metadata": {"originator": "codex_cli_rs"},
|
||||
},
|
||||
messages=None,
|
||||
)
|
||||
|
||||
assert "client_metadata" not in data.get("additionalModelRequestFields", {})
|
||||
|
||||
|
||||
def test_client_metadata_kept_for_arn_naming_a_non_anthropic_family():
|
||||
"""An inference profile ARN that still spells out the family is resolvable, so a
|
||||
non-Anthropic one keeps its passthrough."""
|
||||
config = AmazonConverseConfig()
|
||||
|
||||
data = config._transform_request_helper(
|
||||
model="arn:aws:bedrock:us-east-1:123456789012:inference-profile/us.amazon.nova-pro-v1:0",
|
||||
system_content_blocks=[],
|
||||
optional_params={
|
||||
"maxTokens": 16,
|
||||
"client_metadata": {"originator": "codex_cli_rs"},
|
||||
},
|
||||
messages=None,
|
||||
)
|
||||
|
||||
assert data["additionalModelRequestFields"]["client_metadata"] == {"originator": "codex_cli_rs"}
|
||||
|
||||
|
||||
def test_parallel_tool_calls_config_kept_for_sonnet_5(monkeypatch):
|
||||
old_env = os.environ.get("LITELLM_LOCAL_MODEL_COST_MAP")
|
||||
old_cost = litellm.model_cost
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue