From fd0c82816732dd255c78d8b876da1597d621f7a2 Mon Sep 17 00:00:00 2001 From: Wils Dawson Date: Mon, 5 May 2025 11:54:05 -0700 Subject: [PATCH 01/13] Add user interaction feature --- docs/docs.json | 3 +- docs/specification/draft/basic/lifecycle.mdx | 26 +- docs/specification/draft/changelog.mdx | 5 +- .../draft/client/user_interaction.mdx | 613 ++++++++++++++++++ docs/specification/draft/index.mdx | 3 +- schema/draft/schema.json | 124 ++++ schema/draft/schema.ts | 74 ++- 7 files changed, 829 insertions(+), 19 deletions(-) create mode 100644 docs/specification/draft/client/user_interaction.mdx diff --git a/docs/docs.json b/docs/docs.json index 8a743eb05..1b0296875 100644 --- a/docs/docs.json +++ b/docs/docs.json @@ -203,7 +203,8 @@ "group": "Client Features", "pages": [ "specification/draft/client/roots", - "specification/draft/client/sampling" + "specification/draft/client/sampling", + "specification/draft/client/user_interaction" ] }, { diff --git a/docs/specification/draft/basic/lifecycle.mdx b/docs/specification/draft/basic/lifecycle.mdx index 44bba59dc..9436ab3d7 100644 --- a/docs/specification/draft/basic/lifecycle.mdx +++ b/docs/specification/draft/basic/lifecycle.mdx @@ -61,7 +61,10 @@ The client **MUST** initiate this phase by sending an `initialize` request conta "roots": { "listChanged": true }, - "sampling": {} + "sampling": {}, + "userInteraction": { + "types": ["ua"] + } }, "clientInfo": { "name": "ExampleClient", @@ -144,16 +147,17 @@ available during the session. Key capabilities include: -| Category | Capability | Description | -| -------- | -------------- | -------------------------------------------------------------------------- | -| Client | `roots` | Ability to provide filesystem [roots](/specification/draft/client/roots) | -| Client | `sampling` | Support for LLM [sampling](/specification/draft/client/sampling) requests | -| Client | `experimental` | Describes support for non-standard experimental features | -| Server | `prompts` | Offers [prompt templates](/specification/draft/server/prompts) | -| Server | `resources` | Provides readable [resources](/specification/draft/server/resources) | -| Server | `tools` | Exposes callable [tools](/specification/draft/server/tools) | -| Server | `logging` | Emits structured [log messages](/specification/draft/server/utilities/logging) | -| Server | `experimental` | Describes support for non-standard experimental features | +| Category | Capability | Description | +| -------- | ----------------- | ------------------------------------------------------------------------------ | +| Client | `roots` | Ability to provide filesystem [roots](/specification/draft/client/roots) | +| Client | `sampling` | Support for LLM [sampling](/specification/draft/client/sampling) requests | +| Client | `userInteraction` | Support for user interaction requests | +| Client | `experimental` | Describes support for non-standard experimental features | +| Server | `prompts` | Offers [prompt templates](/specification/draft/server/prompts) | +| Server | `resources` | Provides readable [resources](/specification/draft/server/resources) | +| Server | `tools` | Exposes callable [tools](/specification/draft/server/tools) | +| Server | `logging` | Emits structured [log messages](/specification/draft/server/utilities/logging) | +| Server | `experimental` | Describes support for non-standard experimental features | Capability objects can describe sub-capabilities like: diff --git a/docs/specification/draft/changelog.mdx b/docs/specification/draft/changelog.mdx index 5fff1dd43..3c928ecc1 100644 --- a/docs/specification/draft/changelog.mdx +++ b/docs/specification/draft/changelog.mdx @@ -8,8 +8,9 @@ the previous revision, [2025-03-26](/specification/2025-03-26). ## Major changes 1. Removed support for JSON-RPC **[batching](https://www.jsonrpc.org/specification#batch)** - (PR [#416](https://github.com/modelcontextprotocol/specification/pull/416)) -2. TODO + (PR [#416](https://github.com/modelcontextprotocol/specification/pull/416)) +2. Added support for **[user interaction](./client/user_interaction.mdx)** (PR + [#417](https://github.com/modelcontextprotocol/specification/pull/417)) ## Other schema changes diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx new file mode 100644 index 000000000..11962f1da --- /dev/null +++ b/docs/specification/draft/client/user_interaction.mdx @@ -0,0 +1,613 @@ +--- +title: User Interaction +--- + +**Protocol Revision**: draft + +The Model Context Protocol (MCP) provides a standardized way for servers to interact directly with +users without involving the client or the LLM. This allows servers to maintain control over user +interactions and data sharing while dynamically gathering necessary information. + +The details of the interaction itself are fully under the control of the MCP server, and the MCP +client is only responsible for facilitating the interaction (typically by presenting a URL or +instructions to the end-user). By modeling interactions in this way, the client's responsibilities +remain minimal and the server has the flexibility to implement a wide range of interactions +involving the end-user. For example: + +- A productivity MCP server might request a user to authorize access to a third-party service to + access their documents. +- A news MCP server might request a user to upgrade their subscription to access more features. +- A banking MCP server might request a user to verify their account to access a new feature. +- A media MCP server might request a user's favorite music genre to personalize the user + experience. +- A social media MCP server might request an image to use as a profile picture. + +## Terminology + +- **User agent**: Most familiarly a Web browser, the user agent is a client that is capable of + initiating a request. Broadly, it is used as defined in + [RFC 9110 Section 3.5](https://datatracker.ietf.org/doc/html/rfc9110#section-3.5). + +## User Interaction Flow + +When a user interaction is requested and supported by the client, the MCP client **MUST** present +the user with a user interaction flow. The type of flow is defined by the MCP server and is +specific to the interaction type. + +This specification defines the following types of user interactions: + +- **`ua`**: A User Agent interaction is a user interaction that involves making a request via a + User Agent. +- **`prompt`**: A prompt interaction is a user interaction that involves the MCP client prompting + the user for information. +- **`oob`**: An out-of-band interaction is a user interaction that occurs outside of the MCP + operations. + +There may be other interaction types that a client and server **MAY** negotiate beyond those +outlined above. + +When the client presents a user interaction to the user, it **SHOULD** provide UI that: + +- Makes it clear which server is requesting information. +- Provides a way for the user to cancel the interaction. + +### User agent interactions + +A user agent interaction is a user interaction that involves the MCP client facilitating opening +a URL in a User Agent. This provides a way for the MCP server to obtain data from the user by +redirecting them to a URL that they can interact with and submit data back to the MCP server +without involving the MCP client. The MCP server can, as a result, control the entire interaction +from start to finish including the user experience. + +```mermaid +sequenceDiagram + participant U as User + participant B as User Agent (Browser) + participant C as Client + participant S as Server + + Note over S,C: Server initiates prompt interaction + S->>C: interaction/create type=ua + + C->>U: Present consent to open URL + U-->>C: Provide consent + + C->>B: Open URL + C->>S: Send response + Note over U,B: Human interaction + B-->>S: Perform interaction + + Note over S,B: Completed interaction + + Note over S: Continue operations +``` + +The MCP client **MUST** facilitate the opening of the URL in a User Agent. + +### Prompt interactions + +A prompt interaction is a user interaction that involves the MCP client prompting the user for +information within the MCP client UI. This provides a way for the MCP server to obtain data from +the user without needing to host a URL or create any UI for the user to interact with. The MCP +server can, as a result, receive information from the user with little effort, at the expense of +data privacy. + +```mermaid +sequenceDiagram + participant U as User + participant C as Client + participant S as Server + + Note over S,C: Server initiates prompt interaction + S->>C: interaction/create type=prompt + + C->>U: Present user interaction UI + Note over C,U: Human interaction + U-->>C: Provide requested information + + Note over S,C: Complete request + C->>S: Return user response + + Note over S: Continue operations with new information +``` + +Implementations are free to expose user interactions through any interface pattern that suits +their needs—the protocol itself does not mandate any specific user interaction model. + + + +For trust & safety and security, there **SHOULD** always +be a human in the loop with the ability to deny interaction requests. + +MCP clients **SHOULD**: + +- Provide UI that makes it clear which server is requesting information +- Allow users to review and modify their responses before sending +- Respect user privacy and provide clear cancel options + + + +### Out-of-band interactions + +An out-of-band interaction is a user interaction that occurs outside of the MCP operations. This +provides a way for the MCP server to obtain data from the user by initiating a separate +communication channel with the user, such as email or SMS. The MCP server can, as a result, receive +information from the user asynchronously and without involving the MCP client, while informing the +user that they should check that communication channel for further instructions. + +```mermaid +sequenceDiagram + participant U as User + participant C as Client + participant S as Server + + Note over S,C: Server initiates prompt interaction + S->>C: interaction/create type=oob + + C->>U: Present message to user + U-->>S: Perform interaction out-of-band + + + Note over S: Completed interaction + S-->>C: Send response + + Note over S: Continue operations +``` + +## Capabilities + +Clients that support user interaction **MUST** declare the `userInteraction` capability during +[initialization](/specification/draft/basic/lifecycle#initialization): + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["ua", "prompt", "oob"], + "progress": true + } + } +} +``` + +Clients supporting the `userInteraction` capability **MUST** support at least one interaction type +and list all supported types in the `types` array. + +### User agent interactions + +Sometimes the MCP server may need to obtain data from the user directly, without involving the MCP +client, via a User Agent (commonly a Web browser). This requires the client to support the `ua` +interaction type. + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["ua"] + } + } +} +``` + +The MCP server **MUST NOT** create an interaction with a `ua` type if the client does not support +the `ua` type as negotiated during initialization. + +### Prompt interactions + +Sometimes the MCP server may need to obtain data from the user via the MCP client. This requires +the client to support the `prompt` interaction type. + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["prompt"] + } + } +} +``` + +The MCP server **MUST NOT** create an interaction with a `prompt` type if the client does not +support the `prompt` type as negotiated during initialization. + +### Out-of-band interactions + +Sometimes the MCP server may need to obtain data from the user out-of-band with the MCP operations. +This requires the client to support the `oob` interaction type. + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["oob"] + } + } +} +``` + +The MCP server **MUST NOT** create an interaction with a `oob` type if the client does not support +the `oob` type as negotiated during initialization. + +### Progress tracking + +The MCP client **MAY** optionally support progress tracking for interactions. This can be used to +provide feedback to the user about the progress of the interaction in the MCP client UI. This is +particularly useful for interactions where the user will be interacting out-of-band with the MCP +client, such as `ua` or `oob` interactions, and the MCP client desires some way to update its UI. + +This leverages the [Progress capability](/specification/draft/basic/utilities/progress) in the base +protocol. It requires the MCP server to support the `progress` capability during initialization. + +Note that the MCP server may choose to not send progress notifications for an interaction, even if +the client supports progress tracking and the server supports the progress capability generally. +Therefore, the client **SHOULD NOT** assume that progress notifications will be sent for an +interaction, and should be prepared to handle the case where no progress notifications are sent. + +## Protocol Messages + +### Server-initiated interaction requests + +When the MCP client indicates support for user interactions, the MCP server can request a user +interaction from the client. To request a user interaction, the server sends an +`interaction/create` message to the client. + +The request includes the following fields as part of the `params` object: + +- `id`: The ID of the interaction that **MUST** be unique across the server's concurrent + interactions. +- `type`: The type of interaction, which **MUST** be one of the types negotiated during + initialization. +- `interaction`: The interaction object, the schema of which depends on the type of interaction. +- `progressAvailable`: An optional boolean indicating whether progress can be tracked for this + interaction. This acts as a hint to the client about whether to expect a response to the + `interaction/notify` request, described in the [Tracking progress](#tracking-progress) section. + +The following is an example of a `interaction/create` message for a `ua` interaction: + +```json +{ + "jsonrpc": "2.0", + "id": 1, + "method": "interaction/create", + "params": { + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", + "type": "ua", + "interaction": { + "url": "https://oauth.example.com/authorize?client_id=abc123&...", + "message": { + "type": "text", + "text": "Authorization is required to access your Example Co files." + } + }, + "progressAvailable": true + } +} +``` + +#### User agent interaction schema + +**Server Request:** + +For `ua` interactions, the `interaction` object has the following properties: + +- `url`: The URL that the user should interact with. +- `message`: An optional `TextContent` used to provide context to the user about the interaction. + +```json +{ + "jsonrpc": "2.0", + "id": 1, + "method": "interaction/create", + "params": { + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", + "type": "ua", + "interaction": { + "url": "https://example.com/mcp?state=1234567890&...", + "message": { + "type": "text", + "text": "Please sign in to your account." + } + } + } +} +``` + +**Client Response:** + +When the client opens the URL, it **MUST** send a response to the server: + +```json +{ + "jsonrpc": "2.0", + "id": 1, + "result": {} +} +``` + +#### Prompt interaction schema + +**Server Request:** + +For `prompt` interactions, the `interaction` object has the following properties: + +- `message`: A `TextContent` object used to provide context to the user about the interaction. +- `schema`: A `JSONSchema` object used to define the schema of the prompt for the MCP client. + +```json +{ + "jsonrpc": "2.0", + "id": 1, + "method": "interaction/create", + "params": { + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", + "type": "prompt", + "interaction": { + "message": { + "type": "text", + "text": "Let us know some information about you." + }, + "schema": { + "type": "object", + "properties": { + "name": { + "type": "string", + "description": "Your full name" + }, + "email": { + "type": "string", + "format": "email", + "description": "Your email address" + }, + "age": { + "type": "number", + "minimum": 18, + "description": "Your age" + } + }, + "required": ["name", "email"] + } + } + } +} +``` + +**Client Response:** + +When the user provides their response, the client **MUST** send a response to the server: + +```json +{ + "jsonrpc": "2.0", + "id": 1, + "result": { + "content": { + "name": "Monalisa", + "email": "monalisa@example.com", + "age": 30 + } + } +} +``` + +##### Out-of-band interactions + +**Server Request:** + +For `oob` interactions, the `interaction` object has the following properties: + +- `message`: A `TextContent` used to provide context to the user about the interaction. + +```json +{ + "interaction": { + "message": { + "type": "text", + "text": "Please check your email for a verification link." + } + } +} +``` + +**Client Response:** + +When the client displays the message to the user, it **MUST** send a response to the server: + +```json +{ + "jsonrpc": "2.0", + "id": 1, + "result": {} +} +``` + +### Requiring interaction as an error response + +Sometimes the MCP server may need to require a user interaction as an error response to a client +request. This can be useful when the MCP server or the transport does not support Server-Side +events. It can also be used to require a user interaction as a pre-condition for a request. + +The MCP server **MUST** send an +[error response](/specification/draft/basic/lifecycle#error-handling) with the `code` set to +`-32003` and the `message` set to `interaction_required`. + +The error response **MUST** include an `data` object consistent with an the +[`interaction` schema](#Server-initiated-interaction-requests), defined above. + +In addition, when the transport is **Streamable HTTP**, the error response **MAY** include an +optional `Retry-After` header. This header **MUST** conform to the +[HTTP `Retry-After` header field semantics](https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Retry-After). +It allows the server to provide a hint to the client about how long to wait before retrying the +request. + +```json +{ + "jsonrpc": "2.0", + "id": "abc-123", + "error": { + "code": -32003, + "message": "User interaction required", + "data": { + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", + "type": "ua", + "url": "https://oauth.example.com/authorize?client_id=abc123&...", + "message": { + "type": "text", + "text": "Authorization is required to access your Example Co files." + }, + "progressAvailable": false + } + } +} +``` + +### Tracking progress + +This section is intended to leverage the +[Progress capability](/specification/draft/basic/utilities/progress) to provide a way for MCP +clients to track progress for user interactions. + +Tracking progress for user interactions is optional. If the MCP server does not support progress +tracking, it **MUST NOT** respond to the `interaction/notify` message, in keeping with the +requirements of the +[Progress capability](/specification/draft/basic/utilities/progress#behavior-requirements). + +MCP clients send an `interaction/notify` message to the server to initiate progress tracking for a +particular interaction. The MCP client **MUST** include the interaction ID in the `id` field that +it wants to track progress for. This `id` **MUST** be an interaction that the server created via +the `interaction/create` message. + +```json +{ + "jsonrpc": "2.0", + "id": "track-progress-123", + "method": "interaction/notify", + "params": { + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", + "_meta": { + "progressToken": "abc123" + } + } +} +``` + +MCP servers **MUST NOT** respond to the `interaction/notify` message if: + +- the `id` is not an interaction that the server created via the `interaction/create` message. +- the `id` is not an interaction that is associated with the client. +- the `id` is not an interaction that is associated with the current MCP session, if session + management is in use. + +MCP clients **SHOULD** be aware that MCP servers might not respond to the `interaction/notify` +message, and **SHOULD** be prepared to handle the case where no response is received. + +The following is an example of a progress notification sent by the MCP server: + +```json +{ + "jsonrpc": "2.0", + "method": "notifications/progress", + "params": { + "progressToken": "abc123", + "progress": 50, + "total": 100, + "message": "Reticulating splines..." + } +} +``` + +Once the interaction is complete, the server **MUST** respond to the `interaction/notify` message, +for example: + +```json +{ + "jsonrpc": "2.0", + "id": "track-progress-123", + "result": {} +} +``` + +### Cancelling an interaction + +A user may choose to cancel an interaction, for example, by cancelling submitting a form rendered +by the MCP client as part of a `prompt` interaction or by not consenting to open a URL as part of +a `ua` interaction. In such cases, the MCP client **MAY** cancel an interaction at any time by +sending a `notifications/cancelled` message to the server. Cancellations will be consistent with +the [Cancellation capability](/specification/draft/basic/utilities/cancellation). + +The `requestId` **MUST** be the `id` of the original `interaction/create` request that the +client wants to cancel. + +```json +{ + "jsonrpc": "2.0", + "method": "notifications/cancelled", + "params": { + "requestId": 1, + "reason": "User requested cancellation" + } +} +``` + +TODO: @nbarettini decide what we want to do for cancellation. Define server to client notification? + e.g. timeout, "link expired", etc. + +## Identifying the User + +It is often useful for the MCP server to have some persistent identifier for the user. For the +purposes of this specification, the user identifier is an opaque string that is associated with the +user throughout the duration of the interaction. Obtaining verified information about the user, such +as their name or email address, is out of scope for this specification. + +- Implementations using an HTTP-based transport **SHOULD** use the subject claim (`sub`) from the + OAuth 2 Access Token as the user identifier, if present. +- Implementations using an STDIO transport **SHOULD** acquire the user identifier from the + environment. + +## Security Considerations + +### Handling sensitive information + +One mechanism for which user interaction may be leveraged is passing a user's auth credentials, or +other secret and sensitive data to the MCP server. The specifics of the sensitive data is out of +scope for this specification. However, MCP servers that request secrets, such as auth credentials, +**MUST** leverage an interaction type which prevents the MCP client from interacting with those +secrets in any way. + +### Server-side request forgery (SSRF) + +In the case of `ua` interactions, the MCP client is expected to make a request via a user agent +based on the value of the `url` parameter in the interaction object. Since MCP enables clients +to interoperate with MCP servers it has no prior knowledge of, this opens a risk for Server-Side +Request Forgery (SSRF) attacks by malicious MCP servers. MCP clients **SHOULD** take appropriate +precautions against SSRF attacks, such as blocking requests to internal IP address ranges and +requiring TLS. + +Additionally, the MCP client **SHOULD** validate the `url` parameter in the interaction object and +provide sufficient context to the user about the request that will be made, before it is opened in +a User Agent. + +Further recommendations can be found in the Open Worldwide Application Security +Project (OWASP) SSRF Prevention Cheat Sheet +[OWASP.SSRF](https://cheatsheetseries.owasp.org/cheatsheets/Server_Side_Request_Forgery_Prevention_Cheat_Sheet.html). + +### Phishing + +This specification may be deployed in a way where the `url` parameter in the interaction object +for `ua` interactions points to a URL that defined by something other than the MCP server. For +example, the URL may be an authorization URL of a third-party service such as a file-sharing +service that the MCP server needs the user to authorize access to. If that third-party service +is malicious or compromised, it could trick the user into revealing their account credentials or +other sensitive information. + +To mitigate this risk, MCP clients **SHOULD** take appropriate precautions, such as verifying the +authenticity of the URL and the destination of the request. + +### Impersonation attacks + +Since MCP enables clients to interoperate with MCP servers it has no prior knowledge of, this opens +a risk for impersonation attacks by malicious MCP clients. MCP servers **SHOULD** take appropriate +precautions against impersonation attacks, such as implementing the +[Authorization](/specification/draft/basic/authorization) capabilities and properly validating +interaction IDs that are requested for progress tracking. + +TODO: @nbarettini categorize this as Improper Resource Authorization??? diff --git a/docs/specification/draft/index.mdx b/docs/specification/draft/index.mdx index 67b2cc83b..e8978e278 100644 --- a/docs/specification/draft/index.mdx +++ b/docs/specification/draft/index.mdx @@ -59,9 +59,10 @@ Servers offer any of the following features to clients: - **Prompts**: Templated messages and workflows for users - **Tools**: Functions for the AI model to execute -Clients may offer the following feature to servers: +Clients may offer the following features to servers: - **Sampling**: Server-initiated agentic behaviors and recursive LLM interactions +- **User Interaction**: Server-initiated user interactions ### Additional Utilities diff --git a/schema/draft/schema.json b/schema/draft/schema.json index a1e3f2679..da18c6ec8 100644 --- a/schema/draft/schema.json +++ b/schema/draft/schema.json @@ -194,6 +194,12 @@ "description": "Present if the client supports sampling from an LLM.", "properties": {}, "type": "object" + }, + "userInteraction": { + "additionalProperties": true, + "description": "Present if the client supports user interaction.", + "properties": {}, + "type": "object" } }, "type": "object" @@ -254,6 +260,9 @@ }, { "$ref": "#/definitions/CompleteRequest" + }, + { + "$ref": "#/definitions/NotifyUserInteractionProgressRequest" } ] }, @@ -267,6 +276,9 @@ }, { "$ref": "#/definitions/ListRootsResult" + }, + { + "$ref": "#/definitions/CreateUserInteractionResult" } ] }, @@ -463,6 +475,64 @@ ], "type": "object" }, + "CreateUserInteractionRequest": { + "description": "A request from the server to the client, to create a user interaction.", + "properties": { + "method": { + "const": "interaction/create", + "type": "string" + }, + "params": { + "properties": { + "id": { + "description": "The ID of the interaction.", + "type": "string" + }, + "interaction": { + "additionalProperties": true, + "description": "The interaction object. The schema of the interaction object is dependent on the type of\ninteraction.", + "properties": {}, + "type": "object" + }, + "progressAvailable": { + "description": "Whether progress is available for the interaction.", + "type": "boolean" + }, + "type": { + "description": "The type of interaction.", + "type": "string" + } + }, + "required": [ + "id", + "interaction", + "type" + ], + "type": "object" + } + }, + "required": [ + "method", + "params" + ], + "type": "object" + }, + "CreateUserInteractionResult": { + "description": "The client's response to a user interaction/create request from the server.", + "properties": { + "_meta": { + "additionalProperties": {}, + "description": "This result property is reserved by the protocol to allow clients and servers to attach additional metadata to their responses.", + "type": "object" + }, + "content": { + "additionalProperties": {}, + "description": "The user's response to a prompt interaction. The schema of the content is dependent on the\nrequested schema within the prompt interaction.", + "type": "object" + } + }, + "type": "object" + }, "Cursor": { "description": "An opaque token used to represent a cursor for pagination.", "type": "string" @@ -1226,6 +1296,43 @@ ], "type": "object" }, + "NotifyUserInteractionProgressRequest": { + "description": "A request from the client to the server, requesting progress notifications for a user\ninteraction.", + "properties": { + "method": { + "const": "interaction/notify", + "type": "string" + }, + "params": { + "properties": { + "_meta": { + "properties": { + "progressToken": { + "$ref": "#/definitions/ProgressToken" + } + }, + "required": [ + "progressToken" + ], + "type": "object" + }, + "id": { + "type": "string" + } + }, + "required": [ + "_meta", + "id" + ], + "type": "object" + } + }, + "required": [ + "method", + "params" + ], + "type": "object" + }, "PaginatedRequest": { "properties": { "method": { @@ -1874,6 +1981,9 @@ }, { "$ref": "#/definitions/ListRootsRequest" + }, + { + "$ref": "#/definitions/CreateUserInteractionRequest" } ] }, @@ -1908,6 +2018,9 @@ }, { "$ref": "#/definitions/CompleteResult" + }, + { + "$ref": "#/definitions/UserInteractionProgressResult" } ] }, @@ -2133,6 +2246,17 @@ "params" ], "type": "object" + }, + "UserInteractionProgressResult": { + "description": "A result from the server to the client, containing the progress of a user interaction.", + "properties": { + "_meta": { + "additionalProperties": {}, + "description": "This result property is reserved by the protocol to allow clients and servers to attach additional metadata to their responses.", + "type": "object" + } + }, + "type": "object" } } } diff --git a/schema/draft/schema.ts b/schema/draft/schema.ts index 1f6c3b1e2..fcd29e34e 100644 --- a/schema/draft/schema.ts +++ b/schema/draft/schema.ts @@ -220,6 +220,10 @@ export interface ClientCapabilities { * Present if the client supports sampling from an LLM. */ sampling?: object; + /** + * Present if the client supports user interaction. + */ + userInteraction?: object; } /** @@ -1208,6 +1212,65 @@ export interface RootsListChangedNotification extends Notification { method: "notifications/roots/list_changed"; } +/* User Interaction */ +/** + * A request from the server to the client, to create a user interaction. + */ +export interface CreateUserInteractionRequest extends Request { + method: "interaction/create"; + params: { + /** + * The ID of the interaction. + */ + id: string; + /** + * The type of interaction. + */ + type: string; + /** + * The interaction object. The schema of the interaction object is dependent on the type of + * interaction. + */ + interaction: object; + /** + * Whether progress is available for the interaction. + */ + progressAvailable?: boolean; + }; +} + + +/** + * The client's response to a user interaction/create request from the server. + */ +export interface CreateUserInteractionResult extends Result { + /** + * The user's response to a prompt interaction. The schema of the content is dependent on the + * requested schema within the prompt interaction. + */ + content?: { [key: string]: unknown }; +} + +/** + * A request from the client to the server, requesting progress notifications for a user + * interaction. + */ +export interface NotifyUserInteractionProgressRequest extends Notification { + method: "interaction/notify"; + params: { + id: string; + _meta: { + progressToken: ProgressToken; + }; + }; +} + +/** + * A result from the server to the client, containing the progress of a user interaction. + */ +export interface UserInteractionProgressResult extends Result { +} + /* Client messages */ export type ClientRequest = | PingRequest @@ -1222,7 +1285,8 @@ export type ClientRequest = | SubscribeRequest | UnsubscribeRequest | CallToolRequest - | ListToolsRequest; + | ListToolsRequest + | NotifyUserInteractionProgressRequest; export type ClientNotification = | CancelledNotification @@ -1230,13 +1294,14 @@ export type ClientNotification = | InitializedNotification | RootsListChangedNotification; -export type ClientResult = EmptyResult | CreateMessageResult | ListRootsResult; +export type ClientResult = EmptyResult | CreateMessageResult | ListRootsResult | CreateUserInteractionResult; /* Server messages */ export type ServerRequest = | PingRequest | CreateMessageRequest - | ListRootsRequest; + | ListRootsRequest + | CreateUserInteractionRequest; export type ServerNotification = | CancelledNotification @@ -1257,4 +1322,5 @@ export type ServerResult = | ListResourcesResult | ReadResourceResult | CallToolResult - | ListToolsResult; + | ListToolsResult + | UserInteractionProgressResult; From 2613f620a0cc9e504ca505593f8870eb7240c946 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Mon, 5 May 2025 16:39:20 -0700 Subject: [PATCH 02/13] Initial cleanup --- .../draft/client/user_interaction.mdx | 146 +++++++++--------- 1 file changed, 70 insertions(+), 76 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index 11962f1da..ebf154d4d 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -10,11 +10,11 @@ interactions and data sharing while dynamically gathering necessary information. The details of the interaction itself are fully under the control of the MCP server, and the MCP client is only responsible for facilitating the interaction (typically by presenting a URL or -instructions to the end-user). By modeling interactions in this way, the client's responsibilities -remain minimal and the server has the flexibility to implement a wide range of interactions -involving the end-user. For example: +instructions to the end-user, or by rendering a form for non-sensitive information). With this model, +the client's responsibilities remain minimal and the server has the flexibility to implement a wide +range of interactions involving the end-user. For example: -- A productivity MCP server might request a user to authorize access to a third-party service to +- A productivity MCP server might request a user to authorize a third-party service to access their documents. - A news MCP server might request a user to upgrade their subscription to access more features. - A banking MCP server might request a user to verify their account to access a new feature. @@ -25,9 +25,32 @@ involving the end-user. For example: ## Terminology - **User agent**: Most familiarly a Web browser, the user agent is a client that is capable of - initiating a request. Broadly, it is used as defined in + interacting with the end-user. Broadly, it is used as defined in [RFC 9110 Section 3.5](https://datatracker.ietf.org/doc/html/rfc9110#section-3.5). +## Capabilities + +Clients that support user interaction **MUST** declare the `userInteraction` capability during +[initialization](/specification/draft/basic/lifecycle#initialization): + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["ua", "prompt", "oob"], + "progress": true + } + } +} +``` + +Clients supporting the `userInteraction` capability **MUST** support at least one interaction type +and list all supported types in the `types` array. + +The MCP server **MUST NOT** send an interaction request to the client of a type that is not +supported by the client. + + ## User Interaction Flow When a user interaction is requested and supported by the client, the MCP client **MUST** present @@ -36,8 +59,8 @@ specific to the interaction type. This specification defines the following types of user interactions: -- **`ua`**: A User Agent interaction is a user interaction that involves making a request via a - User Agent. +- **`ua`**: A user agent interaction is a user interaction that involves making a request via a + User Agent (e.g. a Web browser). - **`prompt`**: A prompt interaction is a user interaction that involves the MCP client prompting the user for information. - **`oob`**: An out-of-band interaction is a user interaction that occurs outside of the MCP @@ -46,6 +69,7 @@ This specification defines the following types of user interactions: There may be other interaction types that a client and server **MAY** negotiate beyond those outlined above. + When the client presents a user interaction to the user, it **SHOULD** provide UI that: - Makes it clear which server is requesting information. @@ -54,10 +78,9 @@ When the client presents a user interaction to the user, it **SHOULD** provide U ### User agent interactions A user agent interaction is a user interaction that involves the MCP client facilitating opening -a URL in a User Agent. This provides a way for the MCP server to obtain data from the user by -redirecting them to a URL that they can interact with and submit data back to the MCP server -without involving the MCP client. The MCP server can, as a result, control the entire interaction -from start to finish including the user experience. +a URL in a User Agent (e.g. a Web browser). This provides a way for the MCP server to obtain data without involving the MCP client. + The MCP server can, as a result, control the entire interaction +from start to finish, including the user experience, and guarantee the security of sensitive data (e.g. API keys or authorization grants). ```mermaid sequenceDiagram @@ -84,6 +107,23 @@ sequenceDiagram The MCP client **MUST** facilitate the opening of the URL in a User Agent. +This requires the client to support the `ua` user interaction type. + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["ua"] + } + } +} +``` + + + + + + ### Prompt interactions A prompt interaction is a user interaction that involves the MCP client prompting the user for @@ -111,6 +151,18 @@ sequenceDiagram Note over S: Continue operations with new information ``` +This requires the client to support the `prompt` user interaction type. + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["prompt"] + } + } +} +``` + Implementations are free to expose user interactions through any interface pattern that suits their needs—the protocol itself does not mandate any specific user interaction model. @@ -127,6 +179,8 @@ MCP clients **SHOULD**: + + ### Out-of-band interactions An out-of-band interaction is a user interaction that occurs outside of the MCP operations. This @@ -154,65 +208,6 @@ sequenceDiagram Note over S: Continue operations ``` -## Capabilities - -Clients that support user interaction **MUST** declare the `userInteraction` capability during -[initialization](/specification/draft/basic/lifecycle#initialization): - -```json -{ - "capabilities": { - "userInteraction": { - "types": ["ua", "prompt", "oob"], - "progress": true - } - } -} -``` - -Clients supporting the `userInteraction` capability **MUST** support at least one interaction type -and list all supported types in the `types` array. - -### User agent interactions - -Sometimes the MCP server may need to obtain data from the user directly, without involving the MCP -client, via a User Agent (commonly a Web browser). This requires the client to support the `ua` -interaction type. - -```json -{ - "capabilities": { - "userInteraction": { - "types": ["ua"] - } - } -} -``` - -The MCP server **MUST NOT** create an interaction with a `ua` type if the client does not support -the `ua` type as negotiated during initialization. - -### Prompt interactions - -Sometimes the MCP server may need to obtain data from the user via the MCP client. This requires -the client to support the `prompt` interaction type. - -```json -{ - "capabilities": { - "userInteraction": { - "types": ["prompt"] - } - } -} -``` - -The MCP server **MUST NOT** create an interaction with a `prompt` type if the client does not -support the `prompt` type as negotiated during initialization. - -### Out-of-band interactions - -Sometimes the MCP server may need to obtain data from the user out-of-band with the MCP operations. This requires the client to support the `oob` interaction type. ```json @@ -225,12 +220,11 @@ This requires the client to support the `oob` interaction type. } ``` -The MCP server **MUST NOT** create an interaction with a `oob` type if the client does not support -the `oob` type as negotiated during initialization. -### Progress tracking -The MCP client **MAY** optionally support progress tracking for interactions. This can be used to +## Progress Tracking + +The MCP client **MAY** support progress tracking for interactions. This can be used to provide feedback to the user about the progress of the interaction in the MCP client UI. This is particularly useful for interactions where the user will be interacting out-of-band with the MCP client, such as `ua` or `oob` interactions, and the MCP client desires some way to update its UI. @@ -238,7 +232,7 @@ client, such as `ua` or `oob` interactions, and the MCP client desires some way This leverages the [Progress capability](/specification/draft/basic/utilities/progress) in the base protocol. It requires the MCP server to support the `progress` capability during initialization. -Note that the MCP server may choose to not send progress notifications for an interaction, even if +Note that the MCP server may choose to not send progress notifications for a given interaction, even if the client supports progress tracking and the server supports the progress capability generally. Therefore, the client **SHOULD NOT** assume that progress notifications will be sent for an interaction, and should be prepared to handle the case where no progress notifications are sent. @@ -291,7 +285,7 @@ The following is an example of a `interaction/create` message for a `ua` interac For `ua` interactions, the `interaction` object has the following properties: - `url`: The URL that the user should interact with. -- `message`: An optional `TextContent` used to provide context to the user about the interaction. +- `message`: An optional `TextContent` used to provide an explanation to the user about the interaction. ```json { From 74781b387cf3c4b8d0468eb18b93879a980b83f3 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Mon, 5 May 2025 21:57:11 -0700 Subject: [PATCH 03/13] Finish initial cleanup --- .../draft/client/user_interaction.mdx | 466 +++++++----------- 1 file changed, 185 insertions(+), 281 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index ebf154d4d..f62dd1754 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -5,7 +5,7 @@ title: User Interaction **Protocol Revision**: draft The Model Context Protocol (MCP) provides a standardized way for servers to interact directly with -users without involving the client or the LLM. This allows servers to maintain control over user +end-users without data passing through the client or the LLM. This allows servers to maintain control over user interactions and data sharing while dynamically gathering necessary information. The details of the interaction itself are fully under the control of the MCP server, and the MCP @@ -24,6 +24,7 @@ range of interactions involving the end-user. For example: ## Terminology +- **End-user**: The human who is interacting with the MCP client (and, by extension, the MCP server). - **User agent**: Most familiarly a Web browser, the user agent is a client that is capable of interacting with the end-user. Broadly, it is used as defined in [RFC 9110 Section 3.5](https://datatracker.ietf.org/doc/html/rfc9110#section-3.5). @@ -37,138 +38,109 @@ Clients that support user interaction **MUST** declare the `userInteraction` cap { "capabilities": { "userInteraction": { - "types": ["ua", "prompt", "oob"], + "types": ["ua", "prompt"], "progress": true } } } ``` -Clients supporting the `userInteraction` capability **MUST** support at least one interaction type -and list all supported types in the `types` array. +Clients supporting the `userInteraction` capability **MUST** list all supported interaction types +in the `types` array, and **MUST** support at least one interaction type. The MCP server **MUST NOT** send an interaction request to the client of a type that is not supported by the client. -## User Interaction Flow - -When a user interaction is requested and supported by the client, the MCP client **MUST** present -the user with a user interaction flow. The type of flow is defined by the MCP server and is -specific to the interaction type. - -This specification defines the following types of user interactions: - -- **`ua`**: A user agent interaction is a user interaction that involves making a request via a - User Agent (e.g. a Web browser). -- **`prompt`**: A prompt interaction is a user interaction that involves the MCP client prompting - the user for information. -- **`oob`**: An out-of-band interaction is a user interaction that occurs outside of the MCP - operations. - -There may be other interaction types that a client and server **MAY** negotiate beyond those -outlined above. - - -When the client presents a user interaction to the user, it **SHOULD** provide UI that: - -- Makes it clear which server is requesting information. -- Provides a way for the user to cancel the interaction. - -### User agent interactions - -A user agent interaction is a user interaction that involves the MCP client facilitating opening -a URL in a User Agent (e.g. a Web browser). This provides a way for the MCP server to obtain data without involving the MCP client. - The MCP server can, as a result, control the entire interaction -from start to finish, including the user experience, and guarantee the security of sensitive data (e.g. API keys or authorization grants). - -```mermaid -sequenceDiagram - participant U as User - participant B as User Agent (Browser) - participant C as Client - participant S as Server - - Note over S,C: Server initiates prompt interaction - S->>C: interaction/create type=ua - - C->>U: Present consent to open URL - U-->>C: Provide consent +## Protocol Messages - C->>B: Open URL - C->>S: Send response - Note over U,B: Human interaction - B-->>S: Perform interaction +### Server-Initiated Interaction Requests - Note over S,B: Completed interaction +When the MCP client indicates support for user interactions, the MCP server **MAY** request a user +interaction from the client at any time. To request a user interaction, the server sends an +`interaction/create` message to the client. - Note over S: Continue operations -``` +The request includes the following fields as part of the `params` object: -The MCP client **MUST** facilitate the opening of the URL in a User Agent. +- `id`: The ID of the interaction that **MUST** be unique across the server's concurrent + interactions. +- `type`: The type of interaction, which **MUST** be one of the types negotiated during + initialization. +- `interaction`: The interaction object, the schema of which depends on the type of interaction. Each schema is defined in the [User Interaction Flow](#interaction-flow) section below. -This requires the client to support the `ua` user interaction type. +The following is an example of a `interaction/create` message for a `ua` interaction: ```json { - "capabilities": { - "userInteraction": { - "types": ["ua"] + "jsonrpc": "2.0", + "id": 1, + "method": "interaction/create", + "params": { + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", + "type": "ua", + "interaction": { + "url": "https://oauth.example.com/authorize?client_id=abc123&...", + "message": { + "type": "text", + "text": "Authorization is required to access your Example Co files." + } } } } ``` +### Requiring Interaction as an Error Response +The MCP server **MAY** require a user interaction as an error response to a client request. +This is useful when interaction is required as a pre-condition for a request (e.g. step-up authorization). +The MCP server **MUST** send an +[error response](/specification/draft/basic/lifecycle#error-handling) with the `code` equal to +`-32003` and the `message` equal to `interaction_required`. - -### Prompt interactions - -A prompt interaction is a user interaction that involves the MCP client prompting the user for -information within the MCP client UI. This provides a way for the MCP server to obtain data from -the user without needing to host a URL or create any UI for the user to interact with. The MCP -server can, as a result, receive information from the user with little effort, at the expense of -data privacy. - -```mermaid -sequenceDiagram - participant U as User - participant C as Client - participant S as Server - - Note over S,C: Server initiates prompt interaction - S->>C: interaction/create type=prompt - - C->>U: Present user interaction UI - Note over C,U: Human interaction - U-->>C: Provide requested information - - Note over S,C: Complete request - C->>S: Return user response - - Note over S: Continue operations with new information -``` - -This requires the client to support the `prompt` user interaction type. +The error response **MUST** include an `data` object consistent with one of the defined +[interaction schemas](#interaction-flow). ```json { - "capabilities": { - "userInteraction": { - "types": ["prompt"] + "jsonrpc": "2.0", + "id": "abc-123", + "error": { + "code": -32003, + "message": "interaction_required", + "data": { + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", + "type": "ua", + "url": "https://oauth.example.com/authorize?client_id=abc123&...", + "message": { + "type": "text", + "text": "Authorization is required to access your Example Co files." + } } } } ``` -Implementations are free to expose user interactions through any interface pattern that suits -their needs—the protocol itself does not mandate any specific user interaction model. + +## Interaction Flow + +When a user interaction is requested by the server and supported by the client, the MCP client **MUST** present +the user with an interaction flow. The type of flow is defined by the MCP server, and the client's behavior +is specific to the interaction type. + +This specification defines the following types of user interactions: + +- **`ua`**: A user agent interaction is a user interaction that involves making a request via a + User Agent (e.g. a Web browser). +- **`prompt`**: A prompt interaction is a user interaction that involves the MCP client prompting + the user for structured information (e.g. rendering a form). + +The client and server **MAY** negotiate additional interaction types. -For trust & safety and security, there **SHOULD** always +For trust and safety, there **SHOULD** always be a human in the loop with the ability to deny interaction requests. MCP clients **SHOULD**: @@ -179,113 +151,58 @@ MCP clients **SHOULD**: +### User agent interactions +A user agent interaction is a user interaction that involves the MCP client facilitating navigating to +a URL in a User Agent (e.g. a Web browser). This allows the MCP server to obtain data without involving the MCP client. + The MCP server can, as a result, control the entire interaction +from start to finish, including the user experience, and guarantee the security of sensitive data (e.g. API keys or authorization grants). -### Out-of-band interactions - -An out-of-band interaction is a user interaction that occurs outside of the MCP operations. This -provides a way for the MCP server to obtain data from the user by initiating a separate -communication channel with the user, such as email or SMS. The MCP server can, as a result, receive -information from the user asynchronously and without involving the MCP client, while informing the -user that they should check that communication channel for further instructions. - -```mermaid -sequenceDiagram - participant U as User - participant C as Client - participant S as Server - - Note over S,C: Server initiates prompt interaction - S->>C: interaction/create type=oob - - C->>U: Present message to user - U-->>S: Perform interaction out-of-band - - - Note over S: Completed interaction - S-->>C: Send response - - Note over S: Continue operations -``` - -This requires the client to support the `oob` interaction type. +This flow requires the client to support the `ua` user interaction type. ```json { "capabilities": { "userInteraction": { - "types": ["oob"] + "types": ["ua"] } } } ``` +The MCP client **MUST** facilitate the opening of the URL in a User Agent. +#### Flow Diagram -## Progress Tracking - -The MCP client **MAY** support progress tracking for interactions. This can be used to -provide feedback to the user about the progress of the interaction in the MCP client UI. This is -particularly useful for interactions where the user will be interacting out-of-band with the MCP -client, such as `ua` or `oob` interactions, and the MCP client desires some way to update its UI. - -This leverages the [Progress capability](/specification/draft/basic/utilities/progress) in the base -protocol. It requires the MCP server to support the `progress` capability during initialization. - -Note that the MCP server may choose to not send progress notifications for a given interaction, even if -the client supports progress tracking and the server supports the progress capability generally. -Therefore, the client **SHOULD NOT** assume that progress notifications will be sent for an -interaction, and should be prepared to handle the case where no progress notifications are sent. - -## Protocol Messages - -### Server-initiated interaction requests +```mermaid +sequenceDiagram + participant U as End-User + participant B as User Agent (Browser) + participant C as Client + participant S as Server -When the MCP client indicates support for user interactions, the MCP server can request a user -interaction from the client. To request a user interaction, the server sends an -`interaction/create` message to the client. + Note over S,C: Server initiates prompt interaction + S->>C: interaction/create type=ua -The request includes the following fields as part of the `params` object: + C->>U: Present consent to open URL + U-->>C: Provide consent -- `id`: The ID of the interaction that **MUST** be unique across the server's concurrent - interactions. -- `type`: The type of interaction, which **MUST** be one of the types negotiated during - initialization. -- `interaction`: The interaction object, the schema of which depends on the type of interaction. -- `progressAvailable`: An optional boolean indicating whether progress can be tracked for this - interaction. This acts as a hint to the client about whether to expect a response to the - `interaction/notify` request, described in the [Tracking progress](#tracking-progress) section. + C->>B: Open URL + C->>S: Send response + Note over U,B: Human interaction + B-->>S: Perform interaction -The following is an example of a `interaction/create` message for a `ua` interaction: + Note over S,B: Completed interaction -```json -{ - "jsonrpc": "2.0", - "id": 1, - "method": "interaction/create", - "params": { - "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", - "type": "ua", - "interaction": { - "url": "https://oauth.example.com/authorize?client_id=abc123&...", - "message": { - "type": "text", - "text": "Authorization is required to access your Example Co files." - } - }, - "progressAvailable": true - } -} + Note over S: Continue operations ``` -#### User agent interaction schema - -**Server Request:** +#### Server Request For `ua` interactions, the `interaction` object has the following properties: - `url`: The URL that the user should interact with. -- `message`: An optional `TextContent` used to provide an explanation to the user about the interaction. +- `message`: An optional `TextContent` object used to provide an explanation to the user about the interaction. ```json { @@ -306,9 +223,9 @@ For `ua` interactions, the `interaction` object has the following properties: } ``` -**Client Response:** +#### Client Response -When the client opens the URL, it **MUST** send a response to the server: +When the client facilitates the opening of the URL, it **MUST** send a response to the server: ```json { @@ -318,9 +235,53 @@ When the client opens the URL, it **MUST** send a response to the server: } ``` -#### Prompt interaction schema -**Server Request:** + +### Prompt interactions + +A prompt interaction is a user interaction that involves the MCP client prompting the user for +information within the MCP client UI. This provides a way for the MCP server to obtain data from +the user without needing to host a URL or create any UI for the user to interact with. The MCP +server can, as a result, receive non-sensitive information from the user with little effort. + +This flow requires the client to support the `prompt` user interaction type. + +```json +{ + "capabilities": { + "userInteraction": { + "types": ["prompt"] + } + } +} +``` + +The MCP client **MUST** present the user with a prompt UI consistent with the `schema` object. + +#### Flow Diagram + +```mermaid +sequenceDiagram + participant U as User + participant C as Client + participant S as Server + + Note over S,C: Server initiates prompt interaction + S->>C: interaction/create type=prompt + + C->>U: Present user interaction UI + Note over C,U: Human interaction + U-->>C: Provide requested information + + Note over S,C: Complete request + C->>S: Return user response + + Note over S: Continue operations with new information +``` + + + +#### Server Request For `prompt` interactions, the `interaction` object has the following properties: @@ -365,7 +326,7 @@ For `prompt` interactions, the `interaction` object has the following properties } ``` -**Client Response:** +#### Client Response When the user provides their response, the client **MUST** send a response to the server: @@ -383,89 +344,30 @@ When the user provides their response, the client **MUST** send a response to th } ``` -##### Out-of-band interactions - -**Server Request:** - -For `oob` interactions, the `interaction` object has the following properties: - -- `message`: A `TextContent` used to provide context to the user about the interaction. - -```json -{ - "interaction": { - "message": { - "type": "text", - "text": "Please check your email for a verification link." - } - } -} -``` - -**Client Response:** - -When the client displays the message to the user, it **MUST** send a response to the server: - -```json -{ - "jsonrpc": "2.0", - "id": 1, - "result": {} -} -``` - -### Requiring interaction as an error response -Sometimes the MCP server may need to require a user interaction as an error response to a client -request. This can be useful when the MCP server or the transport does not support Server-Side -events. It can also be used to require a user interaction as a pre-condition for a request. - -The MCP server **MUST** send an -[error response](/specification/draft/basic/lifecycle#error-handling) with the `code` set to -`-32003` and the `message` set to `interaction_required`. -The error response **MUST** include an `data` object consistent with an the -[`interaction` schema](#Server-initiated-interaction-requests), defined above. - -In addition, when the transport is **Streamable HTTP**, the error response **MAY** include an -optional `Retry-After` header. This header **MUST** conform to the -[HTTP `Retry-After` header field semantics](https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Retry-After). -It allows the server to provide a hint to the client about how long to wait before retrying the -request. - -```json -{ - "jsonrpc": "2.0", - "id": "abc-123", - "error": { - "code": -32003, - "message": "User interaction required", - "data": { - "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", - "type": "ua", - "url": "https://oauth.example.com/authorize?client_id=abc123&...", - "message": { - "type": "text", - "text": "Authorization is required to access your Example Co files." - }, - "progressAvailable": false - } - } -} -``` +## Progress Tracking -### Tracking progress +The MCP client **MAY** support progress tracking for interactions. This can be used to +provide feedback to the user about the progress of the interaction in the MCP client's UI. This is +particularly useful for interactions where the user will be interacting out-of-band with the MCP +client, such as `ua` interactions, and the MCP client desires some way to update its UI. -This section is intended to leverage the -[Progress capability](/specification/draft/basic/utilities/progress) to provide a way for MCP -clients to track progress for user interactions. +This leverages the [Progress capability](/specification/draft/basic/utilities/progress) in the base +protocol. It requires the MCP server to support the `progress` capability during initialization. Tracking progress for user interactions is optional. If the MCP server does not support progress tracking, it **MUST NOT** respond to the `interaction/notify` message, in keeping with the requirements of the [Progress capability](/specification/draft/basic/utilities/progress#behavior-requirements). -MCP clients send an `interaction/notify` message to the server to initiate progress tracking for a + +Note that the MCP server may choose to not send progress notifications for a given interaction, even if +the client supports progress tracking and the server supports the progress capability generally. +Therefore, the client **SHOULD NOT** assume that progress notifications will be sent for an +interaction, and should be prepared to handle the case where no progress notifications are sent. + +MCP clients **MAY** send an `interaction/notify` message to the server to initiate progress tracking for a particular interaction. The MCP client **MUST** include the interaction ID in the `id` field that it wants to track progress for. This `id` **MUST** be an interaction that the server created via the `interaction/create` message. @@ -520,46 +422,49 @@ for example: } ``` -### Cancelling an interaction -A user may choose to cancel an interaction, for example, by cancelling submitting a form rendered -by the MCP client as part of a `prompt` interaction or by not consenting to open a URL as part of -a `ua` interaction. In such cases, the MCP client **MAY** cancel an interaction at any time by -sending a `notifications/cancelled` message to the server. Cancellations will be consistent with -the [Cancellation capability](/specification/draft/basic/utilities/cancellation). -The `requestId` **MUST** be the `id` of the original `interaction/create` request that the -client wants to cancel. +## Cancelling an Interaction + +### Server-Initiated Cancellation + +The MCP server **MAY** cancel an interaction at any time by sending a `notifications/cancelled` +message to the client. The MCP client **SHOULD NOT** send a response. This is consistent with the +[Cancellation capability](/specification/draft/basic/utilities/cancellation). + +### Client-Initiated Cancellation + +The end-user may choose to decline or cancel an interaction themselves. For example, the user may decline to submit a form rendered by +the MCP client as part of a `prompt` interaction, or not consent to open a URL as part of a +`ua` interaction. The MCP client **MAY** indicate at any time that the server should abandon (cancel) the interaction by returning an error response: ```json { "jsonrpc": "2.0", - "method": "notifications/cancelled", - "params": { - "requestId": 1, - "reason": "User requested cancellation" + "id": 1, + "error": { + "code": -1, + "message": "User did not consent to the interaction" } } ``` -TODO: @nbarettini decide what we want to do for cancellation. Define server to client notification? - e.g. timeout, "link expired", etc. +The `id` of the request **MUST** be the `id` of the original `interaction/create` request that the +client wants to cancel. ## Identifying the User -It is often useful for the MCP server to have some persistent identifier for the user. For the -purposes of this specification, the user identifier is an opaque string that is associated with the -user throughout the duration of the interaction. Obtaining verified information about the user, such -as their name or email address, is out of scope for this specification. +Most MCP servers will need a persistent identifier for the end-user. The MCP server **MUST NOT** +rely on input from the client or end-user to identify the end-user, as this can be forged and lead to impersonation attacks. +Instead, the MCP server **SHOULD** identify the end-user in trusted (server) code. For example, -- Implementations using an HTTP-based transport **SHOULD** use the subject claim (`sub`) from the - OAuth 2 Access Token as the user identifier, if present. -- Implementations using an STDIO transport **SHOULD** acquire the user identifier from the - environment. +- Implementations using an HTTP transport and [MCP authorization](/specification/draft/basic/authorization) + **MAY** use the subject claim (`sub`) from the OAuth 2.1 Access Token as the user identifier, if present. +- Implementations using an stdio transport **MAY** acquire the user identifier from the environment. ## Security Considerations -### Handling sensitive information +### Handling Sensitive Information One mechanism for which user interaction may be leveraged is passing a user's auth credentials, or other secret and sensitive data to the MCP server. The specifics of the sensitive data is out of @@ -600,8 +505,7 @@ authenticity of the URL and the destination of the request. Since MCP enables clients to interoperate with MCP servers it has no prior knowledge of, this opens a risk for impersonation attacks by malicious MCP clients. MCP servers **SHOULD** take appropriate -precautions against impersonation attacks, such as implementing the -[Authorization](/specification/draft/basic/authorization) capabilities and properly validating -interaction IDs that are requested for progress tracking. +precautions against impersonation attacks, such as implementing +[Authorization](/specification/draft/basic/authorization) and ensuring that user interaction requests are bound +to the MCP session to prevent Insecure Direct Object Reference (IDOR) attacks. -TODO: @nbarettini categorize this as Improper Resource Authorization??? From 175f33a31d5d541df36c26c9365145d22dcb5511 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Mon, 5 May 2025 22:01:01 -0700 Subject: [PATCH 04/13] Whitespace cleanup --- docs/specification/draft/client/user_interaction.mdx | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index f62dd1754..d54cea426 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -66,7 +66,9 @@ The request includes the following fields as part of the `params` object: interactions. - `type`: The type of interaction, which **MUST** be one of the types negotiated during initialization. -- `interaction`: The interaction object, the schema of which depends on the type of interaction. Each schema is defined in the [User Interaction Flow](#interaction-flow) section below. +- `interaction`: The interaction object, the schema of which depends on the type of + interaction. Each schema is defined in the [User Interaction Flow](#interaction-flow) + section below. The following is an example of a `interaction/create` message for a `ua` interaction: @@ -344,8 +346,6 @@ When the user provides their response, the client **MUST** send a response to th } ``` - - ## Progress Tracking The MCP client **MAY** support progress tracking for interactions. This can be used to @@ -422,8 +422,6 @@ for example: } ``` - - ## Cancelling an Interaction ### Server-Initiated Cancellation From a099db4938ae57f072f2dac572cb2a6e7603a03c Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Thu, 8 May 2025 12:31:18 -0700 Subject: [PATCH 05/13] Slim down --- .prettierignore | 1 + docs/specification/draft/basic/lifecycle.mdx | 2 +- docs/specification/draft/changelog.mdx | 2 +- .../draft/client/user_interaction.mdx | 440 ++++++------------ package.json | 6 + schema/draft/schema.json | 110 ++--- schema/draft/schema.ts | 58 ++- 7 files changed, 224 insertions(+), 395 deletions(-) create mode 100644 .prettierignore diff --git a/.prettierignore b/.prettierignore new file mode 100644 index 000000000..e7f32e65e --- /dev/null +++ b/.prettierignore @@ -0,0 +1 @@ +**/schema.json \ No newline at end of file diff --git a/docs/specification/draft/basic/lifecycle.mdx b/docs/specification/draft/basic/lifecycle.mdx index 9436ab3d7..c6ef5a3a2 100644 --- a/docs/specification/draft/basic/lifecycle.mdx +++ b/docs/specification/draft/basic/lifecycle.mdx @@ -151,7 +151,7 @@ Key capabilities include: | -------- | ----------------- | ------------------------------------------------------------------------------ | | Client | `roots` | Ability to provide filesystem [roots](/specification/draft/client/roots) | | Client | `sampling` | Support for LLM [sampling](/specification/draft/client/sampling) requests | -| Client | `userInteraction` | Support for user interaction requests | +| Client | `userInteraction` | Support for [user interactions](/specification/draft/client/user_interaction) | | Client | `experimental` | Describes support for non-standard experimental features | | Server | `prompts` | Offers [prompt templates](/specification/draft/server/prompts) | | Server | `resources` | Provides readable [resources](/specification/draft/server/resources) | diff --git a/docs/specification/draft/changelog.mdx b/docs/specification/draft/changelog.mdx index 3c928ecc1..2721006c3 100644 --- a/docs/specification/draft/changelog.mdx +++ b/docs/specification/draft/changelog.mdx @@ -10,7 +10,7 @@ the previous revision, [2025-03-26](/specification/2025-03-26). 1. Removed support for JSON-RPC **[batching](https://www.jsonrpc.org/specification#batch)** (PR [#416](https://github.com/modelcontextprotocol/specification/pull/416)) 2. Added support for **[user interaction](./client/user_interaction.mdx)** (PR - [#417](https://github.com/modelcontextprotocol/specification/pull/417)) + [#417](https://github.com/modelcontextprotocol/specification/pull/475)) ## Other schema changes diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index d54cea426..9c65cd116 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -4,23 +4,21 @@ title: User Interaction **Protocol Revision**: draft -The Model Context Protocol (MCP) provides a standardized way for servers to interact directly with -end-users without data passing through the client or the LLM. This allows servers to maintain control over user -interactions and data sharing while dynamically gathering necessary information. +The Model Context Protocol (MCP) provides a standardized way for servers to interact +directly with end-users without data passing through the client or the LLM. This allows +servers to maintain control over user interactions and data sharing while dynamically +gathering necessary information. -The details of the interaction itself are fully under the control of the MCP server, and the MCP -client is only responsible for facilitating the interaction (typically by presenting a URL or -instructions to the end-user, or by rendering a form for non-sensitive information). With this model, -the client's responsibilities remain minimal and the server has the flexibility to implement a wide -range of interactions involving the end-user. For example: +The details of the interaction itself are fully under the control of the MCP server, and +the MCP client is only responsible for facilitating the interaction (typically by +presenting a URL to the end-user). Within this model, the client's responsibilities remain +minimal and the server has the flexibility to implement a wide range of secure +interactions involving the end-user. For example: - A productivity MCP server might request a user to authorize a third-party service to access their documents. - A news MCP server might request a user to upgrade their subscription to access more features. - A banking MCP server might request a user to verify their account to access a new feature. -- A media MCP server might request a user's favorite music genre to personalize the user - experience. -- A social media MCP server might request an image to use as a profile picture. ## Terminology @@ -38,19 +36,32 @@ Clients that support user interaction **MUST** declare the `userInteraction` cap { "capabilities": { "userInteraction": { - "types": ["ua", "prompt"], - "progress": true + "types": ["ua"] } } } ``` Clients supporting the `userInteraction` capability **MUST** list all supported interaction types -in the `types` array, and **MUST** support at least one interaction type. +in the `types` array, and **MUST** support at least one interaction type. The acceptable values +are defined in the [Interaction Types](#interaction-types) section below. The MCP server **MUST NOT** send an interaction request to the client of a type that is not supported by the client. + + +For trust and safety, there **SHOULD** always +be a human in the loop with the ability to deny interaction requests. + +MCP clients **SHOULD**: + +- Provide UI that makes it clear which server is requesting information +- Allow users to review and modify their responses before sending +- Respect user privacy and provide clear cancel options + + + ## Protocol Messages @@ -67,7 +78,7 @@ The request includes the following fields as part of the `params` object: - `type`: The type of interaction, which **MUST** be one of the types negotiated during initialization. - `interaction`: The interaction object, the schema of which depends on the type of - interaction. Each schema is defined in the [User Interaction Flow](#interaction-flow) + interaction. Each schema is defined in the [Interaction Types](#interaction-types) section below. The following is an example of a `interaction/create` message for a `ua` interaction: @@ -75,7 +86,7 @@ The following is an example of a `interaction/create` message for a `ua` interac ```json { "jsonrpc": "2.0", - "id": 1, + "id": 123, "method": "interaction/create", "params": { "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", @@ -91,23 +102,52 @@ The following is an example of a `interaction/create` message for a `ua` interac } ``` +The following flow diagram illustrates the `ua` interaction type across the server, the client, and the end-user: + +```mermaid +sequenceDiagram + participant U as End-User + participant B as User Agent (Browser) + participant C as MCP Client + participant S as MCP Server + + Note over S,C: Server initiates prompt interaction + S->>C: interaction/create type=ua + + C->>U: Present consent to open URL + U-->>C: Provide consent + + C->>B: Open URL + C->>S: Send response + Note over U,B: Human interaction + B-->>S: Perform interaction + + Note over S: Continue operations +``` + + ### Requiring Interaction as an Error Response -The MCP server **MAY** require a user interaction as an error response to a client request. -This is useful when interaction is required as a pre-condition for a request (e.g. step-up authorization). +The MCP server **MAY** require a user interaction as an error response to a client +request. This is useful when interaction is required as a pre-condition for a request. For +example, a [tool call](/specification/draft/server/tools#calling-tools) or [resource read](/specification/draft/server/resources#reading-resources) +request that requires the end-user to authorize a third-party service before the request +can be completed. The MCP server **MUST** send an [error response](/specification/draft/basic/lifecycle#error-handling) with the `code` equal to `-32003` and the `message` equal to `interaction_required`. The error response **MUST** include an `data` object consistent with one of the defined -[interaction schemas](#interaction-flow). +[interaction types](#interaction-types). + +The following is an example of an error response containing a `ua` interaction: ```json { "jsonrpc": "2.0", - "id": "abc-123", + "id": 123, "error": { "code": -32003, "message": "interaction_required", @@ -124,204 +164,91 @@ The error response **MUST** include an `data` object consistent with one of the } ``` - -## Interaction Flow - -When a user interaction is requested by the server and supported by the client, the MCP client **MUST** present -the user with an interaction flow. The type of flow is defined by the MCP server, and the client's behavior -is specific to the interaction type. - -This specification defines the following types of user interactions: - -- **`ua`**: A user agent interaction is a user interaction that involves making a request via a - User Agent (e.g. a Web browser). -- **`prompt`**: A prompt interaction is a user interaction that involves the MCP client prompting - the user for structured information (e.g. rendering a form). - -The client and server **MAY** negotiate additional interaction types. - - - -For trust and safety, there **SHOULD** always -be a human in the loop with the ability to deny interaction requests. - -MCP clients **SHOULD**: - -- Provide UI that makes it clear which server is requesting information -- Allow users to review and modify their responses before sending -- Respect user privacy and provide clear cancel options - - - -### User agent interactions - -A user agent interaction is a user interaction that involves the MCP client facilitating navigating to -a URL in a User Agent (e.g. a Web browser). This allows the MCP server to obtain data without involving the MCP client. - The MCP server can, as a result, control the entire interaction -from start to finish, including the user experience, and guarantee the security of sensitive data (e.g. API keys or authorization grants). - -This flow requires the client to support the `ua` user interaction type. - -```json -{ - "capabilities": { - "userInteraction": { - "types": ["ua"] - } - } -} -``` - -The MCP client **MUST** facilitate the opening of the URL in a User Agent. - -#### Flow Diagram +The following flow diagram illustrates a client request (tool call) that requires interaction with a third-party service: ```mermaid sequenceDiagram participant U as End-User participant B as User Agent (Browser) - participant C as Client - participant S as Server + participant C as MCP Client + participant S as MCP Server + participant T as Third-Party Service - Note over S,C: Server initiates prompt interaction - S->>C: interaction/create type=ua + C->>S: tools/call name=send_email + + Note over S: Server determines interaction is required + S->>C: error code=-32003 C->>U: Present consent to open URL U-->>C: Provide consent C->>B: Open URL - C->>S: Send response - Note over U,B: Human interaction - B-->>S: Perform interaction + B->>T: Navigate to URL + Note over T: Human interaction + T-->>S: Redirect to MCP server - Note over S,B: Completed interaction + Note over S: Completed interaction + Note over C: At a later time, retry request + C->>S: tools/call name=send_email Note over S: Continue operations ``` -#### Server Request - -For `ua` interactions, the `interaction` object has the following properties: - -- `url`: The URL that the user should interact with. -- `message`: An optional `TextContent` object used to provide an explanation to the user about the interaction. - -```json -{ - "jsonrpc": "2.0", - "id": 1, - "method": "interaction/create", - "params": { - "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", - "type": "ua", - "interaction": { - "url": "https://example.com/mcp?state=1234567890&...", - "message": { - "type": "text", - "text": "Please sign in to your account." - } - } - } -} -``` - -#### Client Response +## Interaction Types -When the client facilitates the opening of the URL, it **MUST** send a response to the server: +When a user interaction is requested by the server and supported by the client, the MCP client **MUST** present +the user with an interaction flow. The type of flow is defined by the MCP server, and the client's behavior +is specific to the interaction type. -```json -{ - "jsonrpc": "2.0", - "id": 1, - "result": {} -} -``` +This specification defines one type of user interaction: +- **`ua`**: A user agent interaction is a user interaction that involves making a request via a + User Agent (e.g. a Web browser). +The client and server **MAY** negotiate additional interaction types. -### Prompt interactions -A prompt interaction is a user interaction that involves the MCP client prompting the user for -information within the MCP client UI. This provides a way for the MCP server to obtain data from -the user without needing to host a URL or create any UI for the user to interact with. The MCP -server can, as a result, receive non-sensitive information from the user with little effort. +### User Agent Interactions -This flow requires the client to support the `prompt` user interaction type. +A user agent interaction is a user interaction that involves the MCP client facilitating +navigation to a URL in a User Agent (e.g. a Web browser). This allows the MCP server to +obtain data without involving the MCP client. The MCP server can, as a result, control the +entire interaction from start to finish, including the user experience, and guarantee the +security of sensitive data (e.g. API keys or authorization grants). +This flow requires the client to support the `ua` user interaction type: ```json { "capabilities": { "userInteraction": { - "types": ["prompt"] + "types": ["ua"] } } } ``` -The MCP client **MUST** present the user with a prompt UI consistent with the `schema` object. - -#### Flow Diagram - -```mermaid -sequenceDiagram - participant U as User - participant C as Client - participant S as Server - - Note over S,C: Server initiates prompt interaction - S->>C: interaction/create type=prompt - - C->>U: Present user interaction UI - Note over C,U: Human interaction - U-->>C: Provide requested information - - Note over S,C: Complete request - C->>S: Return user response - - Note over S: Continue operations with new information -``` - - +The MCP client **MUST** facilitate the opening of the URL in a User Agent. #### Server Request -For `prompt` interactions, the `interaction` object has the following properties: +For `ua` interactions, the `interaction` object has the following properties: -- `message`: A `TextContent` object used to provide context to the user about the interaction. -- `schema`: A `JSONSchema` object used to define the schema of the prompt for the MCP client. +- `url`: The URL that the user should interact with. +- `message`: An optional `TextContent` object used to provide an explanation to the user about the interaction. ```json { "jsonrpc": "2.0", - "id": 1, + "id": 123, "method": "interaction/create", "params": { "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", - "type": "prompt", + "type": "ua", "interaction": { + "url": "https://example.com/mcp?state=1234567890&...", "message": { "type": "text", - "text": "Let us know some information about you." - }, - "schema": { - "type": "object", - "properties": { - "name": { - "type": "string", - "description": "Your full name" - }, - "email": { - "type": "string", - "format": "email", - "description": "Your email address" - }, - "age": { - "type": "number", - "minimum": 18, - "description": "Your age" - } - }, - "required": ["name", "email"] + "text": "Please sign in to your account." } } } @@ -330,94 +257,12 @@ For `prompt` interactions, the `interaction` object has the following properties #### Client Response -When the user provides their response, the client **MUST** send a response to the server: - -```json -{ - "jsonrpc": "2.0", - "id": 1, - "result": { - "content": { - "name": "Monalisa", - "email": "monalisa@example.com", - "age": 30 - } - } -} -``` - -## Progress Tracking - -The MCP client **MAY** support progress tracking for interactions. This can be used to -provide feedback to the user about the progress of the interaction in the MCP client's UI. This is -particularly useful for interactions where the user will be interacting out-of-band with the MCP -client, such as `ua` interactions, and the MCP client desires some way to update its UI. - -This leverages the [Progress capability](/specification/draft/basic/utilities/progress) in the base -protocol. It requires the MCP server to support the `progress` capability during initialization. - -Tracking progress for user interactions is optional. If the MCP server does not support progress -tracking, it **MUST NOT** respond to the `interaction/notify` message, in keeping with the -requirements of the -[Progress capability](/specification/draft/basic/utilities/progress#behavior-requirements). - - -Note that the MCP server may choose to not send progress notifications for a given interaction, even if -the client supports progress tracking and the server supports the progress capability generally. -Therefore, the client **SHOULD NOT** assume that progress notifications will be sent for an -interaction, and should be prepared to handle the case where no progress notifications are sent. - -MCP clients **MAY** send an `interaction/notify` message to the server to initiate progress tracking for a -particular interaction. The MCP client **MUST** include the interaction ID in the `id` field that -it wants to track progress for. This `id` **MUST** be an interaction that the server created via -the `interaction/create` message. - -```json -{ - "jsonrpc": "2.0", - "id": "track-progress-123", - "method": "interaction/notify", - "params": { - "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8", - "_meta": { - "progressToken": "abc123" - } - } -} -``` - -MCP servers **MUST NOT** respond to the `interaction/notify` message if: - -- the `id` is not an interaction that the server created via the `interaction/create` message. -- the `id` is not an interaction that is associated with the client. -- the `id` is not an interaction that is associated with the current MCP session, if session - management is in use. - -MCP clients **SHOULD** be aware that MCP servers might not respond to the `interaction/notify` -message, and **SHOULD** be prepared to handle the case where no response is received. - -The following is an example of a progress notification sent by the MCP server: - -```json -{ - "jsonrpc": "2.0", - "method": "notifications/progress", - "params": { - "progressToken": "abc123", - "progress": 50, - "total": 100, - "message": "Reticulating splines..." - } -} -``` - -Once the interaction is complete, the server **MUST** respond to the `interaction/notify` message, -for example: +When the client facilitates the opening of the URL, it **MUST** send a response to the server: ```json { "jsonrpc": "2.0", - "id": "track-progress-123", + "id": 123, "result": {} } ``` @@ -426,20 +271,22 @@ for example: ### Server-Initiated Cancellation -The MCP server **MAY** cancel an interaction at any time by sending a `notifications/cancelled` -message to the client. The MCP client **SHOULD NOT** send a response. This is consistent with the -[Cancellation capability](/specification/draft/basic/utilities/cancellation). +The MCP server **MAY** cancel an interaction at any time by sending a +`notifications/cancelled` message to the client, as described in [Cancellation](/specification/draft/basic/utilities/cancellation). +The MCP client **SHOULD NOT** send a response. ### Client-Initiated Cancellation -The end-user may choose to decline or cancel an interaction themselves. For example, the user may decline to submit a form rendered by -the MCP client as part of a `prompt` interaction, or not consent to open a URL as part of a -`ua` interaction. The MCP client **MAY** indicate at any time that the server should abandon (cancel) the interaction by returning an error response: +The end-user may cancel an interaction at any time. For example, the user may decline +consent to open a URL as part of a `ua` interaction. +The MCP client **MAY** indicate at +any time that the server should abandon (cancel) the interaction by returning an error +response: ```json { "jsonrpc": "2.0", - "id": 1, + "id": 123, "error": { "code": -1, "message": "User did not consent to the interaction" @@ -450,29 +297,37 @@ the MCP client as part of a `prompt` interaction, or not consent to open a URL a The `id` of the request **MUST** be the `id` of the original `interaction/create` request that the client wants to cancel. -## Identifying the User - -Most MCP servers will need a persistent identifier for the end-user. The MCP server **MUST NOT** -rely on input from the client or end-user to identify the end-user, as this can be forged and lead to impersonation attacks. -Instead, the MCP server **SHOULD** identify the end-user in trusted (server) code. For example, - -- Implementations using an HTTP transport and [MCP authorization](/specification/draft/basic/authorization) - **MAY** use the subject claim (`sub`) from the OAuth 2.1 Access Token as the user identifier, if present. -- Implementations using an stdio transport **MAY** acquire the user identifier from the environment. ## Security Considerations ### Handling Sensitive Information -One mechanism for which user interaction may be leveraged is passing a user's auth credentials, or -other secret and sensitive data to the MCP server. The specifics of the sensitive data is out of -scope for this specification. However, MCP servers that request secrets, such as auth credentials, -**MUST** leverage an interaction type which prevents the MCP client from interacting with those -secrets in any way. +MCP servers **MUST** use the `ua` interaction type for sensitive information, such as +auth credentials or authorization grants. The MCP client **MUST NOT** send sensitive +information to the MCP server in any other way. + +### User Consent + +The MCP client **SHOULD** clearly communicate the purpose of the interaction to the end-user, +and provide a way for the end-user to consent to the interaction before continuing. + +### Identifying the User + +The MCP server **MUST NOT** rely on input from the client or end-user to identify the +end-user, as this untrusted input can be forged and lead to impersonation attacks. + +Instead, the MCP server **SHOULD** identify the end-user in trusted (server) code. For +example: + +- Implementations using an HTTP transport and [MCP authorization](/specification/draft/basic/authorization) + **MAY** use the subject claim (`sub`) from the OAuth 2.1 Access Token as the user + identifier, if present. +- Implementations using an stdio transport **MAY** acquire the user identifier from the + environment. -### Server-side request forgery (SSRF) +### Server-side Request Forgery -In the case of `ua` interactions, the MCP client is expected to make a request via a user agent +With the `ua` interaction type, the MCP client is expected to make a request via a user agent based on the value of the `url` parameter in the interaction object. Since MCP enables clients to interoperate with MCP servers it has no prior knowledge of, this opens a risk for Server-Side Request Forgery (SSRF) attacks by malicious MCP servers. MCP clients **SHOULD** take appropriate @@ -484,26 +339,27 @@ provide sufficient context to the user about the request that will be made, befo a User Agent. Further recommendations can be found in the Open Worldwide Application Security -Project (OWASP) SSRF Prevention Cheat Sheet -[OWASP.SSRF](https://cheatsheetseries.owasp.org/cheatsheets/Server_Side_Request_Forgery_Prevention_Cheat_Sheet.html). +Project (OWASP) [SSRF Prevention Cheat Sheet](https://cheatsheetseries.owasp.org/cheatsheets/Server_Side_Request_Forgery_Prevention_Cheat_Sheet.html). ### Phishing -This specification may be deployed in a way where the `url` parameter in the interaction object -for `ua` interactions points to a URL that defined by something other than the MCP server. For -example, the URL may be an authorization URL of a third-party service such as a file-sharing -service that the MCP server needs the user to authorize access to. If that third-party service -is malicious or compromised, it could trick the user into revealing their account credentials or -other sensitive information. +The `ua` interaction type may be used in a way where the `url` parameter in the +interaction object points to a URL on a domain that is not the MCP server's domain. For +example, the URL may be an authorization URL of a third-party service that the MCP server +needs the user to authorize access to. If that third-party service is malicious or +compromised, it could trick the user into revealing their account credentials or other +sensitive information. To mitigate this risk, MCP clients **SHOULD** take appropriate precautions, such as verifying the -authenticity of the URL and the destination of the request. +authenticity of the URL and clearly presenting the destination of the request to the user. ### Impersonation attacks -Since MCP enables clients to interoperate with MCP servers it has no prior knowledge of, this opens -a risk for impersonation attacks by malicious MCP clients. MCP servers **SHOULD** take appropriate -precautions against impersonation attacks, such as implementing -[Authorization](/specification/draft/basic/authorization) and ensuring that user interaction requests are bound -to the MCP session to prevent Insecure Direct Object Reference (IDOR) attacks. +Since MCP enables clients to interoperate with MCP servers it has no prior knowledge of, +this opens a risk for impersonation attacks by malicious MCP clients. MCP servers +**SHOULD** take appropriate precautions against impersonation attacks, such as: +- Implementing [Authorization](/specification/draft/basic/authorization) +- Identifying the end-user in trusted (server) code +- Ensuring that user interaction requests are bound to the MCP session to prevent Insecure + Direct Object Reference (IDOR) attacks diff --git a/package.json b/package.json index a3dfd568c..fab3aee69 100644 --- a/package.json +++ b/package.json @@ -18,6 +18,12 @@ "printWidth": 89, "proseWrap": "always" } + }, + { + "files": "*.json", + "options": { + "tabWidth": 4 + } } ] }, diff --git a/schema/draft/schema.json b/schema/draft/schema.json index da18c6ec8..ecd350159 100644 --- a/schema/draft/schema.json +++ b/schema/draft/schema.json @@ -196,9 +196,19 @@ "type": "object" }, "userInteraction": { - "additionalProperties": true, "description": "Present if the client supports user interaction.", - "properties": {}, + "properties": { + "types": { + "description": "An array of supported user interaction types. Clients must support at least one type.\n\nThis specification defines one interaction type:\n- \"ua\": A user agent interaction involving making a request via a User Agent (e.g. a Web browser)\n\nAdditional interaction types may be negotiated between client and server.", + "items": { + "type": "string" + }, + "type": "array" + } + }, + "required": [ + "types" + ], "type": "object" } }, @@ -260,9 +270,6 @@ }, { "$ref": "#/definitions/CompleteRequest" - }, - { - "$ref": "#/definitions/NotifyUserInteractionProgressRequest" } ] }, @@ -489,14 +496,17 @@ "type": "string" }, "interaction": { - "additionalProperties": true, - "description": "The interaction object. The schema of the interaction object is dependent on the type of\ninteraction.", - "properties": {}, - "type": "object" - }, - "progressAvailable": { - "description": "Whether progress is available for the interaction.", - "type": "boolean" + "anyOf": [ + { + "additionalProperties": true, + "properties": {}, + "type": "object" + }, + { + "$ref": "#/definitions/UAInteraction" + } + ], + "description": "The interaction object. The schema of the interaction object is dependent on the type of\ninteraction." }, "type": { "description": "The type of interaction.", @@ -524,11 +534,6 @@ "additionalProperties": {}, "description": "This result property is reserved by the protocol to allow clients and servers to attach additional metadata to their responses.", "type": "object" - }, - "content": { - "additionalProperties": {}, - "description": "The user's response to a prompt interaction. The schema of the content is dependent on the\nrequested schema within the prompt interaction.", - "type": "object" } }, "type": "object" @@ -1296,43 +1301,6 @@ ], "type": "object" }, - "NotifyUserInteractionProgressRequest": { - "description": "A request from the client to the server, requesting progress notifications for a user\ninteraction.", - "properties": { - "method": { - "const": "interaction/notify", - "type": "string" - }, - "params": { - "properties": { - "_meta": { - "properties": { - "progressToken": { - "$ref": "#/definitions/ProgressToken" - } - }, - "required": [ - "progressToken" - ], - "type": "object" - }, - "id": { - "type": "string" - } - }, - "required": [ - "_meta", - "id" - ], - "type": "object" - } - }, - "required": [ - "method", - "params" - ], - "type": "object" - }, "PaginatedRequest": { "properties": { "method": { @@ -2018,9 +1986,6 @@ }, { "$ref": "#/definitions/CompleteResult" - }, - { - "$ref": "#/definitions/UserInteractionProgressResult" } ] }, @@ -2220,6 +2185,24 @@ ], "type": "object" }, + "UAInteraction": { + "description": "Defines the interaction object for \"ua\" (user agent) type interactions.", + "properties": { + "message": { + "$ref": "#/definitions/TextContent", + "description": "An optional message to provide an explanation to the user about the interaction." + }, + "url": { + "description": "The URL that the user should interact with.", + "format": "uri", + "type": "string" + } + }, + "required": [ + "url" + ], + "type": "object" + }, "UnsubscribeRequest": { "description": "Sent from the client to request cancellation of resources/updated notifications from the server. This should follow a previous resources/subscribe request.", "properties": { @@ -2246,17 +2229,6 @@ "params" ], "type": "object" - }, - "UserInteractionProgressResult": { - "description": "A result from the server to the client, containing the progress of a user interaction.", - "properties": { - "_meta": { - "additionalProperties": {}, - "description": "This result property is reserved by the protocol to allow clients and servers to attach additional metadata to their responses.", - "type": "object" - } - }, - "type": "object" } } } diff --git a/schema/draft/schema.ts b/schema/draft/schema.ts index fcd29e34e..8b66c9095 100644 --- a/schema/draft/schema.ts +++ b/schema/draft/schema.ts @@ -223,7 +223,17 @@ export interface ClientCapabilities { /** * Present if the client supports user interaction. */ - userInteraction?: object; + userInteraction?: { + /** + * An array of supported user interaction types. Clients must support at least one type. + * + * This specification defines one interaction type: + * - "ua": A user agent interaction involving making a request via a User Agent (e.g. a Web browser) + * + * Additional interaction types may be negotiated between client and server. + */ + types: string[]; + }; } /** @@ -1231,45 +1241,31 @@ export interface CreateUserInteractionRequest extends Request { * The interaction object. The schema of the interaction object is dependent on the type of * interaction. */ - interaction: object; - /** - * Whether progress is available for the interaction. - */ - progressAvailable?: boolean; + interaction: UAInteraction | object; }; } - /** - * The client's response to a user interaction/create request from the server. + * Defines the interaction object for "ua" (user agent) type interactions. */ -export interface CreateUserInteractionResult extends Result { +export interface UAInteraction { /** - * The user's response to a prompt interaction. The schema of the content is dependent on the - * requested schema within the prompt interaction. + * The URL that the user should interact with. + * + * @format uri */ - content?: { [key: string]: unknown }; -} + url: string; -/** - * A request from the client to the server, requesting progress notifications for a user - * interaction. - */ -export interface NotifyUserInteractionProgressRequest extends Notification { - method: "interaction/notify"; - params: { - id: string; - _meta: { - progressToken: ProgressToken; - }; - }; + /** + * An optional message to provide an explanation to the user about the interaction. + */ + message?: TextContent; } /** - * A result from the server to the client, containing the progress of a user interaction. + * The client's response to a user interaction/create request from the server. */ -export interface UserInteractionProgressResult extends Result { -} +export interface CreateUserInteractionResult extends Result { } /* Client messages */ export type ClientRequest = @@ -1285,8 +1281,7 @@ export type ClientRequest = | SubscribeRequest | UnsubscribeRequest | CallToolRequest - | ListToolsRequest - | NotifyUserInteractionProgressRequest; + | ListToolsRequest; export type ClientNotification = | CancelledNotification @@ -1322,5 +1317,4 @@ export type ServerResult = | ListResourcesResult | ReadResourceResult | CallToolResult - | ListToolsResult - | UserInteractionProgressResult; + | ListToolsResult; From 7fd7411ac0e69070e248aa88a9eaef562d68f632 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Fri, 9 May 2025 11:27:47 -0700 Subject: [PATCH 06/13] Cleaned up cancellation --- .../draft/client/user_interaction.mdx | 28 ++++++------------- 1 file changed, 9 insertions(+), 19 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index 9c65cd116..197fa162b 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -267,35 +267,25 @@ When the client facilitates the opening of the URL, it **MUST** send a response } ``` -## Cancelling an Interaction - -### Server-Initiated Cancellation - -The MCP server **MAY** cancel an interaction at any time by sending a -`notifications/cancelled` message to the client, as described in [Cancellation](/specification/draft/basic/utilities/cancellation). -The MCP client **SHOULD NOT** send a response. - -### Client-Initiated Cancellation +Alternatively, if the end-user cancels or declines the interaction, the client **MUST** +send an error response to the server: -The end-user may cancel an interaction at any time. For example, the user may decline -consent to open a URL as part of a `ua` interaction. - -The MCP client **MAY** indicate at -any time that the server should abandon (cancel) the interaction by returning an error -response: ```json { "jsonrpc": "2.0", "id": 123, "error": { - "code": -1, - "message": "User did not consent to the interaction" + "code": -32099, + "message": "User did not consent to the interaction." } } ``` -The `id` of the request **MUST** be the `id` of the original `interaction/create` request that the -client wants to cancel. +## Cancelling an Interaction + +The MCP server **MAY** cancel an interaction at any time by sending a +`notifications/cancelled` message to the client, as described in [Cancellation](/specification/draft/basic/utilities/cancellation). +The MCP client **SHOULD NOT** send a response. ## Security Considerations From e548346be029d9d888ed4bde491286f89221bcd6 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Thu, 29 May 2025 21:05:50 -0700 Subject: [PATCH 07/13] Apply suggestions from @localden's review MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Den Delimarsky 🌺 <53200638+localden@users.noreply.github.com> --- .../draft/client/user_interaction.mdx | 22 +++++++++---------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index 197fa162b..d6cbf1525 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -9,10 +9,10 @@ directly with end-users without data passing through the client or the LLM. This servers to maintain control over user interactions and data sharing while dynamically gathering necessary information. -The details of the interaction itself are fully under the control of the MCP server, and +The interaction itself is fully under the control of the MCP server and the MCP client is only responsible for facilitating the interaction (typically by presenting a URL to the end-user). Within this model, the client's responsibilities remain -minimal and the server has the flexibility to implement a wide range of secure +minimal and the server has the flexibility to implement a wide range of interactions involving the end-user. For example: - A productivity MCP server might request a user to authorize a third-party service to @@ -22,14 +22,14 @@ interactions involving the end-user. For example: ## Terminology -- **End-user**: The human who is interacting with the MCP client (and, by extension, the MCP server). -- **User agent**: Most familiarly a Web browser, the user agent is a client that is capable of +- **End-user**: The human who is interacting with with the MCP server through their MCP client. +- **User agent**: a client, such as a web brwoser, that is capable of interacting with the end-user. Broadly, it is used as defined in [RFC 9110 Section 3.5](https://datatracker.ietf.org/doc/html/rfc9110#section-3.5). ## Capabilities -Clients that support user interaction **MUST** declare the `userInteraction` capability during +MCP clients that support user interaction **MUST** declare the `userInteraction` capability during [initialization](/specification/draft/basic/lifecycle#initialization): ```json @@ -56,9 +56,9 @@ be a human in the loop with the ability to deny interaction requests. MCP clients **SHOULD**: -- Provide UI that makes it clear which server is requesting information +- Provide UI that makes it clear which server is requesting an interaction - Allow users to review and modify their responses before sending -- Respect user privacy and provide clear cancel options +- Respect user choice and provide clear cancellation options @@ -202,8 +202,8 @@ is specific to the interaction type. This specification defines one type of user interaction: -- **`ua`**: A user agent interaction is a user interaction that involves making a request via a - User Agent (e.g. a Web browser). +- **`ua`**: A user agent interaction that involves making a request via a + client application that acts on behalf of the user, such as a web browser. The client and server **MAY** negotiate additional interaction types. @@ -211,7 +211,7 @@ The client and server **MAY** negotiate additional interaction types. ### User Agent Interactions A user agent interaction is a user interaction that involves the MCP client facilitating -navigation to a URL in a User Agent (e.g. a Web browser). This allows the MCP server to +navigation to a URL in a client application such as a web browser. This allows the MCP server to obtain data without involving the MCP client. The MCP server can, as a result, control the entire interaction from start to finish, including the user experience, and guarantee the security of sensitive data (e.g. API keys or authorization grants). @@ -227,7 +227,7 @@ This flow requires the client to support the `ua` user interaction type: } ``` -The MCP client **MUST** facilitate the opening of the URL in a User Agent. +The MCP client **MUST** facilitate the opening of the URL in a user agent, such as the default web browser. #### Server Request From 62e3d9b1a9d927706b6b437a05da4686354f729a Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Thu, 29 May 2025 21:13:53 -0700 Subject: [PATCH 08/13] More updates from review --- .../draft/client/user_interaction.mdx | 25 +++++++------------ 1 file changed, 9 insertions(+), 16 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index d6cbf1525..1d1641ebc 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -9,11 +9,11 @@ directly with end-users without data passing through the client or the LLM. This servers to maintain control over user interactions and data sharing while dynamically gathering necessary information. -The interaction itself is fully under the control of the MCP server and -the MCP client is only responsible for facilitating the interaction (typically by -presenting a URL to the end-user). Within this model, the client's responsibilities remain -minimal and the server has the flexibility to implement a wide range of -interactions involving the end-user. For example: +The interaction itself is fully under the control of the MCP server and the MCP client is +only responsible for providing an affordance to start it (typically by presenting a URL to +the end-user, and opening it in a user agent such as a web browser). Within this model, +the client's responsibilities remain minimal and the server has the flexibility to +implement a wide range of interactions involving the end-user. For example: - A productivity MCP server might request a user to authorize a third-party service to access their documents. @@ -47,7 +47,7 @@ in the `types` array, and **MUST** support at least one interaction type. The ac are defined in the [Interaction Types](#interaction-types) section below. The MCP server **MUST NOT** send an interaction request to the client of a type that is not -supported by the client. +explicitly declared by the client. @@ -76,7 +76,7 @@ The request includes the following fields as part of the `params` object: - `id`: The ID of the interaction that **MUST** be unique across the server's concurrent interactions. - `type`: The type of interaction, which **MUST** be one of the types negotiated during - initialization. + [initialization](/specification/draft/basic/lifecycle#initialization). - `interaction`: The interaction object, the schema of which depends on the type of interaction. Each schema is defined in the [Interaction Types](#interaction-types) section below. @@ -214,7 +214,7 @@ A user agent interaction is a user interaction that involves the MCP client faci navigation to a URL in a client application such as a web browser. This allows the MCP server to obtain data without involving the MCP client. The MCP server can, as a result, control the entire interaction from start to finish, including the user experience, and guarantee the -security of sensitive data (e.g. API keys or authorization grants). +security of sensitive data, such as API keys or access tokens. This flow requires the client to support the `ua` user interaction type: ```json @@ -306,14 +306,7 @@ and provide a way for the end-user to consent to the interaction before continui The MCP server **MUST NOT** rely on input from the client or end-user to identify the end-user, as this untrusted input can be forged and lead to impersonation attacks. -Instead, the MCP server **SHOULD** identify the end-user in trusted (server) code. For -example: - -- Implementations using an HTTP transport and [MCP authorization](/specification/draft/basic/authorization) - **MAY** use the subject claim (`sub`) from the OAuth 2.1 Access Token as the user - identifier, if present. -- Implementations using an stdio transport **MAY** acquire the user identifier from the - environment. +Instead, the MCP server **SHOULD** follow [security best practices](/specification/draft/basic/security_best_practices). ### Server-side Request Forgery From 26f72d2a185f500da548f918cb4b203e58c3aebe Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Mon, 2 Jun 2025 06:38:15 -0700 Subject: [PATCH 09/13] Clarify language --- docs/specification/draft/client/user_interaction.mdx | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index 1d1641ebc..e759f4789 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -23,7 +23,7 @@ implement a wide range of interactions involving the end-user. For example: ## Terminology - **End-user**: The human who is interacting with with the MCP server through their MCP client. -- **User agent**: a client, such as a web brwoser, that is capable of +- **User agent**: a client, such as a web browser, that is capable of interacting with the end-user. Broadly, it is used as defined in [RFC 9110 Section 3.5](https://datatracker.ietf.org/doc/html/rfc9110#section-3.5). @@ -42,9 +42,10 @@ MCP clients that support user interaction **MUST** declare the `userInteraction` } ``` -Clients supporting the `userInteraction` capability **MUST** list all supported interaction types -in the `types` array, and **MUST** support at least one interaction type. The acceptable values -are defined in the [Interaction Types](#interaction-types) section below. +Clients supporting the `userInteraction` capability **MUST** support at least one +interaction type, and **MUST** list all the interaction types they support in the `types` +array. The acceptable values are defined in the [Interaction Types](#interaction-types) +section below. The MCP server **MUST NOT** send an interaction request to the client of a type that is not explicitly declared by the client. From 7623f5b099a6f6bf2a24a1b248485c20f68d3572 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Wed, 4 Jun 2025 13:58:32 -0700 Subject: [PATCH 10/13] Reintroduce progress tracking --- .../draft/client/user_interaction.mdx | 53 +++++++++++++++++++ 1 file changed, 53 insertions(+) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index e759f4789..472f2c267 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -282,6 +282,59 @@ send an error response to the server: } ``` +## Tracking Progress +The [Progress capability](/specification/draft/basic/utilities/progress) provides a way +for MCP clients to track progress for user interactions. By tracking the progress of an +interaction, the MCP client can provide a better user experience. For example, the MCP +client could: + +- Update the UI when the interaction is complete. +- Automatically retry a tool call that required interaction. + +Tracking progress for user interactions is optional. MCP clients **MAY** send an +`interaction/track` message to the MCP server along with a [progress token](/specification/draft/basic/utilities/progress#progress-flow) +to track the progress of an interaction. The MCP client **MUST** include the interaction +ID in the `id` field for which it wants to track. This `id` **MUST** refer to an +interaction the server sent to the client. + +```json +{ + "jsonrpc": "2.0", + "id": 123, + "method": "interaction/track", + "params": { + "_meta": { + "progressToken": "progress-token-123" + }, + "id": "c8ec9a71-c475-4a88-a774-e9cd154bc7f8" + } +} +``` + +MCP servers **MUST NOT** send progress notifications related to the interaction if: + +- The `id` is not an interaction the server created. +- The `id` is not an interaction associated with the client. +- The `id` is not an interaction associated with the current MCP session, if session management is in use. + +MCP servers that receive a valid `interaction/track` request **SHOULD** send at least 1 +`notifications/progress` message, even if the interaction is already complete. + +The following is an example of a progress notification sent by the MCP server: + +```json +{ + "jsonrpc": "2.0", + "method": "notifications/progress", + "params": { + "progressToken": "progress-token-123", + "progress": 100, + "total": 100, + "message": "Consent granted." + } +} +``` + ## Cancelling an Interaction The MCP server **MAY** cancel an interaction at any time by sending a From f17ced5e0aa2627b675befd25e92171433aa2657 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Wed, 4 Jun 2025 14:05:08 -0700 Subject: [PATCH 11/13] Add interaction/track to schema --- schema/draft/schema.json | 52 +++++++++++++++++++++++++++++++++++++++- schema/draft/schema.ts | 27 ++++++++++++++++++++- 2 files changed, 77 insertions(+), 2 deletions(-) diff --git a/schema/draft/schema.json b/schema/draft/schema.json index 4f4a4c826..713a08a2e 100644 --- a/schema/draft/schema.json +++ b/schema/draft/schema.json @@ -489,7 +489,7 @@ "type": "object" }, "CreateUserInteractionRequest": { - "description": "A request from the server to the client, to create a user interaction.", + "description": "A request from the server to the client to create a user interaction.", "properties": { "method": { "const": "interaction/create", @@ -2218,6 +2218,56 @@ ], "type": "object" }, + "TrackUserInteractionRequest": { + "description": "A request from the client to the server to track the progress of a user interaction.", + "properties": { + "_meta": { + "properties": { + "progressToken": { + "$ref": "#/definitions/ProgressToken", + "description": "The progress token which was given in the initial request, used to associate this notification with the request that is proceeding." + } + }, + "required": [ + "progressToken" + ], + "type": "object" + }, + "method": { + "const": "interaction/track", + "type": "string" + }, + "params": { + "properties": { + "id": { + "description": "The ID of the interaction.", + "type": "string" + } + }, + "required": [ + "id" + ], + "type": "object" + } + }, + "required": [ + "_meta", + "method", + "params" + ], + "type": "object" + }, + "TrackUserInteractionResult": { + "description": "The server's response to a user interaction/track request from the client.", + "properties": { + "_meta": { + "additionalProperties": {}, + "description": "This result property is reserved by the protocol to allow clients and servers to attach additional metadata to their responses.", + "type": "object" + } + }, + "type": "object" + }, "UAInteraction": { "description": "Defines the interaction object for \"ua\" (user agent) type interactions.", "properties": { diff --git a/schema/draft/schema.ts b/schema/draft/schema.ts index 063796997..9cae716d3 100644 --- a/schema/draft/schema.ts +++ b/schema/draft/schema.ts @@ -1242,7 +1242,7 @@ export interface RootsListChangedNotification extends Notification { /* User Interaction */ /** - * A request from the server to the client, to create a user interaction. + * A request from the server to the client to create a user interaction. */ export interface CreateUserInteractionRequest extends Request { method: "interaction/create"; @@ -1285,6 +1285,31 @@ export interface UAInteraction { */ export interface CreateUserInteractionResult extends Result { } +/** + * A request from the client to the server to track the progress of a user interaction. + */ +export interface TrackUserInteractionRequest extends Request { + method: "interaction/track"; + params: { + /** + * The ID of the interaction. + */ + id: string; + }; + _meta: { + /** + * The progress token which was given in the initial request, used to associate this notification with the request that is proceeding. + */ + progressToken: ProgressToken; + }; +} + + +/** + * The server's response to a user interaction/track request from the client. + */ +export interface TrackUserInteractionResult extends Result { } + /* Client messages */ export type ClientRequest = | PingRequest From 708fef5306c42ea74fface5c92ec79cb6b4fb15a Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Wed, 4 Jun 2025 14:35:56 -0700 Subject: [PATCH 12/13] Clarify MUSTs on consent and server context --- docs/specification/draft/client/user_interaction.mdx | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index 472f2c267..691e4db2d 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -55,11 +55,14 @@ explicitly declared by the client. For trust and safety, there **SHOULD** always be a human in the loop with the ability to deny interaction requests. +MCP clients **MUST**: + +- Provide a way for the end-user to consent to the interaction. +- Clearly communicate which server is requesting an interaction. + MCP clients **SHOULD**: -- Provide UI that makes it clear which server is requesting an interaction -- Allow users to review and modify their responses before sending -- Respect user choice and provide clear cancellation options +- Allow the end-user to cancel the interaction. From 780386b137c922dd81538522333739fde1ad91b0 Mon Sep 17 00:00:00 2001 From: Nate Barbettini Date: Tue, 10 Jun 2025 09:48:03 -0700 Subject: [PATCH 13/13] Add note about statefulness --- docs/specification/draft/client/user_interaction.mdx | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/docs/specification/draft/client/user_interaction.mdx b/docs/specification/draft/client/user_interaction.mdx index 691e4db2d..79c69b106 100644 --- a/docs/specification/draft/client/user_interaction.mdx +++ b/docs/specification/draft/client/user_interaction.mdx @@ -66,6 +66,11 @@ MCP clients **SHOULD**: +Using the `userInteraction` capability means that the MCP server **MUST** be stateful, if +it is not already. At a minimum, the MCP server **MUST** keep track of the interactions it +has created for each MCP client. + + ## Protocol Messages