The Wire Contract Evolution in MCP

The Model Context Protocol (MCP) has seen a significant evolution in its handling of tool outputs, particularly concerning arrays. Following a protocol upgrade to the 2026-07-28 version, the way array tool outputs are structured has changed fundamentally. Previously, clients interacting with older versions of the protocol might have consistently expected to unwrap a structuredContent.result field to access array data. This pattern was common when dealing with the older wire shape, where arrays were often nested within a result object.

However, with the adoption of the 2026-07-28 specification, the underlying contract has been updated. The MCP 2026-07-28 tools specification now explicitly states that structuredContent can directly contain any valid JSON value. This means an array is treated as a first-class citizen, and a scalar value (like a string, number, or boolean) is also treated as such. The necessity of a wrapper, such as .result, to access these values has been eliminated. An array is simply an array, and a scalar is a scalar, directly within the structuredContent payload.

This change represents a shift in the wire contract. It's not merely an update to the C# type definitions; it's a change in how data is transmitted and expected at the transport boundary. Developers accustomed to the previous structure must adapt to this new reality. Relying on the old structuredContent.result pattern for arrays will likely lead to errors or unexpected behavior when interacting with systems that have adopted the newer protocol version.

Testing Protocol Version Differences

To effectively manage this transition and ensure compatibility, rigorous testing is crucial. The author of the original post emphasizes treating this wire contract change as a significant event, one that warrants thorough testing at the transport boundary. A simple unit test focusing solely on the C# return type might not be sufficient. Such tests often operate within the compiled language's abstraction layer and may not reveal the actual data shapes being exchanged over the network.

A more robust approach involves verifying the data as it traverses the communication channel. This means testing against both protocol versions to explicitly highlight the differences. The example provided in the source material suggests a small verifier script that can run both protocol versions offline. This allows developers to explicitly see what the tools/list endpoint advertised under each protocol version and, crucially, what data tools/call actually transmitted. Making these differences explicit through testing is key to preventing integration issues and ensuring that applications correctly interpret the tool outputs, whether they are arrays or scalar values.

Diagram illustrating MCP tool output structures pre- and post-2026-07-28 protocol upgrade.

Implications for Developers and Integrations

The implication for developers is clear: any client code that was built around the older wire shape and routinely accesses array outputs via a structuredContent.result wrapper needs to be updated. This is particularly relevant for applications that might interact with a mix of systems running different MCP protocol versions. Failure to adapt could result in runtime errors, incorrect data processing, or a complete breakdown in communication.

The MCP 2026-07-28 specification aims for greater clarity and directness in its data structures. By allowing direct JSON values within structuredContent, it simplifies parsing and reduces the boilerplate code required on the client side. For developers, this means less code to maintain and a more straightforward understanding of the data they are receiving. However, the transition period requires careful management. Developers must be aware of the version negotiation between client and server. When both sides successfully negotiate the 2026-07-28 protocol, the expectation of a .result wrapper for arrays should be abandoned.

This change underscores the importance of versioning in API contracts. Protocol upgrades, especially those that alter fundamental data structures, are not trivial. They require developers to be vigilant about API versions and to implement strategies that can gracefully handle or migrate away from older data formats. The move away from the .result wrapper for arrays is a move towards a cleaner, more direct API design, but it necessitates a corresponding update in client-side logic and testing methodologies to ensure seamless integration.

The Contract Change and Its Testability

The core of the issue lies in the distinction between the C# type system and the actual wire contract. While a C# SDK might define a type that includes a Result property, the underlying JSON payload transmitted over the network is the definitive contract. The MCP specification update directly impacts this wire contract. Before the update, the contract might have implicitly or explicitly dictated that array results were always nested within a result object. After the update, the contract allows for direct representation of arrays.

Testing this change effectively requires looking beyond the immediate C# type. Tests should validate the JSON structure as it is serialized and deserialized. Tools that can inspect network traffic or simulate requests and responses with specific JSON payloads are invaluable. The approach of running both protocol versions offline, as suggested, provides a concrete method to verify that the application behaves as expected under both the old and new contract definitions. This proactive testing ensures that when the 2026-07-28 protocol is negotiated, the application correctly interprets the direct array output without attempting to unwrap a non-existent .result field.

This scenario highlights a common challenge in software development: maintaining compatibility and managing API evolution. As protocols and APIs mature, they often simplify or change their data representations. Developers who build systems relying on these interfaces must stay informed and adapt their code and testing strategies accordingly. The MCP C# SDK’s evolution regarding array outputs serves as a practical example of how critical it is to understand and test the wire contract, not just the language-level abstractions.