diff --git a/litellm/mcp_client/tools.py b/litellm/mcp_client/tools.py index 1c19425eae4..b1faa829712 100644 --- a/litellm/mcp_client/tools.py +++ b/litellm/mcp_client/tools.py @@ -134,6 +134,14 @@ async def list_tools_with_pagination( ListToolsRequest(params=params), _LenientListToolsResult, ) + # ClientSession.list_tools() normally performs this post-processing + # after decoding: it filters invalid x-mcp-header annotations and + # records the derived header/output-schema state used by tools/call. + # Keep those semantics when injecting the lenient result model. + result = session._absorb_tool_listing( + result, + complete=cursor is None and result.next_cursor is None, + ) tools.extend(result.tools) next_cursor = result.next_cursor diff --git a/tests/unit/mcp_client/test_tools.py b/tests/unit/mcp_client/test_tools.py index 039e57c2b69..faec7315406 100644 --- a/tests/unit/mcp_client/test_tools.py +++ b/tests/unit/mcp_client/test_tools.py @@ -46,6 +46,7 @@ def mock_session(): return await session.list_tools() session.send_request = AsyncMock(side_effect=send_request) + session._absorb_tool_listing.side_effect = lambda result, **_kwargs: result return session