| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
|
We hit this in production with mcp 1.28.1 / FastMCP on StreamableHTTP stateless mode: 18 occurrences across 4 workspaces over 2026-07-19–20, always the same stack: ExceptionGroup(
anyio.ClosedResourceError
)
mcp/server/streamable_http_manager.py:180 run_stateless_server
mcp/server/lowlevel/server.py:694 _handle_message
await session.send_log_message(...) # Exception-path arm — client already gone
mcp/server/session.py:213 send_log_message → send_notification
mcp/shared/session.py:335 send_notification
await self._write_stream.send(session_message)
anyio.ClosedResourceError
The trigger: an Exception arrives in the session's read stream (the client disconnected mid-request), _handle_message hits the case Exception() arm and tries to send_log_message back — but the write stream is already closed. This PR (#2502) directly addresses it by hardening send_notification and _send_response at the BaseSession layer. As a stopgap we've applied a local monkey-patch in our downstream server, but we'd very much like to see this merged so we can pin to a clean upstream release. Happy to help with review, testing, or rebasing if that would unblock this. |
Sorry, something went wrong.
|
Friendly bump on this one 🙂 Wanted to share a quick status check in case it's helpful for review prioritization:
Given the production impact we're seeing (18 crashes across 4 workspaces in 2 days on 1.28.1, per the report above), we'd really appreciate a maintainer look when you have a moment. Happy to help with anything — additional test coverage, a rebase, or answering questions — if that would help move it along. Thanks so much for the work on this fix! 🙏 |
Sorry, something went wrong.
| Back | FazBrowse Home | New Git URL |
Audience / Scope / Status
Last verified against: v1.x on 2026-04-24
Relevant upstream issues
Summary
This PR makes BaseSession.send_notification() and BaseSession._send_response() treat writes to an already-closed transport as expected no-ops rather than exceptions.
The goal is narrow: if the peer has already gone away, a late response or notification should be dropped cleanly at the session send boundary.
Failure topology
Why the catch belongs here
Invariants
Changes
Validation
Functional
PYTHONPATH=src python3 -m pytest -o addopts='' \ tests/server/test_session.py \ tests/server/test_lowlevel_exception_handling.py -qLocal result after the CI-fix follow-up:
CI follow-up
The first push exposed two CI-only problems, not a runtime regression:
Targeted local follow-up verification:
Local result:
Non-goals