diff --git a/test/conformance/expected-failures.2026-07-28.yaml b/test/conformance/expected-failures.2026-07-28.yaml index e23ffbe1b3..5c30ea0ade 100644 --- a/test/conformance/expected-failures.2026-07-28.yaml +++ b/test/conformance/expected-failures.2026-07-28.yaml @@ -67,10 +67,6 @@ client: server: # --- Carried-forward scenarios (also run by the 2025 legs) --- - # WARNING-only: see the matching entry in expected-failures.yaml — the - # sep-2575 list_changed-on-listen SHOULD checks; fixture armed in a - # follow-up change. - - server-stateless # Pre-existing fixture/baseline bug: the fixture tool's schema is a plain # Zod object with none of the JSON Schema 2020-12 keywords the scenario # checks; it fails identically at 2025 in `--suite all` (not a 2026-path diff --git a/test/conformance/expected-failures.yaml b/test/conformance/expected-failures.yaml index 3b76bd94bf..c5ab22325a 100644 --- a/test/conformance/expected-failures.yaml +++ b/test/conformance/expected-failures.yaml @@ -49,14 +49,6 @@ client: server: # --- Draft-spec scenarios (in `--suite draft`; the default `active` suite is green) --- - # WARNING-only: with the listChanged capability now advertised in - # server/discover, server-stateless runs three additional SHOULD-level - # checks (sep-2575-server-sends-{tools,prompts,resources}-list-changed-on- - # subscription) that the conformance fixture cannot yet satisfy because it - # is not wired to publish list_changed events to listen streams. The - # fixture is armed in a follow-up change, after which this entry burns - # down. - - server-stateless # SEP-2243 (HTTP header standardization): the reject cells the SDK does # answer now use -32001 (HeaderMismatch), but missing-header enforcement # (Mcp-Method, Mcp-Name) and the Mcp-Name cross-check are not implemented, diff --git a/test/conformance/src/everythingServer.ts b/test/conformance/src/everythingServer.ts index 535b4e1221..5429e3be57 100644 --- a/test/conformance/src/everythingServer.ts +++ b/test/conformance/src/everythingServer.ts @@ -967,6 +967,43 @@ function createMcpServer() { } ); + // ===== SUBSCRIPTION/LISTEN DIAGNOSTIC TRIGGERS (SEP-2575) ===== + // + // The `server-stateless` conformance scenario opens a `subscriptions/listen` + // stream (served by `createMcpHandler`'s built-in listen router), then calls + // one of these triggers and asserts the corresponding `*/list_changed` + // notification arrives on the open stream. The trigger publishes the change + // event onto the handler's bus via the `handler.notify.*` sugar — the + // listen router stamps the subscription id and applies the per-stream + // filter, so the same trigger also exercises the ack-first and + // honors-notification-filter checks. The 2026-07-28 path is per-request + // (each call gets a fresh `McpServer`), so there is no list to mutate; the + // event itself is what the SHOULD requirement measures. + + mcpServer.registerTool( + 'test_trigger_tool_change', + { + description: 'Listen diagnostic (SEP-2575): publishes a tools/list_changed event onto the handler bus', + inputSchema: z.object({}) + }, + async (): Promise => { + modernHandler.notify.toolsChanged(); + return { content: [{ type: 'text', text: 'tools_list_changed published' }] }; + } + ); + + mcpServer.registerTool( + 'test_trigger_prompt_change', + { + description: 'Listen diagnostic (SEP-2575): publishes a prompts/list_changed event onto the handler bus', + inputSchema: z.object({}) + }, + async (): Promise => { + modernHandler.notify.promptsChanged(); + return { content: [{ type: 'text', text: 'prompts_list_changed published' }] }; + } + ); + // ===== RESOURCES ===== // Static text resource