Skip to content

Commit 35b30fa

Browse files
authored
Merge pull request #55 from sacha-development-stuff/codex/fix-incompatible-method-override-errors
Align OAuth metadata handler return types
2 parents 1bb4bc9 + 4d3b51e commit 35b30fa

File tree

1 file changed

+24
-20
lines changed

1 file changed

+24
-20
lines changed

src/mcp/client/auth/oauth2.py

Lines changed: 24 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -215,12 +215,15 @@ def _get_discovery_urls(self, server_url: str | None = None) -> list[str]:
215215
def _create_oauth_metadata_request(self, url: str) -> httpx.Request:
216216
return httpx.Request("GET", url, headers={MCP_PROTOCOL_VERSION: LATEST_PROTOCOL_VERSION})
217217

218-
async def _handle_oauth_metadata_response(self, response: httpx.Response) -> None:
219-
content = await response.aread()
220-
metadata = OAuthMetadata.model_validate_json(content)
221-
self._metadata = metadata
222-
if self.client_metadata.scope is None and metadata.scopes_supported is not None:
223-
self.client_metadata.scope = " ".join(metadata.scopes_supported)
218+
async def _handle_oauth_metadata_response(
219+
self, response: httpx.Response
220+
) -> tuple[bool, OAuthMetadata | None]:
221+
ok, metadata = await handle_auth_metadata_response(response)
222+
if metadata:
223+
self._metadata = metadata
224+
if self.client_metadata.scope is None and metadata.scopes_supported is not None:
225+
self.client_metadata.scope = " ".join(metadata.scopes_supported)
226+
return ok, metadata
224227

225228
def _create_registration_request(self, metadata: OAuthMetadata | None = None) -> httpx.Request | None:
226229
context = getattr(self, "context", None)
@@ -348,15 +351,25 @@ async def _handle_protected_resource_response(self, response: httpx.Response) ->
348351
)
349352
return False
350353

351-
async def _handle_oauth_metadata_response(self, response: httpx.Response) -> tuple[bool, OAuthMetadata | None]:
352-
ok, asm = await handle_auth_metadata_response(response)
354+
async def _handle_oauth_metadata_response(
355+
self, response: httpx.Response
356+
) -> tuple[bool, OAuthMetadata | None]:
357+
ok, asm = await super()._handle_oauth_metadata_response(response)
353358
if asm:
354359
self.context.oauth_metadata = asm
355-
self._metadata = asm
356360
if self.context.client_metadata.scope is None and asm.scopes_supported is not None:
357361
self.context.client_metadata.scope = " ".join(asm.scopes_supported)
358362
return ok, asm
359363

364+
def _select_scopes(self, scope_header: str | None) -> None:
365+
"""Select scopes based on discovery data and WWW-Authenticate header."""
366+
367+
self.context.client_metadata.scope = get_client_metadata_scopes(
368+
scope_header,
369+
self.context.protected_resource_metadata,
370+
self.context.oauth_metadata,
371+
)
372+
360373
async def _perform_authorization(self) -> httpx.Request:
361374
"""Perform the authorization flow."""
362375
auth_code, code_verifier = await self._perform_authorization_code_grant()
@@ -588,12 +601,7 @@ async def async_auth_flow(self, request: httpx.Request) -> AsyncGenerator[httpx.
588601
oauth_metadata_request = self._create_oauth_metadata_request(url)
589602
oauth_metadata_response = yield oauth_metadata_request
590603

591-
result = await self._handle_oauth_metadata_response(oauth_metadata_response)
592-
if isinstance(result, tuple):
593-
ok, asm = result
594-
else:
595-
ok = bool(result) if result is not None else True
596-
asm = self.context.oauth_metadata or self._metadata
604+
ok, asm = await self._handle_oauth_metadata_response(oauth_metadata_response)
597605

598606
if not ok:
599607
break
@@ -608,11 +616,7 @@ async def async_auth_flow(self, request: httpx.Request) -> AsyncGenerator[httpx.
608616
self._metadata = authorization_metadata
609617

610618
# Step 3: Apply scope selection strategy
611-
self.context.client_metadata.scope = get_client_metadata_scopes(
612-
www_auth_scope,
613-
self.context.protected_resource_metadata,
614-
self.context.oauth_metadata,
615-
)
619+
self._select_scopes(www_auth_scope)
616620

617621
# Step 4: Register client if needed
618622
if not self.context.client_info:

0 commit comments

Comments
 (0)