Purpose and architecture
Reusable access to external capabilities
Model Context Protocol (MCP) is a shared interface between applications and providers of external capabilities. Instead of every application inventing a different way to describe and discover an integration, a provider exposes tools, information, and reusable messages through a common contract. Interoperability means independently implemented components can exchange those capabilities using agreed rules.
The service-specific integration still exists. Someone must translate requests into the backend's operations and interpret its responses. Linear's hosted MCP service, for example, supplies centrally maintained access to issue-management operations. Applications can reuse that interface, but still need compatible clients, suitable permissions, and a workflow that uses the returned information correctly.
A direct function or SDK call is often simpler when one application controls both sides. MCP becomes attractive when several applications should reuse a capability provider without duplicating its integration. That benefit comes with a server to operate or trust and a compatibility boundary to test. The useful decision is where reuse earns those obligations—not whether every operation should become MCP.
Hosts, clients, servers, and models
The host is the application coordinating the experience, model access, context, permissions, and consent. An MCP client is its protocol-facing component for communication with one server; a host can contain several clients. An MCP server exposes capabilities through handlers, which may call a separate backend, such as an issue tracker. These are logical roles, not a requirement for separate machines. A server can be a local subprocess or a remote service.
Tool calling is a different interface: a model proposes an operation and arguments; executable application code performs the accepted call and returns its result. The host can adapt MCP tool definitions into the model's tool format. The published LangChain MCP adapter makes that separation visible by loading MCP tools and then passing them to an agent with a separately selected model. Its example illustrates adaptation, not conformance to this chapter's protocol revision.
No model is required to invoke MCP. Application code can deterministically list capabilities, read resources, or call a known tool. Cross-server coordination can also remain in the host without putting every intermediate payload into model context. The model-facing interface is developed in Where MCP meets the local action boundary; acceptance and execution checks belong in a controlled dispatcher.
Turning points in capability exchange
Reusable providers solve a recurring integration problem: independently developed consumers otherwise need separate adapters for the same capability. MCP applies that separation to AI applications. Its history also explains why older examples can teach sound interface ideas while showing incompatible connection mechanics.
| Development | Contribution |
|---|---|
| Language Server Protocol — June 27, 2016 | Microsoft, Red Hat, and Codenvy's announcement described reusable language services across development tools. MCP explicitly identifies LSP as an inspiration for separating consumers from capability providers. |
| Model-facing function calling — June 13, 2023 | OpenAI's announcement introduced model-generated JSON arguments for developer-described functions. This predates MCP but addresses the model–application interface, not reusable server communication. |
| MCP public introduction — November 25, 2024 | Anthropic open-sourced MCP to reduce repeated custom integrations with isolated data sources. The launch included SDKs, reference servers, and local-server support in Claude Desktop; remote production tooling was forthcoming. |
| Streamable HTTP — March 26, 2025 | This revision replaced the earlier HTTP-plus-SSE transport and introduced an OAuth-based authorization framework. Specification changes did not imply simultaneous client adoption. |
| Self-describing requests — July 28, 2026 | Maintainers David Soria Parra and Den Delimarsky explained a shift away from connection-bound protocol state to address reliability and scaling difficulties. Applications could retain state through explicit handles. |
These developments coexist. A model can propose an ordinary local function call, an MCP server can wrap an established API, and a host can choose either path. The later protocol changes matter because they alter how an exchange carries its assumptions—not because they eliminate service-specific behavior or distributed failures.
Exposed interfaces
Tools describe callable operations
A tool definition advertises an executable operation through a name, description, input JSON Schema, and optional output schema. A schema describes permitted data structure; it does not implement the operation. tools/list discovers definitions, while tools/call requests execution using a name and arguments. Names belong to their server. See Tool definitions shape available choices for designing the model-facing description.
| Artifact | Example | Meaning |
|---|---|---|
| Definition | create_issue; required string fields teamId and title | Advertises accepted input shape. |
| Invocation arguments | {"teamId":"team-A","title":"Fix login"} | Requests an operation; no result exists yet. |
| Result excerpt | structuredContent: {"issueId":"issue-42"} | Server-produced data, not model-generated arguments. |
Result structure needs careful interpretation. JSON serialized inside a text content block remains text; it is not the structuredContent field. GitHub's inspected issue-comment handler illustrates this distinction: after backend creation, it returns an ID and URL as serialized JSON in a text result. A host must adapt the actual representation it receives rather than infer the representation from how the text looks.
When an output schema is supplied, results must conform and clients should validate them. A JSON-RPC error differs from an execution failure returned with isError. Neither a well-shaped result nor an annotation such as a read-only hint establishes authority or the intended business effect.
Resources name information
A resource exposes information identified by a Uniform Resource Identifier (URI). A URI names something; it need not be an HTTP address. resources/list returns descriptions, resources/read retrieves content, and resources/templates/list exposes parameterized addresses. Expanding a template selects a URI to read rather than invoking a tool. Content entries can contain text or base64-encoded binary data, with a media type identifying the representation.
| Object | Example |
|---|---|
| Address | issues://team-A/42 |
| Listed metadata | Name: Issue 42; media type: application/json |
| Read content | {"title":"Fix login","state":"Backlog"} |
| Model input | The host's selected representation of that content |
The distinction from tools is not simply reading versus writing: tools can retrieve data too. Resources give applications an addressable information interface. Reading one does not automatically include it in model input. That selection is context assembly, covered in From sources to a request.
Resources can also carry procedural information. Backlog.md exposes a workflow overview and guides for task creation, execution, and completion alongside its callable tools. This gives the host material explaining how to use operations, but availability alone does not ensure that the host reads it or the model follows it.
Prompts return reusable messages
An MCP prompt is a discoverable, parameterized template that returns messages. prompts/list describes templates and their arguments; prompts/get supplies a name and argument values. The server resolves the template, and the host decides whether and how to use its messages. For example, a constructed review_issue template could expand an issue identifier into a user message requesting a review. Retrieving that message does not perform the review.
Prompts are conventionally user-selected. A slash command is one presentation, not a required interface: Mahesh Murag's MCP workshop describes a Zed command that accepts a pull-request identifier and prepares a longer summary prompt. User selection does not make server-authored instructions trusted. Instruction design itself belongs in Prompting and In-Context Learning.
| Interface | Request and return | Remaining application decision |
|---|---|---|
| Tool | Operation and arguments → execution result | Whether to execute and how to interpret the outcome |
| Resource | URI → information | Whether and how to include it in context |
| Prompt | Template and arguments → messages | Whether and how to use those messages |
Protocol exchange and discovery
Read a versioned exchange
A remote procedure call (RPC) requests an operation across an execution boundary and returns its result. Birrell and Nelson's February 1984 Cedar RPC paper pursued accessible distributed programming while acknowledging timing and independent failures. MCP uses JSON-RPC 2.0, the JSON-RPC Working Group's transport-independent message convention. A convenient call interface never makes a remote operation behave exactly like a local function.
In revision 2026-07-28, every request carries protocolVersion and clientCapabilities in its metadata. A request names a method and has a non-null string or integer ID, unique among the sender's outstanding requests. Its response repeats that ID and contains a result or error. An error includes an integer code and message. A notification has no ID and receives no response.
Illustrative pseudocode
Python-like pseudocodeCapability negotiation tells peers which protocol features they implement. The request's client capabilities describe what the client can handle; server/discover lets it learn what the server supports. Servers must implement discovery, but clients need not call it first. An unsupported version produces UnsupportedProtocolVersionError with supported versions; the client can choose a shared version or report incompatibility. An optional extension needs shared support: otherwise use core behavior or reject the request. Feature support grants no permission, and this revision requires no connection-scoped initialization handshake.
| Observed order | Message | Interpretation |
|---|---|---|
| 1 | Request read-A | First outstanding exchange |
| 2 | Request read-B | Second independent exchange |
| 3 | Response read-B | Completes the second exchange |
| 4 | Notification, no ID | Not either request's final response |
| 5 | Response read-A | Completes the first exchange |
Older revisions used initialize, a response containing supported capabilities, and notifications/initialized before normal operation. Keep that compatibility mode separate. Package version is another independent identifier: the TypeScript migration guide distinguishes modern-capable packages from explicitly selecting modern wire behavior. It also treats HTTP 401/403 as authorization failures, not evidence that an older protocol should be tried.
Build and refresh the catalog
Discovery has several meanings. A registry helps locate server packages or remote endpoints; it does not host their binaries or enumerate their live capabilities. Namespace verification identifies a publisher, not safe code. After selecting a server, server/discover describes support, while tools/list, resources/list, resources/templates/list, and prompts/list enumerate its interfaces.
Lists may be paginated. An opaque cursor is a continuation token the client passes back without interpreting or changing it. Continue while nextCursor is present; an empty string is still a valid cursor. Do not infer completion from page length. Invalid cursors require error handling rather than treating the partial inventory as complete.
Illustrative pseudocode
Python-like pseudocodePreserve origin when aggregating catalogs: (server-A, search) and (server-B, search) are different tools. The host may expose either, both, or neither to a model. Discovery is not relevance ranking, and a visible definition is not execution permission.
Caching adds a freshness contract. Complete discover/list/read results carry ttlMs, a time-to-live hint, and cacheScope. Keys include result-affecting parameters; private entries cannot cross authorization contexts. TTL neither freezes content nor schedules polling. Relevant notifications invalidate even fresh entries. Pages are cached independently, so enumeration is not a transactional snapshot; an invalid cursor requires discarding pages and restarting. Continuation exchanges are not cacheable.
subscriptions/listen requests categories of changes or particular resource URIs. Its first message acknowledges the subset the server will honor: inspect that subset. Notification metadata identifies the subscription request. Cancellation or transport loss ends the subscription, so a reconnecting stdio client must subscribe again. A change notification still does not rewrite an existing model input. The host must re-fetch and assemble the next request; Refresh, supersede, remove explains that application responsibility.
A notification invalidates the cache, not the request
Local processes and remote transports
A transport carries protocol messages. With stdio, the client launches a subprocess and exchanges newline-delimited messages through standard input and output. Standard output must remain protocol traffic; diagnostics belong on standard error. With Streamable HTTP, clients POST messages to one MCP endpoint. Responses use JSON or a request-scoped Server-Sent Events (SSE) stream—a server-to-client event delivery format, not necessarily a stream of model tokens.
| Responsibility | Local subprocess | Remote service |
|---|---|---|
| Execution | The client launches configured code. | The service operator runs the server. |
| Trust decision | Executable provenance and process privileges | Endpoint authenticity and operator access |
| Credentials | Secrets explicitly supplied to the process are accessible to it. | The client grants access through the service's supported mechanism. |
| Isolation | Requires host or OS controls. | Authentication does not certify benign server code. |
The inspected TypeScript stdio implementation uses an environment allowlist plus explicitly supplied values and launches with shell:false. These choices limit accidental inheritance and shell interpretation, but do not sandbox the executable. Local execution can still read permitted files and communicate over permitted networks.
July-2026 requests carry their own protocol assumptions rather than depending on an initialized protocol session. This permits routing to different instances without session storage, but applications can still require databases and explicit state handles. The redesign addressed operational complexity and introduced migration costs; it is not a measured throughput guarantee.
Clients must handle both JSON and SSE responses. On an ordinary SSE response stream, related notifications precede the final JSON-RPC response, which should end the stream. In this revision, closing that stream cancels its request, and Last-Event-ID replay is unsupported. Older Streamable HTTP examples with session IDs and resumable streams describe a different contract.
Continue when input is required
Multi Round-Trip Requests let tools/call, resources/read, or prompts/get return an InputRequiredResult for missing information. The client may continue with supported inputs, a different JSON-RPC ID, matching inputResponses, and an exact echo of any opaque requestState. This continues the original operation, rather than initiating an unsolicited server call.
Elicitation obtains user input through the client. Form mode collects permitted structured information; URL mode sends the user to an out-of-band interaction for secrets or third-party authorization. Form mode must not request passwords, access tokens, API keys, or payment credentials. Accept, decline, and cancel are different dispositions. Accepting a URL interaction does not prove completion: the server checks when the operation resumes. Neither mode is blanket approval for later actions.
Continuation fields are operation-specific, never shared with concurrent work. Treat returned state as attacker-controlled: authority or business state needs integrity protection and principal, request, and expiry binding. Single-use behavior requires server enforcement; continuation remains optional.
One operation, two request IDs
Sampling requests client-mediated model generation without transferring provider credentials to the server. Existing supported integrations use the continuation pattern, with the client retaining model choice and permission control. However, sampling is deprecated in revision 2026-07-28: new implementations should not adopt it, and existing ones should migrate to direct provider APIs. Deprecated does not mean removed; its specification remains for at least twelve months before removal eligibility.
Authority and application control
Acquire access to a protected server
Authentication establishes identity; authorization permits access. OAuth supports delegated access without giving an application the user's password. An authorization server issues an access token after the relevant checks and grant. A resource server accepts that token to serve protected operations. Scope describes granted permissions using service-defined strings; requesting a scope does not guarantee receiving it. Here, the protected resource server is the MCP service—not necessarily an item read through resources/read.
MCP authorization support is optional; the following flow concerns protected HTTP services. Separating token issuance from capability serving became explicit in the June 2025 revision, which classified MCP servers as OAuth resource servers and added protected-resource metadata. This lets the MCP implementation rely on an authorization service rather than own every identity function.
| Document | How it is found | What the client establishes |
|---|---|---|
| Protected-resource metadata | A 401 WWW-Authenticate challenge's resource_metadata URL, preferred when present, or prescribed well-known locations | Which authorization servers can issue access credentials |
| Authorization-server metadata | The selected issuer's metadata-discovery procedure | Authorization endpoints; the returned issuer must exactly match the issuer used for discovery |
Once the authorization server is known, client registration identifies the application requesting access and its permitted redirect destinations. A Client ID Metadata Document lets an unfamiliar client supply that information through an HTTPS URL hosting JSON metadata. Clients supporting all registration options should prefer existing registration, then supported metadata documents, then dynamic registration. Manual configuration may be necessary. Dynamic registration is deprecated but remains available. Issued registration credentials are tied to their authorization-server issuer; a metadata-document URL is portable. Registration identifies the client—it does not grant access to business operations.
In a browser-based authorization flow, the user signs in and grants access. The authorization server returns a code to the client, which exchanges it for an access token and presents that token to MCP. Proof Key for Code Exchange (PKCE) binds code redemption to a verifier held by the initiating client. The token's audience is its intended recipient: the client requests access for the MCP resource, and the server checks that the token was issued for it. Secure storage and exact redirect validation protect other parts of the exchange.
An invalid or expired token requires HTTP 401; insufficient permission uses 403. A scope challenge can guide a bounded authorization upgrade, but clients should remember failed upgrades rather than loop. Refresh tokens are sensitive and cannot be assumed available. Before code redemption, validate the returned issuer against the recorded authorization attempt, including its required presence when issuer-response support was advertised. Renewing MCP access does not renew an independent backend credential.
Enforce authority at each boundary
A server must not forward its incoming client token to an upstream API. Backend access uses separate authority appropriate to that recipient. Preserve the represented user and acting service instead of silently substituting a broad service account. Distinguish people and actors develops those identities. Tenant context—the organization or customer boundary—must come from verified authentication context and constrain resource lookup and caches, not from a model-proposed tenant identifier.
Issue access, then present it to the intended recipient
Visibility and authority can be restricted independently. Linear documents a read-only endpoint exposing only read tools and, separately, a read-scoped token that cannot reach write APIs on its standard endpoint. The first narrows discovery; the second limits credential authority. A hidden operation should not remain executable merely because a caller already knows its name.
A confused deputy misuses its own authority on behalf of a less-privileged caller. One MCP proxy risk arises when many clients share the proxy's upstream OAuth identity: remembered upstream consent can suppress a new consent screen for an unfamiliar MCP client. The proxy must track user approval per client and bind the returning authorization flow to that approval. Prior consent for one client is not consent for all clients.
| Decision | Enforcing component |
|---|---|
| Enable a server and expose capabilities | Host configuration and policy |
| Share model context or release data | Host input assembly and outbound controls |
| Approve a consequential action | Host approval bound to actor, target, arguments, scope, and lifetime |
| Accept arguments and current state | Server handler, before protected execution |
| Permit the backend operation | Backend permissions and server-side access checks |
| Bound files, networks, and resources | Host, operating system, and service limits |
Roots communicate workspace locations, not confinement. They are deprecated in July 2026; new implementations should use tool parameters, resource URIs, or configuration instead. A declared file root cannot restrict an otherwise unrestricted process. Sandboxes and Execution Isolation explains the separate enforcement mechanisms.
Tool-description poisoning places attacker instructions in discovered metadata. Invariant's historical experiments included a nominal arithmetic tool that induced sensitive-file transmission and a cross-server redirection attack that did not require invoking the malicious tool. These findings concern the reported configurations, not every current client. They explain why discovery itself crosses an instruction boundary: retain independent enforcement and keep untrusted content in role, rather than treating server descriptions as privileged instructions.
Execution and failure
Trace one issue creation
To carry out a model-proposed action, the host must connect discovery to dispatch: obtain a tool definition, expose it to the model, check the proposed call, and send accepted arguments through its MCP client. The server then maps the call to its backend and returns the outcome. Consider creating “Fix login” in team-A through a Linear-backed adapter.
The handoffs carry different responsibilities: the host accepts the proposed action, the server validates it for execution, and the adapter interprets the backend’s reply.
The identifiers are deliberately different. call-7 associates the model proposal with its observation. rpc-12 associates a protocol request with its response. op-9 is application bookkeeping for the intended operation, not automatic backend deduplication. A created issue ID identifies the resulting record. Store their relationships explicitly rather than assigning one identifier every meaning.
Linear's API uses a GraphQL mutation, a request to change data, for issue creation. Its response includes success and selected issue fields, but HTTP 200 can also carry partial data and errors. Defaults matter too: omitting stateId selects the team's first Backlog state, or Triage when enabled. The returned issue ID permits a separate read. If the user requested a particular state, check that state explicitly; receiving a valid MCP response does not establish it.
From model proposal to backend result
Keep the execution record connected without overclaiming visibility. Trace-context propagation carries execution identity across controlled service boundaries so their records can be joined. It cannot expose an uninstrumented provider's internals, and trace identity is not authorization. Propagate context and observe telemetry develops that mechanism. The user-facing result should distinguish what the backend reported from any separately verified state.
Interpret errors and interrupted requests
Failure handling begins by identifying which boundary supplied the observation. Rejection before dispatch, failure inside a handler, and loss of a response after dispatch require different responses. A single success flag cannot represent all three.
| Observation | Known fact | Responsible response |
|---|---|---|
| Unsupported version or feature | The requested exchange is unsupported. | Client selects shared behavior or reports incompatibility. |
| Authorization rejection | An access check rejected this request. | Resolve identity or permission at that boundary. |
| JSON-RPC error | The protocol operation returned an error. | Interpret its code and operation-specific meaning. |
Tool result with isError | The tool reports execution failure. | Inspect the handler's failure contract, including partial effects. |
| Unusable result | The host cannot safely consume the response. | Reject downstream use; do not assume a mutation never happened. |
| No final response | The client lacks a completed observation. | Preserve uncertainty and investigate external state. |
Progress is optional observation during work. The client supplies a progressToken, unique across active requests; notifications report increasing progress and optionally a total and message. A supplied token does not require reports. Without a meaningful total, do not display a percentage. Reports stop at completion and are neither a final result nor a durable job handle.
Set request timeouts and an overall maximum even if progress resets an inactivity timer. Cancellation is binding-specific: stdio uses notifications/cancelled with the outstanding request ID; HTTP closes the request's SSE stream. Servers should stop processing and release resources, but cancellation can arrive after completion or concern work that cannot stop. Clients must handle races and ignore late responses. This is not rollback.
If issue creation loses its final response, the client may have an unknown outcome: creation might not have committed, or it might have committed before delivery failed. July-2026 HTTP reconnection does not replay that response. Searching for a matching record may help investigate, but a match alone does not identify which concurrent attempt created it.
One observation, two possible realities
ExampleA missing response cannot distinguish absent work from a committed effect whose result was lost.
Read the diagram as text
- Creation dispatched.
- No creation committed. Work stops before the effect.
- Creation committed. The backend record exists.
- Result delivery lost.
- Client: no final response. Effect remains unknown to the client.
- Creation dispatched → No creation committed: Interruption before commit.
- Creation dispatched → Creation committed: Execution reaches commit.
- No creation committed → Client: no final response: No result delivered.
- Creation committed → Result delivery lost: Interruption after commit.
- Result delivery lost → Client: no final response: No result delivered.
Idempotency makes repeated attempts represent one logical operation only when the receiving service enforces that contract. A caller identifier must be recorded consistently with the effect, bound to unchanged parameters, and retained for a defined retry window. Logging an identifier or changing the JSON-RPC ID does not do this. Recover when the effect is unknown explains reconciliation. The agent runtime is the application machinery retaining execution state and recovery policy; its implementation belongs in Agent Runtimes and Harness Engineering.
Separate durable tasks from live requests
Some work must remain inspectable after its initiating connection disappears. MCP's maintainers introduced experimental Tasks in November 2025 for ongoing work and later result retrieval. The separately evolving Tasks extension, described here from its draft specification, is optional rather than part of core July-2026 request handling.
With shared extension support, a tools/call can return an ordinary result or a task handle after the task has been durably created. The client retains taskId and polls tasks/get, respecting pollIntervalMs. An input_required task accepts responses through tasks/update. completed contains the original method result, which can still be a tool result with isError; failed carries a protocol error. Ordinary progress notifications are not task progress.
| Identity | What it represents | What it does not guarantee |
|---|---|---|
| Request ID | One protocol exchange | Retrieval after connection loss |
| Task ID | Stored status and result, subject to retention | Worker restart or successful computation |
| Backend record or operation ID | Domain-specific state or action | Equivalence with protocol task status |
Task cancellation uses tasks/cancel, not request cancellation. Its acknowledgement confirms receipt, not stopped execution; another terminal outcome remains possible. A client retaining the handle can inspect later status. Retrieval still requires authorization and remains subject to retention: expiry can remove the task, and the extension provides no tasks/list recovery path for a lost handle. Cancellation does not reverse completed backend effects.
Keep protocol status separate from domain status. An invoice, for example, can pass through several business states while its task remains working. Cornelia Davis's Tasks discussion makes this mapping explicit. A durable observation mechanism helps recover knowledge of work; it does not supply the application's entire recovery system.
Verification and choice
Verify the integration and choose its boundary
Verification has four levels. Protocol conformance checks the exchange rules. Shared feature support checks whether both implementations provide the required subset. Semantic agreement checks that operations and representations mean what each side expects. Task usefulness checks the intended external outcome. A connection can pass the first level while failing any of the others.
| Property | Focused test | Required evidence |
|---|---|---|
| Version and transport | Shared revision; JSON and SSE handling; explicit incompatibility | Captured exchange and selected wire behavior |
| Catalog | Pagination, duplicate names, changes, authorization-scoped caching | Complete inventory and refreshed host view |
| Primitives and content | Required tools, resource reads, prompt retrieval, result representations | Decoded artifacts and correct host use |
| Authority | Allowed action, denied action, wrong target, insufficient scope | Enforcement result and backend state |
| Continuation | Supported input, refusal, unsupported feature, concurrent operations | Correct request association and disposition |
| Interruption | Timeout, cancellation race, lost response, optional task recovery | Honest outcome status and bounded recovery |
| Business result | Create the intended record under permitted authority | Backend receipt, relevant read-back, and accurate presentation |
MCP Inspector helps inspect interfaces. Its documented fixtures cover cases such as pagination, structured results, authorization discovery, and client-rejected schemas. That is useful coverage, not a certificate that an application achieved its business goal. Exercise the actual host and backend as well; Exercise real integration boundaries explains why substitute-only tests cannot establish the whole path.
The server interface itself remains a design choice. Block's June 16, 2025 Linear account describes moving from endpoint-shaped tools to consolidated tools and then separate GraphQL read and mutation interfaces. The illustrated assignee query became one request, but the report is not a controlled performance benchmark or a universal recommendation for arbitrary GraphQL. It demonstrates that protocol reuse does not choose useful operation granularity.
Existing APIs can coexist with MCP. Azure API Management's REST wrapper exposes selected API operations as tools, not resources or prompts, with authentication configured separately. Intermediaries also affect execution: Microsoft warns that reading response bodies in policies can introduce buffering that interferes with streaming. An adapter preserves only the behavior it actually implements.
Choose direct integration when tight application ownership, specialized access patterns, or a small capability surface make it simpler. Choose MCP when reusable capability exchange justifies operating and testing the boundary. Compare both under the same task and authority requirements, keeping outcome quality, latency, model-context consumption, maintenance, and compatibility costs separate. A shared protocol is valuable when it reduces repeated work without hiding who owns the remaining decisions.
Open questions
Behavioral portability remains harder than message compatibility. Hosts can differ in resource exposure, catalog refresh, and model-facing adaptation while exchanging valid messages. Progress would mean reproducible cross-host tests of a declared feature subset and equivalent backend outcomes, without requiring identical interfaces.
Useful capability discovery must balance completeness against model-context cost. Loading every endpoint description can be impractical, while progressive disclosure adds selection steps and cache interactions. Progress would demonstrate task coverage, correct tool choice, and bounded context consumption under changing catalogs—not merely smaller initial payloads.
Safe recovery across independent services still needs stronger business contracts than correlation alone. Durable task status can preserve observations, but external effects may lack enforced deduplication or a decisive reconciliation interface. Progress would expose operation-specific retry, retention, and effect-status guarantees that remain valid across crashes and concurrent attempts.






































































































































































