InvalidParams Error When All Fields In The Tool Schema Are Optional
Introduction
When working with tools in a schema, it's not uncommon to encounter issues when dealing with optional fields. In this article, we'll delve into the problem of receiving an InvalidParams error when all fields in the tool schema are optional. We'll explore the root cause of this issue, provide steps to reproduce the behavior, and discuss potential solutions to resolve this problem.
Describe the bug
When registering a tool with a schema consisting of all optional fields, some models will try calling the tool without supplying arguments in the request. This, however, fails validation because the zod object being created is non-optional. The issue lies in the fact that the zod object is being created with a non-optional schema, which is causing the validation to fail.
To Reproduce
Unfortunately, this issue doesn't reproduce with all models/agents, but we've seen it happen somewhat consistently with Windsurf. To reproduce the behavior, follow these steps:
Step 1: Register a tool with an all-optional schema
server.tool(
"fetch-records",
"Fetches database records",
{ limit: z.number().optional().describe("The number of records to fetch. Default is 20.") },
({ limit }) => {
return {
content: [{ type: "text", text: `Fetched ${limit ?? 20} records` }],
};
}
);
Step 2: Ask the agent to call the tool
Step 3: Observe the agent receiving MCP error -32602: Invalid arguments for tool [...] "expected": "object", "received": "undefined", "path": []
Expected behavior
I guess I would expect the protocol to be more explicit about when fields are required vs when they're not, or alternatively, we could fallback to an empty object when arguments is not provided in the request, but expected due to the tool schema.
Root cause of the issue
The root cause of this issue lies in the fact that the zod object being created is non-optional. When all fields in the tool schema are optional, the zod object is created with a schema that expects all fields to be present. However, when the arguments are not provided in the request, the zod object is created with an empty object, which fails validation.
Potential solutions
To resolve this issue, we can consider the following potential solutions:
1. Make the zod object optional
We can modify the zod object to be optional by using the optional method.
const schema = z.object({
limit: z.number().optional().describe("The number of records to fetch. Default is 20."),
}).optional();
2. Fallback to an empty object when arguments is not provided
We can modify the tool to fallback to an empty object when arguments is not provided in the request.
server.tool(
"fetch-records",
"Fetches database records",
{ limit: z.number().optional().describe("The number of records to fetch. Default is 20.") },
({ limit = 20 }) => {
return {
content: [{ type: "text", text: `Fetched ${limit} records` }],
};
}
);
3. Use a more explicit protocol
We can modify the protocol to be more explicit about when fields are required vs when they're not. This can be achieved by using a more explicit schema that indicates which fields are required and which are optional.
Conclusion
In conclusion, the InvalidParams error when all fields in the tool schema are optional is a complex issue that requires a deep understanding of the zod object and the protocol. By making the zod object optional, fallback to an empty object when arguments is not provided, or using a more explicit protocol, we can resolve this issue and ensure that our tools work as expected.
Future work
In the future, we can consider the following potential improvements:
- Improve the protocol: We can modify the protocol to be more explicit about when fields are required vs when they're not.
- Add more explicit error handling: We can add more explicit error handling to handle cases where the arguments are not provided in the request.
- Improve the zod object: We can modify the zod object to be more flexible and accommodate cases where the arguments are not provided in the request.
InvalidParams error when all fields in the tool schema are optional: Q&A ====================================================================
Introduction
In our previous article, we explored the issue of receiving an InvalidParams error when all fields in the tool schema are optional. We discussed the root cause of the issue, potential solutions, and future work. In this article, we'll provide a Q&A section to address common questions and concerns related to this issue.
Q: What is the root cause of the InvalidParams error?
A: The root cause of the InvalidParams error lies in the fact that the zod object being created is non-optional. When all fields in the tool schema are optional, the zod object is created with a schema that expects all fields to be present. However, when the arguments are not provided in the request, the zod object is created with an empty object, which fails validation.
Q: How can I resolve the InvalidParams error?
A: To resolve the InvalidParams error, you can consider the following potential solutions:
- Make the zod object optional: You can modify the zod object to be optional by using the optional method.
- Fallback to an empty object when arguments is not provided: You can modify the tool to fallback to an empty object when arguments is not provided in the request.
- Use a more explicit protocol: You can modify the protocol to be more explicit about when fields are required vs when they're not.
Q: What are the benefits of making the zod object optional?
A: Making the zod object optional provides several benefits, including:
- Improved flexibility: By making the zod object optional, you can accommodate cases where the arguments are not provided in the request.
- Reduced errors: By making the zod object optional, you can reduce the likelihood of errors caused by missing arguments.
- Simplified code: By making the zod object optional, you can simplify your code and reduce the complexity of your tool.
Q: What are the benefits of fallback to an empty object when arguments is not provided?
A: Fallback to an empty object when arguments is not provided provides several benefits, including:
- Improved user experience: By fallback to an empty object, you can provide a better user experience by avoiding errors caused by missing arguments.
- Reduced errors: By fallback to an empty object, you can reduce the likelihood of errors caused by missing arguments.
- Simplified code: By fallback to an empty object, you can simplify your code and reduce the complexity of your tool.
Q: What are the benefits of using a more explicit protocol?
A: Using a more explicit protocol provides several benefits, including:
- Improved clarity: By using a more explicit protocol, you can improve the clarity of your code and reduce the likelihood of errors.
- Reduced errors: By using a more explicit protocol, you can reduce the likelihood of errors caused by missing **arguments.
- Simplified code: By using a more explicit protocol, you can simplify your code and reduce the complexity of your tool.
Conclusion
In conclusion, the InvalidParams error when all fields in the tool schema are optional is a complex issue that requires a deep understanding of the zod object and the protocol. By making the zod object optional, fallback to an empty object when arguments is not provided, or using a more explicit protocol, you can resolve this issue and ensure that your tools work as expected.
Future work
In the future, we can consider the following potential improvements:
- Improve the protocol: We can modify the protocol to be more explicit about when fields are required vs when they're not.
- Add more explicit error handling: We can add more explicit error handling to handle cases where the arguments are not provided in the request.
- Improve the zod object: We can modify the zod object to be more flexible and accommodate cases where the arguments are not provided in the request.