Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: customizable JSON-RPC error codes via new enum variant on CallErrror #394

Merged
merged 6 commits into from
Jun 29, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 14 additions & 3 deletions types/src/error.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use serde::{Deserialize, Serialize};
use serde_json::value::RawValue;
use std::fmt;

/// Convenience type for displaying errors.
Expand All @@ -19,12 +20,22 @@ impl<T: fmt::Display> fmt::Display for Mismatch<T> {
/// Error that occurs when a call failed.
#[derive(Debug, thiserror::Error)]
niklasad1 marked this conversation as resolved.
Show resolved Hide resolved
pub enum CallError {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we might want to put non_exhaustive on this but a little weird to just add some error code for non defined enum variant :P

#[error("Invalid params in the RPC call")]
/// Invalid params in the call.
#[error("Invalid params in the call")]
InvalidParams,
/// The call failed (let jsonrpsee assign default error code and error message).
#[error("RPC Call failed: {0}")]
/// The call failed.
Failed(#[source] Box<dyn std::error::Error + Send + Sync>),
Failed(Box<dyn std::error::Error + Send + Sync>),
/// Custom error with specific JSON-RPC error code, message and data.
#[error("RPC Call failed: code: {code}, message: {message}, data: {data:?}")]
Custom {
/// JSON-RPC error code
code: i32,
/// Short description of the error.
message: String,
/// A primitive or structured value that contains additional information about the error.
data: Option<Box<RawValue>>,
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this might save allocations of the value is already a String

},
}

/// Error type.
Expand Down
5 changes: 4 additions & 1 deletion types/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,4 +24,7 @@ pub use beef::Cow;
pub use client::*;
pub use error::Error;
pub use serde::{de::DeserializeOwned, Serialize};
pub use serde_json::{to_value as to_json_value, value::RawValue as JsonRawValue, Value as JsonValue};
pub use serde_json::{
to_value as to_json_value, value::to_raw_value as to_json_raw_value, value::RawValue as JsonRawValue,
Value as JsonValue,
};
22 changes: 15 additions & 7 deletions utils/src/server/rpc_module.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ impl MethodCallback {

if let Err(err) = result {
log::error!("execution of method call '{}' failed: {:?}, request id={:?}", req.method, err, id);
send_error(id, &tx, JsonRpcErrorCode::ServerError(-1).into());
send_error(id, tx, JsonRpcErrorCode::ServerError(-1).into());
}
}
}
Expand Down Expand Up @@ -190,14 +190,18 @@ impl<Context: Send + Sync + 'static> RpcModule<Context> {
match callback(params, &*ctx) {
Ok(res) => send_response(id, tx, res),
Err(CallError::InvalidParams) => send_error(id, tx, JsonRpcErrorCode::InvalidParams.into()),
Err(CallError::Failed(err)) => {
Err(CallError::Failed(e)) => {
let err = JsonRpcErrorObject {
code: JsonRpcErrorCode::ServerError(CALL_EXECUTION_FAILED_CODE),
message: &err.to_string(),
message: &e.to_string(),
data: None,
};
send_error(id, tx, err)
}
Err(CallError::Custom { code, message, data }) => {
let err = JsonRpcErrorObject { code: code.into(), message: &message, data: data.as_deref() };
send_error(id, tx, err)
}
};

Ok(())
Expand Down Expand Up @@ -227,15 +231,19 @@ impl<Context: Send + Sync + 'static> RpcModule<Context> {
match callback(params, ctx).await {
Ok(res) => send_response(id, &tx, res),
Err(CallError::InvalidParams) => send_error(id, &tx, JsonRpcErrorCode::InvalidParams.into()),
Err(CallError::Failed(err)) => {
log::error!("Call failed with: {}", err);
Err(CallError::Failed(e)) => {
let err = JsonRpcErrorObject {
code: JsonRpcErrorCode::ServerError(CALL_EXECUTION_FAILED_CODE),
message: &err.to_string(),
message: &e.to_string(),
data: None,
};
send_error(id, &tx, err)
}
Err(CallError::Custom { code, message, data }) => {
let err =
JsonRpcErrorObject { code: code.into(), message: &message, data: data.as_deref() };
send_error(id, &tx, err)
}
};
Ok(())
};
Expand Down Expand Up @@ -323,7 +331,7 @@ impl<Context: Send + Sync + 'static> RpcModule<Context> {
MethodCallback::Sync(Arc::new(move |id, params, tx, conn_id| {
let sub_id = params.one()?;
subscribers.lock().remove(&SubscriptionKey { conn_id, sub_id });
send_response(id, &tx, "Unsubscribed");
send_response(id, tx, "Unsubscribed");

Ok(())
})),
Expand Down