Buffer per-request StreamableHTTP streams to avoid serial-router head-of-line block (#2934)
This commit is contained in:
parent
44ce901ce3
commit
a527142312
1 changed files with 292 additions and 188 deletions
|
|
@ -1634,84 +1634,6 @@ async def test_handle_sse_event_skips_empty_data() -> None:
|
|||
await read_stream.aclose()
|
||||
|
||||
|
||||
@pytest.mark.anyio
|
||||
async def test_priming_event_not_sent_for_old_protocol_version() -> None:
|
||||
"""_maybe_send_priming_event skips for old protocol versions (backwards compat)."""
|
||||
# Create a transport with an event store
|
||||
transport = StreamableHTTPServerTransport(
|
||||
"/mcp",
|
||||
event_store=SimpleEventStore(),
|
||||
)
|
||||
|
||||
# Create a mock stream writer
|
||||
write_stream, read_stream = anyio.create_memory_object_stream[dict[str, Any]](1)
|
||||
|
||||
try:
|
||||
# Call _maybe_send_priming_event with OLD protocol version - should NOT send
|
||||
await transport._maybe_send_priming_event("test-request-id", write_stream, "2025-06-18")
|
||||
|
||||
# Nothing should have been written to the stream
|
||||
assert write_stream.statistics().current_buffer_used == 0
|
||||
|
||||
# Now test with NEW protocol version - should send
|
||||
await transport._maybe_send_priming_event("test-request-id-2", write_stream, "2025-11-25")
|
||||
|
||||
# Should have written a priming event
|
||||
assert write_stream.statistics().current_buffer_used == 1
|
||||
finally:
|
||||
await write_stream.aclose()
|
||||
await read_stream.aclose()
|
||||
|
||||
|
||||
@pytest.mark.anyio
|
||||
async def test_priming_event_not_sent_without_event_store() -> None:
|
||||
"""_maybe_send_priming_event returns early when no event_store is configured."""
|
||||
# Create a transport WITHOUT an event store
|
||||
transport = StreamableHTTPServerTransport("/mcp")
|
||||
|
||||
# Create a mock stream writer
|
||||
write_stream, read_stream = anyio.create_memory_object_stream[dict[str, Any]](1)
|
||||
|
||||
try:
|
||||
# Call _maybe_send_priming_event - should return early without sending
|
||||
await transport._maybe_send_priming_event("test-request-id", write_stream, "2025-11-25")
|
||||
|
||||
# Nothing should have been written to the stream
|
||||
assert write_stream.statistics().current_buffer_used == 0
|
||||
finally:
|
||||
await write_stream.aclose()
|
||||
await read_stream.aclose()
|
||||
|
||||
|
||||
@pytest.mark.anyio
|
||||
async def test_priming_event_includes_retry_interval() -> None:
|
||||
"""_maybe_send_priming_event includes the retry field when retry_interval is set."""
|
||||
# Create a transport with an event store AND retry_interval
|
||||
transport = StreamableHTTPServerTransport(
|
||||
"/mcp",
|
||||
event_store=SimpleEventStore(),
|
||||
retry_interval=5000,
|
||||
)
|
||||
|
||||
# Create a mock stream writer
|
||||
write_stream, read_stream = anyio.create_memory_object_stream[dict[str, Any]](1)
|
||||
|
||||
try:
|
||||
# Call _maybe_send_priming_event with new protocol version
|
||||
await transport._maybe_send_priming_event("test-request-id", write_stream, "2025-11-25")
|
||||
|
||||
# Should have written a priming event with retry field
|
||||
assert write_stream.statistics().current_buffer_used == 1
|
||||
|
||||
# Read the event and verify it has retry field
|
||||
event = await read_stream.receive()
|
||||
assert "retry" in event
|
||||
assert event["retry"] == 5000
|
||||
finally:
|
||||
await write_stream.aclose()
|
||||
await read_stream.aclose()
|
||||
|
||||
|
||||
@pytest.mark.anyio
|
||||
async def test_close_sse_stream_callback_not_provided_for_old_protocol_version() -> None:
|
||||
"""close_sse_stream callbacks are only provided for protocol versions that support polling."""
|
||||
|
|
@ -1744,30 +1666,6 @@ async def test_close_sse_stream_callback_not_provided_for_old_protocol_version()
|
|||
assert session_msg_new.metadata.close_standalone_sse_stream is not None
|
||||
|
||||
|
||||
@pytest.mark.anyio
|
||||
async def test_priming_event_not_sent_for_unknown_protocol_version() -> None:
|
||||
"""_maybe_send_priming_event treats unrecognized version strings conservatively.
|
||||
|
||||
A garbage version must not be mistaken for a future one (lexicographically
|
||||
"zzz" sorts after every date-shaped revision).
|
||||
"""
|
||||
transport = StreamableHTTPServerTransport(
|
||||
"/mcp",
|
||||
event_store=SimpleEventStore(),
|
||||
)
|
||||
|
||||
write_stream, read_stream = anyio.create_memory_object_stream[dict[str, Any]](1)
|
||||
|
||||
try:
|
||||
await transport._maybe_send_priming_event("test-request-id", write_stream, "zzz")
|
||||
|
||||
# Nothing should have been written to the stream
|
||||
assert write_stream.statistics().current_buffer_used == 0
|
||||
finally:
|
||||
await write_stream.aclose()
|
||||
await read_stream.aclose()
|
||||
|
||||
|
||||
@pytest.mark.anyio
|
||||
async def test_close_sse_stream_callback_not_provided_for_unknown_protocol_version() -> None:
|
||||
"""close_sse_stream callbacks are withheld when the client's version is unrecognized."""
|
||||
|
|
|
|||
Loading…
Reference in a new issue