{"record":{"id":"fda6d513b853c005","repo":"spring-projects/spring-ai","slug":"tool-call-arguments-are-null-or-empty-for-mcp-tool-fda6d5","errorCode":null,"errorMessage":"Tool call arguments are null or empty for MCP tool: <toolName>. Using empty JSON object as default.","messagePattern":"Tool call arguments are null or empty for MCP tool: <toolName>\\. Using empty JSON object as default\\.","errorType":"console","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"mcp/common/src/main/java/org/springframework/ai/mcp/SyncMcpToolCallback.java","lineNumber":117,"sourceCode":"\t * Returns the original MCP tool name without prefixing.\n\t * @return the original tool name\n\t */\n\tpublic String getOriginalToolName() {\n\t\treturn this.tool.name();\n\t}\n\n\t@Override\n\tpublic String call(String toolCallInput) {\n\t\treturn this.call(toolCallInput, null);\n\t}\n\n\t@Override\n\tpublic String call(String toolCallInput, @Nullable ToolContext toolContext) {\n\n\t\t// Handle the possible null parameter situation in streaming mode.\n\t\tif (!StringUtils.hasText(toolCallInput)) {\n\t\t\tif (logger.isWarnEnabled()) {\n\t\t\t\tlogger.warn(\"Tool call arguments are null or empty for MCP tool: \" + this.tool.name()\n\t\t\t\t\t\t+ \". Using empty JSON object as default.\");\n\t\t\t}\n\t\t\ttoolCallInput = \"{}\";\n\t\t}\n\n\t\tMap<String, Object> arguments = jsonHelper.fromJsonToMap(toolCallInput);\n\n\t\tCallToolResult response;\n\t\ttry {\n\t\t\tvar mcpMeta = toolContext != null ? this.toolContextToMcpMetaConverter.convert(toolContext) : null;\n\n\t\t\t// Use the original tool name, not the prefixed one from getToolDefinition\n\t\t\tvar request = CallToolRequest.builder(this.tool.name()).arguments(arguments).meta(mcpMeta).build();\n\n\t\t\t// Note that we use the original tool name here, not the adapted one from\n\t\t\t// getToolDefinition\n\t\t\tresponse = this.mcpClient.callTool(request);\n\t\t}","sourceCodeStart":99,"sourceCodeEnd":135,"githubUrl":"https://github.com/spring-projects/spring-ai/blob/98a7beda4f29d80a71c5837eb4053b03a93a46f7/mcp/common/src/main/java/org/springframework/ai/mcp/SyncMcpToolCallback.java#L99-L135","documentation":"SyncMcpToolCallback.call() received a null/empty tool call input and substitutes \"{}\" instead, logging this warning. The synchronous MCP tool is then invoked with an empty arguments object; tools that require arguments will fail downstream with their own validation error.","triggerScenarios":"Calling call() on a sync MCP tool callback where toolCallInput is null/empty/blank — usually when a streaming model emits a tool call with no arguments or the integration forwards an empty string from the model's tool-call payload.","commonSituations":"Argument-less tool calls in streaming responses; model output truncated so the arguments JSON is missing; wrappers that pass the raw model string straight into the tool callback without checking it.","solutions":["Verify the MCP tool's inputSchema and ensure the model is prompted/schematized to supply required arguments.","Guard the input before calling: substitute a valid JSON object with sensible defaults when input is blank.","If arguments are genuinely optional, treat this warning as informational and move on.","Capture the model's raw tool-call payload in logs to determine why the arguments were missing."],"exampleFix":"// before\nString result = syncToolCallback.call(toolCallInput); // may be null in streaming mode\n// after\nString safeInput = (toolCallInput == null || toolCallInput.isBlank())\n        ? \"{\\\"query\\\":\\\"\\\"}\" : toolCallInput;\nString result = syncToolCallback.call(safeInput);","handlingStrategy":"type-guard","validationCode":"if (input == null || input.isBlank()) {\n    input = \"{\\\"defaults\\\":true}\"; // provide schema-conformant defaults\n}","typeGuard":"boolean hasToolArguments(String input) {\n    return input != null && !input.isBlank();\n}","tryCatchPattern":"// library substitutes {} silently; guard downstream failures\ntry {\n    String result = syncCallback.call(input == null ? \"{}\" : input);\n} catch (ToolExecutionException e) {\n    logger.error(\"MCP tool failed, likely missing required arguments\", e);\n}","preventionTips":["Declare tool parameters in the model's tool schema so arguments are always emitted.","Validate/parse the tool-call JSON before invoking the callback.","Log raw model tool-call payloads when arguments come up empty to diagnose prompting issues.","Design MCP tools to tolerate an empty arguments object where feasible."],"tags":["mcp","tool-calling","empty-argument","streaming"],"backgroundTag":"empty-required-field","analyzedSha":"98a7beda4f29d80a71c5837eb4053b03a93a46f7","analyzedAt":"2026-09-11T14:15:49.441Z","contentChangedAt":"2026-09-11T14:15:49.441Z","schemaVersion":2},"datasetVersion":"2026-09-14T11:17:12.474Z"}