Skip to content

Commit 81fe63a

Browse files
jlowinihrpr
andauthored
Ensure failed oauth registration response is read before accessing response.text (#1118)
Co-authored-by: ihrpr <inna@anthropic.com>
1 parent ee54acb commit 81fe63a

File tree

2 files changed

+37
-0
lines changed

2 files changed

+37
-0
lines changed

src/mcp/client/auth.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -308,6 +308,7 @@ async def _register_client(self) -> httpx.Request | None:
308308
async def _handle_registration_response(self, response: httpx.Response) -> None:
309309
"""Handle registration response."""
310310
if response.status_code not in (200, 201):
311+
await response.aread()
311312
raise OAuthRegistrationError(f"Registration failed: {response.status_code} {response.text}")
312313

313314
try:

tests/client/test_auth.py

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -516,6 +516,42 @@ async def test_resource_param_included_with_protected_resource_metadata(self, oa
516516
assert "resource=" in content
517517

518518

519+
class TestRegistrationResponse:
520+
"""Test client registration response handling."""
521+
522+
@pytest.mark.anyio
523+
async def test_handle_registration_response_reads_before_accessing_text(self, oauth_provider):
524+
"""Test that response.aread() is called before accessing response.text."""
525+
526+
# Track if aread() was called
527+
class MockResponse:
528+
def __init__(self):
529+
self.status_code = 400
530+
self._aread_called = False
531+
self._text = "Registration failed with error"
532+
533+
async def aread(self):
534+
self._aread_called = True
535+
return b"test content"
536+
537+
@property
538+
def text(self):
539+
if not self._aread_called:
540+
raise RuntimeError("Response.text accessed before response.aread()")
541+
return self._text
542+
543+
mock_response = MockResponse()
544+
545+
# This should call aread() before accessing text
546+
with pytest.raises(Exception) as exc_info:
547+
await oauth_provider._handle_registration_response(mock_response)
548+
549+
# Verify aread() was called
550+
assert mock_response._aread_called
551+
# Verify the error message includes the response text
552+
assert "Registration failed: 400" in str(exc_info.value)
553+
554+
519555
class TestAuthFlow:
520556
"""Test the auth flow in httpx."""
521557

0 commit comments

Comments
 (0)