{"record":{"id":"a83c9ad84a338d49","repo":"Hmbown/CodeWhale","slug":"context-inputschema-is-required-for-an-advertised-mcp-tool","errorCode":null,"errorMessage":"{context}.inputSchema is required for an advertised MCP tool","messagePattern":"(.+?)\\.inputSchema is required for an advertised MCP tool","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/mcp/src/stdio_client.rs","lineNumber":156,"sourceCode":"        .as_object()\n        .with_context(|| format!(\"{context} must be an object\"))?;\n    let tool_name = fields\n        .get(\"name\")\n        .and_then(Value::as_str)\n        .with_context(|| format!(\"{context}.name must be a string\"))?\n        .to_string();\n    let description = optional_string_field(fields, \"description\", &context)?;\n    let input_schema = match fields.get(\"inputSchema\") {\n        Some(schema) if valid_tool_input_schema(schema) => schema.clone(),\n        Some(_) => bail!(\"{context}.inputSchema must be a valid object-shaped MCP input schema\"),\n        None if allow_legacy_schema_omission => {\n            // Servers that omit the entire initialize capabilities object are\n            // already identified as legacy by `validate_initialize_result`.\n            // Preserve omission compatibility only for that explicit mode;\n            // a standard advertised tools capability must send inputSchema.\n            json!({\"type\": \"object\", \"properties\": {}})\n        }\n        None => bail!(\"{context}.inputSchema is required for an advertised MCP tool\"),\n    };\n    Ok((\n        McpToolDescriptor {\n            server_name: server_name.to_string(),\n            // The manager owns qualification; report the raw name and let it\n            // build `mcp__server__tool`.\n            qualified_name: tool_name.clone(),\n            tool_name,\n            description,\n        },\n        input_schema,\n    ))\n}\n\nfn parse_resource_entry(\n    server_name: &str,\n    resource: &Value,\n    index: usize,","sourceCodeStart":138,"sourceCodeEnd":174,"githubUrl":"https://github.com/Hmbown/CodeWhale/blob/73e0f67d83c59909b571efdfc88c4bc28c309cb1/crates/mcp/src/stdio_client.rs#L138-L174","documentation":"parse_tool_entry fails closed when an advertised tool has no inputSchema at all and the legacy schema-omission mode is not enabled. Servers that declare the standard tools capability must include inputSchema for every tool; the manager refuses to invent one, unlike the explicit legacy compatibility path.","triggerScenarios":"list_tools_with_input_schemas parses a tools/list entry lacking the \"inputSchema\" key while allow_legacy_schema_omission is false (i.e., the server sent a standard initialize capabilities object advertising tools).","commonSituations":"Server claims tools capability in initialize but omits schemas per tool (common with minimal hand-rolled servers); older server versions predating required inputSchema; frameworks that auto-advertise tools without collecting parameter schemas.","solutions":["Add a valid inputSchema ({\"type\":\"object\",\"properties\":{}} minimally) for each tool in the server's tools/list response.","Update the MCP server to a spec-conformant version that always sends inputSchema with advertised tools.","If the server legitimately cannot send schemas (legacy), run it in/enable the explicit legacy omission mode recognized by validate_initialize_result rather than weakening the standard path."],"exampleFix":"// before (server output)\n{\"name\":\"search\",\"description\":\"Search\"}\n// after\n{\"name\":\"search\",\"description\":\"Search\",\"inputSchema\":{\"type\":\"object\",\"properties\":{\"query\":{\"type\":\"string\"}}}}","handlingStrategy":"validation","validationCode":"fn all_tools_have_input_schema(tools: &[serde_json::Value]) -> bool {\n    tools.iter().all(|t| t.get(\"inputSchema\").is_some())\n}\n// assert on the raw tools/list payload before wiring the server into the manager","typeGuard":null,"tryCatchPattern":"match manager.list_tools_with_input_schemas(server) {\n    Err(e) if e.to_string().contains(\"inputSchema is required\") => {\n        tracing::error!(\"server {server} omits inputSchema: {e}\");\n        // reconnect in legacy mode if the server cannot emit schemas, or fix the server\n    }\n    other => other,\n}","preventionTips":["Always include inputSchema ({\"type\":\"object\",\"properties\":{}} at minimum) for every advertised tool.","Use an MCP SDK that populates inputSchema automatically from tool signatures.","Only rely on legacy schema-omission mode for servers that also omit the initialize capabilities object — never partially."],"tags":["mcp","json-schema","missing-field"],"backgroundTag":"missing-required-argument","analyzedSha":"73e0f67d83c59909b571efdfc88c4bc28c309cb1","analyzedAt":"2026-09-22T01:30:00.501Z","contentChangedAt":"2026-09-22T01:30:00.501Z","schemaVersion":2},"datasetVersion":"2026-09-22T11:17:16.035Z"}