Summary
clean_schema_for_display() in fastapi_mcp/openapi/utils.py (lines 76-86) removes anyOf from schemas but does not hoist the items field from array variants to the top level. This produces {type: "array"} without items, which is invalid JSON Schema.
MCP clients (VS Code Copilot, Claude Code) reject the tool with: Error: tool parameters array type must have items.
Root Cause
For Optional[List[X]] parameters, Pydantic v2 generates:
{
"anyOf": [
{"type": "array", "items": {"type": "object", ...}},
{"type": "null"}
]
}
clean_schema_for_display() strips anyOf (line 76). Then convert.py line 248 calls get_single_param_type_from_schema() which returns "array" from the anyOf, and sets type: "array" on the property — but items was inside the anyOf variant and is now gone.
Result: {type: "array", title: "Images"} — no items.
Reproduction
from fastapi import FastAPI
from pydantic import BaseModel
from typing import Optional, List
app = FastAPI()
class MyRequest(BaseModel):
tags: Optional[List[str]] = None
@app.post("/test")
def test(req: MyRequest):
return {"ok": True}
# Mount fastapi_mcp, then inspect the MCP tool schema for /test
# The 'tags' parameter will have {type: "array"} without items
Affected Versions
- 0.3.7 — confirmed
- 0.4.0 — confirmed (same code path)
Suggested Fix
In clean_schema_for_display(), before stripping anyOf, hoist items and type from array variants:
if "anyOf" in schema:
for variant in schema["anyOf"]:
if isinstance(variant, dict) and variant.get("type") == "array":
if "items" in variant:
schema.setdefault("items", variant["items"])
schema.setdefault("type", "array")
break
Environment
- fastapi-mcp: 0.3.7, 0.4.0
- FastAPI: 0.115+
- Python: 3.11
- MCP clients: VS Code Copilot Chat (v0.45.1), Claude Code
Summary
clean_schema_for_display()infastapi_mcp/openapi/utils.py(lines 76-86) removesanyOffrom schemas but does not hoist theitemsfield from array variants to the top level. This produces{type: "array"}withoutitems, which is invalid JSON Schema.MCP clients (VS Code Copilot, Claude Code) reject the tool with:
Error: tool parameters array type must have items.Root Cause
For
Optional[List[X]]parameters, Pydantic v2 generates:{ "anyOf": [ {"type": "array", "items": {"type": "object", ...}}, {"type": "null"} ] }clean_schema_for_display()stripsanyOf(line 76). Thenconvert.pyline 248 callsget_single_param_type_from_schema()which returns"array"from the anyOf, and setstype: "array"on the property — butitemswas inside the anyOf variant and is now gone.Result:
{type: "array", title: "Images"}— noitems.Reproduction
Affected Versions
Suggested Fix
In
clean_schema_for_display(), before strippinganyOf, hoistitemsandtypefrom array variants:Environment