Documentation Index
Fetch the complete documentation index at: https://modelcontextprotocol.io/llms.txt
Use this file to discover all available pages before exploring further.
DraftStandards Track
Abstract
The current MCP specification recommends-32002 as the error code for resource not found. However, -32002 falls within the JSON-RPC “server error” range (-32000 to -32099) which is reserved for implementation-defined errors, not protocol-level semantics. Additionally, SDK implementations are inconsistent — only 4 of 6 official SDKs use -32002, while the TypeScript SDK uses -32602 and the Python SDK uses 0.
This SEP standardizes on -32602 (Invalid Params), the correct JSON-RPC error code for this case, and aligns the specification with the JSON-RPC standard.
Motivation
Current SDK implementations vary in their error handling for resource not found:| SDK | Current Error Code | Source |
|---|---|---|
| TypeScript | -32602 (InvalidParams) | mcp.ts#L561 |
| Python | 0 (generic) | server.py#L790 |
| C# | -32002 (custom RESOURCE_NOT_FOUND) | McpServerImpl.cs#L289 |
| Rust | -32002 (custom RESOURCE_NOT_FOUND) | model.rs#L450 |
| Java | -32002 (custom RESOURCE_NOT_FOUND) | McpAsyncServer.java#L732 |
| Go | -32002 (custom RESOURCE_NOT_FOUND) | server.go#L786 |
| Kotlin | -32603 (INTERNAL_ERROR) | Server.kt#L618-L621 |
| PHP | -32002 (custom RESOURCE_NOT_FOUND) | Error.php#L37 |
| Ruby | N/A (left to implementor) | server.rb#L375-L379 |
| Swift | N/A (no built-in handler) | N/A |
-32002 (C#, Rust, Java, Go, PHP), -32602 (TypeScript), -32603 (Kotlin), and 0 (Python). Ruby and Swift leave error handling to the server implementor. Clients that need to distinguish “resource not found” from other errors must handle all variants.
Specification
If the requested resource does not exist, servers MUST return a JSON-RPC error with code-32602 (Invalid Params):
data field SHOULD include the uri that was not found.
Servers MUST NOT return an empty contents array for a non-existent resource. An empty array is ambiguous — it could mean the resource exists but has no content, or that it doesn’t exist at all.
Rationale
Why -32602 (Invalid Params)?
-32602 is the standard JSON-RPC error code for invalid parameters. A non-existent URI is semantically an invalid parameter — the client provided a URI that doesn’t correspond to any resource. This aligns with the TypeScript SDK’s existing behavior and avoids introducing custom error codes outside the JSON-RPC reserved range.
Why Not a Custom Error Code?
Several SDKs use-32002 (RESOURCE_NOT_FOUND), but:
- Custom codes in the
-32000to-32099range are “reserved for implementation-defined server errors” per JSON-RPC spec, not for protocol-level semantics - Adding a protocol-defined custom code requires all clients to be updated to recognize it
-32602already has the correct meaning and is universally understood by JSON-RPC libraries
Backward Compatibility
This changes what is specified — the current spec recommends-32002, and this SEP changes it to -32602. However, since the current recommendation is not consistently followed across SDKs (only 5 of 10 use -32002), clients cannot rely on any single error code today. This means the practical impact on clients is minimal — any client robust enough to work across existing SDKs already handles multiple error codes or treats all errors generically.
Migration Path
- SDKs should update their resource-not-found error code to
-32602 - During the transition, clients SHOULD handle both
-32602and-32002as resource-not-found - The specification should document
-32602as the canonical error code