MCP Structured Content Is Not Optional If the Next Tool Call Needs the ID
MCP’s split between human-readable content and machine-shaped structuredContent is useful right up until the agent cannot see the field it needs for the next tool call. OpenClaw PR #87540 fixes one of those deceptively small bridge bugs: OpenClaw exposed structuredContent to the model only when normal content[] was empty. If an MCP server returned both text and structured fields, the model saw the text and lost the handle.
The reported failure involved Codex as an MCP server. The server returned a visible “pong” and a structured threadId. OpenClaw preserved the threadId in metadata for UI/log consumers, but because content[] was non-empty, the model-visible tool output did not include the structured field. The next codex-reply call needed the thread ID. The data existed. The agent could not use it. That is not preservation; that is broken state wearing a metadata badge.
The issue, #87511, was created on May 28 at 2026-05-28T04:37:58Z. PR #87540 followed at 06:08:09Z and was updated at 13:00:29Z. The patch is focused: +57/-12 across src/agents/agent-bundle-mcp-materialize.ts and src/agents/agent-bundle-mcp-tools.materialize.test.ts. It appends a labeled structuredContent: JSON text block to the model-visible tool output while preserving details.structuredContent for UI and logs.
If the next call needs the ID, the model needs the ID
The concrete before/after is clean. Before the fix, a tool response containing { type: "text", text: "pong" } plus structured data such as threadId left the model with only “pong.” After the fix, the output includes the original text block and a second text block labeled structuredContent:, containing JSON with a Codex-style ID such as 019e6cdb-8e7f-7cb2-891f-9edb689f6fc7 and content: "pong". The UI metadata path remains intact.
This matters because multi-turn tool workflows are mostly handle choreography. Thread IDs, cursors, page tokens, approval IDs, file IDs, job IDs, run IDs, and continuation handles are the connective tissue between calls. If the agent can see a friendly sentence but not the handle, it can describe what happened but cannot continue the work. From the user’s perspective, that looks like forgetfulness or tool incompetence. From the runtime’s perspective, it is a projection bug.
The version details make the failure more concrete: the report cites OpenClaw 2026.5.5 with codex-cli 0.134.0 as an MCP server. That is not an obscure theoretical server returning weird payloads. Codex continuation is exactly the kind of workflow MCP should support well. If a bridge hides the continuation ID whenever text is present, the protocol is technically carrying the state while the orchestrator functionally drops it.
Related historical issues #77024 and #57461 show this is not just a Codex quirk. MCP clients including Claude.ai and Cursor have had trouble when important data lived in structuredContent while clients primarily read content. The interoperability lesson is boring but decisive: if the model must reason about or reuse a value, the value has to be projected into the model’s working context somehow.
The minimal fix is right, but the bigger problem is projection policy
Serializing structuredContent as labeled JSON in model-visible text is a pragmatic move. It is not elegant. It can increase prompt size. It can expose fields the model may not need. It relies on the model reading a JSON block out of text instead of using a richer structured reference mechanism. But given today’s tool-call interfaces, it is probably the right default for this bug. The alternative is an agent that cannot perform the next call despite the runtime having the data.
The highest-risk area is not the code diff. It is the policy implied by “make structured content visible.” Structured tool results can contain secrets, PII, bulk payloads, internal URLs, raw logs, or data that belongs in UI metadata but not model context. A blanket “dump all structured JSON into the prompt forever” would be the MCP version of the tool-result token poisoning problem OpenClaw is also working on this week. Visibility is required for continuity; selectivity is required for governance.
The eventual shape should be schema-aware projection. Continuation IDs, cursors, counts, statuses, and safe summaries should be model-visible by default. Sensitive payloads should stay behind explicit tools or redacted views. Large arrays should be summarized with fetch handles. Projection decisions should be logged so operators can answer the basic question: what structured fields did the model actually see? That is the difference between an MCP transport adapter and an MCP governance layer.
PR #87540 is scoped correctly. It fixes the materialization boundary for bundle-MCP results and preserves existing metadata behavior. It adds regression coverage for a response containing both normal text content and structuredContent with a Codex-style threadId. ClawSweeper reviewed it positively and even produced a visual before/after flow after a human requested @clawsweeper visualize. That last bit is worth noting: good agent PR review should explain data flow, not just declare that tests pass.
How practitioners should test MCP tools now
If you build or operate MCP servers, this bug gives you a useful test checklist. Do not only verify that the UI shows the structured fields. Verify that the agent can use those fields in the next turn. If a tool returns a cursor, ask the model to fetch the next page. If it returns a thread ID, ask it to continue the thread. If it returns a file ID, ask it to operate on the file. If it returns an approval ID, ask for the approval flow. Continuation tests catch projection bugs that snapshot tests miss.
Also test mixed responses. Many servers return both human-readable text and structured data because that is a sensible API design. The bridge must not treat those as mutually exclusive worlds. Human-readable text explains the result; structured content often makes the result actionable. Agents need both when the next step depends on both.
For tool authors, make handles explicit and small. Do not bury the only continuation ID deep inside a giant object if a top-level threadId will do. Provide safe summaries alongside raw payloads. Mark sensitive fields clearly if your protocol allows it. The orchestrator still needs projection policy, but servers can make the safe path easier.
The editorial read: MCP interoperability is not only “can the client call the server?” It is “can the agent see the right state to make the next call safely?” OpenClaw’s structured-content bug shows how easy it is to technically preserve data and operationally lose it. In agent systems, metadata hidden from the model is not useful continuity. It is a receipt in a drawer while the agent is trying to pay at the counter.
Sources: OpenClaw PR #87540, Issue #87511, Issue #77024, Issue #57461