Skip to content

Commit 0be8852

Browse files
committed
Refresh the locked runtime dependencies
uv.lock had not moved for most runtime dependencies since mid-2025, so the `locked` CI leg was certifying anyio 4.10 / starlette 0.49 / uvicorn 0.35 / pyjwt 2.10 while a fresh install of the SDK gets releases a year newer. Re-resolve the runtime closure of mcp[cli,rich] (the same set the dependency canary floats) to current versions; test and docs tooling are left where they were for Dependabot to move. Every bumped version is at least two weeks old. Newer stubs need three typing adjustments, none of which change behaviour: anyio 4.12+ types `TaskGroup.start_soon` as taking a coroutine function (which it always required at runtime), so `_spawn` and `_contained_notify` say so; Starlette 0.52 made `Request` generic over its state type, so the one test that reads request attributes pins the parameter; and `start_soon` now returns a handle, so a test callback that must return None wraps it.
1 parent ea01985 commit 0be8852

4 files changed

Lines changed: 653 additions & 509 deletions

File tree

‎src/mcp/shared/jsonrpc_dispatcher.py‎

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99

1010
import contextvars
1111
import logging
12-
from collections.abc import Awaitable, Callable, Mapping
12+
from collections.abc import Awaitable, Callable, Coroutine, Mapping
1313
from dataclasses import dataclass, field
1414
from functools import partial
1515
from typing import Any, Generic, Literal, cast
@@ -209,7 +209,9 @@ async def _wrapped(progress: float, total: float | None, message: str | None) ->
209209
return _wrapped
210210

211211

212-
def _contained_notify(fn: OnNotify) -> OnNotify:
212+
def _contained_notify(
213+
fn: OnNotify,
214+
) -> Callable[[DispatchContext[TransportContext], str, Mapping[str, Any] | None], Coroutine[Any, Any, None]]:
213215
"""Wrap a notification handler so it can't crash the dispatcher (same boundary as `_shielded_progress`)."""
214216

215217
async def _wrapped(dctx: DispatchContext[TransportContext], method: str, params: Mapping[str, Any] | None) -> None:
@@ -670,7 +672,7 @@ def _resolve_pending(self, request_id: RequestId | None, outcome: dict[str, Any]
670672

671673
def _spawn(
672674
self,
673-
fn: Callable[..., Awaitable[Any]],
675+
fn: Callable[..., Coroutine[Any, Any, Any]],
674676
*args: object,
675677
sender_ctx: contextvars.Context | None,
676678
) -> None:

‎tests/client/test_stdio.py‎

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -436,7 +436,10 @@ async def die_late() -> None:
436436
process.exit(0)
437437

438438
# The grace wait starts when stdin closes; anchor the death there.
439-
process.on_stdin_close = lambda: tg.start_soon(die_late)
439+
def schedule_death() -> None:
440+
tg.start_soon(die_late)
441+
442+
process.on_stdin_close = schedule_death
440443
# no branch: the tracer drops this nested async-with's arcs under
441444
# trio's MockClock even though the body runs.
442445
async with stdio_client(FAKE_PARAMS): # pragma: no branch

‎tests/shared/test_streamable_http.py‎

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1314,17 +1314,20 @@ async def _handle_context_list_tools(
13141314

13151315
async def _handle_context_call_tool(ctx: ServerRequestContext, params: CallToolRequestParams) -> CallToolResult:
13161316
assert params.name in ("echo_headers", "echo_context")
1317-
assert isinstance(ctx.request, Request)
1317+
assert ctx.request is not None
1318+
# Starlette's Request is generic over its state type (0.52+); pin the parameter so member access stays typed.
1319+
request: Request[Any] = ctx.request
1320+
assert isinstance(request, Request)
13181321

13191322
if params.name == "echo_headers":
1320-
return CallToolResult(content=[TextContent(type="text", text=json.dumps(dict(ctx.request.headers)))])
1323+
return CallToolResult(content=[TextContent(type="text", text=json.dumps(dict(request.headers)))])
13211324

13221325
assert params.arguments is not None
13231326
context_data: dict[str, Any] = {
13241327
"request_id": params.arguments.get("request_id"),
1325-
"headers": dict(ctx.request.headers),
1326-
"method": ctx.request.method,
1327-
"path": ctx.request.url.path,
1328+
"headers": dict(request.headers),
1329+
"method": request.method,
1330+
"path": request.url.path,
13281331
"protocol_version": ctx.protocol_version,
13291332
"session_protocol_version": ctx.session.protocol_version,
13301333
}

0 commit comments

Comments
 (0)