mcpkit_core/error/
jsonrpc.rs1use serde::{Deserialize, Serialize};
7
8use super::types::McpError;
9
10#[derive(Debug, Clone, Serialize, Deserialize)]
12pub struct JsonRpcError {
13 pub code: i32,
15 pub message: String,
17 #[serde(skip_serializing_if = "Option::is_none")]
19 pub data: Option<serde_json::Value>,
20}
21
22impl JsonRpcError {
23 pub fn invalid_params(message: impl Into<String>) -> Self {
25 Self {
26 code: -32602,
27 message: message.into(),
28 data: None,
29 }
30 }
31
32 pub fn internal_error(message: impl Into<String>) -> Self {
34 Self {
35 code: -32603,
36 message: message.into(),
37 data: None,
38 }
39 }
40
41 pub fn method_not_found(message: impl Into<String>) -> Self {
43 Self {
44 code: -32601,
45 message: message.into(),
46 data: None,
47 }
48 }
49
50 pub fn parse_error(message: impl Into<String>) -> Self {
52 Self {
53 code: -32700,
54 message: message.into(),
55 data: None,
56 }
57 }
58
59 pub fn invalid_request(message: impl Into<String>) -> Self {
61 Self {
62 code: -32600,
63 message: message.into(),
64 data: None,
65 }
66 }
67}
68
69impl From<&McpError> for JsonRpcError {
70 fn from(err: &McpError) -> Self {
71 if let McpError::JsonRpc(e) = err {
73 return e.clone();
74 }
75 let code = err.code();
76 let message = err.to_string();
77 let data = match err {
78 McpError::MethodNotFound {
79 method, available, ..
80 } => Some(serde_json::json!({
81 "method": method,
82 "available": available,
83 })),
84 McpError::InvalidParams(details) => Some(serde_json::json!({
85 "method": details.method,
86 "param_path": details.param_path,
87 "expected": details.expected,
88 "actual": details.actual,
89 })),
90 McpError::Transport(details) => Some(serde_json::json!({
91 "kind": format!("{:?}", details.kind),
92 "context": details.context,
93 })),
94 McpError::ToolExecution(details) => details
95 .data
96 .clone()
97 .or_else(|| Some(serde_json::json!({ "tool": details.tool }))),
98 McpError::HandshakeFailed(details) => Some(serde_json::json!({
99 "client_version": details.client_version,
100 "server_version": details.server_version,
101 })),
102 McpError::UrlElicitationRequired { elicitations } => Some(serde_json::json!({
103 "elicitations": elicitations,
104 })),
105 McpError::WithContext { source, .. } => {
106 let inner: Self = source.as_ref().into();
107 inner.data
108 }
109 _ => None,
110 };
111
112 Self {
113 code,
114 message,
115 data,
116 }
117 }
118}
119
120impl From<McpError> for JsonRpcError {
121 fn from(err: McpError) -> Self {
122 Self::from(&err)
123 }
124}