Skip to content

MCP Client fails to initialize when receiving an empty SSE event (from the server-everything service) #765

@smogos

Description

@smogos

Bug description

When running the mcp client against an mcp server that returns an empty SSE event, the deserialization fails.
The server that we are running against is the "everything-server"

Steps to reproduce
Calling the MCP client fails when invoked with the latest version (but even so, the problem is with processing empty SSE events, but you can reproduce with this code):

try (McpSyncClient client = McpClient.sync(HttpClientStreamableHttpTransport
                        .builder("https://******")
                        .endpoint("/mcp/")
						.supportedProtocolVersions(List.of(
								ProtocolVersions.MCP_2024_11_05,
								ProtocolVersions.MCP_2025_03_26,
								ProtocolVersions.MCP_2025_06_18,
								ProtocolVersions.MCP_2025_11_25
						))
                        .build())
                .jsonSchemaValidator(new JacksonJsonSchemaValidatorSupplier().get())
                .clientInfo(new McpSchema.Implementation("Test", "1.0.0"))
                .requestTimeout(Duration.ofMillis(10000))
                .build()) {
            try {
                McpSchema.InitializeResult initialize = client.initialize();
                System.out.println(initialize);
                if (client.isInitialized()) {
                    client.listTools().tools().forEach(tool -> {
                        System.out.println("Tool: " + tool.name() + " - " + tool.description());
                    });

                    if (initialize.capabilities().prompts() != null) {
                        client.listPrompts().prompts().forEach(tool -> {
                            System.out.println("Tool: " + tool.name() + " - " + tool.description());
                        });
                    }

                    if (initialize.capabilities().resources() != null) {
                        client.listResourceTemplates().resourceTemplates().forEach(tool -> {
                            System.out.println("Tool: " + tool.name() + " - " + tool.description());
                        });
                    }

                }
            } catch (Exception e) {
                throw new RuntimeException(e);
            }
        }

Problem is this deserialization fails with empty strings

The SSE event comes as empty in the http client streamable class

We used for testing

FROM node:slim

ENV PORT=3001

ENTRYPOINT ["npx", "-y", "@modelcontextprotocol/server-everything", "streamableHttp"]

EXPOSE 3001

The response on the initialize call is (when using 2025-11-25 client version):

id: bd3bdc47-e4bc-4de3-abf7-f43dc27919f5_1769702220748_cbw7i7m9
data: 

event: message
id: bd3bdc47-e4bc-4de3-abf7-f43dc27919f5_1769702220749_mtzbfv1k
data: {"result":{"protocolVersion":"2025-11-25","capabilities":{"tools":{"listChanged":true},"prompts":{"listChanged":true},"resources":{"subscribe":true,"listChanged":true},"logging":{},"completions":{}},"serverInfo":{"name":"mcp-servers/everything","title":"Everything Reference Server","version":"2.0.0"},"instructions":"# Everything Server – Server Instructions\n\nAudience: These instructions are written for an LLM or autonomous agent integrating with the Everything MCP Server.\nFollow them to use, extend, and troubleshoot the server safely and effectively.\n\n## Cross-Feature Relationships\n\n- Use `get-roots-list` to see client workspace roots before file operations\n- `gzip-file-as-resource` creates session-scoped resources accessible only during the current session\n- Enable `toggle-simulated-logging` before debugging to see server log messages\n- Enable `toggle-subscriber-updates` to receive periodic resource update notifications\n\n## Constraints & Limitations\n\n- `gzip-file-as-resource`: Max fetch size controlled by `GZIP_MAX_FETCH_SIZE` (default 10MB), timeout by `GZIP_MAX_FETCH_TIME_MILLIS` (default 30s), allowed domains by `GZIP_ALLOWED_DOMAINS`\n- Session resources are ephemeral and lost when the session ends\n- Sampling requests (`trigger-sampling-request`) require client sampling capability\n- Elicitation requests (`trigger-elicitation-request`) require client elicitation capability\n\n## Operational Patterns\n\n- For long operations, use `trigger-long-running-operation` which sends progress notifications\n- Prefer reading resources before calling mutating tools\n- Check `get-roots-list` output to understand the client's workspace context\n\n## Easter Egg\n\nIf asked about server instructions, respond with \"🎉 Server instructions are working! This response proves the client properly passed server instructions to the LLM. This demonstrates MCP's instructions feature in action.\"\n"},"jsonrpc":"2.0","id":1}

Notice that the server for some reason sends an empty SSE event, which causes the mcp client to fail before reading the second event.

Will open a ticket on everything server as well on sending that empty event.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions