Type definitions for MCP protocol version 2026-07-28.
This revision is a breaking, stateless protocol era. These types describe
its wire surface. Runtime support is selected through the dual-era protocol
modes, and rc.6 defaults new connections to :prefer_modern.
Important changes represented here include per-request protocol metadata, typed result envelopes, discovery, caching hints, subscriptions, and multi-round-trip input requests.
Summary
Types
A complete result with mandatory client-side caching hints.
A modern tool result whose structured content may be any JSON value.
Parameters for cooperatively cancelling one task.
Capabilities declared by a modern client on each request.
A server-directed task handle returned instead of an immediate result.
Full task state embedded in tasks/get and notifications/tasks.
The result of server/discover.
Parameters for idempotently reading one task.
A complete result returned by tasks/get.
A JSON-RPC header/body mismatch response (-32020).
Client or server implementation identity.
A server-initiated request embedded in an MRTR result.
Server-assigned input IDs mapped to requests.
An interim result requesting additional client input.
A client result satisfying one server-initiated MRTR request.
Retry fields accepted on client-initiated requests after an MRTR result.
Server-assigned input IDs mapped to client results.
A JSON object with string keys.
Any JSON Schema 2020-12 object, including extension keywords.
A value representable in JSON.
An extensible MCP _meta object.
A missing per-request client capability response (-32021).
Metadata carried by notifications, including subscription correlation.
The numeric elicitation schema from the 2026-07-28 generator.
Metadata required on every modern request.
Common fields present on every modern result.
Metadata carried by results.
A recognized or negotiated extension result discriminator.
Capabilities returned by a modern server from server/discover.
Notification categories selected by subscriptions/listen.
A request that opens a long-lived notification stream.
Parameters for subscriptions/listen.
The graceful close result for subscriptions/listen.
Metadata on the graceful close result of a subscription stream.
Fields common to task handles and detailed task state.
Lifecycle state of a task in the official Tasks extension.
A tool definition using unrestricted JSON Schema 2020-12 objects.
An unsupported protocol version response (-32022).
Parameters for submitting responses to outstanding task inputs.
Functions
Returns the protocol version described by this module.
Types
@type cacheable_result() :: %{ :resultType => result_type(), :ttlMs => non_neg_integer(), :cacheScope => :public | :private, optional(:_meta) => result_meta_object(), optional(atom() | String.t()) => any() }
A complete result with mandatory client-side caching hints.
@type call_tool_result() :: %{ :resultType => result_type(), :content => [ExMCP.Types.content()], optional(:structuredContent) => json_value(), optional(:isError) => boolean(), optional(:_meta) => result_meta_object() }
A modern tool result whose structured content may be any JSON value.
@type cancel_task_request_params() :: %{ _meta: request_meta_object(), taskId: String.t() }
Parameters for cooperatively cancelling one task.
@type client_capabilities() :: %{ optional(:experimental) => %{optional(String.t()) => json_object()}, optional(:roots) => %{}, optional(:sampling) => %{ optional(:context) => json_object(), optional(:tools) => json_object() }, optional(:elicitation) => %{ optional(:form) => json_object(), optional(:url) => json_object() }, optional(:extensions) => %{optional(String.t()) => json_object()} }
Capabilities declared by a modern client on each request.
@type create_task_result() :: %{ :resultType => :task, :taskId => String.t(), :status => task_status(), :createdAt => String.t(), :lastUpdatedAt => String.t(), :ttlMs => non_neg_integer(), optional(:pollIntervalMs) => non_neg_integer(), optional(:statusMessage) => String.t(), optional(:_meta) => result_meta_object() }
A server-directed task handle returned instead of an immediate result.
@type detailed_task() :: %{ :taskId => String.t(), :status => task_status(), :createdAt => String.t(), :lastUpdatedAt => String.t(), :ttlMs => non_neg_integer(), optional(:pollIntervalMs) => non_neg_integer(), optional(:statusMessage) => String.t(), optional(:inputRequests) => input_requests(), optional(:result) => json_object(), optional(:error) => json_object() }
Full task state embedded in tasks/get and notifications/tasks.
@type discover_result() :: %{ :resultType => result_type(), :ttlMs => non_neg_integer(), :cacheScope => :public | :private, :supportedVersions => [String.t()], :capabilities => server_capabilities(), optional(:instructions) => String.t(), optional(:_meta) => result_meta_object() }
The result of server/discover.
@type get_task_request_params() :: %{_meta: request_meta_object(), taskId: String.t()}
Parameters for idempotently reading one task.
@type get_task_result() :: %{ :resultType => :complete, :taskId => String.t(), :status => task_status(), :createdAt => String.t(), :lastUpdatedAt => String.t(), :ttlMs => non_neg_integer(), optional(:pollIntervalMs) => non_neg_integer(), optional(:statusMessage) => String.t(), optional(:inputRequests) => input_requests(), optional(:result) => json_object(), optional(:error) => json_object(), optional(:_meta) => result_meta_object() }
A complete result returned by tasks/get.
@type header_mismatch_error() :: %{ :jsonrpc => String.t(), optional(:id) => request_id(), error: %{:code => -32020, :message => String.t(), optional(:data) => any()} }
A JSON-RPC header/body mismatch response (-32020).
@type implementation() :: %{ :name => String.t(), :version => String.t(), optional(:title) => String.t(), optional(:description) => String.t(), optional(:websiteUrl) => String.t(), optional(:icons) => [ExMCP.Types.V20251125.icon()] }
Client or server implementation identity.
A server-initiated request embedded in an MRTR result.
@type input_requests() :: %{optional(String.t()) => input_request()}
Server-assigned input IDs mapped to requests.
@type input_required_result() :: %{ :resultType => result_type(), optional(:inputRequests) => input_requests(), optional(:requestState) => String.t(), optional(:_meta) => result_meta_object() }
An interim result requesting additional client input.
@type input_response() :: map()
A client result satisfying one server-initiated MRTR request.
@type input_response_request_params() :: %{ :_meta => request_meta_object(), optional(:inputResponses) => input_responses(), optional(:requestState) => String.t(), optional(atom() | String.t()) => any() }
Retry fields accepted on client-initiated requests after an MRTR result.
@type input_responses() :: %{optional(String.t()) => input_response()}
Server-assigned input IDs mapped to client results.
@type json_object() :: %{optional(String.t()) => json_value()}
A JSON object with string keys.
@type json_schema() :: map()
Any JSON Schema 2020-12 object, including extension keywords.
@type json_value() :: String.t() | number() | boolean() | nil | [json_value()] | %{optional(String.t()) => json_value()}
A value representable in JSON.
@type log_level() :: ExMCP.Types.log_level()
An extensible MCP _meta object.
@type missing_required_client_capability_error() :: %{ :jsonrpc => String.t(), optional(:id) => request_id(), error: %{ code: -32021, message: String.t(), data: %{requiredCapabilities: client_capabilities()} } }
A missing per-request client capability response (-32021).
@type notification_meta_object() :: %{ optional(:"io.modelcontextprotocol/subscriptionId") => request_id(), optional(String.t()) => any() }
Metadata carried by notifications, including subscription correlation.
@type number_schema() :: %{ :type => :number | :integer, optional(:title) => String.t(), optional(:description) => String.t(), optional(:minimum) => number(), optional(:maximum) => number(), optional(:default) => number() }
The numeric elicitation schema from the 2026-07-28 generator.
@type progress_token() :: ExMCP.Types.progress_token()
@type request_id() :: ExMCP.Types.request_id()
@type request_meta_object() :: %{ :"io.modelcontextprotocol/protocolVersion" => String.t(), :"io.modelcontextprotocol/clientCapabilities" => client_capabilities(), optional(:"io.modelcontextprotocol/clientInfo") => implementation(), optional(:"io.modelcontextprotocol/logLevel") => log_level(), optional(:progressToken) => progress_token(), optional(String.t()) => any() }
Metadata required on every modern request.
@type result() :: %{ :resultType => result_type(), optional(:_meta) => result_meta_object(), optional(atom() | String.t()) => any() }
Common fields present on every modern result.
@type result_meta_object() :: %{ optional(:"io.modelcontextprotocol/serverInfo") => implementation(), optional(String.t()) => any() }
Metadata carried by results.
@type result_type() :: String.t()
A recognized or negotiated extension result discriminator.
@type server_capabilities() :: %{ optional(:experimental) => %{optional(String.t()) => json_object()}, optional(:logging) => json_object(), optional(:completions) => json_object(), optional(:prompts) => %{optional(:listChanged) => boolean()}, optional(:resources) => %{ optional(:subscribe) => boolean(), optional(:listChanged) => boolean() }, optional(:tools) => %{optional(:listChanged) => boolean()}, optional(:extensions) => %{optional(String.t()) => json_object()} }
Capabilities returned by a modern server from server/discover.
@type subscription_filter() :: %{ optional(:toolsListChanged) => boolean(), optional(:promptsListChanged) => boolean(), optional(:resourcesListChanged) => boolean(), optional(:resourceSubscriptions) => [String.t()], optional(:taskIds) => [String.t()] }
Notification categories selected by subscriptions/listen.
@type subscriptions_listen_request() :: %{ jsonrpc: String.t(), id: request_id(), method: String.t(), params: subscriptions_listen_request_params() }
A request that opens a long-lived notification stream.
@type subscriptions_listen_request_params() :: %{ _meta: request_meta_object(), notifications: subscription_filter() }
Parameters for subscriptions/listen.
@type subscriptions_listen_result() :: %{ resultType: result_type(), _meta: subscriptions_listen_result_meta_object() }
The graceful close result for subscriptions/listen.
@type subscriptions_listen_result_meta_object() :: %{ :"io.modelcontextprotocol/subscriptionId" => request_id(), optional(:"io.modelcontextprotocol/serverInfo") => implementation(), optional(String.t()) => any() }
Metadata on the graceful close result of a subscription stream.
@type task() :: %{ :taskId => String.t(), :status => task_status(), :createdAt => String.t(), :lastUpdatedAt => String.t(), :ttlMs => non_neg_integer(), optional(:pollIntervalMs) => non_neg_integer(), optional(:statusMessage) => String.t() }
Fields common to task handles and detailed task state.
@type task_status() :: :working | :input_required | :completed | :failed | :cancelled
Lifecycle state of a task in the official Tasks extension.
@type tool() :: %{ :name => String.t(), :inputSchema => json_schema(), optional(:title) => String.t(), optional(:description) => String.t(), optional(:outputSchema) => json_schema(), optional(:annotations) => ExMCP.Types.tool_annotations(), optional(:icons) => [ExMCP.Types.V20251125.icon()], optional(:_meta) => meta_object() }
A tool definition using unrestricted JSON Schema 2020-12 objects.
@type unsupported_protocol_version_error() :: %{ :jsonrpc => String.t(), optional(:id) => request_id(), error: %{ code: -32022, message: String.t(), data: %{supported: [String.t()], requested: String.t()} } }
An unsupported protocol version response (-32022).
@type update_task_request_params() :: %{ _meta: request_meta_object(), taskId: String.t(), inputResponses: input_responses() }
Parameters for submitting responses to outstanding task inputs.
Functions
@spec protocol_version() :: String.t()
Returns the protocol version described by this module.