turul_mcp_json_rpc_server/
error.rs1use serde::{Deserialize, Serialize};
2use serde_json::Value;
3use std::fmt;
4use thiserror::Error;
5
6use crate::types::RequestId;
7
8#[derive(Debug, Clone, Copy, PartialEq, Eq)]
10pub enum JsonRpcErrorCode {
11 ParseError,
12 InvalidRequest,
13 MethodNotFound,
14 InvalidParams,
15 InternalError,
16 ServerError(i64), }
18
19impl JsonRpcErrorCode {
20 pub fn code(&self) -> i64 {
21 match self {
22 JsonRpcErrorCode::ParseError => -32700,
23 JsonRpcErrorCode::InvalidRequest => -32600,
24 JsonRpcErrorCode::MethodNotFound => -32601,
25 JsonRpcErrorCode::InvalidParams => -32602,
26 JsonRpcErrorCode::InternalError => -32603,
27 JsonRpcErrorCode::ServerError(code) => *code,
28 }
29 }
30
31 pub fn message(&self) -> &'static str {
32 match self {
33 JsonRpcErrorCode::ParseError => "Parse error",
34 JsonRpcErrorCode::InvalidRequest => "Invalid Request",
35 JsonRpcErrorCode::MethodNotFound => "Method not found",
36 JsonRpcErrorCode::InvalidParams => "Invalid params",
37 JsonRpcErrorCode::InternalError => "Internal error",
38 JsonRpcErrorCode::ServerError(_) => "Server error",
39 }
40 }
41}
42
43impl fmt::Display for JsonRpcErrorCode {
44 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
45 write!(f, "{}: {}", self.code(), self.message())
46 }
47}
48
49#[derive(Debug, Clone, Serialize, Deserialize)]
51pub struct JsonRpcErrorObject {
52 pub code: i64,
53 pub message: String,
54 #[serde(skip_serializing_if = "Option::is_none")]
55 pub data: Option<Value>,
56}
57
58impl JsonRpcErrorObject {
59 pub fn new(code: JsonRpcErrorCode, message: Option<String>, data: Option<Value>) -> Self {
60 Self {
61 code: code.code(),
62 message: message.unwrap_or_else(|| code.message().to_string()),
63 data,
64 }
65 }
66
67 pub fn parse_error(data: Option<Value>) -> Self {
68 Self::new(JsonRpcErrorCode::ParseError, None, data)
69 }
70
71 pub fn invalid_request(data: Option<Value>) -> Self {
72 Self::new(JsonRpcErrorCode::InvalidRequest, None, data)
73 }
74
75 pub fn method_not_found(method: &str) -> Self {
76 Self::new(
77 JsonRpcErrorCode::MethodNotFound,
78 Some(format!("Method '{}' not found", method)),
79 None,
80 )
81 }
82
83 pub fn invalid_params(message: &str) -> Self {
84 Self::new(
85 JsonRpcErrorCode::InvalidParams,
86 Some(message.to_string()),
87 None,
88 )
89 }
90
91 pub fn internal_error(message: Option<String>) -> Self {
92 Self::new(JsonRpcErrorCode::InternalError, message, None)
93 }
94
95 pub fn server_error(code: i64, message: &str, data: Option<Value>) -> Self {
96 assert!(
97 (-32099..=-32000).contains(&code),
98 "Server error code must be in range -32099 to -32000"
99 );
100 Self::new(
101 JsonRpcErrorCode::ServerError(code),
102 Some(message.to_string()),
103 data,
104 )
105 }
106}
107
108#[derive(Debug, Clone, Serialize, Deserialize)]
110pub struct JsonRpcError {
111 #[serde(rename = "jsonrpc")]
112 pub version: String,
113 pub id: Option<RequestId>,
114 pub error: JsonRpcErrorObject,
115}
116
117impl JsonRpcError {
118 pub fn new(id: Option<RequestId>, error: JsonRpcErrorObject) -> Self {
119 Self {
120 version: crate::JSONRPC_VERSION.to_string(),
121 id,
122 error,
123 }
124 }
125
126 pub fn parse_error() -> Self {
127 Self::new(None, JsonRpcErrorObject::parse_error(None))
128 }
129
130 pub fn invalid_request(id: Option<RequestId>) -> Self {
131 Self::new(id, JsonRpcErrorObject::invalid_request(None))
132 }
133
134 pub fn method_not_found(id: RequestId, method: &str) -> Self {
135 Self::new(Some(id), JsonRpcErrorObject::method_not_found(method))
136 }
137
138 pub fn invalid_params(id: RequestId, message: &str) -> Self {
139 Self::new(Some(id), JsonRpcErrorObject::invalid_params(message))
140 }
141
142 pub fn internal_error(id: Option<RequestId>, message: Option<String>) -> Self {
143 Self::new(id, JsonRpcErrorObject::internal_error(message))
144 }
145}
146
147impl fmt::Display for JsonRpcError {
148 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
149 write!(
150 f,
151 "JSON-RPC Error {}: {}",
152 self.error.code, self.error.message
153 )
154 }
155}
156
157impl std::error::Error for JsonRpcError {}
158
159#[derive(Debug, Error)]
161pub enum JsonRpcTransportError {
162 #[error("JSON parse error: {0}")]
163 JsonParseError(#[from] serde_json::Error),
164
165 #[error("IO error: {0}")]
166 IoError(#[from] std::io::Error),
167
168 #[error("Protocol error: {0}")]
169 ProtocolError(String),
170}
171
172#[cfg(test)]
173mod tests {
174 use super::*;
175
176 #[test]
177 fn test_error_codes() {
178 assert_eq!(JsonRpcErrorCode::ParseError.code(), -32700);
179 assert_eq!(JsonRpcErrorCode::MethodNotFound.code(), -32601);
180 }
181
182 #[test]
183 fn test_error_serialization() {
184 let error = JsonRpcError::method_not_found(RequestId::Number(1), "test");
185 let json = serde_json::to_string(&error).unwrap();
186 assert!(json.contains("Method 'test' not found"));
187 }
188}