From 3f2925b9c16c6d0cb66150b263c288a7c697fde3 Mon Sep 17 00:00:00 2001 From: Filippo Costa Date: Wed, 18 Oct 2023 14:04:03 +0200 Subject: [PATCH] Add support for `ledger_getEvents` in `RpcClient` Related GH issue: <#1066>. Signed-off-by: Filippo Costa Co-authored-by: Filippo Costa Co-authored-by: Roman Krasiuk --- full-node/sov-ledger-rpc/src/client.rs | 11 +++-- full-node/sov-ledger-rpc/src/server.rs | 2 +- .../sov-ledger-rpc/tests/empty_ledger.rs | 45 ++++++++++++++++++- 3 files changed, 52 insertions(+), 6 deletions(-) diff --git a/full-node/sov-ledger-rpc/src/client.rs b/full-node/sov-ledger-rpc/src/client.rs index 14ff9e44b..5afbdf9eb 100644 --- a/full-node/sov-ledger-rpc/src/client.rs +++ b/full-node/sov-ledger-rpc/src/client.rs @@ -4,7 +4,9 @@ //! See [`RpcClient`]. use jsonrpsee::proc_macros::rpc; -use sov_rollup_interface::rpc::{BatchIdentifier, QueryMode, SlotIdentifier, TxIdentifier}; +use sov_rollup_interface::rpc::{ + BatchIdentifier, EventIdentifier, QueryMode, SlotIdentifier, TxIdentifier, +}; use sov_rollup_interface::stf::Event; use crate::HexHash; @@ -16,9 +18,6 @@ use crate::HexHash; /// /// For more information about the specific methods, see the /// [`sov_rollup_interface::rpc`] module. -/// -/// TODO: `getEvents`, which has a `Vec` as a single parameter. That's not -/// supported by `jsonrpsee`, surprisingly. #[rpc(client, namespace = "ledger")] pub trait Rpc where @@ -54,6 +53,10 @@ where query_mode: QueryMode, ) -> RpcResult>>; + /// Gets a list of events by ID. The IDs need not be ordered. + #[method(name = "getEvents")] + async fn get_events(&self, event_ids: Vec) -> RpcResult>>; + /// Gets a single slot by hash. #[method(name = "getSlotByHash")] async fn get_slot_by_hash( diff --git a/full-node/sov-ledger-rpc/src/server.rs b/full-node/sov-ledger-rpc/src/server.rs index a844313f4..4ab9a0250 100644 --- a/full-node/sov-ledger-rpc/src/server.rs +++ b/full-node/sov-ledger-rpc/src/server.rs @@ -71,7 +71,7 @@ where .map_err(|e| to_jsonrpsee_error_object(e, LEDGER_RPC_ERROR)) })?; rpc.register_method("ledger_getEvents", move |params, db| { - let ids: Vec = params.parse()?; + let ids: Vec = params.parse().or_else(|_| params.one())?; db.get_events(&ids) .map_err(|e| to_jsonrpsee_error_object(e, LEDGER_RPC_ERROR)) })?; diff --git a/full-node/sov-ledger-rpc/tests/empty_ledger.rs b/full-node/sov-ledger-rpc/tests/empty_ledger.rs index 5b76446a9..73981a8cc 100644 --- a/full-node/sov-ledger-rpc/tests/empty_ledger.rs +++ b/full-node/sov-ledger-rpc/tests/empty_ledger.rs @@ -7,7 +7,11 @@ use sov_db::ledger_db::LedgerDB; use sov_ledger_rpc::client::RpcClient; use sov_ledger_rpc::server::rpc_module; use sov_ledger_rpc::HexHash; -use sov_rollup_interface::rpc::{BatchResponse, QueryMode, SlotResponse, TxResponse}; +use sov_modules_api::Event; +use sov_rollup_interface::rpc::{ + BatchResponse, EventIdentifier, QueryMode, SlotResponse, TxIdAndOffset, TxIdentifier, + TxResponse, +}; use tempfile::tempdir; async fn rpc_server() -> (jsonrpsee::server::ServerHandle, SocketAddr) { @@ -58,6 +62,7 @@ async fn getters_succeed() { .get_transactions(vec![], QueryMode::Compact) .await .unwrap(); + rpc_client.get_events(vec![]).await.unwrap(); let hash = HexHash([0; 32]); rpc_client @@ -130,3 +135,41 @@ async fn get_head_with_optional_query_mode() { .unwrap(); } } + +/// `ledger_getEvents` supports several parameter types, because of a +/// `jsonrpsee` limitation. See: +/// - https://github.com/Sovereign-Labs/sovereign-sdk/pull/1058 +/// - https://github.com/Sovereign-Labs/sovereign-sdk/issues/1037 +/// +/// While `jsonrpsee` macro-generated clients can only generate nested array +/// types as parameters (e.g. `"params": [[1, 2, 3]]`), we want to test that +/// non-nested array types are also supported (e.g. `"params": [1, 2, 3]` and +/// `"params": [{"txId": 1, "offset": 2}]`). +#[tokio::test] +async fn get_events_patterns() { + let (_server_handle, addr) = rpc_server().await; + let rpc_client = rpc_client(addr).await; + + rpc_client + .get_events(vec![EventIdentifier::Number(2)]) + .await + .unwrap(); + rpc_client + .request::>, _>("ledger_getEvents", vec![vec![2]]) + .await + .unwrap(); + rpc_client + .request::>, _>("ledger_getEvents", vec![2]) + .await + .unwrap(); + rpc_client + .request::>, _>( + "ledger_getEvents", + vec![EventIdentifier::TxIdAndOffset(TxIdAndOffset { + tx_id: TxIdentifier::Number(1), + offset: 2, + })], + ) + .await + .unwrap(); +}