Skip to content

v5.5.6 - MCP Clients Receive the Streaming SSE Response

Choose a tag to compare

@AdrianCurtin AdrianCurtin released this 25 Jul 16:24
· 17 commits to main since this release

MCP clients now receive the SSE response instead of hanging

A focused fix release for the MCP Streamable HTTP transport. The SSE path
framed its events with custom event names, which every conforming MCP client
discards — so a streaming tools/call produced no progress and never
delivered its result, leaving the client blocked until its own timeout. All
frames now carry the protocol's message event name and are delivered.

Changes

  • FIXED: The request-scoped SSE stream emitted event: progress for
    notifications/progress and event: response for the terminating JSON-RPC
    response. MCP Streamable HTTP defines a single SSE event type for JSON-RPC
    traffic, and clients match only the default message type, so both frame
    kinds were silently dropped on arrival. Tool progress reported through
    agent.report_progress never surfaced, and — the failure that made
    streaming unusable — the final response never reached the client, which
    blocked until it timed out on its own. Both sites now emit event: message,
    as the server-to-client GET notification stream and the list_changed
    notifications already did.
  • CHANGED: Clients discriminate frames from the JSON-RPC envelope rather
    than the SSE event name — method present marks a notification, id plus
    result/error marks the response — which is how the protocol intends the
    stream to be read and what conforming clients already do.

Behavior Notes

  • This is a wire-format change on Parse::Agent::MCPRackApp when constructed
    with streaming: true. Non-streaming JSON responses, transport-level error
    shapes, status codes, and every event payload are byte-identical to 5.5.5;
    only the SSE event: line changed.
  • Deployments that worked around this with middleware rewriting the event name
    on the way out should remove it. With both sides corrected, a rewrite of
    response to message is a harmless no-op, but a rewrite in the opposite
    direction will reintroduce the hang.
  • Custom clients that were written against this SDK specifically and match on
    event: progress or event: response need to match message and branch on
    the envelope instead.
  • The standalone Parse::Agent::MCPServer is unaffected. It runs on WEBrick,
    which buffers whole response bodies, so it constructs the Rack app with
    streaming: false and never emitted SSE frames.

Wire Format

# 5.5.5 — discarded by clients matching the default `message` type
event: progress
data: {"jsonrpc":"2.0","method":"notifications/progress","params":{...}}

event: response
data: {"jsonrpc":"2.0","id":7,"result":{...}}

# 5.5.6 — delivered; the envelope identifies the frame
event: message
data: {"jsonrpc":"2.0","method":"notifications/progress","params":{...}}

event: message
data: {"jsonrpc":"2.0","id":7,"result":{...}}

Commit: 7c29bb4
Author: Adrian Curtin
Date: July 25, 2026