Fall back to StructuredContent in MCP tool results

When an MCP server sets StructuredContent without populating
Content with TextContent entries, extractMCPContent returned
an empty string, making successful tool calls look empty to
the agent. Now the function serializes StructuredContent as
JSON when no text parts are found.

Signed-off-by: Bryan Frimin <bryan@getprobo.com>
This commit is contained in:
Bryan Frimin
2026-03-13 19:43:19 +01:00
parent cb6189d7ac
commit 5c889a1d47
2 changed files with 57 additions and 2 deletions

View File

@@ -167,7 +167,7 @@ func (t *mcpTool) Execute(ctx context.Context, arguments string) (ToolResult, er
}
func extractMCPContent(result *mcp.CallToolResult) string {
if result == nil || len(result.Content) == 0 {
if result == nil {
return ""
}
@@ -178,5 +178,16 @@ func extractMCPContent(result *mcp.CallToolResult) string {
}
}
return strings.Join(parts, "\n")
if len(parts) > 0 {
return strings.Join(parts, "\n")
}
if result.StructuredContent != nil {
data, err := json.Marshal(result.StructuredContent)
if err == nil {
return string(data)
}
}
return ""
}

View File

@@ -379,4 +379,48 @@ func TestExtractMCPContent(t *testing.T) {
assert.Equal(t, "", extractMCPContent(result))
},
)
t.Run(
"falls back to structured content when no text content",
func(t *testing.T) {
t.Parallel()
result := &mcp.CallToolResult{
StructuredContent: map[string]any{
"status": "ok",
"count": float64(42),
},
}
got := extractMCPContent(result)
assert.Contains(t, got, `"status":"ok"`)
assert.Contains(t, got, `"count":42`)
},
)
t.Run(
"text content takes precedence over structured content",
func(t *testing.T) {
t.Parallel()
result := &mcp.CallToolResult{
Content: []mcp.Content{
&mcp.TextContent{Text: "text wins"},
},
StructuredContent: map[string]any{"key": "value"},
}
assert.Equal(t, "text wins", extractMCPContent(result))
},
)
t.Run(
"structured content used when content has only non-text",
func(t *testing.T) {
t.Parallel()
result := &mcp.CallToolResult{
Content: []mcp.Content{
&mcp.ImageContent{Data: []byte("img"), MIMEType: "image/png"},
},
StructuredContent: map[string]any{"fallback": true},
}
assert.Equal(t, `{"fallback":true}`, extractMCPContent(result))
},
)
}