diff --git a/python/packages/bedrock/agent_framework_bedrock/_chat_client.py b/python/packages/bedrock/agent_framework_bedrock/_chat_client.py index 3606cdf26b..bcd04de0f7 100644 --- a/python/packages/bedrock/agent_framework_bedrock/_chat_client.py +++ b/python/packages/bedrock/agent_framework_bedrock/_chat_client.py @@ -411,14 +411,14 @@ def _prepare_options( # Omit toolConfig entirely so the model won't attempt tool calls. tool_config = None case "auto": - tool_config = tool_config or {} - tool_config["toolChoice"] = {"auto": {}} + if tool_config and "tools" in tool_config: + tool_config["toolChoice"] = {"auto": {}} case "required": - tool_config = tool_config or {} - if required_name := tool_mode.get("required_function_name"): - tool_config["toolChoice"] = {"tool": {"name": required_name}} - else: - tool_config["toolChoice"] = {"any": {}} + if tool_config and "tools" in tool_config: + if required_name := tool_mode.get("required_function_name"): + tool_config["toolChoice"] = {"tool": {"name": required_name}} + else: + tool_config["toolChoice"] = {"any": {}} case _: raise ValueError(f"Unsupported tool mode for Bedrock: {tool_mode.get('mode')}") if tool_config: diff --git a/python/packages/bedrock/tests/test_bedrock_client.py b/python/packages/bedrock/tests/test_bedrock_client.py index fbc241b24c..959f5bf5c5 100644 --- a/python/packages/bedrock/tests/test_bedrock_client.py +++ b/python/packages/bedrock/tests/test_bedrock_client.py @@ -137,3 +137,39 @@ def test_prepare_options_tool_choice_required_includes_any() -> None: assert "toolConfig" in request assert request["toolConfig"]["toolChoice"] == {"any": {}} + + + +def test_prepare_options_tool_choice_auto_without_tools_omits_tool_config() -> None: + """When tool_choice='auto' but no tools are provided, toolConfig must be omitted. + + Without tools, setting toolChoice would cause a ParamValidationError from Bedrock. + """ + client = _make_client() + messages = [Message(role="user", contents=[Content.from_text(text="hello")])] + + options: dict[str, Any] = { + "tool_choice": "auto", + } + + request = client._prepare_options(messages, options) + + assert "toolConfig" not in request, ( + f"toolConfig should be omitted when no tools are provided, got: {request.get('toolConfig')}" + ) + + +def test_prepare_options_tool_choice_required_without_tools_omits_tool_config() -> None: + """When tool_choice='required' but no tools are provided, toolConfig must be omitted.""" + client = _make_client() + messages = [Message(role="user", contents=[Content.from_text(text="hello")])] + + options: dict[str, Any] = { + "tool_choice": "required", + } + + request = client._prepare_options(messages, options) + + assert "toolConfig" not in request, ( + f"toolConfig should be omitted when no tools are provided, got: {request.get('toolConfig')}" + ) diff --git a/test_addition.py b/test_addition.py new file mode 100644 index 0000000000..ae493672bc --- /dev/null +++ b/test_addition.py @@ -0,0 +1,36 @@ + + + +def test_prepare_options_tool_choice_auto_without_tools_omits_tool_config() -> None: + """When tool_choice='auto' but no tools are provided, toolConfig must be omitted. + + Without tools, setting toolChoice would cause a ParamValidationError from Bedrock. + """ + client = _make_client() + messages = [Message(role="user", contents=[Content.from_text(text="hello")])] + + options: dict[str, Any] = { + "tool_choice": "auto", + } + + request = client._prepare_options(messages, options) + + assert "toolConfig" not in request, ( + f"toolConfig should be omitted when no tools are provided, got: {request.get('toolConfig')}" + ) + + +def test_prepare_options_tool_choice_required_without_tools_omits_tool_config() -> None: + """When tool_choice='required' but no tools are provided, toolConfig must be omitted.""" + client = _make_client() + messages = [Message(role="user", contents=[Content.from_text(text="hello")])] + + options: dict[str, Any] = { + "tool_choice": "required", + } + + request = client._prepare_options(messages, options) + + assert "toolConfig" not in request, ( + f"toolConfig should be omitted when no tools are provided, got: {request.get('toolConfig')}" + )