Files
Skald-Circle/docs/mcp/specs/2025-06-18.md
T
2026-07-10 15:02:09 +01:00

89 lines
13 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# MCP Specification — 2025-06-18 (Stable)
> **Status:** Stable
> **Released:** 2025-06-18
> **Spec site:** https://modelcontextprotocol.io/specification/2025-06-18
> **Authoritative schema:** [schema/2025-06-18/schema.ts](https://github.com/modelcontextprotocol/specification/blob/main/schema/2025-06-18/schema.ts)
Revision 2025-06-18 is the "modern stable" baseline of the Model Context Protocol. It supersedes the 2024-11-05 legacy revision by introducing the **Streamable HTTP** transport (single-endpoint, replacing the two-endpoint HTTP+SSE design), the **Elicitation** client feature (`elicitation/create`, server-initiated structured input from the user), and **structured tool output** (typed `structuredContent` validated against an optional `outputSchema`). It also tightens the authorization framework with OAuth 2.1 Resource Indicators (RFC 8707) and OAuth Protected Resource Metadata (RFC 9728), and removes JSON-RPC batching. The authoritative source of truth is the TypeScript schema; the spec text is normative where it restates requirements using BCP 14 keywords (MUST/SHOULD/MAY).
## At a glance
- **Protocol style:** stateful connections
- **Capability negotiation:** connection-level (`initialize`)
- **Transports:** stdio; **Streamable HTTP** (replaces HTTP+SSE)
- **Server features:** Resources, Prompts, Tools, Logging
- **Client features:** Sampling, Roots, **Elicitation**
- **Authorization:** OAuth 2.1 + Resource Indicators (RFC 8707)
## Architecture
Client-host-server topology built on JSON-RPC. A **host** creates and manages multiple **client** instances; each client holds a 1:1 **stateful session** with one **server** and enforces isolation between servers (a server cannot see the full conversation or other servers). Servers expose primitives (resources/prompts/tools) and MAY request client features (sampling/roots/elicitation). Design principles: servers must be easy to build, highly composable, mutually isolated, and progressively extensible via capability negotiation at `initialize`.
## Base Protocol
### Messages
All messages **MUST** be [JSON-RPC 2.0](https://www.jsonrpc.org/specification), UTF-8 encoded. Three kinds: **Requests** (with a string/integer `id`; the id **MUST NOT** be `null` and **MUST NOT** be reused within a session), **Responses** (`result` XOR `error`; both **MUST NOT** be set; error codes are integers), and **Notifications** (no `id`; receiver **MUST NOT** reply). The reserved `_meta` property carries extension metadata; key names with a `mcp`/`modelcontextprotocol` prefix are reserved. **JSON-RPC batching is disallowed** (each message is a standalone request/notification/response).
### Lifecycle
Three phases. (1) **Initialization** — client sends `initialize` with its supported `protocolVersion` (SHOULD be its latest), `capabilities`, and `clientInfo`; server responds with the negotiated `protocolVersion`, its `capabilities`, `serverInfo`, and optional `instructions`; client then sends `notifications/initialized`. The server SHOULD NOT send non-ping/logging requests before `initialized`. (2) **Operation** — both parties **MUST** respect the negotiated version and only use negotiated capabilities. (3) **Shutdown** — no dedicated message; the transport signals termination (stdio: close stdin → SIGTERM → SIGKILL; HTTP: `DELETE` the session or close streams). If versions mismatch the client **SHOULD** disconnect.
### Transports
Two standard transports. **stdio** — the client launches the server as a subprocess; newline-delimited JSON-RPC over stdin/stdout; messages **MUST NOT** contain embedded newlines; stderr is for logs only. **Streamable HTTP** — the server exposes a single **MCP endpoint** supporting `POST` and optionally `GET` (e.g. `https://example.com/mcp`), replacing the 2024-11-05 HTTP+SSE two-endpoint design:
- Every client JSON-RPC message is a fresh `POST`; the request **MUST** send `Accept: application/json, text/event-stream`. For a *request* the server responds either with `application/json` or by opening an SSE `text/event-stream`; for a *notification/response* the server returns `202 Accepted`.
- Server→client traffic (notifications/requests) flows over an SSE stream that the client opens via `GET` (server MAY decline with `405`). The server **MUST NOT** broadcast the same message across multiple concurrent streams.
- **Sessions:** the server MAY assign an `Mcp-Session-Id` (cryptographically secure, visible ASCII 0x210x7E) on the initialize response; the client **MUST** echo it on all subsequent requests; a `404` forces re-initialization; a `DELETE` terminates the session.
- **Resumability:** servers MAY attach SSE event `id`s; the client resumes via the `Last-Event-ID` header on `GET` (per-stream cursor; no cross-stream replay).
- Clients using HTTP **MUST** send `MCP-Protocol-Version: <version>` on all post-initialize requests. Servers **MUST** validate the `Origin` header (DNS-rebinding defence) and **SHOULD** bind localhost when local.
### Authorization
Optional, for HTTP transports only (stdio retrieves credentials from the environment). Built on OAuth 2.1 ([draft-ietf-oauth-v2-1-13](https://datatracker.ietf.org/doc/html/draft-ietf-oauth-v2-1-13)) with PKCE. **Resource Server classification:** the MCP server is an OAuth 2.1 *resource server*; the MCP client is the OAuth 2.1 *client*; tokens are issued by a separate authorization server. Discovery: MCP servers **MUST** implement OAuth 2.0 Protected Resource Metadata ([RFC 9728](https://www.rfc-editor.org/rfc/rfc9728.html)) and signal the metadata URL via `WWW-Authenticate` on `401`; clients **MUST** use Authorization Server Metadata ([RFC 8414](https://datatracker.ietf.org/doc/html/rfc8414)) and **SHOULD** use Dynamic Client Registration ([RFC 7591](https://datatracker.ietf.org/doc/html/rfc7591)). **Resource Indicators (RFC 8707):** the client **MUST** send the `resource` parameter (identifying the target MCP server) in both the authorization and token requests. Token refresh is supported; scopes are server-defined.
### Versioning
Protocol versions are date strings (e.g. `2025-06-18`). Version negotiation happens only in `initialize` (see Lifecycle): the client sends the version it supports; the server returns it if supported, otherwise its latest other version; the client disconnects on an unsupported response. A `CHANGELOG.md` records revisions; SDKs adopt versions at their own pace and rely on negotiation for backwards/forwards compatibility.
## Server Features
Servers advertise implemented primitives in their capabilities. Control model: **Prompts** are user-controlled, **Resources** application-controlled, **Tools** model-controlled.
### Resources
Application-driven context exposed via URIs. Capability `resources` with optional `subscribe` and `listChanged`. Methods: `resources/list`, `resources/read`, `resources/templates/list` (RFC 6570 URI templates), plus `resources/subscribe`/`unsubscribe` and `notifications/resources/*`. **Resource links** — tools and resources can reference related resources; a `resource` content item (with `uri`, optional `mimeType`, and inline `text`/`blob`) embeds a resource, and tool results can emit resource links so clients can pull further context. All content items carry optional `annotations` (`audience`, `priority`, `lastModified`).
### Prompts
User-controlled templated messages. Capability `prompts` (with optional `listChanged`). Methods: `prompts/list`, `prompts/get` (takes `name` + `arguments`). A `PromptMessage` has `role` (`user`/`assistant`) and typed `content` (text/image/audio/embedded-resource). Arguments can be autocompleted via the completion utility.
### Tools
Model-controlled functions. Capability `tools` (with optional `listChanged`). Methods: `tools/list`, `tools/call`. A tool definition carries `name`, optional `title`/`description`, `inputSchema` (JSON Schema), and optional `outputSchema` (JSON Schema) and `annotations` (treated as untrusted). **Structured output:** a `tools/call` result returns a `content[]` array (text/image/audio/resource items) **plus an optional `structuredContent`** JSON object. When `outputSchema` is declared, the server **MUST** return structured results conforming to it and clients **SHOULD** validate; for backwards compatibility a tool returning `structuredContent` **SHOULD** also emit the serialized JSON in a `TextContent` block. Execution failures use `isError: true`; protocol errors use standard JSON-RPC codes.
### Utilities / Logging
Cross-cutting utilities: `ping` (liveness), `notifications/progress` (progress tracking), `notifications/cancelled` (cancellation via request id), `notifications/initialized`, and `completion/complete` (argument autocompletion). **Logging:** servers with the `logging` capability emit `notifications/message` with a level (`debug`..`emergency`) and structured data; clients set level via `logging/setLevel`.
## Client Features
### Sampling
Server-initiated LLM generation. Client capability `sampling`. Method `sampling/createMessage` — the server sends `messages`, optional `systemPrompt`, `maxTokens`, and `modelPreferences` (`hints` + normalized `intelligencePriority`/`speedPriority`/`costPriority` in 01); the client performs human-in-the-loop review, selects the model, and returns `role`/`content`/`model`/`stopReason`. Human approval is expected; the server never supplies API keys.
### Roots
Server-initiated inquiry into client filesystem boundaries. Client capability `roots` (with optional `listChanged`). Method `roots/list` returns `file://` URIs the server may operate within; `notifications/roots/list_changed` signals updates. Clients **MUST** validate URIs (path traversal) and obtain user consent.
### Elicitation
Server-initiated structured input from the end user. Client capability `elicitation`. Method `elicitation/create` — the server sends a human-readable `message` plus a `requestedSchema`, a *restricted* JSON Schema (flat object of primitive properties only: string/number/boolean/enums, no nesting). The client presents a form and responds with `action: "accept"` (+ `content` object), `"decline"`, or `"cancel"`. **Privacy/safety:** servers **MUST NOT** use elicitation to request sensitive information (passwords, API keys, credentials); clients **SHOULD** make the requesting server clear and provide explicit decline/cancel. Because responses may be sensitive, they must not be echoed into logs or persisted beyond need.
## Changes vs 2024-11-05
- **Streamable HTTP** replaces the HTTP+SSE two-endpoint transport (single `POST`/`GET` MCP endpoint, `Mcp-Session-Id` header, SSE resumability via `Last-Event-ID`, `MCP-Protocol-Version` header).
- **Elicitation** client feature added (`elicitation/create` with a restricted JSON Schema form; accept/decline/cancel).
- **Structured tool output** — tools may return `structuredContent` (typed JSON) plus an optional `outputSchema`; structured results SHOULD also serialize to a `TextContent` block.
- **Resource links** — tools/resources can reference related resources (embedded `resource` content items, annotations).
- **JSON-RPC batching removed** (was permitted in 2024-11-05; each message is now standalone).
- **Authorization strengthened:** OAuth 2.1 Resource Indicators (RFC 8707) with the `resource` parameter; OAuth 2.0 Protected Resource Metadata (RFC 9728) + Resource Server classification; Authorization Server Metadata (RFC 8414); Dynamic Client Registration (RFC 7591) recommended.
- **Protocol remains stateful** with connection-level capability negotiation; client features are now Sampling, Roots, and Elicitation.
## Skald relevance
Skald's MCP stack implements this revision. `crates/mcp-client/` provides the transport/runtime primitives — `McpServerClient` trait (`src/lib.rs:67`), stdio server, and `McpHttpServer` (`http_server.rs`) — while `src/core/mcp/mod.rs` (`McpManager`) registers and drives connected servers, and `src/core/elicitation/mod.rs` bridges the new `elicitation/create` server→client request through `ElicitationManager` (surfaced in the Inbox) with secrets never logged or persisted. 2025-06-18 is therefore the baseline that introduced the Elicitation feature Skald implements end-to-end.
## References
- [Specification overview](https://modelcontextprotocol.io/specification/2025-06-18)
- [Architecture](https://modelcontextprotocol.io/specification/2025-06-18/architecture)
- [Base protocol](https://modelcontextprotocol.io/specification/2025-06-18/basic)
- [Server features](https://modelcontextprotocol.io/specification/2025-06-18/server)
- [Client features](https://modelcontextprotocol.io/specification/2025-06-18/client)
- [Schema (schema.ts)](https://github.com/modelcontextprotocol/specification/blob/main/schema/2025-06-18/schema.ts)
- [Release 2025-06-18](https://github.com/modelcontextprotocol/modelcontextprotocol/releases/tag/2025-06-18)