From d37f063172cdaf07bb988de8bd6c19c0685e8e5a Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 5 Sep 2022 12:12:51 +0300 Subject: [PATCH 01/77] proto-compiler: Improve error reporting Print out the prost-build error to display protoc output line by line rather than as an unreadable Debug dump. --- tools/proto-compiler/src/main.rs | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/tools/proto-compiler/src/main.rs b/tools/proto-compiler/src/main.rs index ea65b32bf..b4fd4d31b 100644 --- a/tools/proto-compiler/src/main.rs +++ b/tools/proto-compiler/src/main.rs @@ -1,4 +1,4 @@ -use std::{env::var, path::PathBuf}; +use std::{env::var, path::PathBuf, process}; use tempfile::tempdir; @@ -80,7 +80,13 @@ fn main() { "super::super::google::protobuf::Timestamp", ); println!("[info] => Creating structs."); - pb.compile_protos(&protos, &proto_includes_paths).unwrap(); + match pb.compile_protos(&protos, &proto_includes_paths) { + Ok(()) => {}, + Err(e) => { + eprintln!("{}", e); + process::exit(1); + }, + } println!("[info] => Removing old structs and copying new structs."); copy_files(&out_dir, &target_dir); // This panics if it fails. From ce68dbdd1434c9f8973ac0399a29bc8ab285e951 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 5 Sep 2022 12:45:22 +0300 Subject: [PATCH 02/77] Generate proto from tendermint 0.37.0-alpha.1 Also adapted the tendermint-abci crate as necessary. Committing this helps take stock of the protocol changes since 0.34, before multi-version support can be implemented. --- abci/src/application.rs | 14 + abci/src/application/kvstore.rs | 12 +- proto/src/prost/tendermint.abci.rs | 480 ++++++++++-------- ....blockchain.rs => tendermint.blocksync.rs} | 0 proto/src/prost/tendermint.p2p.rs | 119 +++-- proto/src/prost/tendermint.types.rs | 393 +++++++------- proto/src/tendermint.rs | 62 +-- tendermint/src/consensus/params.rs | 10 +- tools/proto-compiler/src/constants.rs | 2 +- 9 files changed, 602 insertions(+), 490 deletions(-) rename proto/src/prost/{tendermint.blockchain.rs => tendermint.blocksync.rs} (100%) diff --git a/abci/src/application.rs b/abci/src/application.rs index 193307832..1bc9f1804 100644 --- a/abci/src/application.rs +++ b/abci/src/application.rs @@ -98,6 +98,14 @@ pub trait Application: Send + Clone + 'static { ) -> ResponseApplySnapshotChunk { Default::default() } + + fn prepare_proposal(&self, _request: RequestPrepareProposal) -> ResponsePrepareProposal { + Default::default() + } + + fn process_proposal(&self, _request: RequestProcessProposal) -> ResponseProcessProposal { + Default::default() + } } /// Provides a mechanism for the [`Server`] to execute incoming requests while @@ -134,6 +142,12 @@ impl RequestDispatcher for A { Value::ApplySnapshotChunk(req) => { response::Value::ApplySnapshotChunk(self.apply_snapshot_chunk(req)) }, + Value::PrepareProposal(req) => { + response::Value::PrepareProposal(self.prepare_proposal(req)) + }, + Value::ProcessProposal(req) => { + response::Value::ProcessProposal(self.process_proposal(req)) + }, Value::SetOption(_) => response::Value::SetOption(Default::default()), }), } diff --git a/abci/src/application/kvstore.rs b/abci/src/application/kvstore.rs index 62c117a44..8336b71e1 100644 --- a/abci/src/application/kvstore.rs +++ b/abci/src/application/kvstore.rs @@ -199,18 +199,18 @@ impl Application for KeyValueStoreApp { r#type: "app".to_string(), attributes: vec![ EventAttribute { - key: "key".to_string().into_bytes().into(), - value: key.to_string().into_bytes().into(), + key: "key".to_owned(), + value: key.to_owned(), index: true, }, EventAttribute { - key: "index_key".to_string().into_bytes().into(), - value: "index is working".to_string().into_bytes().into(), + key: "index_key".to_owned(), + value: "index is working".to_owned(), index: true, }, EventAttribute { - key: "noindex_key".to_string().into_bytes().into(), - value: "index is working".to_string().into_bytes().into(), + key: "noindex_key".to_owned(), + value: "index is working".to_owned(), index: false, }, ], diff --git a/proto/src/prost/tendermint.abci.rs b/proto/src/prost/tendermint.abci.rs index 8e03b04e8..0ef1caae6 100644 --- a/proto/src/prost/tendermint.abci.rs +++ b/proto/src/prost/tendermint.abci.rs @@ -7,367 +7,399 @@ #[derive(Clone, PartialEq, ::prost::Message)] pub struct Request { - #[prost(oneof="request::Value", tags="1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15")] + #[prost( + oneof = "request::Value", + tags = "1, 2, 3, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17" + )] pub value: ::core::option::Option, } /// Nested message and enum types in `Request`. pub mod request { #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Echo(super::RequestEcho), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] Flush(super::RequestFlush), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Info(super::RequestInfo), - #[prost(message, tag="4")] - SetOption(super::RequestSetOption), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] InitChain(super::RequestInitChain), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] Query(super::RequestQuery), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] BeginBlock(super::RequestBeginBlock), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] CheckTx(super::RequestCheckTx), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] DeliverTx(super::RequestDeliverTx), - #[prost(message, tag="10")] + #[prost(message, tag = "10")] EndBlock(super::RequestEndBlock), - #[prost(message, tag="11")] + #[prost(message, tag = "11")] Commit(super::RequestCommit), - #[prost(message, tag="12")] + #[prost(message, tag = "12")] ListSnapshots(super::RequestListSnapshots), - #[prost(message, tag="13")] + #[prost(message, tag = "13")] OfferSnapshot(super::RequestOfferSnapshot), - #[prost(message, tag="14")] + #[prost(message, tag = "14")] LoadSnapshotChunk(super::RequestLoadSnapshotChunk), - #[prost(message, tag="15")] + #[prost(message, tag = "15")] ApplySnapshotChunk(super::RequestApplySnapshotChunk), + #[prost(message, tag = "16")] + PrepareProposal(super::RequestPrepareProposal), + #[prost(message, tag = "17")] + ProcessProposal(super::RequestProcessProposal), } } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEcho { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub message: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestFlush { -} +pub struct RequestFlush {} #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInfo { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] pub block_version: u64, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] pub p2p_version: u64, -} -/// nondeterministic -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestSetOption { - #[prost(string, tag="1")] - pub key: ::prost::alloc::string::String, - #[prost(string, tag="2")] - pub value: ::prost::alloc::string::String, + #[prost(string, tag = "4")] + pub abci_version: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInitChain { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub time: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(message, optional, tag="3")] - pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, optional, tag = "3")] + pub consensus_params: ::core::option::Option, + #[prost(message, repeated, tag = "4")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] pub app_state_bytes: ::prost::bytes::Bytes, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub initial_height: i64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestQuery { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub data: ::prost::bytes::Bytes, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub path: ::prost::alloc::string::String, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub height: i64, - #[prost(bool, tag="4")] + #[prost(bool, tag = "4")] pub prove: bool, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestBeginBlock { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub hash: ::prost::bytes::Bytes, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub header: ::core::option::Option, - #[prost(message, optional, tag="3")] - pub last_commit_info: ::core::option::Option, - #[prost(message, repeated, tag="4")] - pub byzantine_validators: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag = "3")] + pub last_commit_info: ::core::option::Option, + #[prost(message, repeated, tag = "4")] + pub byzantine_validators: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestCheckTx { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub tx: ::prost::bytes::Bytes, - #[prost(enumeration="CheckTxType", tag="2")] + #[prost(enumeration = "CheckTxType", tag = "2")] pub r#type: i32, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestDeliverTx { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub tx: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEndBlock { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestCommit { -} +pub struct RequestCommit {} /// lists available snapshots #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestListSnapshots { -} +pub struct RequestListSnapshots {} /// offers a snapshot to the application #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestOfferSnapshot { /// snapshot offered by peers - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub snapshot: ::core::option::Option, /// light client-verified app hash for snapshot height - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub app_hash: ::prost::bytes::Bytes, } /// loads a snapshot chunk #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestLoadSnapshotChunk { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunk: u32, } /// Applies a snapshot chunk #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestApplySnapshotChunk { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub index: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub chunk: ::prost::bytes::Bytes, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub sender: ::prost::alloc::string::String, } +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestPrepareProposal { + /// the modified transactions cannot exceed this size. + #[prost(int64, tag = "1")] + pub max_tx_bytes: i64, + /// txs is an array of transactions that will be included in a block, + /// sent to the app for possible modifications. + #[prost(bytes = "vec", repeated, tag = "2")] + pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, + #[prost(message, optional, tag = "3")] + pub local_last_commit: ::core::option::Option, + #[prost(message, repeated, tag = "4")] + pub misbehavior: ::prost::alloc::vec::Vec, + #[prost(int64, tag = "5")] + pub height: i64, + #[prost(message, optional, tag = "6")] + pub time: ::core::option::Option, + #[prost(bytes = "vec", tag = "7")] + pub next_validators_hash: ::prost::alloc::vec::Vec, + /// address of the public key of the validator proposing the block. + #[prost(bytes = "vec", tag = "8")] + pub proposer_address: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestProcessProposal { + #[prost(bytes = "vec", repeated, tag = "1")] + pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, + #[prost(message, optional, tag = "2")] + pub proposed_last_commit: ::core::option::Option, + #[prost(message, repeated, tag = "3")] + pub misbehavior: ::prost::alloc::vec::Vec, + /// hash is the merkle root hash of the fields of the proposed block. + #[prost(bytes = "vec", tag = "4")] + pub hash: ::prost::alloc::vec::Vec, + #[prost(int64, tag = "5")] + pub height: i64, + #[prost(message, optional, tag = "6")] + pub time: ::core::option::Option, + #[prost(bytes = "vec", tag = "7")] + pub next_validators_hash: ::prost::alloc::vec::Vec, + /// address of the public key of the original proposer of the block. + #[prost(bytes = "vec", tag = "8")] + pub proposer_address: ::prost::alloc::vec::Vec, +} // ---------------------------------------- // Response types #[derive(Clone, PartialEq, ::prost::Message)] pub struct Response { - #[prost(oneof="response::Value", tags="1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16")] + #[prost( + oneof = "response::Value", + tags = "1, 2, 3, 4, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18" + )] pub value: ::core::option::Option, } /// Nested message and enum types in `Response`. pub mod response { #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Exception(super::ResponseException), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] Echo(super::ResponseEcho), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Flush(super::ResponseFlush), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] Info(super::ResponseInfo), - #[prost(message, tag="5")] - SetOption(super::ResponseSetOption), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] InitChain(super::ResponseInitChain), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] Query(super::ResponseQuery), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] BeginBlock(super::ResponseBeginBlock), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] CheckTx(super::ResponseCheckTx), - #[prost(message, tag="10")] + #[prost(message, tag = "10")] DeliverTx(super::ResponseDeliverTx), - #[prost(message, tag="11")] + #[prost(message, tag = "11")] EndBlock(super::ResponseEndBlock), - #[prost(message, tag="12")] + #[prost(message, tag = "12")] Commit(super::ResponseCommit), - #[prost(message, tag="13")] + #[prost(message, tag = "13")] ListSnapshots(super::ResponseListSnapshots), - #[prost(message, tag="14")] + #[prost(message, tag = "14")] OfferSnapshot(super::ResponseOfferSnapshot), - #[prost(message, tag="15")] + #[prost(message, tag = "15")] LoadSnapshotChunk(super::ResponseLoadSnapshotChunk), - #[prost(message, tag="16")] + #[prost(message, tag = "16")] ApplySnapshotChunk(super::ResponseApplySnapshotChunk), + #[prost(message, tag = "17")] + PrepareProposal(super::ResponsePrepareProposal), + #[prost(message, tag = "18")] + ProcessProposal(super::ResponseProcessProposal), } } /// nondeterministic #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseException { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub error: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEcho { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub message: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct ResponseFlush { -} -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseFlush {} +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct ResponseInfo { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] #[serde(default)] pub data: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] #[serde(default)] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] #[serde(with = "crate::serializers::from_str", default)] pub app_version: u64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str", default)] pub last_block_height: i64, - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] #[serde(default)] #[serde(skip_serializing_if = "bytes::Bytes::is_empty")] pub last_block_app_hash: ::prost::bytes::Bytes, } -/// nondeterministic -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct ResponseSetOption { - #[prost(uint32, tag="1")] - pub code: u32, - /// bytes data = 2; - #[prost(string, tag="3")] - pub log: ::prost::alloc::string::String, - #[prost(string, tag="4")] - pub info: ::prost::alloc::string::String, -} #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseInitChain { - #[prost(message, optional, tag="1")] - pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag="2")] + #[prost(message, optional, tag = "1")] + pub consensus_params: ::core::option::Option, + #[prost(message, repeated, tag = "2")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes="bytes", tag="3")] + #[prost(bytes = "bytes", tag = "3")] pub app_hash: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseQuery { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, /// bytes data = 2; // use "value" instead. /// /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub index: i64, - #[prost(bytes="bytes", tag="6")] + #[prost(bytes = "bytes", tag = "6")] pub key: ::prost::bytes::Bytes, - #[prost(bytes="bytes", tag="7")] + #[prost(bytes = "bytes", tag = "7")] pub value: ::prost::bytes::Bytes, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub proof_ops: ::core::option::Option, - #[prost(int64, tag="9")] + #[prost(int64, tag = "9")] pub height: i64, - #[prost(string, tag="10")] + #[prost(string, tag = "10")] pub codespace: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseBeginBlock { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub events: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCheckTx { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub gas_wanted: i64, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub gas_used: i64, - #[prost(message, repeated, tag="7")] + #[prost(message, repeated, tag = "7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag="8")] + #[prost(string, tag = "8")] pub codespace: ::prost::alloc::string::String, - #[prost(string, tag="9")] + #[prost(string, tag = "9")] pub sender: ::prost::alloc::string::String, - #[prost(int64, tag="10")] + #[prost(int64, tag = "10")] pub priority: i64, /// mempool_error is set by Tendermint. /// ABCI applictions creating a ResponseCheckTX should not set mempool_error. - #[prost(string, tag="11")] + #[prost(string, tag = "11")] pub mempool_error: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseDeliverTx { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub gas_wanted: i64, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub gas_used: i64, /// nondeterministic - #[prost(message, repeated, tag="7")] + #[prost(message, repeated, tag = "7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag="8")] + #[prost(string, tag = "8")] pub codespace: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEndBlock { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub validator_updates: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] - pub consensus_param_updates: ::core::option::Option, - #[prost(message, repeated, tag="3")] + #[prost(message, optional, tag = "2")] + pub consensus_param_updates: ::core::option::Option, + #[prost(message, repeated, tag = "3")] pub events: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCommit { /// reserve 1 - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub retain_height: i64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseListSnapshots { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub snapshots: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseOfferSnapshot { - #[prost(enumeration="response_offer_snapshot::Result", tag="1")] + #[prost(enumeration = "response_offer_snapshot::Result", tag = "1")] pub result: i32, } /// Nested message and enum types in `ResponseOfferSnapshot`. @@ -407,18 +439,18 @@ pub mod response_offer_snapshot { } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseLoadSnapshotChunk { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub chunk: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseApplySnapshotChunk { - #[prost(enumeration="response_apply_snapshot_chunk::Result", tag="1")] + #[prost(enumeration = "response_apply_snapshot_chunk::Result", tag = "1")] pub result: i32, /// Chunks to refetch and reapply - #[prost(uint32, repeated, tag="2")] + #[prost(uint32, repeated, tag = "2")] pub refetch_chunks: ::prost::alloc::vec::Vec, /// Chunk senders to reject and ban - #[prost(string, repeated, tag="3")] + #[prost(string, repeated, tag = "3")] pub reject_senders: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// Nested message and enum types in `ResponseApplySnapshotChunk`. @@ -456,58 +488,78 @@ pub mod response_apply_snapshot_chunk { } } } +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponsePrepareProposal { + #[prost(bytes = "vec", repeated, tag = "1")] + pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseProcessProposal { + #[prost(enumeration = "response_process_proposal::ProposalStatus", tag = "1")] + pub status: i32, +} +/// Nested message and enum types in `ResponseProcessProposal`. +pub mod response_process_proposal { + #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[repr(i32)] + pub enum ProposalStatus { + Unknown = 0, + Accept = 1, + Reject = 2, + } + impl ProposalStatus { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + ProposalStatus::Unknown => "UNKNOWN", + ProposalStatus::Accept => "ACCEPT", + ProposalStatus::Reject => "REJECT", + } + } + } +} // ---------------------------------------- // Misc. -/// ConsensusParams contains all consensus-relevant parameters -/// that can be adjusted by the abci app -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct ConsensusParams { - #[prost(message, optional, tag="1")] - pub block: ::core::option::Option, - #[prost(message, optional, tag="2")] - pub evidence: ::core::option::Option, - #[prost(message, optional, tag="3")] - pub validator: ::core::option::Option, - #[prost(message, optional, tag="4")] - pub version: ::core::option::Option, -} -/// BlockParams contains limits on the block size. -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct BlockParams { - /// Note: must be greater than 0 - #[prost(int64, tag="1")] - pub max_bytes: i64, - /// Note: must be greater or equal to -1 - #[prost(int64, tag="2")] - pub max_gas: i64, -} -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct LastCommitInfo { - #[prost(int32, tag="1")] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct CommitInfo { + #[prost(int32, tag = "1")] pub round: i32, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub votes: ::prost::alloc::vec::Vec, } +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ExtendedCommitInfo { + /// The round at which the block proposer decided in the previous height. + #[prost(int32, tag = "1")] + pub round: i32, + /// List of validators' addresses in the last validator set with their voting + /// information, including vote extensions. + #[prost(message, repeated, tag = "2")] + pub votes: ::prost::alloc::vec::Vec, +} /// Event allows application developers to attach additional information to /// ResponseBeginBlock, ResponseEndBlock, ResponseCheckTx and ResponseDeliverTx. /// Later, transactions may be queried using these events. #[derive(Clone, PartialEq, ::prost::Message)] pub struct Event { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub r#type: ::prost::alloc::string::String, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub attributes: ::prost::alloc::vec::Vec, } /// EventAttribute is a single key-value pair, associated with an event. #[derive(Clone, PartialEq, ::prost::Message)] pub struct EventAttribute { - #[prost(bytes="bytes", tag="1")] - pub key: ::prost::bytes::Bytes, - #[prost(bytes="bytes", tag="2")] - pub value: ::prost::bytes::Bytes, + #[prost(string, tag = "1")] + pub key: ::prost::alloc::string::String, + #[prost(string, tag = "2")] + pub value: ::prost::alloc::string::String, /// nondeterministic - #[prost(bool, tag="3")] + #[prost(bool, tag = "3")] pub index: bool, } /// TxResult contains results of executing the transaction. @@ -515,13 +567,13 @@ pub struct EventAttribute { /// One usage is indexing transaction results. #[derive(Clone, PartialEq, ::prost::Message)] pub struct TxResult { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub index: u32, - #[prost(bytes="bytes", tag="3")] + #[prost(bytes = "bytes", tag = "3")] pub tx: ::prost::bytes::Bytes, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub result: ::core::option::Option, } // ---------------------------------------- @@ -531,47 +583,57 @@ pub struct TxResult { #[derive(Clone, PartialEq, ::prost::Message)] pub struct Validator { /// The first 20 bytes of SHA256(public key) - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub address: ::prost::bytes::Bytes, /// PubKey pub_key = 2 \[(gogoproto.nullable)=false\]; /// /// The voting power - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub power: i64, } /// ValidatorUpdate #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorUpdate { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub power: i64, } /// VoteInfo #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] + pub validator: ::core::option::Option, + #[prost(bool, tag = "2")] + pub signed_last_block: bool, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ExtendedVoteInfo { + #[prost(message, optional, tag = "1")] pub validator: ::core::option::Option, - #[prost(bool, tag="2")] + #[prost(bool, tag = "2")] pub signed_last_block: bool, + /// Reserved for future use + #[prost(bytes = "vec", tag = "3")] + pub vote_extension: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct Evidence { - #[prost(enumeration="EvidenceType", tag="1")] +pub struct Misbehavior { + #[prost(enumeration = "MisbehaviorType", tag = "1")] pub r#type: i32, /// The offending validator - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub validator: ::core::option::Option, /// The height when the offense occurred - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub height: i64, /// The corresponding time where the offense occurred - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub time: ::core::option::Option, /// Total voting power of the validator set in case the ABCI application does /// not store historical validators. /// - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub total_voting_power: i64, } // ---------------------------------------- @@ -580,19 +642,19 @@ pub struct Evidence { #[derive(Clone, PartialEq, ::prost::Message)] pub struct Snapshot { /// The height at which the snapshot was taken - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, /// The application-specific snapshot format - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, /// Number of chunks in the snapshot - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunks: u32, /// Arbitrary snapshot hash, equal only if identical - #[prost(bytes="bytes", tag="4")] + #[prost(bytes = "bytes", tag = "4")] pub hash: ::prost::bytes::Bytes, /// Arbitrary application metadata - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] pub metadata: ::prost::bytes::Bytes, } #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] @@ -615,21 +677,21 @@ impl CheckTxType { } #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] #[repr(i32)] -pub enum EvidenceType { +pub enum MisbehaviorType { Unknown = 0, DuplicateVote = 1, LightClientAttack = 2, } -impl EvidenceType { +impl MisbehaviorType { /// String value of the enum field names used in the ProtoBuf definition. /// /// The values are not transformed in any way and thus are considered stable /// (if the ProtoBuf definition does not change) and safe for programmatic use. pub fn as_str_name(&self) -> &'static str { match self { - EvidenceType::Unknown => "UNKNOWN", - EvidenceType::DuplicateVote => "DUPLICATE_VOTE", - EvidenceType::LightClientAttack => "LIGHT_CLIENT_ATTACK", + MisbehaviorType::Unknown => "UNKNOWN", + MisbehaviorType::DuplicateVote => "DUPLICATE_VOTE", + MisbehaviorType::LightClientAttack => "LIGHT_CLIENT_ATTACK", } } } diff --git a/proto/src/prost/tendermint.blockchain.rs b/proto/src/prost/tendermint.blocksync.rs similarity index 100% rename from proto/src/prost/tendermint.blockchain.rs rename to proto/src/prost/tendermint.blocksync.rs diff --git a/proto/src/prost/tendermint.p2p.rs b/proto/src/prost/tendermint.p2p.rs index 4dc33809c..ec3ab40ab 100644 --- a/proto/src/prost/tendermint.p2p.rs +++ b/proto/src/prost/tendermint.p2p.rs @@ -1,106 +1,103 @@ #[derive(Clone, PartialEq, ::prost::Message)] +pub struct PacketPing {} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PacketPong {} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PacketMsg { + #[prost(int32, tag = "1")] + pub channel_id: i32, + #[prost(bool, tag = "2")] + pub eof: bool, + #[prost(bytes = "vec", tag = "3")] + pub data: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Packet { + #[prost(oneof = "packet::Sum", tags = "1, 2, 3")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Packet`. +pub mod packet { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag = "1")] + PacketPing(super::PacketPing), + #[prost(message, tag = "2")] + PacketPong(super::PacketPong), + #[prost(message, tag = "3")] + PacketMsg(super::PacketMsg), + } +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct AuthSigMessage { + #[prost(message, optional, tag = "1")] + pub pub_key: ::core::option::Option, + #[prost(bytes = "vec", tag = "2")] + pub sig: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] pub struct NetAddress { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub id: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub ip: ::prost::alloc::string::String, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub port: u32, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProtocolVersion { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub p2p: u64, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] pub block: u64, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] pub app: u64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub protocol_version: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub default_node_id: ::prost::alloc::string::String, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub listen_addr: ::prost::alloc::string::String, - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub network: ::prost::alloc::string::String, - #[prost(string, tag="5")] + #[prost(string, tag = "5")] pub version: ::prost::alloc::string::String, - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] pub channels: ::prost::alloc::vec::Vec, - #[prost(string, tag="7")] + #[prost(string, tag = "7")] pub moniker: ::prost::alloc::string::String, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub other: ::core::option::Option, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfoOther { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub tx_index: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub rpc_address: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPing { -} -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPong { -} -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketMsg { - #[prost(int32, tag="1")] - pub channel_id: i32, - #[prost(bool, tag="2")] - pub eof: bool, - #[prost(bytes="vec", tag="3")] - pub data: ::prost::alloc::vec::Vec, -} -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct Packet { - #[prost(oneof="packet::Sum", tags="1, 2, 3")] - pub sum: ::core::option::Option, -} -/// Nested message and enum types in `Packet`. -pub mod packet { - #[derive(Clone, PartialEq, ::prost::Oneof)] - pub enum Sum { - #[prost(message, tag="1")] - PacketPing(super::PacketPing), - #[prost(message, tag="2")] - PacketPong(super::PacketPong), - #[prost(message, tag="3")] - PacketMsg(super::PacketMsg), - } -} -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct AuthSigMessage { - #[prost(message, optional, tag="1")] - pub pub_key: ::core::option::Option, - #[prost(bytes="vec", tag="2")] - pub sig: ::prost::alloc::vec::Vec, -} -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct PexRequest { -} +pub struct PexRequest {} #[derive(Clone, PartialEq, ::prost::Message)] pub struct PexAddrs { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub addrs: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2")] + #[prost(oneof = "message::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] PexRequest(super::PexRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] PexAddrs(super::PexAddrs), } } diff --git a/proto/src/prost/tendermint.types.rs b/proto/src/prost/tendermint.types.rs index 04368cf8f..b74c73279 100644 --- a/proto/src/prost/tendermint.types.rs +++ b/proto/src/prost/tendermint.types.rs @@ -1,261 +1,259 @@ -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct ValidatorSet { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub validators: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub proposer: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub total_voting_power: i64, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct Validator { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(alias = "power", with = "crate::serializers::from_str")] pub voting_power: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str", default)] pub proposer_priority: i64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct SimpleValidator { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub voting_power: i64, } /// PartsetHeader -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct PartSetHeader { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] #[serde(with = "crate::serializers::part_set_header_total")] pub total: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Part { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub index: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub bytes: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proof: ::core::option::Option, } /// BlockID -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct BlockId { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } // -------------------------------- /// Header defines the structure of a Tendermint block header. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct Header { /// basic block info - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub version: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] #[serde(with = "crate::serializers::optional")] pub time: ::core::option::Option, /// prev block info - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub last_block_id: ::core::option::Option, /// hashes of block data /// /// commit from validators from the last block - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_commit_hash: ::prost::alloc::vec::Vec, /// transactions - #[prost(bytes="vec", tag="7")] + #[prost(bytes = "vec", tag = "7")] #[serde(with = "crate::serializers::bytes::hexstring")] pub data_hash: ::prost::alloc::vec::Vec, /// hashes from the app output from the prev block /// /// validators for the current block - #[prost(bytes="vec", tag="8")] + #[prost(bytes = "vec", tag = "8")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validators_hash: ::prost::alloc::vec::Vec, /// validators for the next block - #[prost(bytes="vec", tag="9")] + #[prost(bytes = "vec", tag = "9")] #[serde(with = "crate::serializers::bytes::hexstring")] pub next_validators_hash: ::prost::alloc::vec::Vec, /// consensus params for current block - #[prost(bytes="vec", tag="10")] + #[prost(bytes = "vec", tag = "10")] #[serde(with = "crate::serializers::bytes::hexstring")] pub consensus_hash: ::prost::alloc::vec::Vec, /// state after txs from the previous block - #[prost(bytes="vec", tag="11")] + #[prost(bytes = "vec", tag = "11")] #[serde(with = "crate::serializers::bytes::hexstring")] pub app_hash: ::prost::alloc::vec::Vec, /// root hash of all results from the txs from the previous block - #[prost(bytes="vec", tag="12")] + #[prost(bytes = "vec", tag = "12")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_results_hash: ::prost::alloc::vec::Vec, /// consensus info /// /// evidence included in the block - #[prost(bytes="vec", tag="13")] + #[prost(bytes = "vec", tag = "13")] #[serde(with = "crate::serializers::bytes::hexstring")] pub evidence_hash: ::prost::alloc::vec::Vec, /// original proposer of the block - #[prost(bytes="vec", tag="14")] + #[prost(bytes = "vec", tag = "14")] #[serde(with = "crate::serializers::bytes::hexstring")] pub proposer_address: ::prost::alloc::vec::Vec, } /// Data contains the set of transactions included in the block -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct Data { /// Txs that will be applied by state @ block.Height+1. /// NOTE: not all txs here are valid. We're just agreeing on the order first. /// This means that block.AppHash does not include these txs. - #[prost(bytes="vec", repeated, tag="1")] + #[prost(bytes = "vec", repeated, tag = "1")] #[serde(with = "crate::serializers::txs")] pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } /// Vote represents a prevote, precommit, or commit vote from validators for /// consensus. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct Vote { - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, /// zero if vote is nil. - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] #[serde(with = "crate::serializers::optional")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(int32, tag="7")] + #[prost(int32, tag = "7")] pub validator_index: i32, - #[prost(bytes="vec", tag="8")] + #[prost(bytes = "vec", tag = "8")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } /// Commit contains the evidence that a block was committed by a set of validators. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct Commit { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub block_id: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] #[serde(with = "crate::serializers::nullable")] pub signatures: ::prost::alloc::vec::Vec, } /// CommitSig is a part of the Vote included in a Commit. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct CommitSig { - #[prost(enumeration="BlockIdFlag", tag="1")] + #[prost(enumeration = "BlockIdFlag", tag = "1")] pub block_id_flag: i32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] #[serde(with = "crate::serializers::optional")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="4")] + #[prost(bytes = "vec", tag = "4")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proposal { - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, - #[prost(int32, tag="4")] + #[prost(int32, tag = "4")] pub pol_round: i32, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="7")] + #[prost(bytes = "vec", tag = "7")] pub signature: ::prost::alloc::vec::Vec, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct SignedHeader { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub commit: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct LightBlock { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub signed_header: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub validator_set: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct BlockMeta { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block_id: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub block_size: i64, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub header: ::core::option::Option
, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str")] pub num_txs: i64, } /// TxProof represents a Merkle proof of the presence of a transaction in the Merkle tree. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct TxProof { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub root_hash: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::base64string")] pub data: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proof: ::core::option::Option, } /// BlockIdFlag indicates which BlcokID the signature is for -#[derive(::num_derive::FromPrimitive, ::num_derive::ToPrimitive)] -#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] +#[derive( + ::num_derive::FromPrimitive, + ::num_derive::ToPrimitive, + Clone, + Copy, + Debug, + PartialEq, + Eq, + Hash, + PartialOrd, + Ord, + ::prost::Enumeration, +)] #[repr(i32)] pub enum BlockIdFlag { Unknown = 0, @@ -302,26 +300,17 @@ impl SignedMsgType { } } } -#[derive(Clone, PartialEq, ::prost::Message)] -pub struct EventDataRoundState { - #[prost(int64, tag="1")] - pub height: i64, - #[prost(int32, tag="2")] - pub round: i32, - #[prost(string, tag="3")] - pub step: ::prost::alloc::string::String, -} /// ConsensusParams contains consensus critical parameters that determine the /// validity of blocks. #[derive(Clone, PartialEq, ::prost::Message)] pub struct ConsensusParams { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub validator: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub version: ::core::option::Option, } /// BlockParams contains limits on the block size. @@ -329,40 +318,33 @@ pub struct ConsensusParams { pub struct BlockParams { /// Max block size, in bytes. /// Note: must be greater than 0 - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_bytes: i64, /// Max gas per block. /// Note: must be greater or equal to -1 - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub max_gas: i64, - /// Minimum time increment between consecutive blocks (in milliseconds) If the - /// block header timestamp is ahead of the system clock, decrease this value. - /// - /// Not exposed to the application. - #[prost(int64, tag="3")] - pub time_iota_ms: i64, } /// EvidenceParams determine how we handle evidence of malfeasance. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct EvidenceParams { /// Max age of evidence, in blocks. /// /// The basic formula for calculating this is: MaxAgeDuration / {average block /// time}. - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_age_num_blocks: i64, /// Max age of evidence, in time. /// /// It should correspond with an app's "unbonding period" or other similar /// mechanism for handling [Nothing-At-Stake /// attacks](). - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub max_age_duration: ::core::option::Option, /// This sets the maximum size of total evidence in bytes that can be committed in a single block. /// and should fall comfortably under the max block bytes. /// Default is 1048576 or 1MB - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(with = "crate::serializers::from_str", default)] pub max_bytes: i64, } @@ -370,152 +352,213 @@ pub struct EvidenceParams { /// NOTE: uses ABCI pubkey naming, not Amino names. #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorParams { - #[prost(string, repeated, tag="1")] + #[prost(string, repeated, tag = "1")] pub pub_key_types: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// VersionParams contains the ABCI application version. #[derive(Clone, PartialEq, ::prost::Message)] pub struct VersionParams { - #[prost(uint64, tag="1")] - pub app_version: u64, + #[prost(uint64, tag = "1")] + pub app: u64, } /// HashedParams is a subset of ConsensusParams. /// /// It is hashed into the Header.ConsensusHash. #[derive(Clone, PartialEq, ::prost::Message)] pub struct HashedParams { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub block_max_bytes: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub block_max_gas: i64, } #[derive(::serde::Deserialize, ::serde::Serialize)] -#[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] +#[serde( + from = "crate::serializers::evidence::EvidenceVariant", + into = "crate::serializers::evidence::EvidenceVariant" +)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Evidence { - #[prost(oneof="evidence::Sum", tags="1, 2")] + #[prost(oneof = "evidence::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Evidence`. pub mod evidence { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] - #[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] + #[serde( + from = "crate::serializers::evidence::EvidenceVariant", + into = "crate::serializers::evidence::EvidenceVariant" + )] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] #[serde(rename = "tendermint/DuplicateVoteEvidence")] DuplicateVoteEvidence(super::DuplicateVoteEvidence), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] #[serde(rename = "tendermint/LightClientAttackEvidence")] LightClientAttackEvidence(super::LightClientAttackEvidence), } } /// DuplicateVoteEvidence contains evidence of a validator signed two conflicting votes. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct DuplicateVoteEvidence { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote_a: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub vote_b: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(alias = "TotalVotingPower", with = "crate::serializers::from_str")] pub total_voting_power: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(alias = "ValidatorPower", with = "crate::serializers::from_str")] pub validator_power: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] #[serde(alias = "Timestamp")] pub timestamp: ::core::option::Option, } /// LightClientAttackEvidence contains evidence of a set of validators attempting to mislead a light client. -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct LightClientAttackEvidence { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub conflicting_block: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub common_height: i64, - #[prost(message, repeated, tag="3")] + #[prost(message, repeated, tag = "3")] pub byzantine_validators: ::prost::alloc::vec::Vec, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub total_voting_power: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub timestamp: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct EvidenceList { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] #[serde(with = "crate::serializers::nullable")] pub evidence: ::prost::alloc::vec::Vec, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct CanonicalBlockId { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct CanonicalPartSetHeader { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub total: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub hash: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalProposal { /// type alias for byte - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="2")] + #[prost(sfixed64, tag = "2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="3")] + #[prost(sfixed64, tag = "3")] pub round: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub pol_round: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub timestamp: ::core::option::Option, - #[prost(string, tag="7")] + #[prost(string, tag = "7")] pub chain_id: ::prost::alloc::string::String, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct CanonicalVote { /// type alias for byte - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="2")] + #[prost(sfixed64, tag = "2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="3")] + #[prost(sfixed64, tag = "3")] pub round: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub timestamp: ::core::option::Option, - #[prost(string, tag="6")] + #[prost(string, tag = "6")] pub chain_id: ::prost::alloc::string::String, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[derive(Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct Block { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub data: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub last_commit: ::core::option::Option, } +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct EventDataRoundState { + #[prost(int64, tag = "1")] + pub height: i64, + #[prost(int32, tag = "2")] + pub round: i32, + #[prost(string, tag = "3")] + pub step: ::prost::alloc::string::String, +} +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +pub struct CanonicalBlockId { + #[prost(bytes = "vec", tag = "1")] + pub hash: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag = "2")] + #[serde(alias = "parts")] + pub part_set_header: ::core::option::Option, +} +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +pub struct CanonicalPartSetHeader { + #[prost(uint32, tag = "1")] + pub total: u32, + #[prost(bytes = "vec", tag = "2")] + pub hash: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct CanonicalProposal { + /// type alias for byte + #[prost(enumeration = "SignedMsgType", tag = "1")] + pub r#type: i32, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag = "2")] + pub height: i64, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag = "3")] + pub round: i64, + #[prost(int64, tag = "4")] + pub pol_round: i64, + #[prost(message, optional, tag = "5")] + pub block_id: ::core::option::Option, + #[prost(message, optional, tag = "6")] + pub timestamp: ::core::option::Option, + #[prost(string, tag = "7")] + pub chain_id: ::prost::alloc::string::String, +} +#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +pub struct CanonicalVote { + /// type alias for byte + #[prost(enumeration = "SignedMsgType", tag = "1")] + pub r#type: i32, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag = "2")] + pub height: i64, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag = "3")] + pub round: i64, + #[prost(message, optional, tag = "4")] + pub block_id: ::core::option::Option, + #[prost(message, optional, tag = "5")] + pub timestamp: ::core::option::Option, + #[prost(string, tag = "6")] + pub chain_id: ::prost::alloc::string::String, +} diff --git a/proto/src/tendermint.rs b/proto/src/tendermint.rs index e4d9b7e46..c9e53b8df 100644 --- a/proto/src/tendermint.rs +++ b/proto/src/tendermint.rs @@ -1,66 +1,66 @@ //! Tendermint-proto auto-generated sub-modules for Tendermint -pub mod statesync { - include!("prost/tendermint.statesync.rs"); +pub mod state { + include!("prost/tendermint.state.rs"); +} + +pub mod version { + include!("prost/tendermint.version.rs"); } pub mod abci { include!("prost/tendermint.abci.rs"); } -pub mod store { - include!("prost/tendermint.store.rs"); +pub mod consensus { + include!("prost/tendermint.consensus.rs"); } -pub mod version { - include!("prost/tendermint.version.rs"); +pub mod crypto { + include!("prost/tendermint.crypto.rs"); +} + +pub mod blocksync { + include!("prost/tendermint.blocksync.rs"); } pub mod types { include!("prost/tendermint.types.rs"); } -pub mod consensus { - include!("prost/tendermint.consensus.rs"); +pub mod rpc { + pub mod grpc { + include!("prost/tendermint.rpc.grpc.rs"); + } } -pub mod p2p { - include!("prost/tendermint.p2p.rs"); +pub mod libs { + pub mod bits { + include!("prost/tendermint.libs.bits.rs"); + } } -pub mod privval { - include!("prost/tendermint.privval.rs"); +pub mod statesync { + include!("prost/tendermint.statesync.rs"); } -pub mod blockchain { - include!("prost/tendermint.blockchain.rs"); +pub mod privval { + include!("prost/tendermint.privval.rs"); } -pub mod crypto { - include!("prost/tendermint.crypto.rs"); +pub mod p2p { + include!("prost/tendermint.p2p.rs"); } pub mod mempool { include!("prost/tendermint.mempool.rs"); } -pub mod state { - include!("prost/tendermint.state.rs"); -} - -pub mod libs { - pub mod bits { - include!("prost/tendermint.libs.bits.rs"); - } -} - -pub mod rpc { - pub mod grpc { - include!("prost/tendermint.rpc.grpc.rs"); - } +pub mod store { + include!("prost/tendermint.store.rs"); } pub mod meta { pub const REPOSITORY: &str = "https://github.com/tendermint/tendermint"; - pub const COMMITISH: &str = "v0.34.21"; + pub const COMMITISH: &str = "v0.37.0-alpha.1"; } diff --git a/tendermint/src/consensus/params.rs b/tendermint/src/consensus/params.rs index e03031ec4..b266aaac4 100644 --- a/tendermint/src/consensus/params.rs +++ b/tendermint/src/consensus/params.rs @@ -155,7 +155,7 @@ impl From for RawValidatorParams { pub struct VersionParams { /// The ABCI application version. #[serde(with = "crate::serializers::from_str")] - pub app_version: u64, + pub app: u64, } impl Protobuf for VersionParams {} @@ -164,16 +164,12 @@ impl TryFrom for VersionParams { type Error = Error; fn try_from(value: RawVersionParams) -> Result { - Ok(Self { - app_version: value.app_version, - }) + Ok(Self { app: value.app }) } } impl From for RawVersionParams { fn from(value: VersionParams) -> Self { - RawVersionParams { - app_version: value.app_version, - } + RawVersionParams { app: value.app } } } diff --git a/tools/proto-compiler/src/constants.rs b/tools/proto-compiler/src/constants.rs index d46458e23..36604a753 100644 --- a/tools/proto-compiler/src/constants.rs +++ b/tools/proto-compiler/src/constants.rs @@ -6,7 +6,7 @@ pub const TENDERMINT_REPO: &str = "https://github.com/tendermint/tendermint"; // Tag: v0.34.0-rc4 // Branch: master // Commit ID (full length): d7d0ffea13c60c98b812d243ba5a2c375f341c15 -pub const TENDERMINT_COMMITISH: &str = "v0.34.21"; +pub const TENDERMINT_COMMITISH: &str = "v0.37.0-alpha.1"; /// Predefined custom attributes for message annotations const PRIMITIVE_ENUM: &str = r#"#[derive(::num_derive::FromPrimitive, ::num_derive::ToPrimitive)]"#; From 95b962ad7a873135a2a1f6aad3e6f294e71c1df1 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 6 Sep 2022 15:25:36 +0300 Subject: [PATCH 03/77] proto: sort includes in generated tendermint.rs This normalizes the content of the module for protocol updates. --- proto/src/tendermint.rs | 52 +++++++++++++-------------- tools/proto-compiler/Cargo.toml | 2 +- tools/proto-compiler/src/functions.rs | 6 ++-- 3 files changed, 31 insertions(+), 29 deletions(-) diff --git a/proto/src/tendermint.rs b/proto/src/tendermint.rs index c9e53b8df..1513aeee8 100644 --- a/proto/src/tendermint.rs +++ b/proto/src/tendermint.rs @@ -1,17 +1,13 @@ //! Tendermint-proto auto-generated sub-modules for Tendermint -pub mod state { - include!("prost/tendermint.state.rs"); -} - -pub mod version { - include!("prost/tendermint.version.rs"); -} - pub mod abci { include!("prost/tendermint.abci.rs"); } +pub mod blocksync { + include!("prost/tendermint.blocksync.rs"); +} + pub mod consensus { include!("prost/tendermint.consensus.rs"); } @@ -20,12 +16,22 @@ pub mod crypto { include!("prost/tendermint.crypto.rs"); } -pub mod blocksync { - include!("prost/tendermint.blocksync.rs"); +pub mod libs { + pub mod bits { + include!("prost/tendermint.libs.bits.rs"); + } } -pub mod types { - include!("prost/tendermint.types.rs"); +pub mod mempool { + include!("prost/tendermint.mempool.rs"); +} + +pub mod p2p { + include!("prost/tendermint.p2p.rs"); +} + +pub mod privval { + include!("prost/tendermint.privval.rs"); } pub mod rpc { @@ -34,30 +40,24 @@ pub mod rpc { } } -pub mod libs { - pub mod bits { - include!("prost/tendermint.libs.bits.rs"); - } +pub mod state { + include!("prost/tendermint.state.rs"); } pub mod statesync { include!("prost/tendermint.statesync.rs"); } -pub mod privval { - include!("prost/tendermint.privval.rs"); -} - -pub mod p2p { - include!("prost/tendermint.p2p.rs"); +pub mod store { + include!("prost/tendermint.store.rs"); } -pub mod mempool { - include!("prost/tendermint.mempool.rs"); +pub mod types { + include!("prost/tendermint.types.rs"); } -pub mod store { - include!("prost/tendermint.store.rs"); +pub mod version { + include!("prost/tendermint.version.rs"); } pub mod meta { diff --git a/tools/proto-compiler/Cargo.toml b/tools/proto-compiler/Cargo.toml index 0ecd67907..82b6168b7 100644 --- a/tools/proto-compiler/Cargo.toml +++ b/tools/proto-compiler/Cargo.toml @@ -2,7 +2,7 @@ name = "tendermint-proto-compiler" version = "0.1.0" authors = ["Informal Systems "] -edition = "2018" +edition = "2021" publish = false [dependencies] diff --git a/tools/proto-compiler/src/functions.rs b/tools/proto-compiler/src/functions.rs index df2158019..e3d9a51ce 100644 --- a/tools/proto-compiler/src/functions.rs +++ b/tools/proto-compiler/src/functions.rs @@ -1,4 +1,5 @@ use std::{ + collections::BTreeSet, fs::{copy, create_dir_all, remove_dir_all, File}, io::Write, path::{Path, PathBuf}, @@ -217,8 +218,9 @@ pub fn generate_tendermint_lib(prost_dir: &Path, tendermint_lib_target: &Path) { && e.file_name().to_str().unwrap().starts_with("tendermint.") && e.file_name().to_str().unwrap().ends_with(".rs") }) - .map(|d| d.file_name().to_str().unwrap().to_string()) - .collect::>(); + .map(|d| d.file_name().to_str().unwrap().to_owned()) + .collect::>(); + let file_names = Vec::from_iter(file_names); let mut content = String::from("//! Tendermint-proto auto-generated sub-modules for Tendermint\n"); From c6807d2c4b9f5b313bb74386345a29c6f66b324a Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 8 Sep 2022 14:27:28 +0300 Subject: [PATCH 04/77] proto: generate structs for 0.34 and 0.37 Modify proto-compiler to generate protobuf modules for both versions of the Tendermint protocol. The different versions are disambiguated by module paths, presently tendermint::v0_34 and tendermint::v0_37, with the latest supported version reimported as tendermint::*. --- proto/src/prost/v0_34/tendermint.abci.rs | 635 ++++++++++++++++++ .../tendermint.blockchain.rs} | 0 .../prost/{ => v0_34}/tendermint.consensus.rs | 4 +- .../prost/{ => v0_34}/tendermint.crypto.rs | 0 .../prost/{ => v0_34}/tendermint.libs.bits.rs | 0 .../prost/{ => v0_34}/tendermint.mempool.rs | 0 proto/src/prost/{ => v0_34}/tendermint.p2p.rs | 67 +- .../prost/{ => v0_34}/tendermint.privval.rs | 0 .../prost/{ => v0_34}/tendermint.rpc.grpc.rs | 0 .../src/prost/{ => v0_34}/tendermint.state.rs | 2 +- .../prost/{ => v0_34}/tendermint.statesync.rs | 0 .../src/prost/{ => v0_34}/tendermint.store.rs | 0 proto/src/prost/v0_34/tendermint.types.rs | 521 ++++++++++++++ .../prost/{ => v0_34}/tendermint.version.rs | 0 .../src/prost/{ => v0_37}/tendermint.abci.rs | 379 ++++++----- proto/src/prost/v0_37/tendermint.blocksync.rs | 51 ++ proto/src/prost/v0_37/tendermint.consensus.rs | 184 +++++ proto/src/prost/v0_37/tendermint.crypto.rs | 73 ++ proto/src/prost/v0_37/tendermint.libs.bits.rs | 8 + proto/src/prost/v0_37/tendermint.mempool.rs | 18 + proto/src/prost/v0_37/tendermint.p2p.rs | 106 +++ proto/src/prost/v0_37/tendermint.privval.rs | 114 ++++ proto/src/prost/v0_37/tendermint.rpc.grpc.rs | 24 + proto/src/prost/v0_37/tendermint.state.rs | 85 +++ proto/src/prost/v0_37/tendermint.statesync.rs | 57 ++ proto/src/prost/v0_37/tendermint.store.rs | 7 + .../src/prost/{ => v0_37}/tendermint.types.rs | 399 +++++------ proto/src/prost/v0_37/tendermint.version.rs | 23 + proto/src/tendermint.rs | 69 +- proto/src/tendermint/v0_34.rs | 66 ++ proto/src/tendermint/v0_37.rs | 66 ++ tools/proto-compiler/Cargo.toml | 2 +- tools/proto-compiler/src/constants.rs | 29 +- tools/proto-compiler/src/functions.rs | 28 +- tools/proto-compiler/src/main.rs | 137 ++-- 35 files changed, 2559 insertions(+), 595 deletions(-) create mode 100644 proto/src/prost/v0_34/tendermint.abci.rs rename proto/src/prost/{tendermint.blocksync.rs => v0_34/tendermint.blockchain.rs} (100%) rename proto/src/prost/{ => v0_34}/tendermint.consensus.rs (97%) rename proto/src/prost/{ => v0_34}/tendermint.crypto.rs (100%) rename proto/src/prost/{ => v0_34}/tendermint.libs.bits.rs (100%) rename proto/src/prost/{ => v0_34}/tendermint.mempool.rs (100%) rename proto/src/prost/{ => v0_34}/tendermint.p2p.rs (67%) rename proto/src/prost/{ => v0_34}/tendermint.privval.rs (100%) rename proto/src/prost/{ => v0_34}/tendermint.rpc.grpc.rs (100%) rename proto/src/prost/{ => v0_34}/tendermint.state.rs (97%) rename proto/src/prost/{ => v0_34}/tendermint.statesync.rs (100%) rename proto/src/prost/{ => v0_34}/tendermint.store.rs (100%) create mode 100644 proto/src/prost/v0_34/tendermint.types.rs rename proto/src/prost/{ => v0_34}/tendermint.version.rs (100%) rename proto/src/prost/{ => v0_37}/tendermint.abci.rs (70%) create mode 100644 proto/src/prost/v0_37/tendermint.blocksync.rs create mode 100644 proto/src/prost/v0_37/tendermint.consensus.rs create mode 100644 proto/src/prost/v0_37/tendermint.crypto.rs create mode 100644 proto/src/prost/v0_37/tendermint.libs.bits.rs create mode 100644 proto/src/prost/v0_37/tendermint.mempool.rs create mode 100644 proto/src/prost/v0_37/tendermint.p2p.rs create mode 100644 proto/src/prost/v0_37/tendermint.privval.rs create mode 100644 proto/src/prost/v0_37/tendermint.rpc.grpc.rs create mode 100644 proto/src/prost/v0_37/tendermint.state.rs create mode 100644 proto/src/prost/v0_37/tendermint.statesync.rs create mode 100644 proto/src/prost/v0_37/tendermint.store.rs rename proto/src/prost/{ => v0_37}/tendermint.types.rs (58%) create mode 100644 proto/src/prost/v0_37/tendermint.version.rs create mode 100644 proto/src/tendermint/v0_34.rs create mode 100644 proto/src/tendermint/v0_37.rs diff --git a/proto/src/prost/v0_34/tendermint.abci.rs b/proto/src/prost/v0_34/tendermint.abci.rs new file mode 100644 index 000000000..04e96b7df --- /dev/null +++ b/proto/src/prost/v0_34/tendermint.abci.rs @@ -0,0 +1,635 @@ +// This file is copied from +// NOTE: When using custom types, mind the warnings. +// + +// ---------------------------------------- +// Request types + +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Request { + #[prost(oneof="request::Value", tags="1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15")] + pub value: ::core::option::Option, +} +/// Nested message and enum types in `Request`. +pub mod request { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Value { + #[prost(message, tag="1")] + Echo(super::RequestEcho), + #[prost(message, tag="2")] + Flush(super::RequestFlush), + #[prost(message, tag="3")] + Info(super::RequestInfo), + #[prost(message, tag="4")] + SetOption(super::RequestSetOption), + #[prost(message, tag="5")] + InitChain(super::RequestInitChain), + #[prost(message, tag="6")] + Query(super::RequestQuery), + #[prost(message, tag="7")] + BeginBlock(super::RequestBeginBlock), + #[prost(message, tag="8")] + CheckTx(super::RequestCheckTx), + #[prost(message, tag="9")] + DeliverTx(super::RequestDeliverTx), + #[prost(message, tag="10")] + EndBlock(super::RequestEndBlock), + #[prost(message, tag="11")] + Commit(super::RequestCommit), + #[prost(message, tag="12")] + ListSnapshots(super::RequestListSnapshots), + #[prost(message, tag="13")] + OfferSnapshot(super::RequestOfferSnapshot), + #[prost(message, tag="14")] + LoadSnapshotChunk(super::RequestLoadSnapshotChunk), + #[prost(message, tag="15")] + ApplySnapshotChunk(super::RequestApplySnapshotChunk), + } +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestEcho { + #[prost(string, tag="1")] + pub message: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestFlush { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestInfo { + #[prost(string, tag="1")] + pub version: ::prost::alloc::string::String, + #[prost(uint64, tag="2")] + pub block_version: u64, + #[prost(uint64, tag="3")] + pub p2p_version: u64, +} +/// nondeterministic +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestSetOption { + #[prost(string, tag="1")] + pub key: ::prost::alloc::string::String, + #[prost(string, tag="2")] + pub value: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestInitChain { + #[prost(message, optional, tag="1")] + pub time: ::core::option::Option, + #[prost(string, tag="2")] + pub chain_id: ::prost::alloc::string::String, + #[prost(message, optional, tag="3")] + pub consensus_params: ::core::option::Option, + #[prost(message, repeated, tag="4")] + pub validators: ::prost::alloc::vec::Vec, + #[prost(bytes="bytes", tag="5")] + pub app_state_bytes: ::prost::bytes::Bytes, + #[prost(int64, tag="6")] + pub initial_height: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestQuery { + #[prost(bytes="bytes", tag="1")] + pub data: ::prost::bytes::Bytes, + #[prost(string, tag="2")] + pub path: ::prost::alloc::string::String, + #[prost(int64, tag="3")] + pub height: i64, + #[prost(bool, tag="4")] + pub prove: bool, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestBeginBlock { + #[prost(bytes="bytes", tag="1")] + pub hash: ::prost::bytes::Bytes, + #[prost(message, optional, tag="2")] + pub header: ::core::option::Option, + #[prost(message, optional, tag="3")] + pub last_commit_info: ::core::option::Option, + #[prost(message, repeated, tag="4")] + pub byzantine_validators: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestCheckTx { + #[prost(bytes="bytes", tag="1")] + pub tx: ::prost::bytes::Bytes, + #[prost(enumeration="CheckTxType", tag="2")] + pub r#type: i32, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestDeliverTx { + #[prost(bytes="bytes", tag="1")] + pub tx: ::prost::bytes::Bytes, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestEndBlock { + #[prost(int64, tag="1")] + pub height: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestCommit { +} +/// lists available snapshots +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestListSnapshots { +} +/// offers a snapshot to the application +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestOfferSnapshot { + /// snapshot offered by peers + #[prost(message, optional, tag="1")] + pub snapshot: ::core::option::Option, + /// light client-verified app hash for snapshot height + #[prost(bytes="bytes", tag="2")] + pub app_hash: ::prost::bytes::Bytes, +} +/// loads a snapshot chunk +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestLoadSnapshotChunk { + #[prost(uint64, tag="1")] + pub height: u64, + #[prost(uint32, tag="2")] + pub format: u32, + #[prost(uint32, tag="3")] + pub chunk: u32, +} +/// Applies a snapshot chunk +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestApplySnapshotChunk { + #[prost(uint32, tag="1")] + pub index: u32, + #[prost(bytes="bytes", tag="2")] + pub chunk: ::prost::bytes::Bytes, + #[prost(string, tag="3")] + pub sender: ::prost::alloc::string::String, +} +// ---------------------------------------- +// Response types + +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Response { + #[prost(oneof="response::Value", tags="1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16")] + pub value: ::core::option::Option, +} +/// Nested message and enum types in `Response`. +pub mod response { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Value { + #[prost(message, tag="1")] + Exception(super::ResponseException), + #[prost(message, tag="2")] + Echo(super::ResponseEcho), + #[prost(message, tag="3")] + Flush(super::ResponseFlush), + #[prost(message, tag="4")] + Info(super::ResponseInfo), + #[prost(message, tag="5")] + SetOption(super::ResponseSetOption), + #[prost(message, tag="6")] + InitChain(super::ResponseInitChain), + #[prost(message, tag="7")] + Query(super::ResponseQuery), + #[prost(message, tag="8")] + BeginBlock(super::ResponseBeginBlock), + #[prost(message, tag="9")] + CheckTx(super::ResponseCheckTx), + #[prost(message, tag="10")] + DeliverTx(super::ResponseDeliverTx), + #[prost(message, tag="11")] + EndBlock(super::ResponseEndBlock), + #[prost(message, tag="12")] + Commit(super::ResponseCommit), + #[prost(message, tag="13")] + ListSnapshots(super::ResponseListSnapshots), + #[prost(message, tag="14")] + OfferSnapshot(super::ResponseOfferSnapshot), + #[prost(message, tag="15")] + LoadSnapshotChunk(super::ResponseLoadSnapshotChunk), + #[prost(message, tag="16")] + ApplySnapshotChunk(super::ResponseApplySnapshotChunk), + } +} +/// nondeterministic +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseException { + #[prost(string, tag="1")] + pub error: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseEcho { + #[prost(string, tag="1")] + pub message: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseFlush { +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseInfo { + #[prost(string, tag="1")] + #[serde(default)] + pub data: ::prost::alloc::string::String, + #[prost(string, tag="2")] + #[serde(default)] + pub version: ::prost::alloc::string::String, + #[prost(uint64, tag="3")] + #[serde(with = "crate::serializers::from_str", default)] + pub app_version: u64, + #[prost(int64, tag="4")] + #[serde(with = "crate::serializers::from_str", default)] + pub last_block_height: i64, + #[prost(bytes="bytes", tag="5")] + #[serde(default)] + #[serde(skip_serializing_if = "bytes::Bytes::is_empty")] + pub last_block_app_hash: ::prost::bytes::Bytes, +} +/// nondeterministic +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseSetOption { + #[prost(uint32, tag="1")] + pub code: u32, + /// bytes data = 2; + #[prost(string, tag="3")] + pub log: ::prost::alloc::string::String, + #[prost(string, tag="4")] + pub info: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseInitChain { + #[prost(message, optional, tag="1")] + pub consensus_params: ::core::option::Option, + #[prost(message, repeated, tag="2")] + pub validators: ::prost::alloc::vec::Vec, + #[prost(bytes="bytes", tag="3")] + pub app_hash: ::prost::bytes::Bytes, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseQuery { + #[prost(uint32, tag="1")] + pub code: u32, + /// bytes data = 2; // use "value" instead. + /// + /// nondeterministic + #[prost(string, tag="3")] + pub log: ::prost::alloc::string::String, + /// nondeterministic + #[prost(string, tag="4")] + pub info: ::prost::alloc::string::String, + #[prost(int64, tag="5")] + pub index: i64, + #[prost(bytes="bytes", tag="6")] + pub key: ::prost::bytes::Bytes, + #[prost(bytes="bytes", tag="7")] + pub value: ::prost::bytes::Bytes, + #[prost(message, optional, tag="8")] + pub proof_ops: ::core::option::Option, + #[prost(int64, tag="9")] + pub height: i64, + #[prost(string, tag="10")] + pub codespace: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseBeginBlock { + #[prost(message, repeated, tag="1")] + pub events: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseCheckTx { + #[prost(uint32, tag="1")] + pub code: u32, + #[prost(bytes="bytes", tag="2")] + pub data: ::prost::bytes::Bytes, + /// nondeterministic + #[prost(string, tag="3")] + pub log: ::prost::alloc::string::String, + /// nondeterministic + #[prost(string, tag="4")] + pub info: ::prost::alloc::string::String, + #[prost(int64, tag="5")] + pub gas_wanted: i64, + #[prost(int64, tag="6")] + pub gas_used: i64, + #[prost(message, repeated, tag="7")] + pub events: ::prost::alloc::vec::Vec, + #[prost(string, tag="8")] + pub codespace: ::prost::alloc::string::String, + #[prost(string, tag="9")] + pub sender: ::prost::alloc::string::String, + #[prost(int64, tag="10")] + pub priority: i64, + /// mempool_error is set by Tendermint. + /// ABCI applictions creating a ResponseCheckTX should not set mempool_error. + #[prost(string, tag="11")] + pub mempool_error: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseDeliverTx { + #[prost(uint32, tag="1")] + pub code: u32, + #[prost(bytes="bytes", tag="2")] + pub data: ::prost::bytes::Bytes, + /// nondeterministic + #[prost(string, tag="3")] + pub log: ::prost::alloc::string::String, + /// nondeterministic + #[prost(string, tag="4")] + pub info: ::prost::alloc::string::String, + #[prost(int64, tag="5")] + pub gas_wanted: i64, + #[prost(int64, tag="6")] + pub gas_used: i64, + /// nondeterministic + #[prost(message, repeated, tag="7")] + pub events: ::prost::alloc::vec::Vec, + #[prost(string, tag="8")] + pub codespace: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseEndBlock { + #[prost(message, repeated, tag="1")] + pub validator_updates: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="2")] + pub consensus_param_updates: ::core::option::Option, + #[prost(message, repeated, tag="3")] + pub events: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseCommit { + /// reserve 1 + #[prost(bytes="bytes", tag="2")] + pub data: ::prost::bytes::Bytes, + #[prost(int64, tag="3")] + pub retain_height: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseListSnapshots { + #[prost(message, repeated, tag="1")] + pub snapshots: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseOfferSnapshot { + #[prost(enumeration="response_offer_snapshot::Result", tag="1")] + pub result: i32, +} +/// Nested message and enum types in `ResponseOfferSnapshot`. +pub mod response_offer_snapshot { + #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[repr(i32)] + pub enum Result { + /// Unknown result, abort all snapshot restoration + Unknown = 0, + /// Snapshot accepted, apply chunks + Accept = 1, + /// Abort all snapshot restoration + Abort = 2, + /// Reject this specific snapshot, try others + Reject = 3, + /// Reject all snapshots of this format, try others + RejectFormat = 4, + /// Reject all snapshots from the sender(s), try others + RejectSender = 5, + } + impl Result { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + Result::Unknown => "UNKNOWN", + Result::Accept => "ACCEPT", + Result::Abort => "ABORT", + Result::Reject => "REJECT", + Result::RejectFormat => "REJECT_FORMAT", + Result::RejectSender => "REJECT_SENDER", + } + } + } +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseLoadSnapshotChunk { + #[prost(bytes="bytes", tag="1")] + pub chunk: ::prost::bytes::Bytes, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseApplySnapshotChunk { + #[prost(enumeration="response_apply_snapshot_chunk::Result", tag="1")] + pub result: i32, + /// Chunks to refetch and reapply + #[prost(uint32, repeated, tag="2")] + pub refetch_chunks: ::prost::alloc::vec::Vec, + /// Chunk senders to reject and ban + #[prost(string, repeated, tag="3")] + pub reject_senders: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, +} +/// Nested message and enum types in `ResponseApplySnapshotChunk`. +pub mod response_apply_snapshot_chunk { + #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[repr(i32)] + pub enum Result { + /// Unknown result, abort all snapshot restoration + Unknown = 0, + /// Chunk successfully accepted + Accept = 1, + /// Abort all snapshot restoration + Abort = 2, + /// Retry chunk (combine with refetch and reject) + Retry = 3, + /// Retry snapshot (combine with refetch and reject) + RetrySnapshot = 4, + /// Reject this snapshot, try others + RejectSnapshot = 5, + } + impl Result { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + Result::Unknown => "UNKNOWN", + Result::Accept => "ACCEPT", + Result::Abort => "ABORT", + Result::Retry => "RETRY", + Result::RetrySnapshot => "RETRY_SNAPSHOT", + Result::RejectSnapshot => "REJECT_SNAPSHOT", + } + } + } +} +// ---------------------------------------- +// Misc. + +/// ConsensusParams contains all consensus-relevant parameters +/// that can be adjusted by the abci app +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ConsensusParams { + #[prost(message, optional, tag="1")] + pub block: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub evidence: ::core::option::Option, + #[prost(message, optional, tag="3")] + pub validator: ::core::option::Option, + #[prost(message, optional, tag="4")] + pub version: ::core::option::Option, +} +/// BlockParams contains limits on the block size. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockParams { + /// Note: must be greater than 0 + #[prost(int64, tag="1")] + pub max_bytes: i64, + /// Note: must be greater or equal to -1 + #[prost(int64, tag="2")] + pub max_gas: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct LastCommitInfo { + #[prost(int32, tag="1")] + pub round: i32, + #[prost(message, repeated, tag="2")] + pub votes: ::prost::alloc::vec::Vec, +} +/// Event allows application developers to attach additional information to +/// ResponseBeginBlock, ResponseEndBlock, ResponseCheckTx and ResponseDeliverTx. +/// Later, transactions may be queried using these events. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Event { + #[prost(string, tag="1")] + pub r#type: ::prost::alloc::string::String, + #[prost(message, repeated, tag="2")] + pub attributes: ::prost::alloc::vec::Vec, +} +/// EventAttribute is a single key-value pair, associated with an event. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct EventAttribute { + #[prost(bytes="bytes", tag="1")] + pub key: ::prost::bytes::Bytes, + #[prost(bytes="bytes", tag="2")] + pub value: ::prost::bytes::Bytes, + /// nondeterministic + #[prost(bool, tag="3")] + pub index: bool, +} +/// TxResult contains results of executing the transaction. +/// +/// One usage is indexing transaction results. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct TxResult { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(uint32, tag="2")] + pub index: u32, + #[prost(bytes="bytes", tag="3")] + pub tx: ::prost::bytes::Bytes, + #[prost(message, optional, tag="4")] + pub result: ::core::option::Option, +} +// ---------------------------------------- +// Blockchain Types + +/// Validator +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Validator { + /// The first 20 bytes of SHA256(public key) + #[prost(bytes="bytes", tag="1")] + pub address: ::prost::bytes::Bytes, + /// PubKey pub_key = 2 \[(gogoproto.nullable)=false\]; + /// + /// The voting power + #[prost(int64, tag="3")] + pub power: i64, +} +/// ValidatorUpdate +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ValidatorUpdate { + #[prost(message, optional, tag="1")] + pub pub_key: ::core::option::Option, + #[prost(int64, tag="2")] + pub power: i64, +} +/// VoteInfo +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct VoteInfo { + #[prost(message, optional, tag="1")] + pub validator: ::core::option::Option, + #[prost(bool, tag="2")] + pub signed_last_block: bool, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Evidence { + #[prost(enumeration="EvidenceType", tag="1")] + pub r#type: i32, + /// The offending validator + #[prost(message, optional, tag="2")] + pub validator: ::core::option::Option, + /// The height when the offense occurred + #[prost(int64, tag="3")] + pub height: i64, + /// The corresponding time where the offense occurred + #[prost(message, optional, tag="4")] + pub time: ::core::option::Option, + /// Total voting power of the validator set in case the ABCI application does + /// not store historical validators. + /// + #[prost(int64, tag="5")] + pub total_voting_power: i64, +} +// ---------------------------------------- +// State Sync Types + +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Snapshot { + /// The height at which the snapshot was taken + #[prost(uint64, tag="1")] + pub height: u64, + /// The application-specific snapshot format + #[prost(uint32, tag="2")] + pub format: u32, + /// Number of chunks in the snapshot + #[prost(uint32, tag="3")] + pub chunks: u32, + /// Arbitrary snapshot hash, equal only if identical + #[prost(bytes="bytes", tag="4")] + pub hash: ::prost::bytes::Bytes, + /// Arbitrary application metadata + #[prost(bytes="bytes", tag="5")] + pub metadata: ::prost::bytes::Bytes, +} +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] +#[repr(i32)] +pub enum CheckTxType { + New = 0, + Recheck = 1, +} +impl CheckTxType { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + CheckTxType::New => "NEW", + CheckTxType::Recheck => "RECHECK", + } + } +} +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] +#[repr(i32)] +pub enum EvidenceType { + Unknown = 0, + DuplicateVote = 1, + LightClientAttack = 2, +} +impl EvidenceType { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + EvidenceType::Unknown => "UNKNOWN", + EvidenceType::DuplicateVote => "DUPLICATE_VOTE", + EvidenceType::LightClientAttack => "LIGHT_CLIENT_ATTACK", + } + } +} diff --git a/proto/src/prost/tendermint.blocksync.rs b/proto/src/prost/v0_34/tendermint.blockchain.rs similarity index 100% rename from proto/src/prost/tendermint.blocksync.rs rename to proto/src/prost/v0_34/tendermint.blockchain.rs diff --git a/proto/src/prost/tendermint.consensus.rs b/proto/src/prost/v0_34/tendermint.consensus.rs similarity index 97% rename from proto/src/prost/tendermint.consensus.rs rename to proto/src/prost/v0_34/tendermint.consensus.rs index 1ada48be4..6f3fe8624 100644 --- a/proto/src/prost/tendermint.consensus.rs +++ b/proto/src/prost/v0_34/tendermint.consensus.rs @@ -140,7 +140,7 @@ pub struct MsgInfo { #[derive(Clone, PartialEq, ::prost::Message)] pub struct TimeoutInfo { #[prost(message, optional, tag="1")] - pub duration: ::core::option::Option, + pub duration: ::core::option::Option, #[prost(int64, tag="2")] pub height: i64, #[prost(int32, tag="3")] @@ -178,7 +178,7 @@ pub mod wal_message { #[derive(Clone, PartialEq, ::prost::Message)] pub struct TimedWalMessage { #[prost(message, optional, tag="1")] - pub time: ::core::option::Option, + pub time: ::core::option::Option, #[prost(message, optional, tag="2")] pub msg: ::core::option::Option, } diff --git a/proto/src/prost/tendermint.crypto.rs b/proto/src/prost/v0_34/tendermint.crypto.rs similarity index 100% rename from proto/src/prost/tendermint.crypto.rs rename to proto/src/prost/v0_34/tendermint.crypto.rs diff --git a/proto/src/prost/tendermint.libs.bits.rs b/proto/src/prost/v0_34/tendermint.libs.bits.rs similarity index 100% rename from proto/src/prost/tendermint.libs.bits.rs rename to proto/src/prost/v0_34/tendermint.libs.bits.rs diff --git a/proto/src/prost/tendermint.mempool.rs b/proto/src/prost/v0_34/tendermint.mempool.rs similarity index 100% rename from proto/src/prost/tendermint.mempool.rs rename to proto/src/prost/v0_34/tendermint.mempool.rs diff --git a/proto/src/prost/tendermint.p2p.rs b/proto/src/prost/v0_34/tendermint.p2p.rs similarity index 67% rename from proto/src/prost/tendermint.p2p.rs rename to proto/src/prost/v0_34/tendermint.p2p.rs index ec3ab40ab..4b81d0be0 100644 --- a/proto/src/prost/tendermint.p2p.rs +++ b/proto/src/prost/v0_34/tendermint.p2p.rs @@ -1,103 +1,106 @@ #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPing {} +pub struct PacketPing { +} #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPong {} +pub struct PacketPong { +} #[derive(Clone, PartialEq, ::prost::Message)] pub struct PacketMsg { - #[prost(int32, tag = "1")] + #[prost(int32, tag="1")] pub channel_id: i32, - #[prost(bool, tag = "2")] + #[prost(bool, tag="2")] pub eof: bool, - #[prost(bytes = "vec", tag = "3")] + #[prost(bytes="vec", tag="3")] pub data: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Packet { - #[prost(oneof = "packet::Sum", tags = "1, 2, 3")] + #[prost(oneof="packet::Sum", tags="1, 2, 3")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Packet`. pub mod packet { #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag = "1")] + #[prost(message, tag="1")] PacketPing(super::PacketPing), - #[prost(message, tag = "2")] + #[prost(message, tag="2")] PacketPong(super::PacketPong), - #[prost(message, tag = "3")] + #[prost(message, tag="3")] PacketMsg(super::PacketMsg), } } #[derive(Clone, PartialEq, ::prost::Message)] pub struct AuthSigMessage { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub pub_key: ::core::option::Option, - #[prost(bytes = "vec", tag = "2")] + #[prost(bytes="vec", tag="2")] pub sig: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct NetAddress { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub id: ::prost::alloc::string::String, - #[prost(string, tag = "2")] + #[prost(string, tag="2")] pub ip: ::prost::alloc::string::String, - #[prost(uint32, tag = "3")] + #[prost(uint32, tag="3")] pub port: u32, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProtocolVersion { - #[prost(uint64, tag = "1")] + #[prost(uint64, tag="1")] pub p2p: u64, - #[prost(uint64, tag = "2")] + #[prost(uint64, tag="2")] pub block: u64, - #[prost(uint64, tag = "3")] + #[prost(uint64, tag="3")] pub app: u64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfo { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub protocol_version: ::core::option::Option, - #[prost(string, tag = "2")] + #[prost(string, tag="2")] pub default_node_id: ::prost::alloc::string::String, - #[prost(string, tag = "3")] + #[prost(string, tag="3")] pub listen_addr: ::prost::alloc::string::String, - #[prost(string, tag = "4")] + #[prost(string, tag="4")] pub network: ::prost::alloc::string::String, - #[prost(string, tag = "5")] + #[prost(string, tag="5")] pub version: ::prost::alloc::string::String, - #[prost(bytes = "vec", tag = "6")] + #[prost(bytes="vec", tag="6")] pub channels: ::prost::alloc::vec::Vec, - #[prost(string, tag = "7")] + #[prost(string, tag="7")] pub moniker: ::prost::alloc::string::String, - #[prost(message, optional, tag = "8")] + #[prost(message, optional, tag="8")] pub other: ::core::option::Option, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfoOther { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub tx_index: ::prost::alloc::string::String, - #[prost(string, tag = "2")] + #[prost(string, tag="2")] pub rpc_address: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PexRequest {} +pub struct PexRequest { +} #[derive(Clone, PartialEq, ::prost::Message)] pub struct PexAddrs { - #[prost(message, repeated, tag = "1")] + #[prost(message, repeated, tag="1")] pub addrs: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof = "message::Sum", tags = "1, 2")] + #[prost(oneof="message::Sum", tags="1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag = "1")] + #[prost(message, tag="1")] PexRequest(super::PexRequest), - #[prost(message, tag = "2")] + #[prost(message, tag="2")] PexAddrs(super::PexAddrs), } } diff --git a/proto/src/prost/tendermint.privval.rs b/proto/src/prost/v0_34/tendermint.privval.rs similarity index 100% rename from proto/src/prost/tendermint.privval.rs rename to proto/src/prost/v0_34/tendermint.privval.rs diff --git a/proto/src/prost/tendermint.rpc.grpc.rs b/proto/src/prost/v0_34/tendermint.rpc.grpc.rs similarity index 100% rename from proto/src/prost/tendermint.rpc.grpc.rs rename to proto/src/prost/v0_34/tendermint.rpc.grpc.rs diff --git a/proto/src/prost/tendermint.state.rs b/proto/src/prost/v0_34/tendermint.state.rs similarity index 97% rename from proto/src/prost/tendermint.state.rs rename to proto/src/prost/v0_34/tendermint.state.rs index c536f5df5..c996b31a5 100644 --- a/proto/src/prost/tendermint.state.rs +++ b/proto/src/prost/v0_34/tendermint.state.rs @@ -55,7 +55,7 @@ pub struct State { #[prost(message, optional, tag="4")] pub last_block_id: ::core::option::Option, #[prost(message, optional, tag="5")] - pub last_block_time: ::core::option::Option, + pub last_block_time: ::core::option::Option, /// LastValidators is used to validate block.LastCommit. /// Validators are persisted to the database separately every time they change, /// so we can query for historical validator sets. diff --git a/proto/src/prost/tendermint.statesync.rs b/proto/src/prost/v0_34/tendermint.statesync.rs similarity index 100% rename from proto/src/prost/tendermint.statesync.rs rename to proto/src/prost/v0_34/tendermint.statesync.rs diff --git a/proto/src/prost/tendermint.store.rs b/proto/src/prost/v0_34/tendermint.store.rs similarity index 100% rename from proto/src/prost/tendermint.store.rs rename to proto/src/prost/v0_34/tendermint.store.rs diff --git a/proto/src/prost/v0_34/tendermint.types.rs b/proto/src/prost/v0_34/tendermint.types.rs new file mode 100644 index 000000000..5e8de00a8 --- /dev/null +++ b/proto/src/prost/v0_34/tendermint.types.rs @@ -0,0 +1,521 @@ +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ValidatorSet { + #[prost(message, repeated, tag="1")] + pub validators: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="2")] + pub proposer: ::core::option::Option, + #[prost(int64, tag="3")] + pub total_voting_power: i64, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Validator { + #[prost(bytes="vec", tag="1")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub address: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="2")] + pub pub_key: ::core::option::Option, + #[prost(int64, tag="3")] + #[serde(alias = "power", with = "crate::serializers::from_str")] + pub voting_power: i64, + #[prost(int64, tag="4")] + #[serde(with = "crate::serializers::from_str", default)] + pub proposer_priority: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SimpleValidator { + #[prost(message, optional, tag="1")] + pub pub_key: ::core::option::Option, + #[prost(int64, tag="2")] + pub voting_power: i64, +} +/// PartsetHeader +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PartSetHeader { + #[prost(uint32, tag="1")] + #[serde(with = "crate::serializers::part_set_header_total")] + pub total: u32, + #[prost(bytes="vec", tag="2")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub hash: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Part { + #[prost(uint32, tag="1")] + pub index: u32, + #[prost(bytes="vec", tag="2")] + pub bytes: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="3")] + pub proof: ::core::option::Option, +} +/// BlockID +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockId { + #[prost(bytes="vec", tag="1")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub hash: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="2")] + #[serde(alias = "parts")] + pub part_set_header: ::core::option::Option, +} +// -------------------------------- + +/// Header defines the structure of a Tendermint block header. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Header { + /// basic block info + #[prost(message, optional, tag="1")] + pub version: ::core::option::Option, + #[prost(string, tag="2")] + pub chain_id: ::prost::alloc::string::String, + #[prost(int64, tag="3")] + #[serde(with = "crate::serializers::from_str")] + pub height: i64, + #[prost(message, optional, tag="4")] + #[serde(with = "crate::serializers::optional")] + pub time: ::core::option::Option, + /// prev block info + #[prost(message, optional, tag="5")] + pub last_block_id: ::core::option::Option, + /// hashes of block data + /// + /// commit from validators from the last block + #[prost(bytes="vec", tag="6")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub last_commit_hash: ::prost::alloc::vec::Vec, + /// transactions + #[prost(bytes="vec", tag="7")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub data_hash: ::prost::alloc::vec::Vec, + /// hashes from the app output from the prev block + /// + /// validators for the current block + #[prost(bytes="vec", tag="8")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub validators_hash: ::prost::alloc::vec::Vec, + /// validators for the next block + #[prost(bytes="vec", tag="9")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub next_validators_hash: ::prost::alloc::vec::Vec, + /// consensus params for current block + #[prost(bytes="vec", tag="10")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub consensus_hash: ::prost::alloc::vec::Vec, + /// state after txs from the previous block + #[prost(bytes="vec", tag="11")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub app_hash: ::prost::alloc::vec::Vec, + /// root hash of all results from the txs from the previous block + #[prost(bytes="vec", tag="12")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub last_results_hash: ::prost::alloc::vec::Vec, + /// consensus info + /// + /// evidence included in the block + #[prost(bytes="vec", tag="13")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub evidence_hash: ::prost::alloc::vec::Vec, + /// original proposer of the block + #[prost(bytes="vec", tag="14")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub proposer_address: ::prost::alloc::vec::Vec, +} +/// Data contains the set of transactions included in the block +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Data { + /// Txs that will be applied by state @ block.Height+1. + /// NOTE: not all txs here are valid. We're just agreeing on the order first. + /// This means that block.AppHash does not include these txs. + #[prost(bytes="vec", repeated, tag="1")] + #[serde(with = "crate::serializers::txs")] + pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, +} +/// Vote represents a prevote, precommit, or commit vote from validators for +/// consensus. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Vote { + #[prost(enumeration="SignedMsgType", tag="1")] + pub r#type: i32, + #[prost(int64, tag="2")] + #[serde(with = "crate::serializers::from_str")] + pub height: i64, + #[prost(int32, tag="3")] + pub round: i32, + /// zero if vote is nil. + #[prost(message, optional, tag="4")] + pub block_id: ::core::option::Option, + #[prost(message, optional, tag="5")] + #[serde(with = "crate::serializers::optional")] + pub timestamp: ::core::option::Option, + #[prost(bytes="vec", tag="6")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub validator_address: ::prost::alloc::vec::Vec, + #[prost(int32, tag="7")] + pub validator_index: i32, + #[prost(bytes="vec", tag="8")] + #[serde(with = "crate::serializers::bytes::base64string")] + pub signature: ::prost::alloc::vec::Vec, +} +/// Commit contains the evidence that a block was committed by a set of validators. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Commit { + #[prost(int64, tag="1")] + #[serde(with = "crate::serializers::from_str")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(message, optional, tag="3")] + pub block_id: ::core::option::Option, + #[prost(message, repeated, tag="4")] + #[serde(with = "crate::serializers::nullable")] + pub signatures: ::prost::alloc::vec::Vec, +} +/// CommitSig is a part of the Vote included in a Commit. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct CommitSig { + #[prost(enumeration="BlockIdFlag", tag="1")] + pub block_id_flag: i32, + #[prost(bytes="vec", tag="2")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub validator_address: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="3")] + #[serde(with = "crate::serializers::optional")] + pub timestamp: ::core::option::Option, + #[prost(bytes="vec", tag="4")] + #[serde(with = "crate::serializers::bytes::base64string")] + pub signature: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Proposal { + #[prost(enumeration="SignedMsgType", tag="1")] + pub r#type: i32, + #[prost(int64, tag="2")] + pub height: i64, + #[prost(int32, tag="3")] + pub round: i32, + #[prost(int32, tag="4")] + pub pol_round: i32, + #[prost(message, optional, tag="5")] + pub block_id: ::core::option::Option, + #[prost(message, optional, tag="6")] + pub timestamp: ::core::option::Option, + #[prost(bytes="vec", tag="7")] + pub signature: ::prost::alloc::vec::Vec, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SignedHeader { + #[prost(message, optional, tag="1")] + pub header: ::core::option::Option
, + #[prost(message, optional, tag="2")] + pub commit: ::core::option::Option, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct LightBlock { + #[prost(message, optional, tag="1")] + pub signed_header: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub validator_set: ::core::option::Option, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockMeta { + #[prost(message, optional, tag="1")] + pub block_id: ::core::option::Option, + #[prost(int64, tag="2")] + #[serde(with = "crate::serializers::from_str")] + pub block_size: i64, + #[prost(message, optional, tag="3")] + pub header: ::core::option::Option
, + #[prost(int64, tag="4")] + #[serde(with = "crate::serializers::from_str")] + pub num_txs: i64, +} +/// TxProof represents a Merkle proof of the presence of a transaction in the Merkle tree. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct TxProof { + #[prost(bytes="vec", tag="1")] + #[serde(with = "crate::serializers::bytes::hexstring")] + pub root_hash: ::prost::alloc::vec::Vec, + #[prost(bytes="vec", tag="2")] + #[serde(with = "crate::serializers::bytes::base64string")] + pub data: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="3")] + pub proof: ::core::option::Option, +} +/// BlockIdFlag indicates which BlcokID the signature is for +#[derive(::num_derive::FromPrimitive, ::num_derive::ToPrimitive)] +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] +#[repr(i32)] +pub enum BlockIdFlag { + Unknown = 0, + Absent = 1, + Commit = 2, + Nil = 3, +} +impl BlockIdFlag { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + BlockIdFlag::Unknown => "BLOCK_ID_FLAG_UNKNOWN", + BlockIdFlag::Absent => "BLOCK_ID_FLAG_ABSENT", + BlockIdFlag::Commit => "BLOCK_ID_FLAG_COMMIT", + BlockIdFlag::Nil => "BLOCK_ID_FLAG_NIL", + } + } +} +/// SignedMsgType is a type of signed message in the consensus. +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] +#[repr(i32)] +pub enum SignedMsgType { + Unknown = 0, + /// Votes + Prevote = 1, + Precommit = 2, + /// Proposals + Proposal = 32, +} +impl SignedMsgType { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + SignedMsgType::Unknown => "SIGNED_MSG_TYPE_UNKNOWN", + SignedMsgType::Prevote => "SIGNED_MSG_TYPE_PREVOTE", + SignedMsgType::Precommit => "SIGNED_MSG_TYPE_PRECOMMIT", + SignedMsgType::Proposal => "SIGNED_MSG_TYPE_PROPOSAL", + } + } +} +/// ConsensusParams contains consensus critical parameters that determine the +/// validity of blocks. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ConsensusParams { + #[prost(message, optional, tag="1")] + pub block: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub evidence: ::core::option::Option, + #[prost(message, optional, tag="3")] + pub validator: ::core::option::Option, + #[prost(message, optional, tag="4")] + pub version: ::core::option::Option, +} +/// BlockParams contains limits on the block size. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockParams { + /// Max block size, in bytes. + /// Note: must be greater than 0 + #[prost(int64, tag="1")] + pub max_bytes: i64, + /// Max gas per block. + /// Note: must be greater or equal to -1 + #[prost(int64, tag="2")] + pub max_gas: i64, + /// Minimum time increment between consecutive blocks (in milliseconds) If the + /// block header timestamp is ahead of the system clock, decrease this value. + /// + /// Not exposed to the application. + #[prost(int64, tag="3")] + pub time_iota_ms: i64, +} +/// EvidenceParams determine how we handle evidence of malfeasance. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct EvidenceParams { + /// Max age of evidence, in blocks. + /// + /// The basic formula for calculating this is: MaxAgeDuration / {average block + /// time}. + #[prost(int64, tag="1")] + pub max_age_num_blocks: i64, + /// Max age of evidence, in time. + /// + /// It should correspond with an app's "unbonding period" or other similar + /// mechanism for handling [Nothing-At-Stake + /// attacks](). + #[prost(message, optional, tag="2")] + pub max_age_duration: ::core::option::Option, + /// This sets the maximum size of total evidence in bytes that can be committed in a single block. + /// and should fall comfortably under the max block bytes. + /// Default is 1048576 or 1MB + #[prost(int64, tag="3")] + #[serde(with = "crate::serializers::from_str", default)] + pub max_bytes: i64, +} +/// ValidatorParams restrict the public key types validators can use. +/// NOTE: uses ABCI pubkey naming, not Amino names. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ValidatorParams { + #[prost(string, repeated, tag="1")] + pub pub_key_types: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, +} +/// VersionParams contains the ABCI application version. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct VersionParams { + #[prost(uint64, tag="1")] + pub app_version: u64, +} +/// HashedParams is a subset of ConsensusParams. +/// +/// It is hashed into the Header.ConsensusHash. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct HashedParams { + #[prost(int64, tag="1")] + pub block_max_bytes: i64, + #[prost(int64, tag="2")] + pub block_max_gas: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct EventDataRoundState { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(string, tag="3")] + pub step: ::prost::alloc::string::String, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Evidence { + #[prost(oneof="evidence::Sum", tags="1, 2")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Evidence`. +pub mod evidence { + #[derive(::serde::Deserialize, ::serde::Serialize)] + #[serde(tag = "type", content = "value")] + #[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + #[serde(rename = "tendermint/DuplicateVoteEvidence")] + DuplicateVoteEvidence(super::DuplicateVoteEvidence), + #[prost(message, tag="2")] + #[serde(rename = "tendermint/LightClientAttackEvidence")] + LightClientAttackEvidence(super::LightClientAttackEvidence), + } +} +/// DuplicateVoteEvidence contains evidence of a validator signed two conflicting votes. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct DuplicateVoteEvidence { + #[prost(message, optional, tag="1")] + pub vote_a: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub vote_b: ::core::option::Option, + #[prost(int64, tag="3")] + #[serde(alias = "TotalVotingPower", with = "crate::serializers::from_str")] + pub total_voting_power: i64, + #[prost(int64, tag="4")] + #[serde(alias = "ValidatorPower", with = "crate::serializers::from_str")] + pub validator_power: i64, + #[prost(message, optional, tag="5")] + #[serde(alias = "Timestamp")] + pub timestamp: ::core::option::Option, +} +/// LightClientAttackEvidence contains evidence of a set of validators attempting to mislead a light client. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct LightClientAttackEvidence { + #[prost(message, optional, tag="1")] + pub conflicting_block: ::core::option::Option, + #[prost(int64, tag="2")] + pub common_height: i64, + #[prost(message, repeated, tag="3")] + pub byzantine_validators: ::prost::alloc::vec::Vec, + #[prost(int64, tag="4")] + pub total_voting_power: i64, + #[prost(message, optional, tag="5")] + pub timestamp: ::core::option::Option, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct EvidenceList { + #[prost(message, repeated, tag="1")] + #[serde(with = "crate::serializers::nullable")] + pub evidence: ::prost::alloc::vec::Vec, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Block { + #[prost(message, optional, tag="1")] + pub header: ::core::option::Option
, + #[prost(message, optional, tag="2")] + pub data: ::core::option::Option, + #[prost(message, optional, tag="3")] + pub evidence: ::core::option::Option, + #[prost(message, optional, tag="4")] + pub last_commit: ::core::option::Option, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct CanonicalBlockId { + #[prost(bytes="vec", tag="1")] + pub hash: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="2")] + #[serde(alias = "parts")] + pub part_set_header: ::core::option::Option, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct CanonicalPartSetHeader { + #[prost(uint32, tag="1")] + pub total: u32, + #[prost(bytes="vec", tag="2")] + pub hash: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct CanonicalProposal { + /// type alias for byte + #[prost(enumeration="SignedMsgType", tag="1")] + pub r#type: i32, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag="2")] + pub height: i64, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag="3")] + pub round: i64, + #[prost(int64, tag="4")] + pub pol_round: i64, + #[prost(message, optional, tag="5")] + pub block_id: ::core::option::Option, + #[prost(message, optional, tag="6")] + pub timestamp: ::core::option::Option, + #[prost(string, tag="7")] + pub chain_id: ::prost::alloc::string::String, +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct CanonicalVote { + /// type alias for byte + #[prost(enumeration="SignedMsgType", tag="1")] + pub r#type: i32, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag="2")] + pub height: i64, + /// canonicalization requires fixed size encoding here + #[prost(sfixed64, tag="3")] + pub round: i64, + #[prost(message, optional, tag="4")] + pub block_id: ::core::option::Option, + #[prost(message, optional, tag="5")] + pub timestamp: ::core::option::Option, + #[prost(string, tag="6")] + pub chain_id: ::prost::alloc::string::String, +} diff --git a/proto/src/prost/tendermint.version.rs b/proto/src/prost/v0_34/tendermint.version.rs similarity index 100% rename from proto/src/prost/tendermint.version.rs rename to proto/src/prost/v0_34/tendermint.version.rs diff --git a/proto/src/prost/tendermint.abci.rs b/proto/src/prost/v0_37/tendermint.abci.rs similarity index 70% rename from proto/src/prost/tendermint.abci.rs rename to proto/src/prost/v0_37/tendermint.abci.rs index 0ef1caae6..8a62bb862 100644 --- a/proto/src/prost/tendermint.abci.rs +++ b/proto/src/prost/v0_37/tendermint.abci.rs @@ -7,399 +7,398 @@ #[derive(Clone, PartialEq, ::prost::Message)] pub struct Request { - #[prost( - oneof = "request::Value", - tags = "1, 2, 3, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17" - )] + #[prost(oneof="request::Value", tags="1, 2, 3, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17")] pub value: ::core::option::Option, } /// Nested message and enum types in `Request`. pub mod request { #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag = "1")] + #[prost(message, tag="1")] Echo(super::RequestEcho), - #[prost(message, tag = "2")] + #[prost(message, tag="2")] Flush(super::RequestFlush), - #[prost(message, tag = "3")] + #[prost(message, tag="3")] Info(super::RequestInfo), - #[prost(message, tag = "5")] + #[prost(message, tag="5")] InitChain(super::RequestInitChain), - #[prost(message, tag = "6")] + #[prost(message, tag="6")] Query(super::RequestQuery), - #[prost(message, tag = "7")] + #[prost(message, tag="7")] BeginBlock(super::RequestBeginBlock), - #[prost(message, tag = "8")] + #[prost(message, tag="8")] CheckTx(super::RequestCheckTx), - #[prost(message, tag = "9")] + #[prost(message, tag="9")] DeliverTx(super::RequestDeliverTx), - #[prost(message, tag = "10")] + #[prost(message, tag="10")] EndBlock(super::RequestEndBlock), - #[prost(message, tag = "11")] + #[prost(message, tag="11")] Commit(super::RequestCommit), - #[prost(message, tag = "12")] + #[prost(message, tag="12")] ListSnapshots(super::RequestListSnapshots), - #[prost(message, tag = "13")] + #[prost(message, tag="13")] OfferSnapshot(super::RequestOfferSnapshot), - #[prost(message, tag = "14")] + #[prost(message, tag="14")] LoadSnapshotChunk(super::RequestLoadSnapshotChunk), - #[prost(message, tag = "15")] + #[prost(message, tag="15")] ApplySnapshotChunk(super::RequestApplySnapshotChunk), - #[prost(message, tag = "16")] + #[prost(message, tag="16")] PrepareProposal(super::RequestPrepareProposal), - #[prost(message, tag = "17")] + #[prost(message, tag="17")] ProcessProposal(super::RequestProcessProposal), } } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEcho { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub message: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestFlush {} +pub struct RequestFlush { +} #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInfo { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag = "2")] + #[prost(uint64, tag="2")] pub block_version: u64, - #[prost(uint64, tag = "3")] + #[prost(uint64, tag="3")] pub p2p_version: u64, - #[prost(string, tag = "4")] + #[prost(string, tag="4")] pub abci_version: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInitChain { - #[prost(message, optional, tag = "1")] - pub time: ::core::option::Option, - #[prost(string, tag = "2")] + #[prost(message, optional, tag="1")] + pub time: ::core::option::Option, + #[prost(string, tag="2")] pub chain_id: ::prost::alloc::string::String, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag = "4")] + #[prost(message, repeated, tag="4")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes = "bytes", tag = "5")] + #[prost(bytes="bytes", tag="5")] pub app_state_bytes: ::prost::bytes::Bytes, - #[prost(int64, tag = "6")] + #[prost(int64, tag="6")] pub initial_height: i64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestQuery { - #[prost(bytes = "bytes", tag = "1")] + #[prost(bytes="bytes", tag="1")] pub data: ::prost::bytes::Bytes, - #[prost(string, tag = "2")] + #[prost(string, tag="2")] pub path: ::prost::alloc::string::String, - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] pub height: i64, - #[prost(bool, tag = "4")] + #[prost(bool, tag="4")] pub prove: bool, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestBeginBlock { - #[prost(bytes = "bytes", tag = "1")] + #[prost(bytes="bytes", tag="1")] pub hash: ::prost::bytes::Bytes, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub header: ::core::option::Option, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub last_commit_info: ::core::option::Option, - #[prost(message, repeated, tag = "4")] + #[prost(message, repeated, tag="4")] pub byzantine_validators: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestCheckTx { - #[prost(bytes = "bytes", tag = "1")] + #[prost(bytes="bytes", tag="1")] pub tx: ::prost::bytes::Bytes, - #[prost(enumeration = "CheckTxType", tag = "2")] + #[prost(enumeration="CheckTxType", tag="2")] pub r#type: i32, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestDeliverTx { - #[prost(bytes = "bytes", tag = "1")] + #[prost(bytes="bytes", tag="1")] pub tx: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEndBlock { - #[prost(int64, tag = "1")] + #[prost(int64, tag="1")] pub height: i64, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestCommit {} +pub struct RequestCommit { +} /// lists available snapshots #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestListSnapshots {} +pub struct RequestListSnapshots { +} /// offers a snapshot to the application #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestOfferSnapshot { /// snapshot offered by peers - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub snapshot: ::core::option::Option, /// light client-verified app hash for snapshot height - #[prost(bytes = "bytes", tag = "2")] + #[prost(bytes="bytes", tag="2")] pub app_hash: ::prost::bytes::Bytes, } /// loads a snapshot chunk #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestLoadSnapshotChunk { - #[prost(uint64, tag = "1")] + #[prost(uint64, tag="1")] pub height: u64, - #[prost(uint32, tag = "2")] + #[prost(uint32, tag="2")] pub format: u32, - #[prost(uint32, tag = "3")] + #[prost(uint32, tag="3")] pub chunk: u32, } /// Applies a snapshot chunk #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestApplySnapshotChunk { - #[prost(uint32, tag = "1")] + #[prost(uint32, tag="1")] pub index: u32, - #[prost(bytes = "bytes", tag = "2")] + #[prost(bytes="bytes", tag="2")] pub chunk: ::prost::bytes::Bytes, - #[prost(string, tag = "3")] + #[prost(string, tag="3")] pub sender: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestPrepareProposal { /// the modified transactions cannot exceed this size. - #[prost(int64, tag = "1")] + #[prost(int64, tag="1")] pub max_tx_bytes: i64, /// txs is an array of transactions that will be included in a block, /// sent to the app for possible modifications. - #[prost(bytes = "vec", repeated, tag = "2")] - pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, - #[prost(message, optional, tag = "3")] + #[prost(bytes="bytes", repeated, tag="2")] + pub txs: ::prost::alloc::vec::Vec<::prost::bytes::Bytes>, + #[prost(message, optional, tag="3")] pub local_last_commit: ::core::option::Option, - #[prost(message, repeated, tag = "4")] + #[prost(message, repeated, tag="4")] pub misbehavior: ::prost::alloc::vec::Vec, - #[prost(int64, tag = "5")] + #[prost(int64, tag="5")] pub height: i64, - #[prost(message, optional, tag = "6")] - pub time: ::core::option::Option, - #[prost(bytes = "vec", tag = "7")] - pub next_validators_hash: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="6")] + pub time: ::core::option::Option, + #[prost(bytes="bytes", tag="7")] + pub next_validators_hash: ::prost::bytes::Bytes, /// address of the public key of the validator proposing the block. - #[prost(bytes = "vec", tag = "8")] - pub proposer_address: ::prost::alloc::vec::Vec, + #[prost(bytes="bytes", tag="8")] + pub proposer_address: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestProcessProposal { - #[prost(bytes = "vec", repeated, tag = "1")] - pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, - #[prost(message, optional, tag = "2")] + #[prost(bytes="bytes", repeated, tag="1")] + pub txs: ::prost::alloc::vec::Vec<::prost::bytes::Bytes>, + #[prost(message, optional, tag="2")] pub proposed_last_commit: ::core::option::Option, - #[prost(message, repeated, tag = "3")] + #[prost(message, repeated, tag="3")] pub misbehavior: ::prost::alloc::vec::Vec, /// hash is the merkle root hash of the fields of the proposed block. - #[prost(bytes = "vec", tag = "4")] - pub hash: ::prost::alloc::vec::Vec, - #[prost(int64, tag = "5")] + #[prost(bytes="bytes", tag="4")] + pub hash: ::prost::bytes::Bytes, + #[prost(int64, tag="5")] pub height: i64, - #[prost(message, optional, tag = "6")] - pub time: ::core::option::Option, - #[prost(bytes = "vec", tag = "7")] - pub next_validators_hash: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="6")] + pub time: ::core::option::Option, + #[prost(bytes="bytes", tag="7")] + pub next_validators_hash: ::prost::bytes::Bytes, /// address of the public key of the original proposer of the block. - #[prost(bytes = "vec", tag = "8")] - pub proposer_address: ::prost::alloc::vec::Vec, + #[prost(bytes="bytes", tag="8")] + pub proposer_address: ::prost::bytes::Bytes, } // ---------------------------------------- // Response types #[derive(Clone, PartialEq, ::prost::Message)] pub struct Response { - #[prost( - oneof = "response::Value", - tags = "1, 2, 3, 4, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18" - )] + #[prost(oneof="response::Value", tags="1, 2, 3, 4, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18")] pub value: ::core::option::Option, } /// Nested message and enum types in `Response`. pub mod response { #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag = "1")] + #[prost(message, tag="1")] Exception(super::ResponseException), - #[prost(message, tag = "2")] + #[prost(message, tag="2")] Echo(super::ResponseEcho), - #[prost(message, tag = "3")] + #[prost(message, tag="3")] Flush(super::ResponseFlush), - #[prost(message, tag = "4")] + #[prost(message, tag="4")] Info(super::ResponseInfo), - #[prost(message, tag = "6")] + #[prost(message, tag="6")] InitChain(super::ResponseInitChain), - #[prost(message, tag = "7")] + #[prost(message, tag="7")] Query(super::ResponseQuery), - #[prost(message, tag = "8")] + #[prost(message, tag="8")] BeginBlock(super::ResponseBeginBlock), - #[prost(message, tag = "9")] + #[prost(message, tag="9")] CheckTx(super::ResponseCheckTx), - #[prost(message, tag = "10")] + #[prost(message, tag="10")] DeliverTx(super::ResponseDeliverTx), - #[prost(message, tag = "11")] + #[prost(message, tag="11")] EndBlock(super::ResponseEndBlock), - #[prost(message, tag = "12")] + #[prost(message, tag="12")] Commit(super::ResponseCommit), - #[prost(message, tag = "13")] + #[prost(message, tag="13")] ListSnapshots(super::ResponseListSnapshots), - #[prost(message, tag = "14")] + #[prost(message, tag="14")] OfferSnapshot(super::ResponseOfferSnapshot), - #[prost(message, tag = "15")] + #[prost(message, tag="15")] LoadSnapshotChunk(super::ResponseLoadSnapshotChunk), - #[prost(message, tag = "16")] + #[prost(message, tag="16")] ApplySnapshotChunk(super::ResponseApplySnapshotChunk), - #[prost(message, tag = "17")] + #[prost(message, tag="17")] PrepareProposal(super::ResponsePrepareProposal), - #[prost(message, tag = "18")] + #[prost(message, tag="18")] ProcessProposal(super::ResponseProcessProposal), } } /// nondeterministic #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseException { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub error: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEcho { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub message: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] -pub struct ResponseFlush {} -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +pub struct ResponseFlush { +} +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseInfo { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] #[serde(default)] pub data: ::prost::alloc::string::String, - #[prost(string, tag = "2")] + #[prost(string, tag="2")] #[serde(default)] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag = "3")] + #[prost(uint64, tag="3")] #[serde(with = "crate::serializers::from_str", default)] pub app_version: u64, - #[prost(int64, tag = "4")] + #[prost(int64, tag="4")] #[serde(with = "crate::serializers::from_str", default)] pub last_block_height: i64, - #[prost(bytes = "bytes", tag = "5")] + #[prost(bytes="bytes", tag="5")] #[serde(default)] #[serde(skip_serializing_if = "bytes::Bytes::is_empty")] pub last_block_app_hash: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseInitChain { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag = "2")] + #[prost(message, repeated, tag="2")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes = "bytes", tag = "3")] + #[prost(bytes="bytes", tag="3")] pub app_hash: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseQuery { - #[prost(uint32, tag = "1")] + #[prost(uint32, tag="1")] pub code: u32, /// bytes data = 2; // use "value" instead. /// /// nondeterministic - #[prost(string, tag = "3")] + #[prost(string, tag="3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag = "4")] + #[prost(string, tag="4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag = "5")] + #[prost(int64, tag="5")] pub index: i64, - #[prost(bytes = "bytes", tag = "6")] + #[prost(bytes="bytes", tag="6")] pub key: ::prost::bytes::Bytes, - #[prost(bytes = "bytes", tag = "7")] + #[prost(bytes="bytes", tag="7")] pub value: ::prost::bytes::Bytes, - #[prost(message, optional, tag = "8")] + #[prost(message, optional, tag="8")] pub proof_ops: ::core::option::Option, - #[prost(int64, tag = "9")] + #[prost(int64, tag="9")] pub height: i64, - #[prost(string, tag = "10")] + #[prost(string, tag="10")] pub codespace: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseBeginBlock { - #[prost(message, repeated, tag = "1")] + #[prost(message, repeated, tag="1")] pub events: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCheckTx { - #[prost(uint32, tag = "1")] + #[prost(uint32, tag="1")] pub code: u32, - #[prost(bytes = "bytes", tag = "2")] + #[prost(bytes="bytes", tag="2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag = "3")] + #[prost(string, tag="3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag = "4")] + #[prost(string, tag="4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag = "5")] + #[prost(int64, tag="5")] pub gas_wanted: i64, - #[prost(int64, tag = "6")] + #[prost(int64, tag="6")] pub gas_used: i64, - #[prost(message, repeated, tag = "7")] + #[prost(message, repeated, tag="7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag = "8")] + #[prost(string, tag="8")] pub codespace: ::prost::alloc::string::String, - #[prost(string, tag = "9")] + #[prost(string, tag="9")] pub sender: ::prost::alloc::string::String, - #[prost(int64, tag = "10")] + #[prost(int64, tag="10")] pub priority: i64, /// mempool_error is set by Tendermint. /// ABCI applictions creating a ResponseCheckTX should not set mempool_error. - #[prost(string, tag = "11")] + #[prost(string, tag="11")] pub mempool_error: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseDeliverTx { - #[prost(uint32, tag = "1")] + #[prost(uint32, tag="1")] pub code: u32, - #[prost(bytes = "bytes", tag = "2")] + #[prost(bytes="bytes", tag="2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag = "3")] + #[prost(string, tag="3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag = "4")] + #[prost(string, tag="4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag = "5")] + #[prost(int64, tag="5")] pub gas_wanted: i64, - #[prost(int64, tag = "6")] + #[prost(int64, tag="6")] pub gas_used: i64, /// nondeterministic - #[prost(message, repeated, tag = "7")] + #[prost(message, repeated, tag="7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag = "8")] + #[prost(string, tag="8")] pub codespace: ::prost::alloc::string::String, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEndBlock { - #[prost(message, repeated, tag = "1")] + #[prost(message, repeated, tag="1")] pub validator_updates: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub consensus_param_updates: ::core::option::Option, - #[prost(message, repeated, tag = "3")] + #[prost(message, repeated, tag="3")] pub events: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCommit { /// reserve 1 - #[prost(bytes = "bytes", tag = "2")] + #[prost(bytes="bytes", tag="2")] pub data: ::prost::bytes::Bytes, - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] pub retain_height: i64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseListSnapshots { - #[prost(message, repeated, tag = "1")] + #[prost(message, repeated, tag="1")] pub snapshots: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseOfferSnapshot { - #[prost(enumeration = "response_offer_snapshot::Result", tag = "1")] + #[prost(enumeration="response_offer_snapshot::Result", tag="1")] pub result: i32, } /// Nested message and enum types in `ResponseOfferSnapshot`. @@ -439,18 +438,18 @@ pub mod response_offer_snapshot { } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseLoadSnapshotChunk { - #[prost(bytes = "bytes", tag = "1")] + #[prost(bytes="bytes", tag="1")] pub chunk: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseApplySnapshotChunk { - #[prost(enumeration = "response_apply_snapshot_chunk::Result", tag = "1")] + #[prost(enumeration="response_apply_snapshot_chunk::Result", tag="1")] pub result: i32, /// Chunks to refetch and reapply - #[prost(uint32, repeated, tag = "2")] + #[prost(uint32, repeated, tag="2")] pub refetch_chunks: ::prost::alloc::vec::Vec, /// Chunk senders to reject and ban - #[prost(string, repeated, tag = "3")] + #[prost(string, repeated, tag="3")] pub reject_senders: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// Nested message and enum types in `ResponseApplySnapshotChunk`. @@ -490,12 +489,12 @@ pub mod response_apply_snapshot_chunk { } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponsePrepareProposal { - #[prost(bytes = "vec", repeated, tag = "1")] - pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, + #[prost(bytes="bytes", repeated, tag="1")] + pub txs: ::prost::alloc::vec::Vec<::prost::bytes::Bytes>, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseProcessProposal { - #[prost(enumeration = "response_process_proposal::ProposalStatus", tag = "1")] + #[prost(enumeration="response_process_proposal::ProposalStatus", tag="1")] pub status: i32, } /// Nested message and enum types in `ResponseProcessProposal`. @@ -526,19 +525,19 @@ pub mod response_process_proposal { #[derive(Clone, PartialEq, ::prost::Message)] pub struct CommitInfo { - #[prost(int32, tag = "1")] + #[prost(int32, tag="1")] pub round: i32, - #[prost(message, repeated, tag = "2")] + #[prost(message, repeated, tag="2")] pub votes: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ExtendedCommitInfo { /// The round at which the block proposer decided in the previous height. - #[prost(int32, tag = "1")] + #[prost(int32, tag="1")] pub round: i32, /// List of validators' addresses in the last validator set with their voting /// information, including vote extensions. - #[prost(message, repeated, tag = "2")] + #[prost(message, repeated, tag="2")] pub votes: ::prost::alloc::vec::Vec, } /// Event allows application developers to attach additional information to @@ -546,20 +545,20 @@ pub struct ExtendedCommitInfo { /// Later, transactions may be queried using these events. #[derive(Clone, PartialEq, ::prost::Message)] pub struct Event { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub r#type: ::prost::alloc::string::String, - #[prost(message, repeated, tag = "2")] + #[prost(message, repeated, tag="2")] pub attributes: ::prost::alloc::vec::Vec, } /// EventAttribute is a single key-value pair, associated with an event. #[derive(Clone, PartialEq, ::prost::Message)] pub struct EventAttribute { - #[prost(string, tag = "1")] + #[prost(string, tag="1")] pub key: ::prost::alloc::string::String, - #[prost(string, tag = "2")] + #[prost(string, tag="2")] pub value: ::prost::alloc::string::String, /// nondeterministic - #[prost(bool, tag = "3")] + #[prost(bool, tag="3")] pub index: bool, } /// TxResult contains results of executing the transaction. @@ -567,13 +566,13 @@ pub struct EventAttribute { /// One usage is indexing transaction results. #[derive(Clone, PartialEq, ::prost::Message)] pub struct TxResult { - #[prost(int64, tag = "1")] + #[prost(int64, tag="1")] pub height: i64, - #[prost(uint32, tag = "2")] + #[prost(uint32, tag="2")] pub index: u32, - #[prost(bytes = "bytes", tag = "3")] + #[prost(bytes="bytes", tag="3")] pub tx: ::prost::bytes::Bytes, - #[prost(message, optional, tag = "4")] + #[prost(message, optional, tag="4")] pub result: ::core::option::Option, } // ---------------------------------------- @@ -583,57 +582,57 @@ pub struct TxResult { #[derive(Clone, PartialEq, ::prost::Message)] pub struct Validator { /// The first 20 bytes of SHA256(public key) - #[prost(bytes = "bytes", tag = "1")] + #[prost(bytes="bytes", tag="1")] pub address: ::prost::bytes::Bytes, /// PubKey pub_key = 2 \[(gogoproto.nullable)=false\]; /// /// The voting power - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] pub power: i64, } /// ValidatorUpdate #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorUpdate { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] pub power: i64, } /// VoteInfo #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteInfo { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub validator: ::core::option::Option, - #[prost(bool, tag = "2")] + #[prost(bool, tag="2")] pub signed_last_block: bool, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct ExtendedVoteInfo { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub validator: ::core::option::Option, - #[prost(bool, tag = "2")] + #[prost(bool, tag="2")] pub signed_last_block: bool, /// Reserved for future use - #[prost(bytes = "vec", tag = "3")] - pub vote_extension: ::prost::alloc::vec::Vec, + #[prost(bytes="bytes", tag="3")] + pub vote_extension: ::prost::bytes::Bytes, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Misbehavior { - #[prost(enumeration = "MisbehaviorType", tag = "1")] + #[prost(enumeration="MisbehaviorType", tag="1")] pub r#type: i32, /// The offending validator - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub validator: ::core::option::Option, /// The height when the offense occurred - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] pub height: i64, /// The corresponding time where the offense occurred - #[prost(message, optional, tag = "4")] - pub time: ::core::option::Option, + #[prost(message, optional, tag="4")] + pub time: ::core::option::Option, /// Total voting power of the validator set in case the ABCI application does /// not store historical validators. /// - #[prost(int64, tag = "5")] + #[prost(int64, tag="5")] pub total_voting_power: i64, } // ---------------------------------------- @@ -642,19 +641,19 @@ pub struct Misbehavior { #[derive(Clone, PartialEq, ::prost::Message)] pub struct Snapshot { /// The height at which the snapshot was taken - #[prost(uint64, tag = "1")] + #[prost(uint64, tag="1")] pub height: u64, /// The application-specific snapshot format - #[prost(uint32, tag = "2")] + #[prost(uint32, tag="2")] pub format: u32, /// Number of chunks in the snapshot - #[prost(uint32, tag = "3")] + #[prost(uint32, tag="3")] pub chunks: u32, /// Arbitrary snapshot hash, equal only if identical - #[prost(bytes = "bytes", tag = "4")] + #[prost(bytes="bytes", tag="4")] pub hash: ::prost::bytes::Bytes, /// Arbitrary application metadata - #[prost(bytes = "bytes", tag = "5")] + #[prost(bytes="bytes", tag="5")] pub metadata: ::prost::bytes::Bytes, } #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] diff --git a/proto/src/prost/v0_37/tendermint.blocksync.rs b/proto/src/prost/v0_37/tendermint.blocksync.rs new file mode 100644 index 000000000..492aa692e --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.blocksync.rs @@ -0,0 +1,51 @@ +/// BlockRequest requests a block for a specific height +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockRequest { + #[prost(int64, tag="1")] + pub height: i64, +} +/// NoBlockResponse informs the node that the peer does not have block at the requested height +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct NoBlockResponse { + #[prost(int64, tag="1")] + pub height: i64, +} +/// BlockResponse returns block to the requested +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockResponse { + #[prost(message, optional, tag="1")] + pub block: ::core::option::Option, +} +/// StatusRequest requests the status of a peer. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct StatusRequest { +} +/// StatusResponse is a peer response to inform their status. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct StatusResponse { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int64, tag="2")] + pub base: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Message { + #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Message`. +pub mod message { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + BlockRequest(super::BlockRequest), + #[prost(message, tag="2")] + NoBlockResponse(super::NoBlockResponse), + #[prost(message, tag="3")] + BlockResponse(super::BlockResponse), + #[prost(message, tag="4")] + StatusRequest(super::StatusRequest), + #[prost(message, tag="5")] + StatusResponse(super::StatusResponse), + } +} diff --git a/proto/src/prost/v0_37/tendermint.consensus.rs b/proto/src/prost/v0_37/tendermint.consensus.rs new file mode 100644 index 000000000..6f3fe8624 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.consensus.rs @@ -0,0 +1,184 @@ +/// NewRoundStep is sent for every step taken in the ConsensusState. +/// For every height/round/step transition +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct NewRoundStep { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(uint32, tag="3")] + pub step: u32, + #[prost(int64, tag="4")] + pub seconds_since_start_time: i64, + #[prost(int32, tag="5")] + pub last_commit_round: i32, +} +/// NewValidBlock is sent when a validator observes a valid block B in some round r, +/// i.e., there is a Proposal for block B and 2/3+ prevotes for the block B in the round r. +/// In case the block is also committed, then IsCommit flag is set to true. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct NewValidBlock { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(message, optional, tag="3")] + pub block_part_set_header: ::core::option::Option, + #[prost(message, optional, tag="4")] + pub block_parts: ::core::option::Option, + #[prost(bool, tag="5")] + pub is_commit: bool, +} +/// Proposal is sent when a new block is proposed. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Proposal { + #[prost(message, optional, tag="1")] + pub proposal: ::core::option::Option, +} +/// ProposalPOL is sent when a previous proposal is re-proposed. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ProposalPol { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub proposal_pol_round: i32, + #[prost(message, optional, tag="3")] + pub proposal_pol: ::core::option::Option, +} +/// BlockPart is sent when gossipping a piece of the proposed block. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockPart { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(message, optional, tag="3")] + pub part: ::core::option::Option, +} +/// Vote is sent when voting for a proposal (or lack thereof). +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Vote { + #[prost(message, optional, tag="1")] + pub vote: ::core::option::Option, +} +/// HasVote is sent to indicate that a particular vote has been received. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct HasVote { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(enumeration="super::types::SignedMsgType", tag="3")] + pub r#type: i32, + #[prost(int32, tag="4")] + pub index: i32, +} +/// VoteSetMaj23 is sent to indicate that a given BlockID has seen +2/3 votes. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct VoteSetMaj23 { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(enumeration="super::types::SignedMsgType", tag="3")] + pub r#type: i32, + #[prost(message, optional, tag="4")] + pub block_id: ::core::option::Option, +} +/// VoteSetBits is sent to communicate the bit-array of votes seen for the BlockID. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct VoteSetBits { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(enumeration="super::types::SignedMsgType", tag="3")] + pub r#type: i32, + #[prost(message, optional, tag="4")] + pub block_id: ::core::option::Option, + #[prost(message, optional, tag="5")] + pub votes: ::core::option::Option, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Message { + #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5, 6, 7, 8, 9")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Message`. +pub mod message { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + NewRoundStep(super::NewRoundStep), + #[prost(message, tag="2")] + NewValidBlock(super::NewValidBlock), + #[prost(message, tag="3")] + Proposal(super::Proposal), + #[prost(message, tag="4")] + ProposalPol(super::ProposalPol), + #[prost(message, tag="5")] + BlockPart(super::BlockPart), + #[prost(message, tag="6")] + Vote(super::Vote), + #[prost(message, tag="7")] + HasVote(super::HasVote), + #[prost(message, tag="8")] + VoteSetMaj23(super::VoteSetMaj23), + #[prost(message, tag="9")] + VoteSetBits(super::VoteSetBits), + } +} +/// MsgInfo are msgs from the reactor which may update the state +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct MsgInfo { + #[prost(message, optional, tag="1")] + pub msg: ::core::option::Option, + #[prost(string, tag="2")] + pub peer_id: ::prost::alloc::string::String, +} +/// TimeoutInfo internally generated messages which may update the state +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct TimeoutInfo { + #[prost(message, optional, tag="1")] + pub duration: ::core::option::Option, + #[prost(int64, tag="2")] + pub height: i64, + #[prost(int32, tag="3")] + pub round: i32, + #[prost(uint32, tag="4")] + pub step: u32, +} +/// EndHeight marks the end of the given height inside WAL. +/// @internal used by scripts/wal2json util. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct EndHeight { + #[prost(int64, tag="1")] + pub height: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct WalMessage { + #[prost(oneof="wal_message::Sum", tags="1, 2, 3, 4")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `WALMessage`. +pub mod wal_message { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + EventDataRoundState(super::super::types::EventDataRoundState), + #[prost(message, tag="2")] + MsgInfo(super::MsgInfo), + #[prost(message, tag="3")] + TimeoutInfo(super::TimeoutInfo), + #[prost(message, tag="4")] + EndHeight(super::EndHeight), + } +} +/// TimedWALMessage wraps WALMessage and adds Time for debugging purposes. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct TimedWalMessage { + #[prost(message, optional, tag="1")] + pub time: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub msg: ::core::option::Option, +} diff --git a/proto/src/prost/v0_37/tendermint.crypto.rs b/proto/src/prost/v0_37/tendermint.crypto.rs new file mode 100644 index 000000000..0fac07973 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.crypto.rs @@ -0,0 +1,73 @@ +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Proof { + #[prost(int64, tag="1")] + #[serde(with = "crate::serializers::from_str")] + pub total: i64, + #[prost(int64, tag="2")] + #[serde(with = "crate::serializers::from_str")] + pub index: i64, + #[prost(bytes="vec", tag="3")] + #[serde(with = "crate::serializers::bytes::base64string")] + pub leaf_hash: ::prost::alloc::vec::Vec, + #[prost(bytes="vec", repeated, tag="4")] + #[serde(with = "crate::serializers::bytes::vec_base64string")] + pub aunts: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ValueOp { + /// Encoded in ProofOp.Key. + #[prost(bytes="vec", tag="1")] + pub key: ::prost::alloc::vec::Vec, + /// To encode in ProofOp.Data + #[prost(message, optional, tag="2")] + pub proof: ::core::option::Option, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct DominoOp { + #[prost(string, tag="1")] + pub key: ::prost::alloc::string::String, + #[prost(string, tag="2")] + pub input: ::prost::alloc::string::String, + #[prost(string, tag="3")] + pub output: ::prost::alloc::string::String, +} +/// ProofOp defines an operation used for calculating Merkle root +/// The data could be arbitrary format, providing nessecary data +/// for example neighbouring node hash +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ProofOp { + #[prost(string, tag="1")] + pub r#type: ::prost::alloc::string::String, + #[prost(bytes="vec", tag="2")] + pub key: ::prost::alloc::vec::Vec, + #[prost(bytes="vec", tag="3")] + pub data: ::prost::alloc::vec::Vec, +} +/// ProofOps is Merkle proof defined by the list of ProofOps +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ProofOps { + #[prost(message, repeated, tag="1")] + pub ops: ::prost::alloc::vec::Vec, +} +/// PublicKey defines the keys available for use with Tendermint Validators +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PublicKey { + #[prost(oneof="public_key::Sum", tags="1, 2")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `PublicKey`. +pub mod public_key { + #[derive(::serde::Deserialize, ::serde::Serialize)] + #[serde(tag = "type", content = "value")] + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(bytes, tag="1")] + #[serde(rename = "tendermint/PubKeyEd25519", with = "crate::serializers::bytes::base64string")] + Ed25519(::prost::alloc::vec::Vec), + #[prost(bytes, tag="2")] + #[serde(rename = "tendermint/PubKeySecp256k1", with = "crate::serializers::bytes::base64string")] + Secp256k1(::prost::alloc::vec::Vec), + } +} diff --git a/proto/src/prost/v0_37/tendermint.libs.bits.rs b/proto/src/prost/v0_37/tendermint.libs.bits.rs new file mode 100644 index 000000000..47eee3773 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.libs.bits.rs @@ -0,0 +1,8 @@ +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BitArray { + #[prost(int64, tag="1")] + pub bits: i64, + #[prost(uint64, repeated, tag="2")] + pub elems: ::prost::alloc::vec::Vec, +} diff --git a/proto/src/prost/v0_37/tendermint.mempool.rs b/proto/src/prost/v0_37/tendermint.mempool.rs new file mode 100644 index 000000000..af22801ba --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.mempool.rs @@ -0,0 +1,18 @@ +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Txs { + #[prost(bytes="vec", repeated, tag="1")] + pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Message { + #[prost(oneof="message::Sum", tags="1")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Message`. +pub mod message { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + Txs(super::Txs), + } +} diff --git a/proto/src/prost/v0_37/tendermint.p2p.rs b/proto/src/prost/v0_37/tendermint.p2p.rs new file mode 100644 index 000000000..4b81d0be0 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.p2p.rs @@ -0,0 +1,106 @@ +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PacketPing { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PacketPong { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PacketMsg { + #[prost(int32, tag="1")] + pub channel_id: i32, + #[prost(bool, tag="2")] + pub eof: bool, + #[prost(bytes="vec", tag="3")] + pub data: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Packet { + #[prost(oneof="packet::Sum", tags="1, 2, 3")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Packet`. +pub mod packet { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + PacketPing(super::PacketPing), + #[prost(message, tag="2")] + PacketPong(super::PacketPong), + #[prost(message, tag="3")] + PacketMsg(super::PacketMsg), + } +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct AuthSigMessage { + #[prost(message, optional, tag="1")] + pub pub_key: ::core::option::Option, + #[prost(bytes="vec", tag="2")] + pub sig: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct NetAddress { + #[prost(string, tag="1")] + pub id: ::prost::alloc::string::String, + #[prost(string, tag="2")] + pub ip: ::prost::alloc::string::String, + #[prost(uint32, tag="3")] + pub port: u32, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ProtocolVersion { + #[prost(uint64, tag="1")] + pub p2p: u64, + #[prost(uint64, tag="2")] + pub block: u64, + #[prost(uint64, tag="3")] + pub app: u64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct DefaultNodeInfo { + #[prost(message, optional, tag="1")] + pub protocol_version: ::core::option::Option, + #[prost(string, tag="2")] + pub default_node_id: ::prost::alloc::string::String, + #[prost(string, tag="3")] + pub listen_addr: ::prost::alloc::string::String, + #[prost(string, tag="4")] + pub network: ::prost::alloc::string::String, + #[prost(string, tag="5")] + pub version: ::prost::alloc::string::String, + #[prost(bytes="vec", tag="6")] + pub channels: ::prost::alloc::vec::Vec, + #[prost(string, tag="7")] + pub moniker: ::prost::alloc::string::String, + #[prost(message, optional, tag="8")] + pub other: ::core::option::Option, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct DefaultNodeInfoOther { + #[prost(string, tag="1")] + pub tx_index: ::prost::alloc::string::String, + #[prost(string, tag="2")] + pub rpc_address: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PexRequest { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PexAddrs { + #[prost(message, repeated, tag="1")] + pub addrs: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Message { + #[prost(oneof="message::Sum", tags="1, 2")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Message`. +pub mod message { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + PexRequest(super::PexRequest), + #[prost(message, tag="2")] + PexAddrs(super::PexAddrs), + } +} diff --git a/proto/src/prost/v0_37/tendermint.privval.rs b/proto/src/prost/v0_37/tendermint.privval.rs new file mode 100644 index 000000000..892a10bbf --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.privval.rs @@ -0,0 +1,114 @@ +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RemoteSignerError { + #[prost(int32, tag="1")] + pub code: i32, + #[prost(string, tag="2")] + pub description: ::prost::alloc::string::String, +} +/// PubKeyRequest requests the consensus public key from the remote signer. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PubKeyRequest { + #[prost(string, tag="1")] + pub chain_id: ::prost::alloc::string::String, +} +/// PubKeyResponse is a response message containing the public key. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PubKeyResponse { + #[prost(message, optional, tag="1")] + pub pub_key: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub error: ::core::option::Option, +} +/// SignVoteRequest is a request to sign a vote +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SignVoteRequest { + #[prost(message, optional, tag="1")] + pub vote: ::core::option::Option, + #[prost(string, tag="2")] + pub chain_id: ::prost::alloc::string::String, +} +/// SignedVoteResponse is a response containing a signed vote or an error +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SignedVoteResponse { + #[prost(message, optional, tag="1")] + pub vote: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub error: ::core::option::Option, +} +/// SignProposalRequest is a request to sign a proposal +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SignProposalRequest { + #[prost(message, optional, tag="1")] + pub proposal: ::core::option::Option, + #[prost(string, tag="2")] + pub chain_id: ::prost::alloc::string::String, +} +/// SignedProposalResponse is response containing a signed proposal or an error +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SignedProposalResponse { + #[prost(message, optional, tag="1")] + pub proposal: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub error: ::core::option::Option, +} +/// PingRequest is a request to confirm that the connection is alive. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PingRequest { +} +/// PingResponse is a response to confirm that the connection is alive. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct PingResponse { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Message { + #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5, 6, 7, 8")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Message`. +pub mod message { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + PubKeyRequest(super::PubKeyRequest), + #[prost(message, tag="2")] + PubKeyResponse(super::PubKeyResponse), + #[prost(message, tag="3")] + SignVoteRequest(super::SignVoteRequest), + #[prost(message, tag="4")] + SignedVoteResponse(super::SignedVoteResponse), + #[prost(message, tag="5")] + SignProposalRequest(super::SignProposalRequest), + #[prost(message, tag="6")] + SignedProposalResponse(super::SignedProposalResponse), + #[prost(message, tag="7")] + PingRequest(super::PingRequest), + #[prost(message, tag="8")] + PingResponse(super::PingResponse), + } +} +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] +#[repr(i32)] +pub enum Errors { + Unknown = 0, + UnexpectedResponse = 1, + NoConnection = 2, + ConnectionTimeout = 3, + ReadTimeout = 4, + WriteTimeout = 5, +} +impl Errors { + /// String value of the enum field names used in the ProtoBuf definition. + /// + /// The values are not transformed in any way and thus are considered stable + /// (if the ProtoBuf definition does not change) and safe for programmatic use. + pub fn as_str_name(&self) -> &'static str { + match self { + Errors::Unknown => "ERRORS_UNKNOWN", + Errors::UnexpectedResponse => "ERRORS_UNEXPECTED_RESPONSE", + Errors::NoConnection => "ERRORS_NO_CONNECTION", + Errors::ConnectionTimeout => "ERRORS_CONNECTION_TIMEOUT", + Errors::ReadTimeout => "ERRORS_READ_TIMEOUT", + Errors::WriteTimeout => "ERRORS_WRITE_TIMEOUT", + } + } +} diff --git a/proto/src/prost/v0_37/tendermint.rpc.grpc.rs b/proto/src/prost/v0_37/tendermint.rpc.grpc.rs new file mode 100644 index 000000000..4739bccac --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.rpc.grpc.rs @@ -0,0 +1,24 @@ +// ---------------------------------------- +// Request types + +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestPing { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct RequestBroadcastTx { + #[prost(bytes="vec", tag="1")] + pub tx: ::prost::alloc::vec::Vec, +} +// ---------------------------------------- +// Response types + +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponsePing { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ResponseBroadcastTx { + #[prost(message, optional, tag="1")] + pub check_tx: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub deliver_tx: ::core::option::Option, +} diff --git a/proto/src/prost/v0_37/tendermint.state.rs b/proto/src/prost/v0_37/tendermint.state.rs new file mode 100644 index 000000000..c996b31a5 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.state.rs @@ -0,0 +1,85 @@ +/// ABCIResponses retains the responses +/// of the various ABCI calls during block processing. +/// It is persisted to disk for each height before calling Commit. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct AbciResponses { + #[prost(message, repeated, tag="1")] + pub deliver_txs: ::prost::alloc::vec::Vec, + #[prost(message, optional, tag="2")] + pub end_block: ::core::option::Option, + #[prost(message, optional, tag="3")] + pub begin_block: ::core::option::Option, +} +/// ValidatorsInfo represents the latest validator set, or the last height it changed +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ValidatorsInfo { + #[prost(message, optional, tag="1")] + pub validator_set: ::core::option::Option, + #[prost(int64, tag="2")] + pub last_height_changed: i64, +} +/// ConsensusParamsInfo represents the latest consensus params, or the last height it changed +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ConsensusParamsInfo { + #[prost(message, optional, tag="1")] + pub consensus_params: ::core::option::Option, + #[prost(int64, tag="2")] + pub last_height_changed: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct AbciResponsesInfo { + #[prost(message, optional, tag="1")] + pub abci_responses: ::core::option::Option, + #[prost(int64, tag="2")] + pub height: i64, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Version { + #[prost(message, optional, tag="1")] + pub consensus: ::core::option::Option, + #[prost(string, tag="2")] + pub software: ::prost::alloc::string::String, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct State { + #[prost(message, optional, tag="1")] + pub version: ::core::option::Option, + /// immutable + #[prost(string, tag="2")] + pub chain_id: ::prost::alloc::string::String, + #[prost(int64, tag="14")] + pub initial_height: i64, + /// LastBlockHeight=0 at genesis (ie. block(H=0) does not exist) + #[prost(int64, tag="3")] + pub last_block_height: i64, + #[prost(message, optional, tag="4")] + pub last_block_id: ::core::option::Option, + #[prost(message, optional, tag="5")] + pub last_block_time: ::core::option::Option, + /// LastValidators is used to validate block.LastCommit. + /// Validators are persisted to the database separately every time they change, + /// so we can query for historical validator sets. + /// Note that if s.LastBlockHeight causes a valset change, + /// we set s.LastHeightValidatorsChanged = s.LastBlockHeight + 1 + 1 + /// Extra +1 due to nextValSet delay. + #[prost(message, optional, tag="6")] + pub next_validators: ::core::option::Option, + #[prost(message, optional, tag="7")] + pub validators: ::core::option::Option, + #[prost(message, optional, tag="8")] + pub last_validators: ::core::option::Option, + #[prost(int64, tag="9")] + pub last_height_validators_changed: i64, + /// Consensus parameters used for validating blocks. + /// Changes returned by EndBlock and updated after Commit. + #[prost(message, optional, tag="10")] + pub consensus_params: ::core::option::Option, + #[prost(int64, tag="11")] + pub last_height_consensus_params_changed: i64, + /// Merkle root of the results from executing prev block + #[prost(bytes="vec", tag="12")] + pub last_results_hash: ::prost::alloc::vec::Vec, + /// the latest AppHash we've received from calling abci.Commit() + #[prost(bytes="vec", tag="13")] + pub app_hash: ::prost::alloc::vec::Vec, +} diff --git a/proto/src/prost/v0_37/tendermint.statesync.rs b/proto/src/prost/v0_37/tendermint.statesync.rs new file mode 100644 index 000000000..593bd0222 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.statesync.rs @@ -0,0 +1,57 @@ +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Message { + #[prost(oneof="message::Sum", tags="1, 2, 3, 4")] + pub sum: ::core::option::Option, +} +/// Nested message and enum types in `Message`. +pub mod message { + #[derive(Clone, PartialEq, ::prost::Oneof)] + pub enum Sum { + #[prost(message, tag="1")] + SnapshotsRequest(super::SnapshotsRequest), + #[prost(message, tag="2")] + SnapshotsResponse(super::SnapshotsResponse), + #[prost(message, tag="3")] + ChunkRequest(super::ChunkRequest), + #[prost(message, tag="4")] + ChunkResponse(super::ChunkResponse), + } +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SnapshotsRequest { +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct SnapshotsResponse { + #[prost(uint64, tag="1")] + pub height: u64, + #[prost(uint32, tag="2")] + pub format: u32, + #[prost(uint32, tag="3")] + pub chunks: u32, + #[prost(bytes="vec", tag="4")] + pub hash: ::prost::alloc::vec::Vec, + #[prost(bytes="vec", tag="5")] + pub metadata: ::prost::alloc::vec::Vec, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ChunkRequest { + #[prost(uint64, tag="1")] + pub height: u64, + #[prost(uint32, tag="2")] + pub format: u32, + #[prost(uint32, tag="3")] + pub index: u32, +} +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct ChunkResponse { + #[prost(uint64, tag="1")] + pub height: u64, + #[prost(uint32, tag="2")] + pub format: u32, + #[prost(uint32, tag="3")] + pub index: u32, + #[prost(bytes="vec", tag="4")] + pub chunk: ::prost::alloc::vec::Vec, + #[prost(bool, tag="5")] + pub missing: bool, +} diff --git a/proto/src/prost/v0_37/tendermint.store.rs b/proto/src/prost/v0_37/tendermint.store.rs new file mode 100644 index 000000000..a4c2799d9 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.store.rs @@ -0,0 +1,7 @@ +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct BlockStoreState { + #[prost(int64, tag="1")] + pub base: i64, + #[prost(int64, tag="2")] + pub height: i64, +} diff --git a/proto/src/prost/tendermint.types.rs b/proto/src/prost/v0_37/tendermint.types.rs similarity index 58% rename from proto/src/prost/tendermint.types.rs rename to proto/src/prost/v0_37/tendermint.types.rs index b74c73279..7b205cede 100644 --- a/proto/src/prost/tendermint.types.rs +++ b/proto/src/prost/v0_37/tendermint.types.rs @@ -1,259 +1,261 @@ -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorSet { - #[prost(message, repeated, tag = "1")] + #[prost(message, repeated, tag="1")] pub validators: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub proposer: ::core::option::Option, - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] pub total_voting_power: i64, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct Validator { - #[prost(bytes = "vec", tag = "1")] + #[prost(bytes="vec", tag="1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub pub_key: ::core::option::Option, - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] #[serde(alias = "power", with = "crate::serializers::from_str")] pub voting_power: i64, - #[prost(int64, tag = "4")] + #[prost(int64, tag="4")] #[serde(with = "crate::serializers::from_str", default)] pub proposer_priority: i64, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct SimpleValidator { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] pub voting_power: i64, } /// PartsetHeader -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct PartSetHeader { - #[prost(uint32, tag = "1")] + #[prost(uint32, tag="1")] #[serde(with = "crate::serializers::part_set_header_total")] pub total: u32, - #[prost(bytes = "vec", tag = "2")] + #[prost(bytes="vec", tag="2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Part { - #[prost(uint32, tag = "1")] + #[prost(uint32, tag="1")] pub index: u32, - #[prost(bytes = "vec", tag = "2")] + #[prost(bytes="vec", tag="2")] pub bytes: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub proof: ::core::option::Option, } /// BlockID -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockId { - #[prost(bytes = "vec", tag = "1")] + #[prost(bytes="vec", tag="1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } // -------------------------------- /// Header defines the structure of a Tendermint block header. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct Header { /// basic block info - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub version: ::core::option::Option, - #[prost(string, tag = "2")] + #[prost(string, tag="2")] pub chain_id: ::prost::alloc::string::String, - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(message, optional, tag = "4")] + #[prost(message, optional, tag="4")] #[serde(with = "crate::serializers::optional")] - pub time: ::core::option::Option, + pub time: ::core::option::Option, /// prev block info - #[prost(message, optional, tag = "5")] + #[prost(message, optional, tag="5")] pub last_block_id: ::core::option::Option, /// hashes of block data /// /// commit from validators from the last block - #[prost(bytes = "vec", tag = "6")] + #[prost(bytes="vec", tag="6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_commit_hash: ::prost::alloc::vec::Vec, /// transactions - #[prost(bytes = "vec", tag = "7")] + #[prost(bytes="vec", tag="7")] #[serde(with = "crate::serializers::bytes::hexstring")] pub data_hash: ::prost::alloc::vec::Vec, /// hashes from the app output from the prev block /// /// validators for the current block - #[prost(bytes = "vec", tag = "8")] + #[prost(bytes="vec", tag="8")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validators_hash: ::prost::alloc::vec::Vec, /// validators for the next block - #[prost(bytes = "vec", tag = "9")] + #[prost(bytes="vec", tag="9")] #[serde(with = "crate::serializers::bytes::hexstring")] pub next_validators_hash: ::prost::alloc::vec::Vec, /// consensus params for current block - #[prost(bytes = "vec", tag = "10")] + #[prost(bytes="vec", tag="10")] #[serde(with = "crate::serializers::bytes::hexstring")] pub consensus_hash: ::prost::alloc::vec::Vec, /// state after txs from the previous block - #[prost(bytes = "vec", tag = "11")] + #[prost(bytes="vec", tag="11")] #[serde(with = "crate::serializers::bytes::hexstring")] pub app_hash: ::prost::alloc::vec::Vec, /// root hash of all results from the txs from the previous block - #[prost(bytes = "vec", tag = "12")] + #[prost(bytes="vec", tag="12")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_results_hash: ::prost::alloc::vec::Vec, /// consensus info /// /// evidence included in the block - #[prost(bytes = "vec", tag = "13")] + #[prost(bytes="vec", tag="13")] #[serde(with = "crate::serializers::bytes::hexstring")] pub evidence_hash: ::prost::alloc::vec::Vec, /// original proposer of the block - #[prost(bytes = "vec", tag = "14")] + #[prost(bytes="vec", tag="14")] #[serde(with = "crate::serializers::bytes::hexstring")] pub proposer_address: ::prost::alloc::vec::Vec, } /// Data contains the set of transactions included in the block -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct Data { /// Txs that will be applied by state @ block.Height+1. /// NOTE: not all txs here are valid. We're just agreeing on the order first. /// This means that block.AppHash does not include these txs. - #[prost(bytes = "vec", repeated, tag = "1")] + #[prost(bytes="vec", repeated, tag="1")] #[serde(with = "crate::serializers::txs")] pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } /// Vote represents a prevote, precommit, or commit vote from validators for /// consensus. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct Vote { - #[prost(enumeration = "SignedMsgType", tag = "1")] + #[prost(enumeration="SignedMsgType", tag="1")] pub r#type: i32, - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag = "3")] + #[prost(int32, tag="3")] pub round: i32, /// zero if vote is nil. - #[prost(message, optional, tag = "4")] + #[prost(message, optional, tag="4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag = "5")] + #[prost(message, optional, tag="5")] #[serde(with = "crate::serializers::optional")] - pub timestamp: ::core::option::Option, - #[prost(bytes = "vec", tag = "6")] + pub timestamp: ::core::option::Option, + #[prost(bytes="vec", tag="6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(int32, tag = "7")] + #[prost(int32, tag="7")] pub validator_index: i32, - #[prost(bytes = "vec", tag = "8")] + #[prost(bytes="vec", tag="8")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } /// Commit contains the evidence that a block was committed by a set of validators. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct Commit { - #[prost(int64, tag = "1")] + #[prost(int64, tag="1")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag = "2")] + #[prost(int32, tag="2")] pub round: i32, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub block_id: ::core::option::Option, - #[prost(message, repeated, tag = "4")] + #[prost(message, repeated, tag="4")] #[serde(with = "crate::serializers::nullable")] pub signatures: ::prost::alloc::vec::Vec, } /// CommitSig is a part of the Vote included in a Commit. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct CommitSig { - #[prost(enumeration = "BlockIdFlag", tag = "1")] + #[prost(enumeration="BlockIdFlag", tag="1")] pub block_id_flag: i32, - #[prost(bytes = "vec", tag = "2")] + #[prost(bytes="vec", tag="2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] #[serde(with = "crate::serializers::optional")] - pub timestamp: ::core::option::Option, - #[prost(bytes = "vec", tag = "4")] + pub timestamp: ::core::option::Option, + #[prost(bytes="vec", tag="4")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proposal { - #[prost(enumeration = "SignedMsgType", tag = "1")] + #[prost(enumeration="SignedMsgType", tag="1")] pub r#type: i32, - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] pub height: i64, - #[prost(int32, tag = "3")] + #[prost(int32, tag="3")] pub round: i32, - #[prost(int32, tag = "4")] + #[prost(int32, tag="4")] pub pol_round: i32, - #[prost(message, optional, tag = "5")] + #[prost(message, optional, tag="5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag = "6")] - pub timestamp: ::core::option::Option, - #[prost(bytes = "vec", tag = "7")] + #[prost(message, optional, tag="6")] + pub timestamp: ::core::option::Option, + #[prost(bytes="vec", tag="7")] pub signature: ::prost::alloc::vec::Vec, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct SignedHeader { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub commit: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct LightBlock { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub signed_header: ::core::option::Option, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub validator_set: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockMeta { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub block_id: ::core::option::Option, - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] #[serde(with = "crate::serializers::from_str")] pub block_size: i64, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub header: ::core::option::Option
, - #[prost(int64, tag = "4")] + #[prost(int64, tag="4")] #[serde(with = "crate::serializers::from_str")] pub num_txs: i64, } /// TxProof represents a Merkle proof of the presence of a transaction in the Merkle tree. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct TxProof { - #[prost(bytes = "vec", tag = "1")] + #[prost(bytes="vec", tag="1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub root_hash: ::prost::alloc::vec::Vec, - #[prost(bytes = "vec", tag = "2")] + #[prost(bytes="vec", tag="2")] #[serde(with = "crate::serializers::bytes::base64string")] pub data: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub proof: ::core::option::Option, } /// BlockIdFlag indicates which BlcokID the signature is for -#[derive( - ::num_derive::FromPrimitive, - ::num_derive::ToPrimitive, - Clone, - Copy, - Debug, - PartialEq, - Eq, - Hash, - PartialOrd, - Ord, - ::prost::Enumeration, -)] +#[derive(::num_derive::FromPrimitive, ::num_derive::ToPrimitive)] +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] #[repr(i32)] pub enum BlockIdFlag { Unknown = 0, @@ -304,13 +306,13 @@ impl SignedMsgType { /// validity of blocks. #[derive(Clone, PartialEq, ::prost::Message)] pub struct ConsensusParams { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub block: ::core::option::Option, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub validator: ::core::option::Option, - #[prost(message, optional, tag = "4")] + #[prost(message, optional, tag="4")] pub version: ::core::option::Option, } /// BlockParams contains limits on the block size. @@ -318,33 +320,34 @@ pub struct ConsensusParams { pub struct BlockParams { /// Max block size, in bytes. /// Note: must be greater than 0 - #[prost(int64, tag = "1")] + #[prost(int64, tag="1")] pub max_bytes: i64, /// Max gas per block. /// Note: must be greater or equal to -1 - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] pub max_gas: i64, } /// EvidenceParams determine how we handle evidence of malfeasance. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct EvidenceParams { /// Max age of evidence, in blocks. /// /// The basic formula for calculating this is: MaxAgeDuration / {average block /// time}. - #[prost(int64, tag = "1")] + #[prost(int64, tag="1")] pub max_age_num_blocks: i64, /// Max age of evidence, in time. /// /// It should correspond with an app's "unbonding period" or other similar /// mechanism for handling [Nothing-At-Stake /// attacks](). - #[prost(message, optional, tag = "2")] - pub max_age_duration: ::core::option::Option, + #[prost(message, optional, tag="2")] + pub max_age_duration: ::core::option::Option, /// This sets the maximum size of total evidence in bytes that can be committed in a single block. /// and should fall comfortably under the max block bytes. /// Default is 1048576 or 1MB - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] #[serde(with = "crate::serializers::from_str", default)] pub max_bytes: i64, } @@ -352,13 +355,13 @@ pub struct EvidenceParams { /// NOTE: uses ABCI pubkey naming, not Amino names. #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorParams { - #[prost(string, repeated, tag = "1")] + #[prost(string, repeated, tag="1")] pub pub_key_types: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// VersionParams contains the ABCI application version. #[derive(Clone, PartialEq, ::prost::Message)] pub struct VersionParams { - #[prost(uint64, tag = "1")] + #[prost(uint64, tag="1")] pub app: u64, } /// HashedParams is a subset of ConsensusParams. @@ -366,199 +369,147 @@ pub struct VersionParams { /// It is hashed into the Header.ConsensusHash. #[derive(Clone, PartialEq, ::prost::Message)] pub struct HashedParams { - #[prost(int64, tag = "1")] + #[prost(int64, tag="1")] pub block_max_bytes: i64, - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] pub block_max_gas: i64, } +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct EventDataRoundState { + #[prost(int64, tag="1")] + pub height: i64, + #[prost(int32, tag="2")] + pub round: i32, + #[prost(string, tag="3")] + pub step: ::prost::alloc::string::String, +} #[derive(::serde::Deserialize, ::serde::Serialize)] -#[serde( - from = "crate::serializers::evidence::EvidenceVariant", - into = "crate::serializers::evidence::EvidenceVariant" -)] +#[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Evidence { - #[prost(oneof = "evidence::Sum", tags = "1, 2")] + #[prost(oneof="evidence::Sum", tags="1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Evidence`. pub mod evidence { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] - #[serde( - from = "crate::serializers::evidence::EvidenceVariant", - into = "crate::serializers::evidence::EvidenceVariant" - )] + #[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag = "1")] + #[prost(message, tag="1")] #[serde(rename = "tendermint/DuplicateVoteEvidence")] DuplicateVoteEvidence(super::DuplicateVoteEvidence), - #[prost(message, tag = "2")] + #[prost(message, tag="2")] #[serde(rename = "tendermint/LightClientAttackEvidence")] LightClientAttackEvidence(super::LightClientAttackEvidence), } } /// DuplicateVoteEvidence contains evidence of a validator signed two conflicting votes. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct DuplicateVoteEvidence { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub vote_a: ::core::option::Option, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub vote_b: ::core::option::Option, - #[prost(int64, tag = "3")] + #[prost(int64, tag="3")] #[serde(alias = "TotalVotingPower", with = "crate::serializers::from_str")] pub total_voting_power: i64, - #[prost(int64, tag = "4")] + #[prost(int64, tag="4")] #[serde(alias = "ValidatorPower", with = "crate::serializers::from_str")] pub validator_power: i64, - #[prost(message, optional, tag = "5")] + #[prost(message, optional, tag="5")] #[serde(alias = "Timestamp")] - pub timestamp: ::core::option::Option, + pub timestamp: ::core::option::Option, } /// LightClientAttackEvidence contains evidence of a set of validators attempting to mislead a light client. -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct LightClientAttackEvidence { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub conflicting_block: ::core::option::Option, - #[prost(int64, tag = "2")] + #[prost(int64, tag="2")] pub common_height: i64, - #[prost(message, repeated, tag = "3")] + #[prost(message, repeated, tag="3")] pub byzantine_validators: ::prost::alloc::vec::Vec, - #[prost(int64, tag = "4")] + #[prost(int64, tag="4")] pub total_voting_power: i64, - #[prost(message, optional, tag = "5")] - pub timestamp: ::core::option::Option, + #[prost(message, optional, tag="5")] + pub timestamp: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct EvidenceList { - #[prost(message, repeated, tag = "1")] + #[prost(message, repeated, tag="1")] #[serde(with = "crate::serializers::nullable")] pub evidence: ::prost::alloc::vec::Vec, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] -pub struct CanonicalBlockId { - #[prost(bytes = "vec", tag = "1")] - pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "2")] - #[serde(alias = "parts")] - pub part_set_header: ::core::option::Option, -} -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] -pub struct CanonicalPartSetHeader { - #[prost(uint32, tag = "1")] - pub total: u32, - #[prost(bytes = "vec", tag = "2")] - pub hash: ::prost::alloc::vec::Vec, -} +#[derive(::serde::Deserialize, ::serde::Serialize)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct CanonicalProposal { - /// type alias for byte - #[prost(enumeration = "SignedMsgType", tag = "1")] - pub r#type: i32, - /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "2")] - pub height: i64, - /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "3")] - pub round: i64, - #[prost(int64, tag = "4")] - pub pol_round: i64, - #[prost(message, optional, tag = "5")] - pub block_id: ::core::option::Option, - #[prost(message, optional, tag = "6")] - pub timestamp: ::core::option::Option, - #[prost(string, tag = "7")] - pub chain_id: ::prost::alloc::string::String, -} -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] -pub struct CanonicalVote { - /// type alias for byte - #[prost(enumeration = "SignedMsgType", tag = "1")] - pub r#type: i32, - /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "2")] - pub height: i64, - /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "3")] - pub round: i64, - #[prost(message, optional, tag = "4")] - pub block_id: ::core::option::Option, - #[prost(message, optional, tag = "5")] - pub timestamp: ::core::option::Option, - #[prost(string, tag = "6")] - pub chain_id: ::prost::alloc::string::String, -} -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct Block { - #[prost(message, optional, tag = "1")] + #[prost(message, optional, tag="1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] pub data: ::core::option::Option, - #[prost(message, optional, tag = "3")] + #[prost(message, optional, tag="3")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag = "4")] + #[prost(message, optional, tag="4")] pub last_commit: ::core::option::Option, } +#[derive(::serde::Deserialize, ::serde::Serialize)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct EventDataRoundState { - #[prost(int64, tag = "1")] - pub height: i64, - #[prost(int32, tag = "2")] - pub round: i32, - #[prost(string, tag = "3")] - pub step: ::prost::alloc::string::String, -} -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] pub struct CanonicalBlockId { - #[prost(bytes = "vec", tag = "1")] + #[prost(bytes="vec", tag="1")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag = "2")] + #[prost(message, optional, tag="2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalPartSetHeader { - #[prost(uint32, tag = "1")] + #[prost(uint32, tag="1")] pub total: u32, - #[prost(bytes = "vec", tag = "2")] + #[prost(bytes="vec", tag="2")] pub hash: ::prost::alloc::vec::Vec, } #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalProposal { /// type alias for byte - #[prost(enumeration = "SignedMsgType", tag = "1")] + #[prost(enumeration="SignedMsgType", tag="1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "2")] + #[prost(sfixed64, tag="2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "3")] + #[prost(sfixed64, tag="3")] pub round: i64, - #[prost(int64, tag = "4")] + #[prost(int64, tag="4")] pub pol_round: i64, - #[prost(message, optional, tag = "5")] + #[prost(message, optional, tag="5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag = "6")] - pub timestamp: ::core::option::Option, - #[prost(string, tag = "7")] + #[prost(message, optional, tag="6")] + pub timestamp: ::core::option::Option, + #[prost(string, tag="7")] pub chain_id: ::prost::alloc::string::String, } -#[derive(::serde::Deserialize, ::serde::Serialize, Clone, PartialEq, ::prost::Message)] +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalVote { /// type alias for byte - #[prost(enumeration = "SignedMsgType", tag = "1")] + #[prost(enumeration="SignedMsgType", tag="1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "2")] + #[prost(sfixed64, tag="2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag = "3")] + #[prost(sfixed64, tag="3")] pub round: i64, - #[prost(message, optional, tag = "4")] + #[prost(message, optional, tag="4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag = "5")] - pub timestamp: ::core::option::Option, - #[prost(string, tag = "6")] + #[prost(message, optional, tag="5")] + pub timestamp: ::core::option::Option, + #[prost(string, tag="6")] pub chain_id: ::prost::alloc::string::String, } diff --git a/proto/src/prost/v0_37/tendermint.version.rs b/proto/src/prost/v0_37/tendermint.version.rs new file mode 100644 index 000000000..bd1227266 --- /dev/null +++ b/proto/src/prost/v0_37/tendermint.version.rs @@ -0,0 +1,23 @@ +/// App includes the protocol and software version for the application. +/// This information is included in ResponseInfo. The App.Protocol can be +/// updated in ResponseEndBlock. +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct App { + #[prost(uint64, tag="1")] + pub protocol: u64, + #[prost(string, tag="2")] + pub software: ::prost::alloc::string::String, +} +/// Consensus captures the consensus rules for processing a block in the blockchain, +/// including all blockchain data structures and the rules of the application's +/// state transition machine. +#[derive(::serde::Deserialize, ::serde::Serialize)] +#[derive(Clone, PartialEq, ::prost::Message)] +pub struct Consensus { + #[prost(uint64, tag="1")] + #[serde(with = "crate::serializers::from_str")] + pub block: u64, + #[prost(uint64, tag="2")] + #[serde(with = "crate::serializers::from_str", default)] + pub app: u64, +} diff --git a/proto/src/tendermint.rs b/proto/src/tendermint.rs index 1513aeee8..4a8211a91 100644 --- a/proto/src/tendermint.rs +++ b/proto/src/tendermint.rs @@ -1,66 +1,3 @@ -//! Tendermint-proto auto-generated sub-modules for Tendermint - -pub mod abci { - include!("prost/tendermint.abci.rs"); -} - -pub mod blocksync { - include!("prost/tendermint.blocksync.rs"); -} - -pub mod consensus { - include!("prost/tendermint.consensus.rs"); -} - -pub mod crypto { - include!("prost/tendermint.crypto.rs"); -} - -pub mod libs { - pub mod bits { - include!("prost/tendermint.libs.bits.rs"); - } -} - -pub mod mempool { - include!("prost/tendermint.mempool.rs"); -} - -pub mod p2p { - include!("prost/tendermint.p2p.rs"); -} - -pub mod privval { - include!("prost/tendermint.privval.rs"); -} - -pub mod rpc { - pub mod grpc { - include!("prost/tendermint.rpc.grpc.rs"); - } -} - -pub mod state { - include!("prost/tendermint.state.rs"); -} - -pub mod statesync { - include!("prost/tendermint.statesync.rs"); -} - -pub mod store { - include!("prost/tendermint.store.rs"); -} - -pub mod types { - include!("prost/tendermint.types.rs"); -} - -pub mod version { - include!("prost/tendermint.version.rs"); -} - -pub mod meta { - pub const REPOSITORY: &str = "https://github.com/tendermint/tendermint"; - pub const COMMITISH: &str = "v0.37.0-alpha.1"; -} +pub mod v0_34; +pub mod v0_37; +pub use v0_37::*; diff --git a/proto/src/tendermint/v0_34.rs b/proto/src/tendermint/v0_34.rs new file mode 100644 index 000000000..950815c7d --- /dev/null +++ b/proto/src/tendermint/v0_34.rs @@ -0,0 +1,66 @@ +//! Tendermint-proto auto-generated sub-modules for Tendermint + +pub mod abci { + include!("../prost/v0_34/tendermint.abci.rs"); +} + +pub mod blockchain { + include!("../prost/v0_34/tendermint.blockchain.rs"); +} + +pub mod consensus { + include!("../prost/v0_34/tendermint.consensus.rs"); +} + +pub mod crypto { + include!("../prost/v0_34/tendermint.crypto.rs"); +} + +pub mod libs { + pub mod bits { + include!("../prost/v0_34/tendermint.libs.bits.rs"); + } +} + +pub mod mempool { + include!("../prost/v0_34/tendermint.mempool.rs"); +} + +pub mod p2p { + include!("../prost/v0_34/tendermint.p2p.rs"); +} + +pub mod privval { + include!("../prost/v0_34/tendermint.privval.rs"); +} + +pub mod rpc { + pub mod grpc { + include!("../prost/v0_34/tendermint.rpc.grpc.rs"); + } +} + +pub mod state { + include!("../prost/v0_34/tendermint.state.rs"); +} + +pub mod statesync { + include!("../prost/v0_34/tendermint.statesync.rs"); +} + +pub mod store { + include!("../prost/v0_34/tendermint.store.rs"); +} + +pub mod types { + include!("../prost/v0_34/tendermint.types.rs"); +} + +pub mod version { + include!("../prost/v0_34/tendermint.version.rs"); +} + +pub mod meta { + pub const REPOSITORY: &str = "https://github.com/tendermint/tendermint"; + pub const COMMITISH: &str = "v0.34.21"; +} diff --git a/proto/src/tendermint/v0_37.rs b/proto/src/tendermint/v0_37.rs new file mode 100644 index 000000000..292f1a337 --- /dev/null +++ b/proto/src/tendermint/v0_37.rs @@ -0,0 +1,66 @@ +//! Tendermint-proto auto-generated sub-modules for Tendermint + +pub mod abci { + include!("../prost/v0_37/tendermint.abci.rs"); +} + +pub mod blocksync { + include!("../prost/v0_37/tendermint.blocksync.rs"); +} + +pub mod consensus { + include!("../prost/v0_37/tendermint.consensus.rs"); +} + +pub mod crypto { + include!("../prost/v0_37/tendermint.crypto.rs"); +} + +pub mod libs { + pub mod bits { + include!("../prost/v0_37/tendermint.libs.bits.rs"); + } +} + +pub mod mempool { + include!("../prost/v0_37/tendermint.mempool.rs"); +} + +pub mod p2p { + include!("../prost/v0_37/tendermint.p2p.rs"); +} + +pub mod privval { + include!("../prost/v0_37/tendermint.privval.rs"); +} + +pub mod rpc { + pub mod grpc { + include!("../prost/v0_37/tendermint.rpc.grpc.rs"); + } +} + +pub mod state { + include!("../prost/v0_37/tendermint.state.rs"); +} + +pub mod statesync { + include!("../prost/v0_37/tendermint.statesync.rs"); +} + +pub mod store { + include!("../prost/v0_37/tendermint.store.rs"); +} + +pub mod types { + include!("../prost/v0_37/tendermint.types.rs"); +} + +pub mod version { + include!("../prost/v0_37/tendermint.version.rs"); +} + +pub mod meta { + pub const REPOSITORY: &str = "https://github.com/tendermint/tendermint"; + pub const COMMITISH: &str = "v0.37.0-alpha.1"; +} diff --git a/tools/proto-compiler/Cargo.toml b/tools/proto-compiler/Cargo.toml index 82b6168b7..1e5806428 100644 --- a/tools/proto-compiler/Cargo.toml +++ b/tools/proto-compiler/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tendermint-proto-compiler" -version = "0.1.0" +version = "0.2.0" authors = ["Informal Systems "] edition = "2021" publish = false diff --git a/tools/proto-compiler/src/constants.rs b/tools/proto-compiler/src/constants.rs index 36604a753..98be71f53 100644 --- a/tools/proto-compiler/src/constants.rs +++ b/tools/proto-compiler/src/constants.rs @@ -2,11 +2,30 @@ /// Tendermint repository URL. pub const TENDERMINT_REPO: &str = "https://github.com/tendermint/tendermint"; -// Commitish formats: -// Tag: v0.34.0-rc4 -// Branch: master -// Commit ID (full length): d7d0ffea13c60c98b812d243ba5a2c375f341c15 -pub const TENDERMINT_COMMITISH: &str = "v0.37.0-alpha.1"; + +/// Information on a Tendermint snapshot to generate prost structures from. +pub struct TendermintVersion { + /// Identifier to use in module names. + pub ident: &'static str, + /// A commitish reference in the tendermint git repository, for example: + /// + /// - Tag: `v0.34.0-rc4` + /// - Branch: `main` + /// - Commit ID (full length): `d7d0ffea13c60c98b812d243ba5a2c375f341c15` + pub commitish: &'static str, +} + +/// All Tendermint versions to generate code for +pub const TENDERMINT_VERSIONS: &[TendermintVersion] = &[ + TendermintVersion { + ident: "v0_34", + commitish: "v0.34.21", + }, + TendermintVersion { + ident: "v0_37", + commitish: "v0.37.0-alpha.1", + }, +]; /// Predefined custom attributes for message annotations const PRIMITIVE_ENUM: &str = r#"#[derive(::num_derive::FromPrimitive, ::num_derive::ToPrimitive)]"#; diff --git a/tools/proto-compiler/src/functions.rs b/tools/proto-compiler/src/functions.rs index e3d9a51ce..03da98ccc 100644 --- a/tools/proto-compiler/src/functions.rs +++ b/tools/proto-compiler/src/functions.rs @@ -12,6 +12,8 @@ use git2::{ use subtle_encoding::hex; use walkdir::WalkDir; +use crate::constants::TendermintVersion; + /// Clone or open+fetch a repository and check out a specific commitish /// In case of an existing repository, the origin remote will be set to `url`. pub fn get_commitish(dir: &Path, url: &str, commitish: &str) { @@ -208,8 +210,10 @@ pub fn find_proto_files(proto_paths: Vec) -> Vec { protos } -/// Create tendermint.rs with library information -pub fn generate_tendermint_lib(prost_dir: &Path, tendermint_lib_target: &Path) { +/// Create a module including generated content for the specified +/// Tendermint source version. +pub fn generate_tendermint_mod(prost_dir: &Path, version: &TendermintVersion, target_dir: &Path) { + create_dir_all(target_dir).unwrap(); let file_names = WalkDir::new(prost_dir) .into_iter() .filter_map(|e| e.ok()) @@ -239,8 +243,9 @@ pub fn generate_tendermint_lib(prost_dir: &Path, tendermint_lib_target: &Path) { let mut tab_count = parts.len(); let mut inner_content = format!( - "{}include!(\"prost/{}\");", + "{}include!(\"../prost/{}/{}\");", tab.repeat(tab_count), + &version.ident, file_name ); @@ -263,11 +268,22 @@ pub fn generate_tendermint_lib(prost_dir: &Path, tendermint_lib_target: &Path) { tab, crate::constants::TENDERMINT_REPO, tab, - crate::constants::TENDERMINT_COMMITISH, + &version.commitish, ); + let tendermint_mod_target = target_dir.join(format!("{}.rs", version.ident)); let mut file = - File::create(tendermint_lib_target).expect("tendermint library file create failed"); + File::create(tendermint_mod_target).expect("tendermint module file create failed"); file.write_all(content.as_bytes()) - .expect("tendermint library file write failed"); + .expect("tendermint module file write failed"); +} + +pub fn generate_tendermint_lib(versions: &[TendermintVersion], tendermint_lib_target: &Path) { + let mut file = + File::create(tendermint_lib_target).expect("tendermint library file create failed"); + for version in versions { + writeln!(&mut file, "pub mod {};", version.ident).unwrap(); + } + let last_version = versions.last().unwrap(); + writeln!(&mut file, "pub use {}::*;", last_version.ident).unwrap(); } diff --git a/tools/proto-compiler/src/main.rs b/tools/proto-compiler/src/main.rs index b4fd4d31b..507ae32e1 100644 --- a/tools/proto-compiler/src/main.rs +++ b/tools/proto-compiler/src/main.rs @@ -1,33 +1,24 @@ -use std::{env::var, path::PathBuf, process}; +use std::{ + env::var, + path::{Path, PathBuf}, + process, +}; use tempfile::tempdir; mod functions; -use functions::{copy_files, find_proto_files, generate_tendermint_lib, get_commitish}; +use functions::{ + copy_files, find_proto_files, generate_tendermint_lib, generate_tendermint_mod, get_commitish, +}; mod constants; use constants::{ - CUSTOM_FIELD_ATTRIBUTES, CUSTOM_TYPE_ATTRIBUTES, TENDERMINT_COMMITISH, TENDERMINT_REPO, + CUSTOM_FIELD_ATTRIBUTES, CUSTOM_TYPE_ATTRIBUTES, TENDERMINT_REPO, TENDERMINT_VERSIONS, }; fn main() { let root = PathBuf::from(env!("CARGO_MANIFEST_DIR")); - let tendermint_lib_target = root - .join("..") - .join("..") - .join("proto") - .join("src") - .join("tendermint.rs"); - let target_dir = root - .join("..") - .join("..") - .join("proto") - .join("src") - .join("prost"); - let out_dir = var("OUT_DIR") - .map(PathBuf::from) - .or_else(|_| tempdir().map(|d| d.into_path())) - .unwrap(); + let target_dir = ["..", "..", "proto", "src"].iter().collect::(); let tendermint_dir = PathBuf::from(var("TENDERMINT_DIR").unwrap_or_else(|_| { root.join("..") .join("target") @@ -37,60 +28,70 @@ fn main() { .to_string() })); - println!( - "[info] => Fetching {} at {} into {:?}", - TENDERMINT_REPO, TENDERMINT_COMMITISH, tendermint_dir - ); - get_commitish( - &PathBuf::from(&tendermint_dir), - TENDERMINT_REPO, - TENDERMINT_COMMITISH, - ); // This panics if it fails. + for version in TENDERMINT_VERSIONS { + println!( + "[info] => Fetching {} at {} into {:?}", + TENDERMINT_REPO, &version.commitish, tendermint_dir + ); + get_commitish(&tendermint_dir, TENDERMINT_REPO, &version.commitish); // This panics if it fails. - let proto_paths = vec![tendermint_dir.join("proto")]; - let proto_includes_paths = vec![ - tendermint_dir.join("proto"), - tendermint_dir.join("third_party").join("proto"), - ]; - // List available proto files - let protos = find_proto_files(proto_paths); + let proto_paths = vec![tendermint_dir.join("proto")]; + let proto_includes_paths = vec![ + tendermint_dir.join("proto"), + tendermint_dir.join("third_party").join("proto"), + ]; + // List available proto files + let protos = find_proto_files(proto_paths); - let mut pb = prost_build::Config::new(); + let ver_target_dir = target_dir.join("prost").join(&version.ident); + let ver_module_dir = target_dir.join("tendermint"); - // Use shared Bytes buffers for ABCI messages: - pb.bytes(&[".tendermint.abci"]); + let out_dir = var("OUT_DIR") + .map(|d| Path::new(&d).join(&version.ident)) + .or_else(|_| tempdir().map(|d| d.into_path())) + .unwrap(); - // Compile proto files with added annotations, exchange prost_types to our own - pb.out_dir(&out_dir); - for type_attribute in CUSTOM_TYPE_ATTRIBUTES { - pb.type_attribute(type_attribute.0, type_attribute.1); - } - for field_attribute in CUSTOM_FIELD_ATTRIBUTES { - pb.field_attribute(field_attribute.0, field_attribute.1); - } - // The below in-place path redirection replaces references to the Duration - // and Timestamp WKTs with our own versions that have valid doctest comments. - // See also https://github.com/danburkert/prost/issues/374 . - pb.extern_path( - ".google.protobuf.Duration", - "super::super::google::protobuf::Duration", - ); - pb.extern_path( - ".google.protobuf.Timestamp", - "super::super::google::protobuf::Timestamp", - ); - println!("[info] => Creating structs."); - match pb.compile_protos(&protos, &proto_includes_paths) { - Ok(()) => {}, - Err(e) => { - eprintln!("{}", e); - process::exit(1); - }, - } + let mut pb = prost_build::Config::new(); + + // Use shared Bytes buffers for ABCI messages: + pb.bytes(&[".tendermint.abci"]); - println!("[info] => Removing old structs and copying new structs."); - copy_files(&out_dir, &target_dir); // This panics if it fails. - generate_tendermint_lib(&out_dir, &tendermint_lib_target); + // Compile proto files with added annotations, exchange prost_types to our own + pb.out_dir(&out_dir); + for type_attribute in CUSTOM_TYPE_ATTRIBUTES { + pb.type_attribute(type_attribute.0, type_attribute.1); + } + for field_attribute in CUSTOM_FIELD_ATTRIBUTES { + pb.field_attribute(field_attribute.0, field_attribute.1); + } + // The below in-place path redirection replaces references to the Duration + // and Timestamp WKTs with our own versions that have valid doctest comments. + // See also https://github.com/danburkert/prost/issues/374 . + pb.extern_path( + ".google.protobuf.Duration", + "crate::google::protobuf::Duration", + ); + pb.extern_path( + ".google.protobuf.Timestamp", + "crate::google::protobuf::Timestamp", + ); + println!("[info] => Creating structs."); + match pb.compile_protos(&protos, &proto_includes_paths) { + Ok(()) => {}, + Err(e) => { + eprintln!("{}", e); + process::exit(1); + }, + } + + println!( + "[info] => Removing old structs and copying new structs to {}", + ver_target_dir.to_string_lossy(), + ); + copy_files(&out_dir, &ver_target_dir); // This panics if it fails. + generate_tendermint_mod(&out_dir, &version, &ver_module_dir); + } + generate_tendermint_lib(TENDERMINT_VERSIONS, &target_dir.join("tendermint.rs")); println!("[info] => Done!"); } From df05a475fe6e0192d2321e071fa0b38cbab48ab4 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 19 Oct 2022 14:23:20 +0300 Subject: [PATCH 05/77] tendermint: Remove Evidence::ConflictingHeaders This variant does not get expressed in RPC or protobuf, seems like this protocol change was not taken as per https://github.com/tendermint/tendermint/blob/91fba07e49cee43048fd761c8b2c2ec3c017acc8/docs/architecture/adr-047-handling-evidence-from-light-client.md --- light-client/src/supervisor.rs | 21 +-------------------- tendermint/src/evidence.rs | 22 ---------------------- 2 files changed, 1 insertion(+), 42 deletions(-) diff --git a/light-client/src/supervisor.rs b/light-client/src/supervisor.rs index 297f8463d..5be0a8346 100644 --- a/light-client/src/supervisor.rs +++ b/light-client/src/supervisor.rs @@ -1,7 +1,7 @@ //! Supervisor and Handle implementation. use crossbeam_channel as channel; -use tendermint::evidence::{ConflictingHeadersEvidence, Evidence}; +use tendermint::evidence::Evidence; use crate::{ errors::Error, @@ -283,25 +283,6 @@ impl Supervisor { Ok(forked) } - /// Report the given evidence of a fork. - fn report_evidence( - &mut self, - provider: PeerId, - primary: &LightBlock, - witness: &LightBlock, - ) -> Result<(), Error> { - let evidence = ConflictingHeadersEvidence::new( - primary.signed_header.clone(), - witness.signed_header.clone(), - ); - - self.evidence_reporter - .report(Evidence::ConflictingHeaders(Box::new(evidence)), provider) - .map_err(Error::io)?; - - Ok(()) - } - /// Perform fork detection with the given verified block and trusted block. fn detect_forks( &self, diff --git a/tendermint/src/evidence.rs b/tendermint/src/evidence.rs index cf8d6b524..267ff7806 100644 --- a/tendermint/src/evidence.rs +++ b/tendermint/src/evidence.rs @@ -36,10 +36,6 @@ pub enum Evidence { //#[serde(rename = "tendermint/DuplicateVoteEvidence")] DuplicateVote(DuplicateVoteEvidence), - /// Conflicting headers evidence - Todo: this is not implemented in protobuf, it's ignored now - //#[serde(rename = "tendermint/ConflictingHeadersEvidence")] - ConflictingHeaders(Box), - /// LightClient attack evidence - Todo: Implement details LightClientAttackEvidence, } @@ -61,7 +57,6 @@ impl From for RawEvidence { Evidence::DuplicateVote(ev) => RawEvidence { sum: Some(RawSum::DuplicateVoteEvidence(ev.into())), }, - Evidence::ConflictingHeaders(_ev) => RawEvidence { sum: None }, // Todo: implement Evidence::LightClientAttackEvidence => RawEvidence { sum: None }, // Todo: implement } } @@ -133,23 +128,6 @@ impl DuplicateVoteEvidence { } } -/// Conflicting headers evidence. -// Todo: This struct doesn't seem to have a protobuf definition. -#[derive(Clone, Debug, PartialEq, Eq)] -pub struct ConflictingHeadersEvidence { - //#[serde(rename = "H1")] - pub h1: SignedHeader, - //#[serde(rename = "H2")] - pub h2: SignedHeader, -} - -impl ConflictingHeadersEvidence { - /// Create a new evidence of conflicting headers - pub fn new(h1: SignedHeader, h2: SignedHeader) -> Self { - Self { h1, h2 } - } -} - /// Evidence data is a wrapper for a list of `Evidence`. /// /// From eb160fb4e240b9f1cd3c357db3fbf502ff527959 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 20 Oct 2022 16:23:10 +0300 Subject: [PATCH 06/77] Add serializers::allow_null This should be used in preference to nullable where `nil` in the format could be met as a quirk admitted by the Go implementation, but otherwise the preferred form is some, possibly default value. --- proto/src/serializers.rs | 2 ++ proto/src/serializers/allow_null.rs | 27 +++++++++++++++++++++++++++ 2 files changed, 29 insertions(+) create mode 100644 proto/src/serializers/allow_null.rs diff --git a/proto/src/serializers.rs b/proto/src/serializers.rs index 651a197f6..1f9ffd94a 100644 --- a/proto/src/serializers.rs +++ b/proto/src/serializers.rs @@ -52,6 +52,8 @@ // Todo: remove dead_code allowance as soon as more types are implemented #![allow(dead_code)] + +pub mod allow_null; pub mod bytes; pub mod evidence; pub mod from_str; diff --git a/proto/src/serializers/allow_null.rs b/proto/src/serializers/allow_null.rs new file mode 100644 index 000000000..b9c9bf463 --- /dev/null +++ b/proto/src/serializers/allow_null.rs @@ -0,0 +1,27 @@ +//! Serialize/deserialize `nil`able value into `T`, where `nil` turns into the `Default` value. +//! +//! Serialize any value of `T`, including the default value, +//! using the serialization for `Some` variant of `Option`. +//! +//! This helper can be used to tolerate `nil` values from a serialization producer, +//! while the default value is normatively serialized as such. + +use serde::{Deserialize, Deserializer, Serialize, Serializer}; + +/// Deserialize `T` from a `nil`-able representation, accepting the `nil` +pub fn deserialize<'de, D, T>(deserializer: D) -> Result +where + D: Deserializer<'de>, + T: Deserialize<'de> + Default, +{ + Ok(Option::::deserialize(deserializer)?.unwrap_or_default()) +} + +/// Serialize `T` as `Some` value of `Option`. +pub fn serialize(value: &T, serializer: S) -> Result +where + S: Serializer, + T: Serialize, +{ + serializer.serialize_some(value) +} From 8e04a06038c19e2a40eb6733b356c799db569420 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 27 Sep 2022 15:38:16 +0300 Subject: [PATCH 07/77] Adapt domain types to v0.37 and add multi-version conversions. --- abci/src/application.rs | 9 +- abci/src/client.rs | 17 +- proto/src/serializers.rs | 1 - proto/src/serializers/evidence.rs | 73 --- .../src/abci/doc/request-prepareproposal.md | 1 + .../src/abci/doc/request-processproposal.md | 1 + tendermint/src/abci/event.rs | 149 ++++-- tendermint/src/abci/request.rs | 185 +++++-- tendermint/src/abci/request/echo.rs | 58 ++- .../src/abci/request/prepare_proposal.rs | 76 +++ .../src/abci/request/process_proposal.rs | 75 +++ tendermint/src/abci/types.rs | 486 +++++++++++++----- tendermint/src/account.rs | 20 + tendermint/src/block.rs | 6 +- tendermint/src/consensus/params.rs | 262 +++++----- tendermint/src/evidence.rs | 273 +++++----- tendermint/src/lib.rs | 2 + tendermint/src/proto_macros.rs | 20 + 18 files changed, 1124 insertions(+), 590 deletions(-) delete mode 100644 proto/src/serializers/evidence.rs create mode 100644 tendermint/src/abci/doc/request-prepareproposal.md create mode 100644 tendermint/src/abci/doc/request-processproposal.md create mode 100644 tendermint/src/abci/request/prepare_proposal.rs create mode 100644 tendermint/src/abci/request/process_proposal.rs create mode 100644 tendermint/src/proto_macros.rs diff --git a/abci/src/application.rs b/abci/src/application.rs index 1bc9f1804..bd8947864 100644 --- a/abci/src/application.rs +++ b/abci/src/application.rs @@ -8,11 +8,11 @@ pub mod kvstore; use tendermint_proto::abci::{ request::Value, response, Request, RequestApplySnapshotChunk, RequestBeginBlock, RequestCheckTx, RequestDeliverTx, RequestEcho, RequestEndBlock, RequestInfo, RequestInitChain, - RequestLoadSnapshotChunk, RequestOfferSnapshot, RequestQuery, Response, - ResponseApplySnapshotChunk, ResponseBeginBlock, ResponseCheckTx, ResponseCommit, - ResponseDeliverTx, ResponseEcho, ResponseEndBlock, ResponseFlush, ResponseInfo, + RequestLoadSnapshotChunk, RequestOfferSnapshot, RequestPrepareProposal, RequestProcessProposal, + RequestQuery, Response, ResponseApplySnapshotChunk, ResponseBeginBlock, ResponseCheckTx, + ResponseCommit, ResponseDeliverTx, ResponseEcho, ResponseEndBlock, ResponseFlush, ResponseInfo, ResponseInitChain, ResponseListSnapshots, ResponseLoadSnapshotChunk, ResponseOfferSnapshot, - ResponseQuery, + ResponsePrepareProposal, ResponseProcessProposal, ResponseQuery, }; /// An ABCI application. @@ -148,7 +148,6 @@ impl RequestDispatcher for A { Value::ProcessProposal(req) => { response::Value::ProcessProposal(self.process_proposal(req)) }, - Value::SetOption(_) => response::Value::SetOption(Default::default()), }), } } diff --git a/abci/src/client.rs b/abci/src/client.rs index cbb039ec2..a7a82be44 100644 --- a/abci/src/client.rs +++ b/abci/src/client.rs @@ -6,10 +6,10 @@ use tendermint_proto::abci::{ request, response, Request, RequestApplySnapshotChunk, RequestBeginBlock, RequestCheckTx, RequestCommit, RequestDeliverTx, RequestEcho, RequestEndBlock, RequestFlush, RequestInfo, RequestInitChain, RequestListSnapshots, RequestLoadSnapshotChunk, RequestOfferSnapshot, - RequestQuery, RequestSetOption, ResponseApplySnapshotChunk, ResponseBeginBlock, - ResponseCheckTx, ResponseCommit, ResponseDeliverTx, ResponseEcho, ResponseEndBlock, - ResponseFlush, ResponseInfo, ResponseInitChain, ResponseListSnapshots, - ResponseLoadSnapshotChunk, ResponseOfferSnapshot, ResponseQuery, ResponseSetOption, + RequestQuery, ResponseApplySnapshotChunk, ResponseBeginBlock, ResponseCheckTx, ResponseCommit, + ResponseDeliverTx, ResponseEcho, ResponseEndBlock, ResponseFlush, ResponseInfo, + ResponseInitChain, ResponseListSnapshots, ResponseLoadSnapshotChunk, ResponseOfferSnapshot, + ResponseQuery, }; use crate::{codec::ClientCodec, Error}; @@ -113,15 +113,6 @@ impl Client { perform!(self, Commit, RequestCommit {}) } - /// Request that the application set an option to a particular value. - /// - /// This request lacks specification and should not be used. - /// It will be removed in Tendermint Core v0.37. - #[deprecated(note = "The set_option ABCI method will be removed in Tendermint Core v0.37")] - pub fn set_option(&mut self, req: RequestSetOption) -> Result { - perform!(self, SetOption, req) - } - /// Used during state sync to discover available snapshots on peers. pub fn list_snapshots(&mut self) -> Result { perform!(self, ListSnapshots, RequestListSnapshots {}) diff --git a/proto/src/serializers.rs b/proto/src/serializers.rs index 1f9ffd94a..c506cb003 100644 --- a/proto/src/serializers.rs +++ b/proto/src/serializers.rs @@ -55,7 +55,6 @@ pub mod allow_null; pub mod bytes; -pub mod evidence; pub mod from_str; pub mod nullable; pub mod optional; diff --git a/proto/src/serializers/evidence.rs b/proto/src/serializers/evidence.rs deleted file mode 100644 index fdfffdeef..000000000 --- a/proto/src/serializers/evidence.rs +++ /dev/null @@ -1,73 +0,0 @@ -use crate::tendermint::types::{evidence::Sum, Evidence}; - -/// EvidenceVariant helper struct for evidence serialization -/// This is a workaround until we figure a better way of JSON serializing evidence. -/// It is a modified copy of the crate::tendermint::types::evidence::Sum struct. -#[allow(clippy::large_enum_variant)] -#[derive(Clone, PartialEq, ::serde::Deserialize, ::serde::Serialize)] -#[serde(tag = "type", content = "value")] -pub enum EvidenceVariant { - /// Provided for when the evidence struct's optional `sum` field is `None`. - None, - #[serde(rename = "tendermint/DuplicateVoteEvidence")] - DuplicateVoteEvidence(crate::tendermint::types::DuplicateVoteEvidence), - #[serde(rename = "tendermint/LightClientAttackEvidence")] - LightClientAttackEvidence(crate::tendermint::types::LightClientAttackEvidence), -} - -impl From for Evidence { - fn from(value: EvidenceVariant) -> Self { - match value { - EvidenceVariant::None => Evidence { sum: None }, - _ => Evidence { - sum: Some(value.into()), - }, - } - } -} - -impl From for EvidenceVariant { - fn from(value: Evidence) -> Self { - match value.sum { - Some(sum) => sum.into(), - None => Self::None, - } - } -} - -impl From for EvidenceVariant { - fn from(value: Sum) -> Self { - match value { - Sum::DuplicateVoteEvidence(d) => Self::DuplicateVoteEvidence(d), - Sum::LightClientAttackEvidence(l) => Self::LightClientAttackEvidence(l), - } - } -} - -impl From for Sum { - fn from(value: EvidenceVariant) -> Self { - match value { - // This should never be called - should be handled instead in the - // `impl From for Evidence` above. - EvidenceVariant::None => { - panic!("non-existent evidence cannot be converted into its protobuf representation") - }, - EvidenceVariant::DuplicateVoteEvidence(d) => Self::DuplicateVoteEvidence(d), - EvidenceVariant::LightClientAttackEvidence(l) => Self::LightClientAttackEvidence(l), - } - } -} - -#[cfg(test)] -mod test { - use super::*; - - // Minimally reproduce https://github.com/informalsystems/tendermint-rs/issues/782 - #[test] - fn empty_evidence() { - let ev = Evidence { sum: None }; - let ev_json = serde_json::to_string(&ev).unwrap(); - let ev_deserialized = serde_json::from_str::(&ev_json).unwrap(); - assert_eq!(ev, ev_deserialized); - } -} diff --git a/tendermint/src/abci/doc/request-prepareproposal.md b/tendermint/src/abci/doc/request-prepareproposal.md new file mode 100644 index 000000000..b76cbb647 --- /dev/null +++ b/tendermint/src/abci/doc/request-prepareproposal.md @@ -0,0 +1 @@ +[ABCI documentation](https://github.com/tendermint/tendermint/blob/main/spec/abci/abci++_methods.md#prepareproposal) diff --git a/tendermint/src/abci/doc/request-processproposal.md b/tendermint/src/abci/doc/request-processproposal.md new file mode 100644 index 000000000..b7474ce7f --- /dev/null +++ b/tendermint/src/abci/doc/request-processproposal.md @@ -0,0 +1 @@ +[ABCI documentation](https://github.com/tendermint/tendermint/blob/main/spec/abci/abci++_methods.md#processproposal) diff --git a/tendermint/src/abci/event.rs b/tendermint/src/abci/event.rs index 8b69ba2ff..868c40602 100644 --- a/tendermint/src/abci/event.rs +++ b/tendermint/src/abci/event.rs @@ -139,59 +139,124 @@ impl, V: Into> From<(K, V)> for EventAttribute { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; +mod v0_34 { + use super::{Event, EventAttribute}; + use crate::prelude::*; + use core::convert::{TryFrom, TryInto}; -use tendermint_proto::{abci as pb, Protobuf}; + use tendermint_proto::v0_34::abci as pb; + use tendermint_proto::Protobuf; -impl From for pb::EventAttribute { - fn from(event: EventAttribute) -> Self { - Self { - key: event.key.into(), - value: event.value.into(), - index: event.index, + impl From for pb::EventAttribute { + fn from(event: EventAttribute) -> Self { + Self { + key: event.key.into(), + value: event.value.into(), + index: event.index, + } } } -} -impl TryFrom for EventAttribute { - type Error = crate::Error; - - fn try_from(event: pb::EventAttribute) -> Result { - // We insist that keys and values are strings, like tm 0.35 did. - Ok(Self { - key: String::from_utf8(event.key.to_vec()) - .map_err(|e| crate::Error::parse(e.to_string()))?, - value: String::from_utf8(event.value.to_vec()) - .map_err(|e| crate::Error::parse(e.to_string()))?, - index: event.index, - }) + impl TryFrom for EventAttribute { + type Error = crate::Error; + + fn try_from(event: pb::EventAttribute) -> Result { + // We insist that keys and values are strings, like tm 0.35 did. + Ok(Self { + key: String::from_utf8(event.key.to_vec()) + .map_err(|e| crate::Error::parse(e.to_string()))?, + value: String::from_utf8(event.value.to_vec()) + .map_err(|e| crate::Error::parse(e.to_string()))?, + index: event.index, + }) + } } -} -impl Protobuf for EventAttribute {} + impl Protobuf for EventAttribute {} -impl From for pb::Event { - fn from(event: Event) -> Self { - Self { - r#type: event.kind, - attributes: event.attributes.into_iter().map(Into::into).collect(), + impl From for pb::Event { + fn from(event: Event) -> Self { + Self { + r#type: event.kind, + attributes: event.attributes.into_iter().map(Into::into).collect(), + } } } -} -impl TryFrom for Event { - type Error = crate::Error; - - fn try_from(event: pb::Event) -> Result { - Ok(Self { - kind: event.r#type, - attributes: event - .attributes - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - }) + impl TryFrom for Event { + type Error = crate::Error; + + fn try_from(event: pb::Event) -> Result { + Ok(Self { + kind: event.r#type, + attributes: event + .attributes + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } } + + impl Protobuf for Event {} } -impl Protobuf for Event {} +mod v0_37 { + use super::{Event, EventAttribute}; + use crate::prelude::*; + use core::convert::{TryFrom, TryInto}; + + use tendermint_proto::v0_37::abci as pb; + use tendermint_proto::Protobuf; + + impl From for pb::EventAttribute { + fn from(event: EventAttribute) -> Self { + Self { + key: event.key.into(), + value: event.value.into(), + index: event.index, + } + } + } + + impl TryFrom for EventAttribute { + type Error = crate::Error; + + fn try_from(event: pb::EventAttribute) -> Result { + // We insist that keys and values are strings, like tm 0.35 did. + Ok(Self { + key: event.key, + value: event.value, + index: event.index, + }) + } + } + + impl Protobuf for EventAttribute {} + + impl From for pb::Event { + fn from(event: Event) -> Self { + Self { + r#type: event.kind, + attributes: event.attributes.into_iter().map(Into::into).collect(), + } + } + } + + impl TryFrom for Event { + type Error = crate::Error; + + fn try_from(event: pb::Event) -> Result { + Ok(Self { + kind: event.r#type, + attributes: event + .attributes + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } + } + + impl Protobuf for Event {} +} diff --git a/tendermint/src/abci/request.rs b/tendermint/src/abci/request.rs index 990b567d9..309565da2 100644 --- a/tendermint/src/abci/request.rs +++ b/tendermint/src/abci/request.rs @@ -18,7 +18,7 @@ // This is also why certain submodules have #[allow(unused)] imports to bring // items into scope for doc links, rather than changing the doc links -- it // allows the doc comments to be copied without editing. -use core::convert::{TryFrom, TryInto}; +use core::convert::TryFrom; // bring into scope for doc links #[allow(unused)] @@ -36,6 +36,8 @@ mod info; mod init_chain; mod load_snapshot_chunk; mod offer_snapshot; +mod prepare_proposal; +mod process_proposal; mod query; mod set_option; @@ -49,6 +51,8 @@ pub use info::Info; pub use init_chain::InitChain; pub use load_snapshot_chunk::LoadSnapshotChunk; pub use offer_snapshot::OfferSnapshot; +pub use prepare_proposal::PrepareProposal; +pub use process_proposal::ProcessProposal; pub use query::Query; pub use set_option::SetOption; @@ -86,6 +90,10 @@ pub enum Request { LoadSnapshotChunk(LoadSnapshotChunk), #[doc = include_str!("doc/request-applysnapshotchunk.md")] ApplySnapshotChunk(ApplySnapshotChunk), + #[doc = include_str!("doc/request-prepareproposal.md")] + PrepareProposal(PrepareProposal), + #[doc = include_str!("doc/request-processproposal.md")] + ProcessProposal(ProcessProposal), } impl Request { @@ -99,6 +107,8 @@ impl Request { DeliverTx(_) => MethodKind::Consensus, EndBlock(_) => MethodKind::Consensus, Commit => MethodKind::Consensus, + PrepareProposal(_) => MethodKind::Consensus, + ProcessProposal(_) => MethodKind::Consensus, CheckTx(_) => MethodKind::Mempool, ListSnapshots => MethodKind::Snapshot, OfferSnapshot(_) => MethodKind::Snapshot, @@ -257,56 +267,139 @@ impl TryFrom for SnapshotRequest { // Protobuf conversions // ============================================================================= -use tendermint_proto::{abci as pb, Protobuf}; +mod v0_34 { + use super::Request; + use crate::{prelude::*, Error}; + use tendermint_proto::v0_34::abci as pb; + use tendermint_proto::Protobuf; -impl From for pb::Request { - fn from(request: Request) -> pb::Request { - use pb::request::Value; - let value = match request { - Request::Echo(x) => Some(Value::Echo(x.into())), - Request::Flush => Some(Value::Flush(Default::default())), - Request::Info(x) => Some(Value::Info(x.into())), - Request::SetOption(x) => Some(Value::SetOption(x.into())), - Request::InitChain(x) => Some(Value::InitChain(x.into())), - Request::Query(x) => Some(Value::Query(x.into())), - Request::BeginBlock(x) => Some(Value::BeginBlock(x.into())), - Request::CheckTx(x) => Some(Value::CheckTx(x.into())), - Request::DeliverTx(x) => Some(Value::DeliverTx(x.into())), - Request::EndBlock(x) => Some(Value::EndBlock(x.into())), - Request::Commit => Some(Value::Commit(Default::default())), - Request::ListSnapshots => Some(Value::ListSnapshots(Default::default())), - Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), - Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), - Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), - }; - pb::Request { value } + impl From for pb::Request { + fn from(request: Request) -> pb::Request { + use pb::request::Value; + let value = match request { + Request::Echo(x) => Some(Value::Echo(x.into())), + Request::Flush => Some(Value::Flush(Default::default())), + Request::Info(x) => Some(Value::Info(x.into())), + Request::SetOption(x) => Some(Value::SetOption(x.into())), + Request::InitChain(x) => Some(Value::InitChain(x.into())), + Request::Query(x) => Some(Value::Query(x.into())), + Request::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Request::CheckTx(x) => Some(Value::CheckTx(x.into())), + Request::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Request::EndBlock(x) => Some(Value::EndBlock(x.into())), + Request::Commit => Some(Value::Commit(Default::default())), + Request::ListSnapshots => Some(Value::ListSnapshots(Default::default())), + Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + Request::PrepareProposal(x) => { + panic!("PrepareProposal should not be used with Tendermint 0.34") + }, + Request::ProcessProposal(x) => { + panic!("ProcessProposal should not be used with Tendermint 0.34") + }, + }; + pb::Request { value } + } } -} -impl TryFrom for Request { - type Error = Error; + impl TryFrom for Request { + type Error = Error; - fn try_from(request: pb::Request) -> Result { - use pb::request::Value; - match request.value { - Some(Value::Echo(x)) => Ok(Request::Echo(x.try_into()?)), - Some(Value::Flush(pb::RequestFlush {})) => Ok(Request::Flush), - Some(Value::Info(x)) => Ok(Request::Info(x.try_into()?)), - Some(Value::SetOption(x)) => Ok(Request::SetOption(x.try_into()?)), - Some(Value::InitChain(x)) => Ok(Request::InitChain(x.try_into()?)), - Some(Value::Query(x)) => Ok(Request::Query(x.try_into()?)), - Some(Value::BeginBlock(x)) => Ok(Request::BeginBlock(x.try_into()?)), - Some(Value::CheckTx(x)) => Ok(Request::CheckTx(x.try_into()?)), - Some(Value::DeliverTx(x)) => Ok(Request::DeliverTx(x.try_into()?)), - Some(Value::EndBlock(x)) => Ok(Request::EndBlock(x.try_into()?)), - Some(Value::Commit(pb::RequestCommit {})) => Ok(Request::Commit), - Some(Value::ListSnapshots(pb::RequestListSnapshots {})) => Ok(Request::ListSnapshots), - Some(Value::OfferSnapshot(x)) => Ok(Request::OfferSnapshot(x.try_into()?)), - Some(Value::LoadSnapshotChunk(x)) => Ok(Request::LoadSnapshotChunk(x.try_into()?)), - Some(Value::ApplySnapshotChunk(x)) => Ok(Request::ApplySnapshotChunk(x.try_into()?)), - None => Err(crate::Error::missing_data()), + fn try_from(request: pb::Request) -> Result { + use pb::request::Value; + match request.value { + Some(Value::Echo(x)) => Ok(Request::Echo(x.try_into()?)), + Some(Value::Flush(pb::RequestFlush {})) => Ok(Request::Flush), + Some(Value::Info(x)) => Ok(Request::Info(x.try_into()?)), + Some(Value::SetOption(x)) => Ok(Request::SetOption(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Request::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Request::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Request::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Request::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Request::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Request::EndBlock(x.try_into()?)), + Some(Value::Commit(pb::RequestCommit {})) => Ok(Request::Commit), + Some(Value::ListSnapshots(pb::RequestListSnapshots {})) => { + Ok(Request::ListSnapshots) + }, + Some(Value::OfferSnapshot(x)) => Ok(Request::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Request::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => { + Ok(Request::ApplySnapshotChunk(x.try_into()?)) + }, + None => Err(crate::Error::missing_data()), + } } } + + impl Protobuf for Request {} } -impl Protobuf for Request {} +mod v0_37 { + use super::Request; + use crate::{prelude::*, Error}; + use tendermint_proto::v0_37::abci as pb; + use tendermint_proto::Protobuf; + + impl From for pb::Request { + fn from(request: Request) -> pb::Request { + use pb::request::Value; + let value = match request { + Request::Echo(x) => Some(Value::Echo(x.into())), + Request::Flush => Some(Value::Flush(Default::default())), + Request::Info(x) => Some(Value::Info(x.into())), + Request::InitChain(x) => Some(Value::InitChain(x.into())), + Request::Query(x) => Some(Value::Query(x.into())), + Request::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Request::CheckTx(x) => Some(Value::CheckTx(x.into())), + Request::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Request::EndBlock(x) => Some(Value::EndBlock(x.into())), + Request::Commit => Some(Value::Commit(Default::default())), + Request::ListSnapshots => Some(Value::ListSnapshots(Default::default())), + Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + Request::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), + Request::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), + Request::SetOption(x) => { + panic!("SetOption should not be used with Tendermint 0.37") + }, + }; + pb::Request { value } + } + } + + impl TryFrom for Request { + type Error = Error; + + fn try_from(request: pb::Request) -> Result { + use pb::request::Value; + match request.value { + Some(Value::Echo(x)) => Ok(Request::Echo(x.try_into()?)), + Some(Value::Flush(pb::RequestFlush {})) => Ok(Request::Flush), + Some(Value::Info(x)) => Ok(Request::Info(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Request::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Request::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Request::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Request::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Request::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Request::EndBlock(x.try_into()?)), + Some(Value::Commit(pb::RequestCommit {})) => Ok(Request::Commit), + Some(Value::ListSnapshots(pb::RequestListSnapshots {})) => { + Ok(Request::ListSnapshots) + }, + Some(Value::OfferSnapshot(x)) => Ok(Request::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Request::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => { + Ok(Request::ApplySnapshotChunk(x.try_into()?)) + }, + Some(Value::PrepareProposal(x)) => Ok(Request::PrepareProposal(x.try_into()?)), + Some(Value::ProcessProposal(x)) => Ok(Request::ProcessProposal(x.try_into()?)), + None => Err(crate::Error::missing_data()), + } + } + } + + impl Protobuf for Request {} +} diff --git a/tendermint/src/abci/request/echo.rs b/tendermint/src/abci/request/echo.rs index 3ae62456e..469096367 100644 --- a/tendermint/src/abci/request/echo.rs +++ b/tendermint/src/abci/request/echo.rs @@ -11,26 +11,56 @@ pub struct Echo { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +mod v0_34 { + use tendermint_proto::v0_34::abci as pb; + use tendermint_proto::Protobuf; -use tendermint_proto::{abci as pb, Protobuf}; + use super::Echo; -impl From for pb::RequestEcho { - fn from(echo: Echo) -> Self { - Self { - message: echo.message, + impl From for pb::RequestEcho { + fn from(echo: Echo) -> Self { + Self { + message: echo.message, + } } } -} -impl TryFrom for Echo { - type Error = crate::Error; + impl TryFrom for Echo { + type Error = crate::Error; - fn try_from(echo: pb::RequestEcho) -> Result { - Ok(Self { - message: echo.message, - }) + fn try_from(echo: pb::RequestEcho) -> Result { + Ok(Self { + message: echo.message, + }) + } } + + impl Protobuf for Echo {} } -impl Protobuf for Echo {} +mod v0_37 { + use tendermint_proto::v0_37::abci as pb; + use tendermint_proto::Protobuf; + + use super::Echo; + + impl From for pb::RequestEcho { + fn from(echo: Echo) -> Self { + Self { + message: echo.message, + } + } + } + + impl TryFrom for Echo { + type Error = crate::Error; + + fn try_from(echo: pb::RequestEcho) -> Result { + Ok(Self { + message: echo.message, + }) + } + } + + impl Protobuf for Echo {} +} diff --git a/tendermint/src/abci/request/prepare_proposal.rs b/tendermint/src/abci/request/prepare_proposal.rs new file mode 100644 index 000000000..30e618063 --- /dev/null +++ b/tendermint/src/abci/request/prepare_proposal.rs @@ -0,0 +1,76 @@ +use crate::prelude::*; +use crate::{ + abci::types::{CommitInfo, Misbehavior}, + account, block, Error, Hash, Time, +}; + +use bytes::Bytes; + +#[doc = include_str!("../doc/request-prepareproposal.md")] +#[derive(Clone, Debug, PartialEq, Eq)] +pub struct PrepareProposal { + /// the modified transactions cannot exceed this size. + pub max_tx_bytes: i64, + /// txs is an array of transactions that will be included in a block, + /// sent to the app for possible modifications. + pub txs: Vec, + pub local_last_commit: Option, + pub misbehavior: Vec, + pub height: block::Height, + pub time: Time, + pub next_validators_hash: Hash, + /// address of the public key of the validator proposing the block. + pub proposer_address: account::Id, +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +use tendermint_proto::v0_37::abci as pb; +use tendermint_proto::Protobuf; + +impl From for pb::RequestPrepareProposal { + fn from(value: PrepareProposal) -> Self { + Self { + max_tx_bytes: value.max_tx_bytes, + txs: value.txs, + local_last_commit: value.local_last_commit.map(Into::into), + misbehavior: value.misbehavior.into_iter().map(Into::into).collect(), + height: value.height.into(), + time: Some(value.time.into()), + next_validators_hash: value.next_validators_hash.into(), + proposer_address: value.proposer_address.into(), + } + } +} + +impl TryFrom for PrepareProposal { + type Error = Error; + + fn try_from(message: pb::RequestPrepareProposal) -> Result { + let req = Self { + max_tx_bytes: message.max_tx_bytes, + txs: message.txs, + local_last_commit: message + .local_last_commit + .map(TryInto::try_into) + .transpose()?, + misbehavior: message + .misbehavior + .into_iter() + .map(TryInto::try_into) + .collect::, _>>()?, + height: message.height.try_into()?, + time: message + .time + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + next_validators_hash: message.next_validators_hash.try_into()?, + proposer_address: message.proposer_address.try_into()?, + }; + Ok(req) + } +} + +impl Protobuf for PrepareProposal {} diff --git a/tendermint/src/abci/request/process_proposal.rs b/tendermint/src/abci/request/process_proposal.rs new file mode 100644 index 000000000..97937b1c8 --- /dev/null +++ b/tendermint/src/abci/request/process_proposal.rs @@ -0,0 +1,75 @@ +use crate::prelude::*; +use crate::{ + abci::types::{CommitInfo, Misbehavior}, + account, block, Error, Hash, Time, +}; + +use bytes::Bytes; + +#[doc = include_str!("../doc/request-processproposal.md")] +#[derive(Clone, Debug, PartialEq, Eq)] +pub struct ProcessProposal { + /// txs is an array of transactions that will be included in a block, + /// sent to the app for possible modifications. + pub txs: Vec, + pub proposed_last_commit: Option, + pub misbehavior: Vec, + pub hash: Hash, + pub height: block::Height, + pub time: Time, + pub next_validators_hash: Hash, + /// address of the public key of the validator proposing the block. + pub proposer_address: account::Id, +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +use tendermint_proto::v0_37::abci as pb; +use tendermint_proto::Protobuf; + +impl From for pb::RequestProcessProposal { + fn from(value: ProcessProposal) -> Self { + Self { + txs: value.txs, + proposed_last_commit: value.proposed_last_commit.map(Into::into), + misbehavior: value.misbehavior.into_iter().map(Into::into).collect(), + hash: value.hash.into(), + height: value.height.into(), + time: Some(value.time.into()), + next_validators_hash: value.next_validators_hash.into(), + proposer_address: value.proposer_address.into(), + } + } +} + +impl TryFrom for ProcessProposal { + type Error = Error; + + fn try_from(message: pb::RequestProcessProposal) -> Result { + let req = Self { + txs: message.txs, + proposed_last_commit: message + .proposed_last_commit + .map(TryInto::try_into) + .transpose()?, + misbehavior: message + .misbehavior + .into_iter() + .map(TryInto::try_into) + .collect::, _>>()?, + hash: message.hash.try_into()?, + height: message.height.try_into()?, + time: message + .time + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + next_validators_hash: message.next_validators_hash.try_into()?, + proposer_address: message.proposer_address.try_into()?, + }; + Ok(req) + } +} + +impl Protobuf for ProcessProposal {} diff --git a/tendermint/src/abci/types.rs b/tendermint/src/abci/types.rs index 11f8afa28..6aeaf7536 100644 --- a/tendermint/src/abci/types.rs +++ b/tendermint/src/abci/types.rs @@ -5,11 +5,9 @@ //! //! [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#data-types) -use core::convert::{TryFrom, TryInto}; - use bytes::Bytes; -use crate::{block, prelude::*, vote, Error, Time}; +use crate::{block, prelude::*, vote, Time}; /// A validator address with voting power. /// @@ -33,15 +31,15 @@ pub struct VoteInfo { pub signed_last_block: bool, } -/// The possible kinds of [`Evidence`]. +/// The possible kinds of [`Misbehavior`]. /// /// Note: the -/// [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#evidencetype-2) -/// calls this `EvidenceType`, but we follow the Rust convention and name it `EvidenceKind` +/// [ABCI documentation](https://github.com/tendermint/tendermint/blob/main/spec/abci/abci++_methods.md#misbehaviortype) +/// calls this `MisbehaviorType`, but we follow the Rust convention and name it `MisbehaviorKind` /// to avoid confusion with Rust types. #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] #[repr(i32)] -pub enum EvidenceKind { +pub enum MisbehaviorKind { /// Unknown evidence type (proto default value). Unknown = 0, /// Evidence that the validator voted for two different blocks in the same @@ -55,12 +53,12 @@ pub enum EvidenceKind { /// /// [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#evidence) #[derive(Clone, PartialEq, Eq, Debug)] -pub struct Evidence { +pub struct Misbehavior { /// The kind of evidence. /// /// Note: this field is called `type` in the protobuf, but we call it `kind` /// to avoid the Rust keyword. - pub kind: EvidenceKind, + pub kind: MisbehaviorKind, /// The offending validator. pub validator: Validator, /// The height when the offense occurred. @@ -75,11 +73,11 @@ pub struct Evidence { pub total_voting_power: vote::Power, } -/// Information on the last block commit. +/// Information on a block commit. /// -/// [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#lastcommitinfo) +/// [ABCI documentation](https://github.com/tendermint/tendermint/blob/main/spec/abci/abci++_methods.md#extendedcommitinfo) #[derive(Clone, PartialEq, Eq, Debug)] -pub struct LastCommitInfo { +pub struct CommitInfo { /// The commit round. /// /// Reflects the total number of rounds it took to come to consensus for the @@ -120,154 +118,378 @@ pub struct Snapshot { // Protobuf conversions // ============================================================================= -use tendermint_proto::{abci as pb, Protobuf}; +mod v0_34 { + use super::{CommitInfo, Misbehavior, MisbehaviorKind, Snapshot, Validator, VoteInfo}; + use crate::{prelude::*, Error}; + use tendermint_proto::v0_34::abci as pb; + use tendermint_proto::Protobuf; + + use bytes::Bytes; -impl From for pb::Validator { - fn from(v: Validator) -> Self { - Self { - address: Bytes::copy_from_slice(&v.address[..]), - power: v.power.into(), + impl From for pb::Validator { + fn from(v: Validator) -> Self { + Self { + address: Bytes::copy_from_slice(&v.address[..]), + power: v.power.into(), + } } } -} -impl TryFrom for Validator { - type Error = Error; - - fn try_from(vu: pb::Validator) -> Result { - let address = if vu.address.len() == 20 { - let mut bytes = [0u8; 20]; - bytes.copy_from_slice(&vu.address); - bytes - } else { - return Err(Error::invalid_account_id_length()); - }; - - Ok(Self { - address, - power: vu.power.try_into()?, - }) + impl TryFrom for Validator { + type Error = Error; + + fn try_from(vu: pb::Validator) -> Result { + let address = if vu.address.len() == 20 { + let mut bytes = [0u8; 20]; + bytes.copy_from_slice(&vu.address); + bytes + } else { + return Err(Error::invalid_account_id_length()); + }; + + Ok(Self { + address, + power: vu.power.try_into()?, + }) + } } -} -impl Protobuf for Validator {} + impl Protobuf for Validator {} -impl From for pb::VoteInfo { - fn from(vi: VoteInfo) -> Self { - Self { - validator: Some(vi.validator.into()), - signed_last_block: vi.signed_last_block, + impl From for pb::VoteInfo { + fn from(vi: VoteInfo) -> Self { + Self { + validator: Some(vi.validator.into()), + signed_last_block: vi.signed_last_block, + } } } -} -impl TryFrom for VoteInfo { - type Error = Error; - - fn try_from(vi: pb::VoteInfo) -> Result { - Ok(Self { - validator: vi - .validator - .ok_or_else(Error::missing_validator)? - .try_into()?, - signed_last_block: vi.signed_last_block, - }) + impl TryFrom for VoteInfo { + type Error = Error; + + fn try_from(vi: pb::VoteInfo) -> Result { + Ok(Self { + validator: vi + .validator + .ok_or_else(Error::missing_validator)? + .try_into()?, + signed_last_block: vi.signed_last_block, + }) + } } -} -impl Protobuf for VoteInfo {} + impl Protobuf for VoteInfo {} + + impl From for pb::Evidence { + fn from(evidence: Misbehavior) -> Self { + Self { + r#type: evidence.kind as i32, + validator: Some(evidence.validator.into()), + height: evidence.height.into(), + time: Some(evidence.time.into()), + total_voting_power: evidence.total_voting_power.into(), + } + } + } -impl From for pb::Evidence { - fn from(evidence: Evidence) -> Self { - Self { - r#type: evidence.kind as i32, - validator: Some(evidence.validator.into()), - height: evidence.height.into(), - time: Some(evidence.time.into()), - total_voting_power: evidence.total_voting_power.into(), + impl TryFrom for Misbehavior { + type Error = Error; + + fn try_from(evidence: pb::Evidence) -> Result { + let kind = match evidence.r#type { + 0 => MisbehaviorKind::Unknown, + 1 => MisbehaviorKind::DuplicateVote, + 2 => MisbehaviorKind::LightClientAttack, + _ => return Err(Error::invalid_evidence()), + }; + + Ok(Self { + kind, + validator: evidence + .validator + .ok_or_else(Error::missing_validator)? + .try_into()?, + height: evidence.height.try_into()?, + time: evidence + .time + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + total_voting_power: evidence.total_voting_power.try_into()?, + }) } } -} -impl TryFrom for Evidence { - type Error = Error; - - fn try_from(evidence: pb::Evidence) -> Result { - let kind = match evidence.r#type { - 0 => EvidenceKind::Unknown, - 1 => EvidenceKind::DuplicateVote, - 2 => EvidenceKind::LightClientAttack, - _ => return Err(Error::invalid_evidence()), - }; - - Ok(Self { - kind, - validator: evidence - .validator - .ok_or_else(Error::missing_validator)? - .try_into()?, - height: evidence.height.try_into()?, - time: evidence - .time - .ok_or_else(Error::missing_timestamp)? - .try_into()?, - total_voting_power: evidence.total_voting_power.try_into()?, - }) + impl Protobuf for Misbehavior {} + + impl From for pb::LastCommitInfo { + fn from(lci: CommitInfo) -> Self { + Self { + round: lci.round.into(), + votes: lci.votes.into_iter().map(Into::into).collect(), + } + } } -} -impl Protobuf for Evidence {} + impl TryFrom for CommitInfo { + type Error = Error; + + fn try_from(lci: pb::LastCommitInfo) -> Result { + Ok(Self { + round: lci.round.try_into()?, + votes: lci + .votes + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } + } -impl From for pb::LastCommitInfo { - fn from(lci: LastCommitInfo) -> Self { - Self { - round: lci.round.into(), - votes: lci.votes.into_iter().map(Into::into).collect(), + impl Protobuf for CommitInfo {} + + impl From for pb::Snapshot { + fn from(snapshot: Snapshot) -> Self { + Self { + height: snapshot.height.into(), + format: snapshot.format, + chunks: snapshot.chunks, + hash: snapshot.hash, + metadata: snapshot.metadata, + } } } -} -impl TryFrom for LastCommitInfo { - type Error = Error; - - fn try_from(lci: pb::LastCommitInfo) -> Result { - Ok(Self { - round: lci.round.try_into()?, - votes: lci - .votes - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - }) + impl TryFrom for Snapshot { + type Error = Error; + + fn try_from(snapshot: pb::Snapshot) -> Result { + Ok(Self { + height: snapshot.height.try_into()?, + format: snapshot.format, + chunks: snapshot.chunks, + hash: snapshot.hash, + metadata: snapshot.metadata, + }) + } } + + impl Protobuf for Snapshot {} } -impl Protobuf for LastCommitInfo {} +mod v0_37 { + use super::{CommitInfo, Misbehavior, MisbehaviorKind, Snapshot, Validator, VoteInfo}; + use crate::{prelude::*, Error}; + use tendermint_proto::v0_37::abci as pb; + use tendermint_proto::Protobuf; -impl From for pb::Snapshot { - fn from(snapshot: Snapshot) -> Self { - Self { - height: snapshot.height.into(), - format: snapshot.format, - chunks: snapshot.chunks, - hash: snapshot.hash, - metadata: snapshot.metadata, + use bytes::Bytes; + + impl From for pb::Validator { + fn from(v: Validator) -> Self { + Self { + address: Bytes::copy_from_slice(&v.address[..]), + power: v.power.into(), + } } } -} -impl TryFrom for Snapshot { - type Error = Error; - - fn try_from(snapshot: pb::Snapshot) -> Result { - Ok(Self { - height: snapshot.height.try_into()?, - format: snapshot.format, - chunks: snapshot.chunks, - hash: snapshot.hash, - metadata: snapshot.metadata, - }) + impl TryFrom for Validator { + type Error = Error; + + fn try_from(vu: pb::Validator) -> Result { + let address = if vu.address.len() == 20 { + let mut bytes = [0u8; 20]; + bytes.copy_from_slice(&vu.address); + bytes + } else { + return Err(Error::invalid_account_id_length()); + }; + + Ok(Self { + address, + power: vu.power.try_into()?, + }) + } + } + + impl Protobuf for Validator {} + + impl From for pb::VoteInfo { + fn from(vi: VoteInfo) -> Self { + Self { + validator: Some(vi.validator.into()), + signed_last_block: vi.signed_last_block, + } + } + } + + impl TryFrom for VoteInfo { + type Error = Error; + + fn try_from(vi: pb::VoteInfo) -> Result { + Ok(Self { + validator: vi + .validator + .ok_or_else(Error::missing_validator)? + .try_into()?, + signed_last_block: vi.signed_last_block, + }) + } + } + + impl Protobuf for VoteInfo {} + + // ExtendedVoteInfo is defined in 0.37, but the vote_extension field is always nil, + // so we can omit it from VoteInfo for the time being. + + impl From for pb::ExtendedVoteInfo { + fn from(vi: VoteInfo) -> Self { + Self { + validator: Some(vi.validator.into()), + signed_last_block: vi.signed_last_block, + vote_extension: Default::default(), + } + } + } + + impl TryFrom for VoteInfo { + type Error = Error; + + fn try_from(vi: pb::ExtendedVoteInfo) -> Result { + Ok(Self { + validator: vi + .validator + .ok_or_else(Error::missing_validator)? + .try_into()?, + signed_last_block: vi.signed_last_block, + }) + } } -} -impl Protobuf for Snapshot {} + impl Protobuf for VoteInfo {} + + impl From for pb::Misbehavior { + fn from(evidence: Misbehavior) -> Self { + Self { + r#type: evidence.kind as i32, + validator: Some(evidence.validator.into()), + height: evidence.height.into(), + time: Some(evidence.time.into()), + total_voting_power: evidence.total_voting_power.into(), + } + } + } + + impl TryFrom for Misbehavior { + type Error = Error; + + fn try_from(evidence: pb::Misbehavior) -> Result { + let kind = match evidence.r#type { + 0 => MisbehaviorKind::Unknown, + 1 => MisbehaviorKind::DuplicateVote, + 2 => MisbehaviorKind::LightClientAttack, + _ => return Err(Error::invalid_evidence()), + }; + + Ok(Self { + kind, + validator: evidence + .validator + .ok_or_else(Error::missing_validator)? + .try_into()?, + height: evidence.height.try_into()?, + time: evidence + .time + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + total_voting_power: evidence.total_voting_power.try_into()?, + }) + } + } + + impl Protobuf for Misbehavior {} + + // The CommitInfo domain type represents both CommitInfo and ExtendedCommitInfo + // as defined in protobuf for 0.37. + + impl From for pb::CommitInfo { + fn from(lci: CommitInfo) -> Self { + Self { + round: lci.round.into(), + votes: lci.votes.into_iter().map(Into::into).collect(), + } + } + } + + impl TryFrom for CommitInfo { + type Error = Error; + + fn try_from(lci: pb::CommitInfo) -> Result { + Ok(Self { + round: lci.round.try_into()?, + votes: lci + .votes + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } + } + + impl Protobuf for CommitInfo {} + + impl From for pb::ExtendedCommitInfo { + fn from(lci: CommitInfo) -> Self { + Self { + round: lci.round.into(), + votes: lci.votes.into_iter().map(Into::into).collect(), + } + } + } + + impl TryFrom for CommitInfo { + type Error = Error; + + fn try_from(lci: pb::ExtendedCommitInfo) -> Result { + Ok(Self { + round: lci.round.try_into()?, + votes: lci + .votes + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } + } + + impl Protobuf for CommitInfo {} + + impl From for pb::Snapshot { + fn from(snapshot: Snapshot) -> Self { + Self { + height: snapshot.height.into(), + format: snapshot.format, + chunks: snapshot.chunks, + hash: snapshot.hash, + metadata: snapshot.metadata, + } + } + } + + impl TryFrom for Snapshot { + type Error = Error; + + fn try_from(snapshot: pb::Snapshot) -> Result { + Ok(Self { + height: snapshot.height.try_into()?, + format: snapshot.format, + chunks: snapshot.chunks, + hash: snapshot.hash, + metadata: snapshot.metadata, + }) + } + } + + impl Protobuf for Snapshot {} +} diff --git a/tendermint/src/account.rs b/tendermint/src/account.rs index e01d83074..0fcc8cc71 100644 --- a/tendermint/src/account.rs +++ b/tendermint/src/account.rs @@ -6,6 +6,7 @@ use core::{ str::FromStr, }; +use bytes::Bytes; #[cfg(feature = "secp256k1")] use ripemd160::Ripemd160; use serde::{de, Deserialize, Deserializer, Serialize, Serializer}; @@ -46,6 +47,25 @@ impl From for Vec { } } +impl TryFrom for Id { + type Error = Error; + + fn try_from(value: Bytes) -> Result { + if value.len() != LENGTH { + return Err(Error::invalid_account_id_length()); + } + let mut slice: [u8; LENGTH] = [0; LENGTH]; + slice.copy_from_slice(&value[..]); + Ok(Id(slice)) + } +} + +impl From for Bytes { + fn from(value: Id) -> Self { + value.as_bytes().into() + } +} + impl Id { /// Create a new account ID from raw bytes pub fn new(bytes: [u8; LENGTH]) -> Id { diff --git a/tendermint/src/block.rs b/tendermint/src/block.rs index 0f961c05c..845fd36cd 100644 --- a/tendermint/src/block.rs +++ b/tendermint/src/block.rs @@ -11,8 +11,6 @@ mod round; pub mod signed_header; mod size; -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; use tendermint_proto::{types::Block as RawBlock, Protobuf}; @@ -26,7 +24,7 @@ pub use self::{ round::*, size::Size, }; -use crate::{error::Error, evidence, prelude::*}; +use crate::{error::Error, evidence, prelude::*, serializers}; /// Blocks consist of a header, transactions, votes (the commit), and a list of /// evidence of malfeasance (i.e. signing conflicting votes). @@ -35,7 +33,6 @@ use crate::{error::Error, evidence, prelude::*}; // Default serialization - all fields serialize; used by /block endpoint #[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq)] #[non_exhaustive] -#[serde(try_from = "RawBlock", into = "RawBlock")] pub struct Block { /// Block header pub header: Header, @@ -44,6 +41,7 @@ pub struct Block { pub data: Vec>, /// Evidence of malfeasance + #[serde(with = "serializers::allow_null")] pub evidence: evidence::Data, /// Last commit diff --git a/tendermint/src/consensus/params.rs b/tendermint/src/consensus/params.rs index b266aaac4..cf4fb728a 100644 --- a/tendermint/src/consensus/params.rs +++ b/tendermint/src/consensus/params.rs @@ -1,18 +1,8 @@ //! Tendermint consensus parameters -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; -use tendermint_proto::{ - abci::ConsensusParams as RawAbciParams, - types::{ - ConsensusParams as RawParams, ValidatorParams as RawValidatorParams, - VersionParams as RawVersionParams, - }, - Protobuf, -}; -use crate::{block, error::Error, evidence, prelude::*, public_key}; +use crate::{block, evidence, prelude::*, public_key}; /// All consensus-relevant parameters that can be adjusted by the ABCI app. /// @@ -31,76 +21,6 @@ pub struct Params { pub version: Option, } -impl Protobuf for Params {} - -impl TryFrom for Params { - type Error = Error; - - fn try_from(value: RawParams) -> Result { - Ok(Self { - block: value - .block - .ok_or_else(|| Error::invalid_block("missing block".to_string()))? - .try_into()?, - evidence: value - .evidence - .ok_or_else(Error::invalid_evidence)? - .try_into()?, - validator: value - .validator - .ok_or_else(Error::invalid_validator_params)? - .try_into()?, - version: value.version.map(TryFrom::try_from).transpose()?, - }) - } -} - -impl From for RawParams { - fn from(value: Params) -> Self { - RawParams { - block: Some(value.block.into()), - evidence: Some(value.evidence.into()), - validator: Some(value.validator.into()), - version: value.version.map(From::from), - } - } -} - -impl Protobuf for Params {} - -impl TryFrom for Params { - type Error = Error; - - fn try_from(value: RawAbciParams) -> Result { - Ok(Self { - block: value - .block - .ok_or_else(|| Error::invalid_block("missing block".to_string()))? - .try_into()?, - evidence: value - .evidence - .ok_or_else(Error::invalid_evidence)? - .try_into()?, - validator: value - .validator - .ok_or_else(Error::invalid_validator_params)? - .try_into()?, - version: value.version.map(TryFrom::try_from).transpose()?, - }) - } -} - -impl From for RawAbciParams { - fn from(value: Params) -> Self { - RawAbciParams { - block: Some(value.block.into()), - evidence: Some(value.evidence.into()), - validator: Some(value.validator.into()), - version: value.version.map(From::from), - } - } -} - /// ValidatorParams restrict the public key types validators can use. /// /// [Tendermint documentation](https://docs.tendermint.com/master/spec/core/data_structures.html#validatorparams) @@ -110,66 +30,154 @@ pub struct ValidatorParams { pub pub_key_types: Vec, } -impl Protobuf for ValidatorParams {} +/// Version Parameters +/// +/// [Tendermint documentation](https://docs.tendermint.com/master/spec/core/data_structures.html#versionparams) +#[derive(Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Default)] +pub struct VersionParams { + /// The ABCI application version. + #[serde(with = "crate::serializers::from_str")] + pub app: u64, +} -impl TryFrom for ValidatorParams { - type Error = Error; +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +mod v0_34 { + use tendermint_proto::v0_34::{ + abci::ConsensusParams as RawAbciParams, + types::{ + ConsensusParams as RawParams, ValidatorParams as RawValidatorParams, + VersionParams as RawVersionParams, + }, + }; + use tendermint_proto::Protobuf; + + use super::{Params, ValidatorParams, VersionParams}; + use crate::{error::Error, prelude::*, public_key}; + + impl Protobuf for Params {} + + impl TryFrom for Params { + type Error = Error; + + fn try_from(value: RawParams) -> Result { + Ok(Self { + block: value + .block + .ok_or_else(|| Error::invalid_block("missing block".to_string()))? + .try_into()?, + evidence: value + .evidence + .ok_or_else(Error::invalid_evidence)? + .try_into()?, + validator: value + .validator + .ok_or_else(Error::invalid_validator_params)? + .try_into()?, + version: value.version.map(TryFrom::try_from).transpose()?, + }) + } + } - fn try_from(value: RawValidatorParams) -> Result { - Ok(Self { - pub_key_types: value.pub_key_types.iter().map(|f| key_type(f)).collect(), - }) + impl From for RawParams { + fn from(value: Params) -> Self { + RawParams { + block: Some(value.block.into()), + evidence: Some(value.evidence.into()), + validator: Some(value.validator.into()), + version: value.version.map(From::from), + } + } } -} -// Todo: How are these key types created? -fn key_type(s: &str) -> public_key::Algorithm { - if s == "Ed25519" || s == "ed25519" { - return public_key::Algorithm::Ed25519; + impl Protobuf for Params {} + + impl TryFrom for Params { + type Error = Error; + + fn try_from(value: RawAbciParams) -> Result { + Ok(Self { + block: value + .block + .ok_or_else(|| Error::invalid_block("missing block".to_string()))? + .try_into()?, + evidence: value + .evidence + .ok_or_else(Error::invalid_evidence)? + .try_into()?, + validator: value + .validator + .ok_or_else(Error::invalid_validator_params)? + .try_into()?, + version: value.version.map(TryFrom::try_from).transpose()?, + }) + } } - if s == "Secp256k1" || s == "secp256k1" { - return public_key::Algorithm::Secp256k1; + + impl From for RawAbciParams { + fn from(value: Params) -> Self { + RawAbciParams { + block: Some(value.block.into()), + evidence: Some(value.evidence.into()), + validator: Some(value.validator.into()), + version: value.version.map(From::from), + } + } } - public_key::Algorithm::Ed25519 // Todo: Shall we error out for invalid key types? -} -impl From for RawValidatorParams { - fn from(value: ValidatorParams) -> Self { - RawValidatorParams { - pub_key_types: value - .pub_key_types - .into_iter() - .map(|k| match k { - public_key::Algorithm::Ed25519 => "ed25519".to_string(), - public_key::Algorithm::Secp256k1 => "secp256k1".to_string(), - }) - .collect(), + impl Protobuf for ValidatorParams {} + + impl TryFrom for ValidatorParams { + type Error = Error; + + fn try_from(value: RawValidatorParams) -> Result { + Ok(Self { + pub_key_types: value.pub_key_types.iter().map(|f| key_type(f)).collect(), + }) } } -} -/// Version Parameters -/// -/// [Tendermint documentation](https://docs.tendermint.com/master/spec/core/data_structures.html#versionparams) -#[derive(Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Default)] -pub struct VersionParams { - /// The ABCI application version. - #[serde(with = "crate::serializers::from_str")] - pub app: u64, -} + // Todo: How are these key types created? + fn key_type(s: &str) -> public_key::Algorithm { + if s == "Ed25519" || s == "ed25519" { + return public_key::Algorithm::Ed25519; + } + if s == "Secp256k1" || s == "secp256k1" { + return public_key::Algorithm::Secp256k1; + } + public_key::Algorithm::Ed25519 // Todo: Shall we error out for invalid key types? + } -impl Protobuf for VersionParams {} + impl From for RawValidatorParams { + fn from(value: ValidatorParams) -> Self { + RawValidatorParams { + pub_key_types: value + .pub_key_types + .into_iter() + .map(|k| match k { + public_key::Algorithm::Ed25519 => "ed25519".to_string(), + public_key::Algorithm::Secp256k1 => "secp256k1".to_string(), + }) + .collect(), + } + } + } + + impl Protobuf for VersionParams {} -impl TryFrom for VersionParams { - type Error = Error; + impl TryFrom for VersionParams { + type Error = Error; - fn try_from(value: RawVersionParams) -> Result { - Ok(Self { app: value.app }) + fn try_from(value: RawVersionParams) -> Result { + Ok(Self { app: value.app }) + } } -} -impl From for RawVersionParams { - fn from(value: VersionParams) -> Self { - RawVersionParams { app: value.app } + impl From for RawVersionParams { + fn from(value: VersionParams) -> Self { + RawVersionParams { app: value.app } + } } } diff --git a/tendermint/src/evidence.rs b/tendermint/src/evidence.rs index 267ff7806..b7b93db90 100644 --- a/tendermint/src/evidence.rs +++ b/tendermint/src/evidence.rs @@ -7,19 +7,10 @@ use core::{ use serde::{Deserialize, Serialize}; use tendermint_proto::{ - google::protobuf::Duration as RawDuration, - types::{ - evidence::{Sum as RawSum, Sum}, - DuplicateVoteEvidence as RawDuplicateVoteEvidence, Evidence as RawEvidence, - EvidenceList as RawEvidenceList, EvidenceParams as RawEvidenceParams, - }, - Protobuf, + google::protobuf::Duration as RawDuration, types::evidence::Sum as RawSum, Protobuf, }; -use crate::{ - block::signed_header::SignedHeader, error::Error, prelude::*, serializers, vote::Power, Time, - Vote, -}; +use crate::{error::Error, prelude::*, serializers, vote::Power, Time, Vote}; /// Evidence of malfeasance by validators (i.e. signing conflicting votes). /// encoded using an Amino prefix. There is currently only a single type of @@ -27,41 +18,15 @@ use crate::{ /// /// #[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] -//#[serde(tag = "type", content = "value")] -#[serde(try_from = "RawEvidence", into = "RawEvidence")] // Used by RPC /broadcast_evidence endpoint -// To be fixed in 0.24 -#[allow(clippy::large_enum_variant)] +#[serde(try_from = "RawSum", into = "Option")] // Used by RPC /broadcast_evidence endpoint pub enum Evidence { /// Duplicate vote evidence - //#[serde(rename = "tendermint/DuplicateVoteEvidence")] DuplicateVote(DuplicateVoteEvidence), /// LightClient attack evidence - Todo: Implement details LightClientAttackEvidence, } -impl TryFrom for Evidence { - type Error = Error; - - fn try_from(value: RawEvidence) -> Result { - match value.sum.ok_or_else(Error::invalid_evidence)? { - Sum::DuplicateVoteEvidence(ev) => Ok(Evidence::DuplicateVote(ev.try_into()?)), - Sum::LightClientAttackEvidence(_ev) => Ok(Evidence::LightClientAttackEvidence), - } - } -} - -impl From for RawEvidence { - fn from(value: Evidence) -> Self { - match value { - Evidence::DuplicateVote(ev) => RawEvidence { - sum: Some(RawSum::DuplicateVoteEvidence(ev.into())), - }, - Evidence::LightClientAttackEvidence => RawEvidence { sum: None }, // Todo: implement - } - } -} - /// Duplicate vote evidence #[derive(Clone, Debug, PartialEq, Eq)] pub struct DuplicateVoteEvidence { @@ -72,41 +37,6 @@ pub struct DuplicateVoteEvidence { pub timestamp: Time, } -impl TryFrom for DuplicateVoteEvidence { - type Error = Error; - - fn try_from(value: RawDuplicateVoteEvidence) -> Result { - Ok(Self { - vote_a: value - .vote_a - .ok_or_else(Error::missing_evidence)? - .try_into()?, - vote_b: value - .vote_b - .ok_or_else(Error::missing_evidence)? - .try_into()?, - total_voting_power: value.total_voting_power.try_into()?, - validator_power: value.validator_power.try_into()?, - timestamp: value - .timestamp - .ok_or_else(Error::missing_timestamp)? - .try_into()?, - }) - } -} - -impl From for RawDuplicateVoteEvidence { - fn from(value: DuplicateVoteEvidence) -> Self { - RawDuplicateVoteEvidence { - vote_a: Some(value.vote_a.into()), - vote_b: Some(value.vote_b.into()), - total_voting_power: value.total_voting_power.into(), - validator_power: value.total_voting_power.into(), - timestamp: Some(value.timestamp.into()), - } - } -} - impl DuplicateVoteEvidence { /// constructor pub fn new(vote_a: Vote, vote_b: Vote) -> Result { @@ -132,37 +62,7 @@ impl DuplicateVoteEvidence { /// /// #[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)] -#[serde(try_from = "RawEvidenceList", into = "RawEvidenceList")] -pub struct Data { - evidence: Option>, -} - -impl TryFrom for Data { - type Error = Error; - fn try_from(value: RawEvidenceList) -> Result { - if value.evidence.is_empty() { - return Ok(Self { evidence: None }); - } - let evidence: Result, Error> = - value.evidence.into_iter().map(TryInto::try_into).collect(); - Ok(Self { - evidence: Some(evidence?), - }) - } -} - -impl From for RawEvidenceList { - fn from(value: Data) -> Self { - RawEvidenceList { - evidence: value - .evidence - .unwrap_or_default() - .into_iter() - .map(Into::into) - .collect(), - } - } -} +pub struct Data(Vec); impl Data { /// Create a new evidence data collection @@ -170,25 +70,23 @@ impl Data { where I: Into>, { - Data { - evidence: Some(into_evidence.into()), - } + Data(into_evidence.into()) } /// Convert this evidence data into a vector pub fn into_vec(self) -> Vec { - self.iter().cloned().collect() + self.0 } /// Iterate over the evidence data pub fn iter(&self) -> slice::Iter<'_, Evidence> { - self.as_ref().iter() + self.0.iter() } } impl AsRef<[Evidence]> for Data { fn as_ref(&self) -> &[Evidence] { - self.evidence.as_deref().unwrap_or(&[]) + &self.0 } } @@ -218,33 +116,142 @@ pub struct Params { pub max_bytes: i64, } -impl Protobuf for Params {} +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +mod v0_37 { + use tendermint_proto::v0_37::types::{ + evidence::Sum as RawSum, DuplicateVoteEvidence as RawDuplicateVoteEvidence, + Evidence as RawEvidence, EvidenceList as RawEvidenceList, + EvidenceParams as RawEvidenceParams, + }; + use tendermint_proto::Protobuf; + + use super::{Data, DuplicateVoteEvidence, Evidence, Params}; + use crate::{error::Error, prelude::*}; + + impl TryFrom for Evidence { + type Error = Error; + + fn try_from(value: RawSum) -> Result { + use RawSum::*; + match value { + DuplicateVoteEvidence(ev) => Ok(Evidence::DuplicateVote(ev.try_into()?)), + LightClientAttackEvidence(_ev) => Ok(Evidence::LightClientAttackEvidence), + } + } + } -impl TryFrom for Params { - type Error = Error; + impl TryFrom for Evidence { + type Error = Error; - fn try_from(value: RawEvidenceParams) -> Result { - Ok(Self { - max_age_num_blocks: value - .max_age_num_blocks - .try_into() - .map_err(Error::negative_max_age_num)?, - max_age_duration: value - .max_age_duration - .ok_or_else(Error::missing_max_age_duration)? - .try_into()?, - max_bytes: value.max_bytes, - }) + fn try_from(value: RawEvidence) -> Result { + value + .sum + .ok_or_else(Error::invalid_evidence) + .and_then(TryInto::try_into) + } } -} -impl From for RawEvidenceParams { - fn from(value: Params) -> Self { - Self { - // Todo: Implement proper domain types so this becomes infallible - max_age_num_blocks: value.max_age_num_blocks.try_into().unwrap(), - max_age_duration: Some(value.max_age_duration.into()), - max_bytes: value.max_bytes, + impl From for Option { + fn from(value: Evidence) -> Self { + match value { + Evidence::DuplicateVote(ev) => Some(RawSum::DuplicateVoteEvidence(ev.into())), + Evidence::LightClientAttackEvidence => None, + } + } + } + + impl From for RawEvidence { + fn from(value: Evidence) -> Self { + RawEvidence { sum: value.into() } + } + } + + impl TryFrom for DuplicateVoteEvidence { + type Error = Error; + + fn try_from(value: RawDuplicateVoteEvidence) -> Result { + Ok(Self { + vote_a: value + .vote_a + .ok_or_else(Error::missing_evidence)? + .try_into()?, + vote_b: value + .vote_b + .ok_or_else(Error::missing_evidence)? + .try_into()?, + total_voting_power: value.total_voting_power.try_into()?, + validator_power: value.validator_power.try_into()?, + timestamp: value + .timestamp + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + }) + } + } + + impl From for RawDuplicateVoteEvidence { + fn from(value: DuplicateVoteEvidence) -> Self { + RawDuplicateVoteEvidence { + vote_a: Some(value.vote_a.into()), + vote_b: Some(value.vote_b.into()), + total_voting_power: value.total_voting_power.into(), + validator_power: value.total_voting_power.into(), + timestamp: Some(value.timestamp.into()), + } + } + } + + impl TryFrom for Data { + type Error = Error; + fn try_from(value: RawEvidenceList) -> Result { + let evidence = value + .evidence + .into_iter() + .map(TryInto::try_into) + .collect::, _>>()?; + Ok(Self(evidence)) + } + } + + impl From for RawEvidenceList { + fn from(value: Data) -> Self { + RawEvidenceList { + evidence: value.0.into_iter().map(Into::into).collect(), + } + } + } + + impl Protobuf for Params {} + + impl TryFrom for Params { + type Error = Error; + + fn try_from(value: RawEvidenceParams) -> Result { + Ok(Self { + max_age_num_blocks: value + .max_age_num_blocks + .try_into() + .map_err(Error::negative_max_age_num)?, + max_age_duration: value + .max_age_duration + .ok_or_else(Error::missing_max_age_duration)? + .try_into()?, + max_bytes: value.max_bytes, + }) + } + } + + impl From for RawEvidenceParams { + fn from(value: Params) -> Self { + Self { + // Todo: Implement proper domain types so this becomes infallible + max_age_num_blocks: value.max_age_num_blocks.try_into().unwrap(), + max_age_duration: Some(value.max_age_duration.into()), + max_bytes: value.max_bytes, + } } } } diff --git a/tendermint/src/lib.rs b/tendermint/src/lib.rs index 74a554014..a6abfddd2 100644 --- a/tendermint/src/lib.rs +++ b/tendermint/src/lib.rs @@ -25,6 +25,8 @@ extern crate alloc; extern crate std; #[macro_use] +mod proto_macros; + pub mod error; pub mod abci; diff --git a/tendermint/src/proto_macros.rs b/tendermint/src/proto_macros.rs new file mode 100644 index 000000000..d0c1c4222 --- /dev/null +++ b/tendermint/src/proto_macros.rs @@ -0,0 +1,20 @@ +//! Macros to facilitate protobuf conversions + +macro_rules! tendermint_pb_modules { + { + $(contents:item)* + } => { + mod v0_34 { + use tendermint_proto::v0_34 as pb; + use tendermint_proto::Protobuf; + + $(contents)* + } + mod v0_37 { + use tendermint_proto::v0_37 as pb; + use tendermint_proto::Protobuf; + + $(contents)* + } + }; +} From d33945a025ea293210928090f4e07c42e28e0256 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Fri, 21 Oct 2022 15:29:54 +0300 Subject: [PATCH 08/77] Multi-version protobuf support for request types --- .../src/abci/request/apply_snapshot_chunk.rs | 40 +-- tendermint/src/abci/request/begin_block.rs | 85 +++--- tendermint/src/abci/request/check_tx.rs | 46 ++-- tendermint/src/abci/request/deliver_tx.rs | 26 +- tendermint/src/abci/request/echo.rs | 40 +-- tendermint/src/abci/request/end_block.rs | 34 +-- tendermint/src/abci/request/info.rs | 73 +++-- tendermint/src/abci/request/init_chain.rs | 75 +++-- .../src/abci/request/load_snapshot_chunk.rs | 42 +-- tendermint/src/abci/request/offer_snapshot.rs | 46 ++-- .../src/abci/request/prepare_proposal.rs | 2 + .../src/abci/request/process_proposal.rs | 2 + tendermint/src/abci/request/query.rs | 46 ++-- tendermint/src/abci/request/set_option.rs | 5 +- tendermint/src/abci/response/set_option.rs | 5 +- tendermint/src/block/header.rs | 250 +++++++++-------- tendermint/src/block/id.rs | 116 ++++---- tendermint/src/block/parts.rs | 93 +++---- tendermint/src/block/size.rs | 128 ++++++--- tendermint/src/consensus/params.rs | 109 +++++++- tendermint/src/evidence.rs | 138 +++++++++- tendermint/src/proto_macros.rs | 6 +- tendermint/src/public_key.rs | 72 ++--- tendermint/src/validator.rs | 256 +++++++++--------- tendermint/src/vote.rs | 82 +++--- tendermint/src/vote/sign_vote.rs | 108 ++++---- 26 files changed, 1118 insertions(+), 807 deletions(-) diff --git a/tendermint/src/abci/request/apply_snapshot_chunk.rs b/tendermint/src/abci/request/apply_snapshot_chunk.rs index f893cbb47..d11f1b3c6 100644 --- a/tendermint/src/abci/request/apply_snapshot_chunk.rs +++ b/tendermint/src/abci/request/apply_snapshot_chunk.rs @@ -40,30 +40,30 @@ pub struct ApplySnapshotChunk { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +tendermint_pb_modules! { + use super::ApplySnapshotChunk; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestApplySnapshotChunk { - fn from(apply_snapshot_chunk: ApplySnapshotChunk) -> Self { - Self { - index: apply_snapshot_chunk.index, - chunk: apply_snapshot_chunk.chunk, - sender: apply_snapshot_chunk.sender, + impl From for pb::abci::RequestApplySnapshotChunk { + fn from(apply_snapshot_chunk: ApplySnapshotChunk) -> Self { + Self { + index: apply_snapshot_chunk.index, + chunk: apply_snapshot_chunk.chunk, + sender: apply_snapshot_chunk.sender, + } } } -} -impl TryFrom for ApplySnapshotChunk { - type Error = crate::Error; + impl TryFrom for ApplySnapshotChunk { + type Error = crate::Error; - fn try_from(apply_snapshot_chunk: pb::RequestApplySnapshotChunk) -> Result { - Ok(Self { - index: apply_snapshot_chunk.index, - chunk: apply_snapshot_chunk.chunk, - sender: apply_snapshot_chunk.sender, - }) + fn try_from(apply_snapshot_chunk: pb::abci::RequestApplySnapshotChunk) -> Result { + Ok(Self { + index: apply_snapshot_chunk.index, + chunk: apply_snapshot_chunk.chunk, + sender: apply_snapshot_chunk.sender, + }) + } } -} -impl Protobuf for ApplySnapshotChunk {} + impl Protobuf for ApplySnapshotChunk {} +} diff --git a/tendermint/src/abci/request/begin_block.rs b/tendermint/src/abci/request/begin_block.rs index e7da9be76..9174d77b3 100644 --- a/tendermint/src/abci/request/begin_block.rs +++ b/tendermint/src/abci/request/begin_block.rs @@ -1,8 +1,12 @@ -use super::super::types::{Evidence, LastCommitInfo}; // bring into scope for doc links #[allow(unused)] use super::DeliverTx; -use crate::{block, prelude::*, Error, Hash}; +use crate::{ + abci::types::{CommitInfo, Misbehavior}, + block, + prelude::*, + Hash, +}; #[doc = include_str!("../doc/request-beginblock.md")] #[derive(Clone, PartialEq, Eq, Debug)] @@ -17,55 +21,56 @@ pub struct BeginBlock { /// /// This includes the round, the list of validators, and which validators /// signed the last block. - pub last_commit_info: LastCommitInfo, + pub last_commit_info: CommitInfo, /// Evidence of validator misbehavior. - pub byzantine_validators: Vec, + pub byzantine_validators: Vec, } // ============================================================================= // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; +tendermint_pb_modules! { + use super::BeginBlock; + use crate::Error; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestBeginBlock { - fn from(begin_block: BeginBlock) -> Self { - Self { - hash: begin_block.hash.into(), - header: Some(begin_block.header.into()), - last_commit_info: Some(begin_block.last_commit_info.into()), - byzantine_validators: begin_block - .byzantine_validators - .into_iter() - .map(Into::into) - .collect(), + impl From for pb::abci::RequestBeginBlock { + fn from(begin_block: BeginBlock) -> Self { + Self { + hash: begin_block.hash.into(), + header: Some(begin_block.header.into()), + last_commit_info: Some(begin_block.last_commit_info.into()), + byzantine_validators: begin_block + .byzantine_validators + .into_iter() + .map(Into::into) + .collect(), + } } } -} -impl TryFrom for BeginBlock { - type Error = Error; + impl TryFrom for BeginBlock { + type Error = Error; - fn try_from(begin_block: pb::RequestBeginBlock) -> Result { - Ok(Self { - hash: begin_block.hash.try_into()?, - header: begin_block - .header - .ok_or_else(Error::missing_header)? - .try_into()?, - last_commit_info: begin_block - .last_commit_info - .ok_or_else(Error::missing_last_commit_info)? - .try_into()?, - byzantine_validators: begin_block - .byzantine_validators - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - }) + fn try_from(begin_block: pb::abci::RequestBeginBlock) -> Result { + Ok(Self { + hash: begin_block.hash.try_into()?, + header: begin_block + .header + .ok_or_else(Error::missing_header)? + .try_into()?, + last_commit_info: begin_block + .last_commit_info + .ok_or_else(Error::missing_last_commit_info)? + .try_into()?, + byzantine_validators: begin_block + .byzantine_validators + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } } -} -impl Protobuf for BeginBlock {} + impl Protobuf for BeginBlock {} +} diff --git a/tendermint/src/abci/request/check_tx.rs b/tendermint/src/abci/request/check_tx.rs index 0fbf8f10f..8afbc5af7 100644 --- a/tendermint/src/abci/request/check_tx.rs +++ b/tendermint/src/abci/request/check_tx.rs @@ -39,33 +39,33 @@ impl Default for CheckTxKind { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +tendermint_pb_modules! { + use super::{CheckTx, CheckTxKind}; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestCheckTx { - fn from(check_tx: CheckTx) -> Self { - Self { - tx: check_tx.tx, - r#type: check_tx.kind as i32, + impl From for pb::abci::RequestCheckTx { + fn from(check_tx: CheckTx) -> Self { + Self { + tx: check_tx.tx, + r#type: check_tx.kind as i32, + } } } -} -impl TryFrom for CheckTx { - type Error = crate::Error; + impl TryFrom for CheckTx { + type Error = crate::Error; - fn try_from(check_tx: pb::RequestCheckTx) -> Result { - let kind = match check_tx.r#type { - 0 => CheckTxKind::New, - 1 => CheckTxKind::Recheck, - _ => return Err(crate::Error::unsupported_check_tx_type()), - }; - Ok(Self { - tx: check_tx.tx, - kind, - }) + fn try_from(check_tx: pb::abci::RequestCheckTx) -> Result { + let kind = match check_tx.r#type { + 0 => CheckTxKind::New, + 1 => CheckTxKind::Recheck, + _ => return Err(crate::Error::unsupported_check_tx_type()), + }; + Ok(Self { + tx: check_tx.tx, + kind, + }) + } } -} -impl Protobuf for CheckTx {} + impl Protobuf for CheckTx {} +} diff --git a/tendermint/src/abci/request/deliver_tx.rs b/tendermint/src/abci/request/deliver_tx.rs index 4c9bc6d50..83fc11a14 100644 --- a/tendermint/src/abci/request/deliver_tx.rs +++ b/tendermint/src/abci/request/deliver_tx.rs @@ -13,22 +13,22 @@ pub struct DeliverTx { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +tendermint_pb_modules! { + use super::DeliverTx; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestDeliverTx { - fn from(deliver_tx: DeliverTx) -> Self { - Self { tx: deliver_tx.tx } + impl From for pb::abci::RequestDeliverTx { + fn from(deliver_tx: DeliverTx) -> Self { + Self { tx: deliver_tx.tx } + } } -} -impl TryFrom for DeliverTx { - type Error = crate::Error; + impl TryFrom for DeliverTx { + type Error = crate::Error; - fn try_from(deliver_tx: pb::RequestDeliverTx) -> Result { - Ok(Self { tx: deliver_tx.tx }) + fn try_from(deliver_tx: pb::abci::RequestDeliverTx) -> Result { + Ok(Self { tx: deliver_tx.tx }) + } } -} -impl Protobuf for DeliverTx {} + impl Protobuf for DeliverTx {} +} diff --git a/tendermint/src/abci/request/echo.rs b/tendermint/src/abci/request/echo.rs index 469096367..d930c7691 100644 --- a/tendermint/src/abci/request/echo.rs +++ b/tendermint/src/abci/request/echo.rs @@ -11,40 +11,10 @@ pub struct Echo { // Protobuf conversions // ============================================================================= -mod v0_34 { - use tendermint_proto::v0_34::abci as pb; - use tendermint_proto::Protobuf; - - use super::Echo; - - impl From for pb::RequestEcho { - fn from(echo: Echo) -> Self { - Self { - message: echo.message, - } - } - } - - impl TryFrom for Echo { - type Error = crate::Error; - - fn try_from(echo: pb::RequestEcho) -> Result { - Ok(Self { - message: echo.message, - }) - } - } - - impl Protobuf for Echo {} -} - -mod v0_37 { - use tendermint_proto::v0_37::abci as pb; - use tendermint_proto::Protobuf; - +tendermint_pb_modules! { use super::Echo; - impl From for pb::RequestEcho { + impl From for pb::abci::RequestEcho { fn from(echo: Echo) -> Self { Self { message: echo.message, @@ -52,15 +22,15 @@ mod v0_37 { } } - impl TryFrom for Echo { + impl TryFrom for Echo { type Error = crate::Error; - fn try_from(echo: pb::RequestEcho) -> Result { + fn try_from(echo: pb::abci::RequestEcho) -> Result { Ok(Self { message: echo.message, }) } } - impl Protobuf for Echo {} + impl Protobuf for Echo {} } diff --git a/tendermint/src/abci/request/end_block.rs b/tendermint/src/abci/request/end_block.rs index 7095ea39f..c3b05b8b8 100644 --- a/tendermint/src/abci/request/end_block.rs +++ b/tendermint/src/abci/request/end_block.rs @@ -11,26 +11,26 @@ pub struct EndBlock { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestEndBlock { - fn from(end_block: EndBlock) -> Self { - Self { - height: end_block.height, +tendermint_pb_modules! { + use super::EndBlock; + + impl From for pb::abci::RequestEndBlock { + fn from(end_block: EndBlock) -> Self { + Self { + height: end_block.height, + } } } -} -impl TryFrom for EndBlock { - type Error = crate::Error; + impl TryFrom for EndBlock { + type Error = crate::Error; - fn try_from(end_block: pb::RequestEndBlock) -> Result { - Ok(Self { - height: end_block.height, - }) + fn try_from(end_block: pb::abci::RequestEndBlock) -> Result { + Ok(Self { + height: end_block.height, + }) + } } -} -impl Protobuf for EndBlock {} + impl Protobuf for EndBlock {} +} diff --git a/tendermint/src/abci/request/info.rs b/tendermint/src/abci/request/info.rs index 1a2c900d8..f9be161b6 100644 --- a/tendermint/src/abci/request/info.rs +++ b/tendermint/src/abci/request/info.rs @@ -9,36 +9,73 @@ pub struct Info { pub block_version: u64, /// The Tendermint p2p protocol version. pub p2p_version: u64, + /// The ABCI protocol version. + pub abci_version: String, } // ============================================================================= // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +mod v0_34 { + use super::Info; + use tendermint_proto::v0_34::abci as pb; + use tendermint_proto::Protobuf; -use tendermint_proto::{abci as pb, Protobuf}; + impl From for pb::RequestInfo { + fn from(info: Info) -> Self { + Self { + version: info.version, + block_version: info.block_version, + p2p_version: info.p2p_version, + } + } + } + + impl TryFrom for Info { + type Error = crate::Error; -impl From for pb::RequestInfo { - fn from(info: Info) -> Self { - Self { - version: info.version, - block_version: info.block_version, - p2p_version: info.p2p_version, + fn try_from(info: pb::RequestInfo) -> Result { + Ok(Self { + version: info.version, + block_version: info.block_version, + p2p_version: info.p2p_version, + abci_version: Default::default(), + }) } } + + impl Protobuf for Info {} } -impl TryFrom for Info { - type Error = crate::Error; +mod v0_37 { + use super::Info; + use tendermint_proto::v0_37::abci as pb; + use tendermint_proto::Protobuf; - fn try_from(info: pb::RequestInfo) -> Result { - Ok(Self { - version: info.version, - block_version: info.block_version, - p2p_version: info.p2p_version, - }) + impl From for pb::RequestInfo { + fn from(info: Info) -> Self { + Self { + version: info.version, + block_version: info.block_version, + p2p_version: info.p2p_version, + abci_version: info.abci_version, + } + } } -} -impl Protobuf for Info {} + impl TryFrom for Info { + type Error = crate::Error; + + fn try_from(info: pb::RequestInfo) -> Result { + Ok(Self { + version: info.version, + block_version: info.block_version, + p2p_version: info.p2p_version, + abci_version: info.abci_version, + }) + } + } + + impl Protobuf for Info {} +} diff --git a/tendermint/src/abci/request/init_chain.rs b/tendermint/src/abci/request/init_chain.rs index 31a803f3f..6c5d01836 100644 --- a/tendermint/src/abci/request/init_chain.rs +++ b/tendermint/src/abci/request/init_chain.rs @@ -25,48 +25,47 @@ pub struct InitChain { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; +tendermint_pb_modules! { + use super::InitChain; + use crate::Error; -use tendermint_proto::{abci as pb, Protobuf}; - -use crate::Error; - -impl From for pb::RequestInitChain { - fn from(init_chain: InitChain) -> Self { - Self { - time: Some(init_chain.time.into()), - chain_id: init_chain.chain_id, - consensus_params: Some(init_chain.consensus_params.into()), - validators: init_chain.validators.into_iter().map(Into::into).collect(), - app_state_bytes: init_chain.app_state_bytes, - initial_height: init_chain.initial_height.into(), + impl From for pb::abci::RequestInitChain { + fn from(init_chain: InitChain) -> Self { + Self { + time: Some(init_chain.time.into()), + chain_id: init_chain.chain_id, + consensus_params: Some(init_chain.consensus_params.into()), + validators: init_chain.validators.into_iter().map(Into::into).collect(), + app_state_bytes: init_chain.app_state_bytes, + initial_height: init_chain.initial_height.into(), + } } } -} -impl TryFrom for InitChain { - type Error = Error; + impl TryFrom for InitChain { + type Error = Error; - fn try_from(init_chain: pb::RequestInitChain) -> Result { - Ok(Self { - time: init_chain - .time - .ok_or_else(Error::missing_genesis_time)? - .try_into()?, - chain_id: init_chain.chain_id, - consensus_params: init_chain - .consensus_params - .ok_or_else(Error::missing_consensus_params)? - .try_into()?, - validators: init_chain - .validators - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - app_state_bytes: init_chain.app_state_bytes, - initial_height: init_chain.initial_height.try_into()?, - }) + fn try_from(init_chain: pb::abci::RequestInitChain) -> Result { + Ok(Self { + time: init_chain + .time + .ok_or_else(Error::missing_genesis_time)? + .try_into()?, + chain_id: init_chain.chain_id, + consensus_params: init_chain + .consensus_params + .ok_or_else(Error::missing_consensus_params)? + .try_into()?, + validators: init_chain + .validators + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + app_state_bytes: init_chain.app_state_bytes, + initial_height: init_chain.initial_height.try_into()?, + }) + } } -} -impl Protobuf for InitChain {} + impl Protobuf for InitChain {} +} diff --git a/tendermint/src/abci/request/load_snapshot_chunk.rs b/tendermint/src/abci/request/load_snapshot_chunk.rs index 4c56ed6e3..1639c27f9 100644 --- a/tendermint/src/abci/request/load_snapshot_chunk.rs +++ b/tendermint/src/abci/request/load_snapshot_chunk.rs @@ -15,30 +15,30 @@ pub struct LoadSnapshotChunk { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestLoadSnapshotChunk { - fn from(load_snapshot_chunk: LoadSnapshotChunk) -> Self { - Self { - height: load_snapshot_chunk.height.into(), - format: load_snapshot_chunk.format, - chunk: load_snapshot_chunk.chunk, +tendermint_pb_modules! { + use super::LoadSnapshotChunk; + + impl From for pb::abci::RequestLoadSnapshotChunk { + fn from(load_snapshot_chunk: LoadSnapshotChunk) -> Self { + Self { + height: load_snapshot_chunk.height.into(), + format: load_snapshot_chunk.format, + chunk: load_snapshot_chunk.chunk, + } } } -} -impl TryFrom for LoadSnapshotChunk { - type Error = crate::Error; + impl TryFrom for LoadSnapshotChunk { + type Error = crate::Error; - fn try_from(load_snapshot_chunk: pb::RequestLoadSnapshotChunk) -> Result { - Ok(Self { - height: load_snapshot_chunk.height.try_into()?, - format: load_snapshot_chunk.format, - chunk: load_snapshot_chunk.chunk, - }) + fn try_from(load_snapshot_chunk: pb::abci::RequestLoadSnapshotChunk) -> Result { + Ok(Self { + height: load_snapshot_chunk.height.try_into()?, + format: load_snapshot_chunk.format, + chunk: load_snapshot_chunk.chunk, + }) + } } -} -impl Protobuf for LoadSnapshotChunk {} + impl Protobuf for LoadSnapshotChunk {} +} diff --git a/tendermint/src/abci/request/offer_snapshot.rs b/tendermint/src/abci/request/offer_snapshot.rs index c641c8ad2..af50c0c75 100644 --- a/tendermint/src/abci/request/offer_snapshot.rs +++ b/tendermint/src/abci/request/offer_snapshot.rs @@ -17,31 +17,31 @@ pub struct OfferSnapshot { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestOfferSnapshot { - fn from(offer_snapshot: OfferSnapshot) -> Self { - Self { - snapshot: Some(offer_snapshot.snapshot.into()), - app_hash: offer_snapshot.app_hash.into(), +tendermint_pb_modules! { + use super::OfferSnapshot; + + impl From for pb::abci::RequestOfferSnapshot { + fn from(offer_snapshot: OfferSnapshot) -> Self { + Self { + snapshot: Some(offer_snapshot.snapshot.into()), + app_hash: offer_snapshot.app_hash.into(), + } } } -} - -impl TryFrom for OfferSnapshot { - type Error = crate::Error; - fn try_from(offer_snapshot: pb::RequestOfferSnapshot) -> Result { - Ok(Self { - snapshot: offer_snapshot - .snapshot - .ok_or_else(crate::Error::missing_data)? - .try_into()?, - app_hash: offer_snapshot.app_hash.try_into()?, - }) + impl TryFrom for OfferSnapshot { + type Error = crate::Error; + + fn try_from(offer_snapshot: pb::abci::RequestOfferSnapshot) -> Result { + Ok(Self { + snapshot: offer_snapshot + .snapshot + .ok_or_else(crate::Error::missing_data)? + .try_into()?, + app_hash: offer_snapshot.app_hash.try_into()?, + }) + } } -} -impl Protobuf for OfferSnapshot {} + impl Protobuf for OfferSnapshot {} +} diff --git a/tendermint/src/abci/request/prepare_proposal.rs b/tendermint/src/abci/request/prepare_proposal.rs index 30e618063..a95dc691e 100644 --- a/tendermint/src/abci/request/prepare_proposal.rs +++ b/tendermint/src/abci/request/prepare_proposal.rs @@ -27,6 +27,8 @@ pub struct PrepareProposal { // Protobuf conversions // ============================================================================= +// The PrepareProposal request has been added in 0.37. + use tendermint_proto::v0_37::abci as pb; use tendermint_proto::Protobuf; diff --git a/tendermint/src/abci/request/process_proposal.rs b/tendermint/src/abci/request/process_proposal.rs index 97937b1c8..bb3020048 100644 --- a/tendermint/src/abci/request/process_proposal.rs +++ b/tendermint/src/abci/request/process_proposal.rs @@ -26,6 +26,8 @@ pub struct ProcessProposal { // Protobuf conversions // ============================================================================= +// The ProcessProposal request has been added in 0.37. + use tendermint_proto::v0_37::abci as pb; use tendermint_proto::Protobuf; diff --git a/tendermint/src/abci/request/query.rs b/tendermint/src/abci/request/query.rs index 07dade853..260a4a120 100644 --- a/tendermint/src/abci/request/query.rs +++ b/tendermint/src/abci/request/query.rs @@ -32,32 +32,32 @@ pub struct Query { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::RequestQuery { - fn from(query: Query) -> Self { - Self { - data: query.data, - path: query.path, - height: query.height.into(), - prove: query.prove, +tendermint_pb_modules! { + use super::Query; + + impl From for pb::abci::RequestQuery { + fn from(query: Query) -> Self { + Self { + data: query.data, + path: query.path, + height: query.height.into(), + prove: query.prove, + } } } -} -impl TryFrom for Query { - type Error = crate::Error; + impl TryFrom for Query { + type Error = crate::Error; - fn try_from(query: pb::RequestQuery) -> Result { - Ok(Self { - data: query.data, - path: query.path, - height: query.height.try_into()?, - prove: query.prove, - }) + fn try_from(query: pb::abci::RequestQuery) -> Result { + Ok(Self { + data: query.data, + path: query.path, + height: query.height.try_into()?, + prove: query.prove, + }) + } } -} -impl Protobuf for Query {} + impl Protobuf for Query {} +} diff --git a/tendermint/src/abci/request/set_option.rs b/tendermint/src/abci/request/set_option.rs index ffb4dd9bb..3f2f5397c 100644 --- a/tendermint/src/abci/request/set_option.rs +++ b/tendermint/src/abci/request/set_option.rs @@ -11,9 +11,10 @@ pub struct SetOption { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +// The SetOption request has been removed after 0.34. -use tendermint_proto::{abci as pb, Protobuf}; +use tendermint_proto::v0_34::abci as pb; +use tendermint_proto::Protobuf; impl From for pb::RequestSetOption { fn from(message: SetOption) -> Self { diff --git a/tendermint/src/abci/response/set_option.rs b/tendermint/src/abci/response/set_option.rs index 028eafde5..98399dbb1 100644 --- a/tendermint/src/abci/response/set_option.rs +++ b/tendermint/src/abci/response/set_option.rs @@ -13,9 +13,10 @@ pub struct SetOption { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +// The SetOption request has been removed after 0.34. -use tendermint_proto::{abci as pb, Protobuf}; +use tendermint_proto::v0_34::abci as pb; +use tendermint_proto::Protobuf; impl From for pb::ResponseSetOption { fn from(message: SetOption) -> Self { diff --git a/tendermint/src/block/header.rs b/tendermint/src/block/header.rs index 5c4f73b93..cc99443b5 100644 --- a/tendermint/src/block/header.rs +++ b/tendermint/src/block/header.rs @@ -1,15 +1,14 @@ //! Block headers -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; use tendermint_proto::{ - types::Header as RawHeader, version::Consensus as RawConsensusVersion, Protobuf, + types::{BlockId as RawBlockId, Header as RawHeader}, + version::Consensus as RawConsensusVersion, + Protobuf, }; use crate::{ - account, block, chain, merkle::simple_hash_from_byte_vectors, prelude::*, AppHash, Error, Hash, - Time, + account, block, chain, merkle::simple_hash_from_byte_vectors, prelude::*, AppHash, Hash, Time, }; /// Block `Header` values contain metadata about the block and about the @@ -63,106 +62,6 @@ pub struct Header { pub proposer_address: account::Id, } -impl Protobuf for Header {} - -impl TryFrom for Header { - type Error = Error; - - fn try_from(value: RawHeader) -> Result { - // If last block id is unfilled, it is considered nil by Go. - let last_block_id = value - .last_block_id - .map(TryInto::try_into) - .transpose()? - .filter(|l| l != &block::Id::default()); - let last_commit_hash = if value.last_commit_hash.is_empty() { - None - } else { - Some(value.last_commit_hash.try_into()?) - }; - let last_results_hash = if value.last_results_hash.is_empty() { - None - } else { - Some(value.last_results_hash.try_into()?) - }; - let height: block::Height = value.height.try_into()?; - - // Todo: fix domain logic - // if last_block_id.is_none() && height.value() != 1 { - // return Err(Kind::InvalidHeader.context("last_block_id is null on non-first - // height").into()); - //} - if last_block_id.is_some() && height.value() == 1 { - return Err(Error::invalid_first_header()); - } - // if last_commit_hash.is_none() && height.value() != 1 { - // return Err(Kind::InvalidHeader.context("last_commit_hash is null on non-first - // height").into()); - //} - // if height.value() == 1 && last_commit_hash.is_some() && - // last_commit_hash.as_ref().unwrap() != simple_hash_from_byte_vectors(Vec::new()) { - // return Err(Kind::InvalidFirstHeader.context("last_commit_hash is not empty Merkle tree - // on first height").into()); - //} - // if last_results_hash.is_none() && height.value() != 1 { - // return Err(Kind::InvalidHeader.context("last_results_hash is null on non-first - // height").into()); - //} - // if last_results_hash.is_some() && height.value() == 1 { - // return Err(Kind::InvalidFirstHeader.context("last_results_hash is not ull on first - // height").into()); - //} - Ok(Header { - version: value.version.ok_or_else(Error::missing_version)?.into(), - chain_id: value.chain_id.try_into()?, - height, - time: value - .time - .ok_or_else(Error::missing_timestamp)? - .try_into()?, - last_block_id, - last_commit_hash, - data_hash: if value.data_hash.is_empty() { - None - } else { - Some(value.data_hash.try_into()?) - }, - validators_hash: value.validators_hash.try_into()?, - next_validators_hash: value.next_validators_hash.try_into()?, - consensus_hash: value.consensus_hash.try_into()?, - app_hash: value.app_hash.try_into()?, - last_results_hash, - evidence_hash: if value.evidence_hash.is_empty() { - None - } else { - Some(value.evidence_hash.try_into()?) - }, // Todo: Is it illegal to have evidence of wrongdoing in the first block? - proposer_address: value.proposer_address.try_into()?, - }) - } -} - -impl From
for RawHeader { - fn from(value: Header) -> Self { - RawHeader { - version: Some(value.version.into()), - chain_id: value.chain_id.into(), - height: value.height.into(), - time: Some(value.time.into()), - last_block_id: value.last_block_id.map(Into::into), - last_commit_hash: value.last_commit_hash.unwrap_or_default().into(), - data_hash: value.data_hash.unwrap_or_default().into(), - validators_hash: value.validators_hash.into(), - next_validators_hash: value.next_validators_hash.into(), - consensus_hash: value.consensus_hash.into(), - app_hash: value.app_hash.into(), - last_results_hash: value.last_results_hash.unwrap_or_default().into(), - evidence_hash: value.evidence_hash.unwrap_or_default().into(), - proposer_address: value.proposer_address.into(), - } - } -} - impl Header { /// Hash this header pub fn hash(&self) -> Hash { @@ -172,11 +71,11 @@ impl Header { // https://github.com/tendermint/tendermint/blob/134fe2896275bb926b49743c1e25493f6b24cc31/types/encoding_helper.go#L9:6 let fields_bytes = vec![ - self.version.encode_vec().unwrap(), + Protobuf::::encode_vec(&self.version).unwrap(), self.chain_id.encode_vec().unwrap(), self.height.encode_vec().unwrap(), self.time.encode_vec().unwrap(), - self.last_block_id.unwrap_or_default().encode_vec().unwrap(), + Protobuf::::encode_vec(&self.last_block_id.unwrap_or_default()).unwrap(), self.last_commit_hash .unwrap_or_default() .encode_vec() @@ -211,22 +110,135 @@ pub struct Version { pub app: u64, } -impl Protobuf for Version {} +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +tendermint_pb_modules! { + use super::{Header, Version}; + use crate::{block, Error}; + use pb::{ + types::Header as RawHeader, + version::Consensus as RawConsensusVersion, + }; + + impl Protobuf for Header {} + + impl TryFrom for Header { + type Error = Error; + + fn try_from(value: RawHeader) -> Result { + // If last block id is unfilled, it is considered nil by Go. + let last_block_id = value + .last_block_id + .map(TryInto::try_into) + .transpose()? + .filter(|l| l != &block::Id::default()); + let last_commit_hash = if value.last_commit_hash.is_empty() { + None + } else { + Some(value.last_commit_hash.try_into()?) + }; + let last_results_hash = if value.last_results_hash.is_empty() { + None + } else { + Some(value.last_results_hash.try_into()?) + }; + let height: block::Height = value.height.try_into()?; + + // Todo: fix domain logic + // if last_block_id.is_none() && height.value() != 1 { + // return Err(Kind::InvalidHeader.context("last_block_id is null on non-first + // height").into()); + //} + if last_block_id.is_some() && height.value() == 1 { + return Err(Error::invalid_first_header()); + } + // if last_commit_hash.is_none() && height.value() != 1 { + // return Err(Kind::InvalidHeader.context("last_commit_hash is null on non-first + // height").into()); + //} + // if height.value() == 1 && last_commit_hash.is_some() && + // last_commit_hash.as_ref().unwrap() != simple_hash_from_byte_vectors(Vec::new()) { + // return Err(Kind::InvalidFirstHeader.context("last_commit_hash is not empty Merkle tree + // on first height").into()); + //} + // if last_results_hash.is_none() && height.value() != 1 { + // return Err(Kind::InvalidHeader.context("last_results_hash is null on non-first + // height").into()); + //} + // if last_results_hash.is_some() && height.value() == 1 { + // return Err(Kind::InvalidFirstHeader.context("last_results_hash is not ull on first + // height").into()); + //} + Ok(Header { + version: value.version.ok_or_else(Error::missing_version)?.into(), + chain_id: value.chain_id.try_into()?, + height, + time: value + .time + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + last_block_id, + last_commit_hash, + data_hash: if value.data_hash.is_empty() { + None + } else { + Some(value.data_hash.try_into()?) + }, + validators_hash: value.validators_hash.try_into()?, + next_validators_hash: value.next_validators_hash.try_into()?, + consensus_hash: value.consensus_hash.try_into()?, + app_hash: value.app_hash.try_into()?, + last_results_hash, + evidence_hash: if value.evidence_hash.is_empty() { + None + } else { + Some(value.evidence_hash.try_into()?) + }, // Todo: Is it illegal to have evidence of wrongdoing in the first block? + proposer_address: value.proposer_address.try_into()?, + }) + } + } + + impl From
for RawHeader { + fn from(value: Header) -> Self { + RawHeader { + version: Some(value.version.into()), + chain_id: value.chain_id.into(), + height: value.height.into(), + time: Some(value.time.into()), + last_block_id: value.last_block_id.map(Into::into), + last_commit_hash: value.last_commit_hash.unwrap_or_default().into(), + data_hash: value.data_hash.unwrap_or_default().into(), + validators_hash: value.validators_hash.into(), + next_validators_hash: value.next_validators_hash.into(), + consensus_hash: value.consensus_hash.into(), + app_hash: value.app_hash.into(), + last_results_hash: value.last_results_hash.unwrap_or_default().into(), + evidence_hash: value.evidence_hash.unwrap_or_default().into(), + proposer_address: value.proposer_address.into(), + } + } + } + + impl Protobuf for Version {} -impl From for Version { - fn from(value: RawConsensusVersion) -> Self { - Version { - block: value.block, - app: value.app, + impl From for Version { + fn from(value: RawConsensusVersion) -> Self { + Version { + block: value.block, + app: value.app, + } } } -} -impl From for RawConsensusVersion { - fn from(value: Version) -> Self { - RawConsensusVersion { - block: value.block, - app: value.app, + impl From for RawConsensusVersion { + fn from(value: Version) -> Self { + RawConsensusVersion { + block: value.block, + app: value.app, + } } } } diff --git a/tendermint/src/block/id.rs b/tendermint/src/block/id.rs index e42e50ca4..fc29bb506 100644 --- a/tendermint/src/block/id.rs +++ b/tendermint/src/block/id.rs @@ -1,17 +1,10 @@ use core::{ - convert::{TryFrom, TryInto}, fmt::{self, Display}, str::{self, FromStr}, }; use serde::{Deserialize, Serialize}; -use tendermint_proto::{ - types::{ - BlockId as RawBlockId, CanonicalBlockId as RawCanonicalBlockId, - PartSetHeader as RawPartSetHeader, - }, - Protobuf, -}; +use tendermint_proto::types::BlockId as RawBlockId; use crate::{ block::parts::Header as PartSetHeader, @@ -62,68 +55,79 @@ pub struct Id { pub part_set_header: PartSetHeader, } -impl Protobuf for Id {} +tendermint_pb_modules! { + use pb::{ + types::{ + BlockId as RawBlockId, CanonicalBlockId as RawCanonicalBlockId, + PartSetHeader as RawPartSetHeader, + } + }; + use super::Id; + use crate::{prelude::*, Error}; + + impl Protobuf for Id {} -impl TryFrom for Id { - type Error = Error; + impl TryFrom for Id { + type Error = Error; - fn try_from(value: RawBlockId) -> Result { - if value.part_set_header.is_none() { - return Err(Error::invalid_part_set_header( - "part_set_header is None".to_string(), - )); + fn try_from(value: RawBlockId) -> Result { + if value.part_set_header.is_none() { + return Err(Error::invalid_part_set_header( + "part_set_header is None".to_string(), + )); + } + Ok(Self { + hash: value.hash.try_into()?, + part_set_header: value.part_set_header.unwrap().try_into()?, + }) } - Ok(Self { - hash: value.hash.try_into()?, - part_set_header: value.part_set_header.unwrap().try_into()?, - }) } -} -impl From for RawBlockId { - fn from(value: Id) -> Self { - // https://github.com/tendermint/tendermint/blob/1635d1339c73ae6a82e062cd2dc7191b029efa14/types/block.go#L1204 - // The Go implementation encodes a nil value into an empty struct. We try our best to - // anticipate an empty struct by using the default implementation which would otherwise be - // invalid. - if value == Id::default() { - RawBlockId { - hash: vec![], - part_set_header: Some(RawPartSetHeader { - total: 0, + impl From for RawBlockId { + fn from(value: Id) -> Self { + // https://github.com/tendermint/tendermint/blob/1635d1339c73ae6a82e062cd2dc7191b029efa14/types/block.go#L1204 + // The Go implementation encodes a nil value into an empty struct. We try our best to + // anticipate an empty struct by using the default implementation which would otherwise be + // invalid. + if value == Id::default() { + RawBlockId { hash: vec![], - }), - } - } else { - RawBlockId { - hash: value.hash.into(), - part_set_header: Some(value.part_set_header.into()), + part_set_header: Some(RawPartSetHeader { + total: 0, + hash: vec![], + }), + } + } else { + RawBlockId { + hash: value.hash.into(), + part_set_header: Some(value.part_set_header.into()), + } } } } -} -impl TryFrom for Id { - type Error = Error; + impl TryFrom for Id { + type Error = Error; - fn try_from(value: RawCanonicalBlockId) -> Result { - if value.part_set_header.is_none() { - return Err(Error::invalid_part_set_header( - "part_set_header is None".to_string(), - )); + fn try_from(value: RawCanonicalBlockId) -> Result { + if value.part_set_header.is_none() { + return Err(Error::invalid_part_set_header( + "part_set_header is None".to_string(), + )); + } + Ok(Self { + hash: value.hash.try_into()?, + part_set_header: value.part_set_header.unwrap().try_into()?, + }) } - Ok(Self { - hash: value.hash.try_into()?, - part_set_header: value.part_set_header.unwrap().try_into()?, - }) } -} -impl From for RawCanonicalBlockId { - fn from(value: Id) -> Self { - RawCanonicalBlockId { - hash: value.hash.as_bytes().to_vec(), - part_set_header: Some(value.part_set_header.into()), + impl From for RawCanonicalBlockId { + fn from(value: Id) -> Self { + RawCanonicalBlockId { + hash: value.hash.as_bytes().to_vec(), + part_set_header: Some(value.part_set_header.into()), + } } } } diff --git a/tendermint/src/block/parts.rs b/tendermint/src/block/parts.rs index 6ae906ec7..19d6fdf2d 100644 --- a/tendermint/src/block/parts.rs +++ b/tendermint/src/block/parts.rs @@ -1,21 +1,9 @@ //! Block parts -use core::convert::TryFrom; - use serde::{Deserialize, Serialize}; -use tendermint_proto::{ - types::{ - CanonicalPartSetHeader as RawCanonicalPartSetHeader, PartSetHeader as RawPartSetHeader, - }, - Protobuf, -}; +use tendermint_proto::types::PartSetHeader as RawPartSetHeader; -use crate::{ - error::Error, - hash::{Algorithm, SHA256_HASH_SIZE}, - prelude::*, - Hash, -}; +use crate::{error::Error, prelude::*, Hash}; /// Block parts header #[derive( @@ -31,50 +19,63 @@ pub struct Header { pub hash: Hash, } -impl Protobuf for Header {} +tendermint_pb_modules! { + use pb::types::{ + CanonicalPartSetHeader as RawCanonicalPartSetHeader, PartSetHeader as RawPartSetHeader, + }; + use crate::{ + error::Error, + hash::{Algorithm, SHA256_HASH_SIZE}, + prelude::*, + Hash, + }; + use super::Header; + + impl Protobuf for Header {} -impl TryFrom for Header { - type Error = Error; + impl TryFrom for Header { + type Error = Error; - fn try_from(value: RawPartSetHeader) -> Result { - if !value.hash.is_empty() && value.hash.len() != SHA256_HASH_SIZE { - return Err(Error::invalid_hash_size()); + fn try_from(value: RawPartSetHeader) -> Result { + if !value.hash.is_empty() && value.hash.len() != SHA256_HASH_SIZE { + return Err(Error::invalid_hash_size()); + } + Ok(Self { + total: value.total, + hash: Hash::from_bytes(Algorithm::Sha256, &value.hash)?, + }) } - Ok(Self { - total: value.total, - hash: Hash::from_bytes(Algorithm::Sha256, &value.hash)?, - }) } -} -impl From
for RawPartSetHeader { - fn from(value: Header) -> Self { - RawPartSetHeader { - total: value.total, - hash: value.hash.into(), + impl From
for RawPartSetHeader { + fn from(value: Header) -> Self { + RawPartSetHeader { + total: value.total, + hash: value.hash.into(), + } } } -} -impl TryFrom for Header { - type Error = Error; + impl TryFrom for Header { + type Error = Error; - fn try_from(value: RawCanonicalPartSetHeader) -> Result { - if !value.hash.is_empty() && value.hash.len() != SHA256_HASH_SIZE { - return Err(Error::invalid_hash_size()); + fn try_from(value: RawCanonicalPartSetHeader) -> Result { + if !value.hash.is_empty() && value.hash.len() != SHA256_HASH_SIZE { + return Err(Error::invalid_hash_size()); + } + Ok(Self { + total: value.total, + hash: Hash::from_bytes(Algorithm::Sha256, &value.hash)?, + }) } - Ok(Self { - total: value.total, - hash: Hash::from_bytes(Algorithm::Sha256, &value.hash)?, - }) } -} -impl From
for RawCanonicalPartSetHeader { - fn from(value: Header) -> Self { - RawCanonicalPartSetHeader { - total: value.total, - hash: value.hash.into(), + impl From
for RawCanonicalPartSetHeader { + fn from(value: Header) -> Self { + RawCanonicalPartSetHeader { + total: value.total, + hash: value.hash.into(), + } } } } diff --git a/tendermint/src/block/size.rs b/tendermint/src/block/size.rs index 093cd580d..52204eec5 100644 --- a/tendermint/src/block/size.rs +++ b/tendermint/src/block/size.rs @@ -1,11 +1,8 @@ //! Block size parameters -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; -use tendermint_proto::{abci::BlockParams as RawAbciSize, types::BlockParams as RawSize, Protobuf}; -use crate::{error::Error, serializers}; +use crate::serializers; /// Block size parameters #[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq)] @@ -25,62 +22,105 @@ pub struct Size { impl Size { /// The default value for the `time_iota_ms` parameter. - pub fn default_time_iota_ms() -> i64 { + pub const fn default_time_iota_ms() -> i64 { 1000 } } -impl Protobuf for Size {} +mod v0_34 { + use super::Size; + use crate::error::Error; + use tendermint_proto::v0_34::{ + abci::BlockParams as RawAbciSize, types::BlockParams as RawSize, + }; + use tendermint_proto::Protobuf; + + impl Protobuf for Size {} -impl TryFrom for Size { - type Error = Error; + impl TryFrom for Size { + type Error = Error; - fn try_from(value: RawSize) -> Result { - Ok(Self { - max_bytes: value - .max_bytes - .try_into() - .map_err(Error::integer_overflow)?, - max_gas: value.max_gas, - time_iota_ms: value.time_iota_ms, - }) + fn try_from(value: RawSize) -> Result { + Ok(Self { + max_bytes: value + .max_bytes + .try_into() + .map_err(Error::integer_overflow)?, + max_gas: value.max_gas, + time_iota_ms: value.time_iota_ms, + }) + } } -} -impl From for RawSize { - fn from(value: Size) -> Self { - // Todo: make the struct more robust so this can become infallible. - RawSize { - max_bytes: value.max_bytes as i64, - max_gas: value.max_gas, - time_iota_ms: value.time_iota_ms, + impl From for RawSize { + fn from(value: Size) -> Self { + // Todo: make the struct more robust so this can become infallible. + RawSize { + max_bytes: value.max_bytes as i64, + max_gas: value.max_gas, + time_iota_ms: value.time_iota_ms, + } } } -} -impl Protobuf for Size {} + impl Protobuf for Size {} -impl TryFrom for Size { - type Error = Error; + impl TryFrom for Size { + type Error = Error; - fn try_from(value: RawAbciSize) -> Result { - Ok(Self { - max_bytes: value - .max_bytes - .try_into() - .map_err(Error::integer_overflow)?, - max_gas: value.max_gas, - time_iota_ms: Self::default_time_iota_ms(), - }) + fn try_from(value: RawAbciSize) -> Result { + Ok(Self { + max_bytes: value + .max_bytes + .try_into() + .map_err(Error::integer_overflow)?, + max_gas: value.max_gas, + time_iota_ms: Self::default_time_iota_ms(), + }) + } + } + + impl From for RawAbciSize { + fn from(value: Size) -> Self { + // Todo: make the struct more robust so this can become infallible. + RawAbciSize { + max_bytes: value.max_bytes as i64, + max_gas: value.max_gas, + } + } } } -impl From for RawAbciSize { - fn from(value: Size) -> Self { - // Todo: make the struct more robust so this can become infallible. - RawAbciSize { - max_bytes: value.max_bytes as i64, - max_gas: value.max_gas, +mod v0_37 { + use super::Size; + use crate::error::Error; + use tendermint_proto::v0_37::types::BlockParams as RawSize; + use tendermint_proto::Protobuf; + + impl Protobuf for Size {} + + impl TryFrom for Size { + type Error = Error; + + fn try_from(value: RawSize) -> Result { + Ok(Self { + max_bytes: value + .max_bytes + .try_into() + .map_err(Error::integer_overflow)?, + max_gas: value.max_gas, + time_iota_ms: Size::default_time_iota_ms(), + }) + } + } + + impl From for RawSize { + fn from(value: Size) -> Self { + // Todo: make the struct more robust so this can become infallible. + RawSize { + max_bytes: value.max_bytes as i64, + max_gas: value.max_gas, + } } } } diff --git a/tendermint/src/consensus/params.rs b/tendermint/src/consensus/params.rs index cf4fb728a..10361050a 100644 --- a/tendermint/src/consensus/params.rs +++ b/tendermint/src/consensus/params.rs @@ -44,6 +44,17 @@ pub struct VersionParams { // Protobuf conversions // ============================================================================= +// Todo: How are these key types created? +fn key_type(s: &str) -> public_key::Algorithm { + if s == "Ed25519" || s == "ed25519" { + return public_key::Algorithm::Ed25519; + } + if s == "Secp256k1" || s == "secp256k1" { + return public_key::Algorithm::Secp256k1; + } + public_key::Algorithm::Ed25519 // Todo: Shall we error out for invalid key types? +} + mod v0_34 { use tendermint_proto::v0_34::{ abci::ConsensusParams as RawAbciParams, @@ -54,7 +65,7 @@ mod v0_34 { }; use tendermint_proto::Protobuf; - use super::{Params, ValidatorParams, VersionParams}; + use super::{key_type, Params, ValidatorParams, VersionParams}; use crate::{error::Error, prelude::*, public_key}; impl Protobuf for Params {} @@ -139,15 +150,97 @@ mod v0_34 { } } - // Todo: How are these key types created? - fn key_type(s: &str) -> public_key::Algorithm { - if s == "Ed25519" || s == "ed25519" { - return public_key::Algorithm::Ed25519; + impl From for RawValidatorParams { + fn from(value: ValidatorParams) -> Self { + RawValidatorParams { + pub_key_types: value + .pub_key_types + .into_iter() + .map(|k| match k { + public_key::Algorithm::Ed25519 => "ed25519".to_string(), + public_key::Algorithm::Secp256k1 => "secp256k1".to_string(), + }) + .collect(), + } } - if s == "Secp256k1" || s == "secp256k1" { - return public_key::Algorithm::Secp256k1; + } + + impl Protobuf for VersionParams {} + + impl TryFrom for VersionParams { + type Error = Error; + + fn try_from(value: RawVersionParams) -> Result { + Ok(Self { + app: value.app_version, + }) + } + } + + impl From for RawVersionParams { + fn from(value: VersionParams) -> Self { + RawVersionParams { + app_version: value.app, + } + } + } +} + +mod v0_37 { + use tendermint_proto::v0_37::types::{ + ConsensusParams as RawParams, ValidatorParams as RawValidatorParams, + VersionParams as RawVersionParams, + }; + use tendermint_proto::Protobuf; + + use super::{key_type, Params, ValidatorParams, VersionParams}; + use crate::{error::Error, prelude::*, public_key}; + + impl Protobuf for Params {} + + impl TryFrom for Params { + type Error = Error; + + fn try_from(value: RawParams) -> Result { + Ok(Self { + block: value + .block + .ok_or_else(|| Error::invalid_block("missing block".to_string()))? + .try_into()?, + evidence: value + .evidence + .ok_or_else(Error::invalid_evidence)? + .try_into()?, + validator: value + .validator + .ok_or_else(Error::invalid_validator_params)? + .try_into()?, + version: value.version.map(TryFrom::try_from).transpose()?, + }) + } + } + + impl From for RawParams { + fn from(value: Params) -> Self { + RawParams { + block: Some(value.block.into()), + evidence: Some(value.evidence.into()), + validator: Some(value.validator.into()), + version: value.version.map(From::from), + } + } + } + + impl Protobuf for ValidatorParams {} + + impl TryFrom for ValidatorParams { + type Error = Error; + + fn try_from(value: RawValidatorParams) -> Result { + Ok(Self { + pub_key_types: value.pub_key_types.iter().map(|f| key_type(f)).collect(), + }) } - public_key::Algorithm::Ed25519 // Todo: Shall we error out for invalid key types? } impl From for RawValidatorParams { diff --git a/tendermint/src/evidence.rs b/tendermint/src/evidence.rs index b7b93db90..6da571a53 100644 --- a/tendermint/src/evidence.rs +++ b/tendermint/src/evidence.rs @@ -120,7 +120,7 @@ pub struct Params { // Protobuf conversions // ============================================================================= -mod v0_37 { +mod v0_34 { use tendermint_proto::v0_37::types::{ evidence::Sum as RawSum, DuplicateVoteEvidence as RawDuplicateVoteEvidence, Evidence as RawEvidence, EvidenceList as RawEvidenceList, @@ -256,6 +256,142 @@ mod v0_37 { } } +mod v0_37 { + use tendermint_proto::v0_34::types::{ + evidence::Sum as RawSum, DuplicateVoteEvidence as RawDuplicateVoteEvidence, + Evidence as RawEvidence, EvidenceList as RawEvidenceList, + EvidenceParams as RawEvidenceParams, + }; + use tendermint_proto::Protobuf; + + use super::{Data, DuplicateVoteEvidence, Evidence, Params}; + use crate::{error::Error, prelude::*}; + + impl TryFrom for Evidence { + type Error = Error; + + fn try_from(value: RawSum) -> Result { + use RawSum::*; + match value { + DuplicateVoteEvidence(ev) => Ok(Evidence::DuplicateVote(ev.try_into()?)), + LightClientAttackEvidence(_ev) => Ok(Evidence::LightClientAttackEvidence), + } + } + } + + impl TryFrom for Evidence { + type Error = Error; + + fn try_from(value: RawEvidence) -> Result { + value + .sum + .ok_or_else(Error::invalid_evidence) + .and_then(TryInto::try_into) + } + } + + impl From for Option { + fn from(value: Evidence) -> Self { + match value { + Evidence::DuplicateVote(ev) => Some(RawSum::DuplicateVoteEvidence(ev.into())), + Evidence::LightClientAttackEvidence => None, + } + } + } + + impl From for RawEvidence { + fn from(value: Evidence) -> Self { + RawEvidence { sum: value.into() } + } + } + + impl TryFrom for DuplicateVoteEvidence { + type Error = Error; + + fn try_from(value: RawDuplicateVoteEvidence) -> Result { + Ok(Self { + vote_a: value + .vote_a + .ok_or_else(Error::missing_evidence)? + .try_into()?, + vote_b: value + .vote_b + .ok_or_else(Error::missing_evidence)? + .try_into()?, + total_voting_power: value.total_voting_power.try_into()?, + validator_power: value.validator_power.try_into()?, + timestamp: value + .timestamp + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + }) + } + } + + impl From for RawDuplicateVoteEvidence { + fn from(value: DuplicateVoteEvidence) -> Self { + RawDuplicateVoteEvidence { + vote_a: Some(value.vote_a.into()), + vote_b: Some(value.vote_b.into()), + total_voting_power: value.total_voting_power.into(), + validator_power: value.total_voting_power.into(), + timestamp: Some(value.timestamp.into()), + } + } + } + + impl TryFrom for Data { + type Error = Error; + fn try_from(value: RawEvidenceList) -> Result { + let evidence = value + .evidence + .into_iter() + .map(TryInto::try_into) + .collect::, _>>()?; + Ok(Self(evidence)) + } + } + + impl From for RawEvidenceList { + fn from(value: Data) -> Self { + RawEvidenceList { + evidence: value.0.into_iter().map(Into::into).collect(), + } + } + } + + impl Protobuf for Params {} + + impl TryFrom for Params { + type Error = Error; + + fn try_from(value: RawEvidenceParams) -> Result { + Ok(Self { + max_age_num_blocks: value + .max_age_num_blocks + .try_into() + .map_err(Error::negative_max_age_num)?, + max_age_duration: value + .max_age_duration + .ok_or_else(Error::missing_max_age_duration)? + .try_into()?, + max_bytes: value.max_bytes, + }) + } + } + + impl From for RawEvidenceParams { + fn from(value: Params) -> Self { + Self { + // Todo: Implement proper domain types so this becomes infallible + max_age_num_blocks: value.max_age_num_blocks.try_into().unwrap(), + max_age_duration: Some(value.max_age_duration.into()), + max_bytes: value.max_bytes, + } + } + } +} + /// Duration is a wrapper around core::time::Duration /// essentially, to keep the usages look cleaner /// i.e. you can avoid using serde annotations everywhere diff --git a/tendermint/src/proto_macros.rs b/tendermint/src/proto_macros.rs index d0c1c4222..1fb5d55a6 100644 --- a/tendermint/src/proto_macros.rs +++ b/tendermint/src/proto_macros.rs @@ -2,19 +2,19 @@ macro_rules! tendermint_pb_modules { { - $(contents:item)* + $($contents:item)* } => { mod v0_34 { use tendermint_proto::v0_34 as pb; use tendermint_proto::Protobuf; - $(contents)* + $($contents)* } mod v0_37 { use tendermint_proto::v0_37 as pb; use tendermint_proto::Protobuf; - $(contents)* + $($contents)* } }; } diff --git a/tendermint/src/public_key.rs b/tendermint/src/public_key.rs index 5b39e5040..779c406ef 100644 --- a/tendermint/src/public_key.rs +++ b/tendermint/src/public_key.rs @@ -14,10 +14,6 @@ use serde::{de, ser, Deserialize, Deserializer, Serialize}; use serde_json::Value; use signature::Verifier as _; use subtle_encoding::{base64, bech32, hex}; -use tendermint_proto::{ - crypto::{public_key::Sum, PublicKey as RawPublicKey}, - Protobuf, -}; use crate::{error::Error, prelude::*, signature::Signature}; @@ -118,42 +114,48 @@ where .map_err(serde::de::Error::custom) } -impl Protobuf for PublicKey {} +tendermint_pb_modules! { + use super::PublicKey; + use pb::crypto::{PublicKey as RawPublicKey, public_key::Sum}; + use crate::{prelude::*, Error}; -impl TryFrom for PublicKey { - type Error = Error; + impl Protobuf for PublicKey {} - fn try_from(value: RawPublicKey) -> Result { - let sum = &value - .sum - .ok_or_else(|| Error::invalid_key("empty sum".to_string()))?; - if let Sum::Ed25519(b) = sum { - return Self::from_raw_ed25519(b) - .ok_or_else(|| Error::invalid_key("malformed ed25519 key".to_string())); - } - #[cfg(feature = "secp256k1")] - if let Sum::Secp256k1(b) = sum { - return Self::from_raw_secp256k1(b) - .ok_or_else(|| Error::invalid_key("malformed key".to_string())); + impl TryFrom for PublicKey { + type Error = Error; + + fn try_from(value: RawPublicKey) -> Result { + let sum = &value + .sum + .ok_or_else(|| Error::invalid_key("empty sum".to_string()))?; + if let Sum::Ed25519(b) = sum { + return Self::from_raw_ed25519(b) + .ok_or_else(|| Error::invalid_key("malformed ed25519 key".to_string())); + } + #[cfg(feature = "secp256k1")] + if let Sum::Secp256k1(b) = sum { + return Self::from_raw_secp256k1(b) + .ok_or_else(|| Error::invalid_key("malformed key".to_string())); + } + Err(Error::invalid_key("not an ed25519 key".to_string())) } - Err(Error::invalid_key("not an ed25519 key".to_string())) } -} -impl From for RawPublicKey { - fn from(value: PublicKey) -> Self { - match value { - PublicKey::Ed25519(ref pk) => RawPublicKey { - sum: Some(tendermint_proto::crypto::public_key::Sum::Ed25519( - pk.as_bytes().to_vec(), - )), - }, - #[cfg(feature = "secp256k1")] - PublicKey::Secp256k1(ref pk) => RawPublicKey { - sum: Some(tendermint_proto::crypto::public_key::Sum::Secp256k1( - pk.to_bytes().to_vec(), - )), - }, + impl From for RawPublicKey { + fn from(value: PublicKey) -> Self { + match value { + PublicKey::Ed25519(ref pk) => RawPublicKey { + sum: Some(Sum::Ed25519( + pk.as_bytes().to_vec(), + )), + }, + #[cfg(feature = "secp256k1")] + PublicKey::Secp256k1(ref pk) => RawPublicKey { + sum: Some(Sum::Secp256k1( + pk.to_bytes().to_vec(), + )), + }, + } } } } diff --git a/tendermint/src/validator.rs b/tendermint/src/validator.rs index ad2993782..12d462c2a 100644 --- a/tendermint/src/validator.rs +++ b/tendermint/src/validator.rs @@ -1,16 +1,7 @@ //! Tendermint validators -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; -use tendermint_proto::{ - abci::ValidatorUpdate as RawValidatorUpdate, - types::{ - SimpleValidator as RawSimpleValidator, Validator as RawValidator, - ValidatorSet as RawValidatorSet, - }, - Protobuf, -}; +use tendermint_proto::{types::SimpleValidator as RawSimpleValidator, Protobuf}; use crate::{ account, hash::Hash, merkle, prelude::*, public_key::deserialize_public_key, vote, Error, @@ -25,44 +16,6 @@ pub struct Set { total_voting_power: vote::Power, } -impl Protobuf for Set {} - -impl TryFrom for Set { - type Error = Error; - - fn try_from(value: RawValidatorSet) -> Result { - let validators = value - .validators - .into_iter() - .map(TryInto::try_into) - .collect::, _>>()?; - - let proposer = value.proposer.map(TryInto::try_into).transpose()?; - let validator_set = Self::new(validators, proposer); - - // Ensure that the raw voting power matches the computed one - let raw_voting_power = value.total_voting_power.try_into()?; - if raw_voting_power != validator_set.total_voting_power() { - return Err(Error::raw_voting_power_mismatch( - raw_voting_power, - validator_set.total_voting_power(), - )); - } - - Ok(validator_set) - } -} - -impl From for RawValidatorSet { - fn from(value: Set) -> Self { - RawValidatorSet { - validators: value.validators.into_iter().map(Into::into).collect(), - proposer: value.proposer.map(Into::into), - total_voting_power: value.total_voting_power.into(), - } - } -} - impl Set { /// Constructor pub fn new(mut validators: Vec, proposer: Option) -> Set { @@ -169,34 +122,6 @@ pub struct Info { pub proposer_priority: ProposerPriority, } -impl TryFrom for Info { - type Error = Error; - - fn try_from(value: RawValidator) -> Result { - Ok(Info { - address: value.address.try_into()?, - pub_key: value - .pub_key - .ok_or_else(Error::missing_public_key)? - .try_into()?, - power: value.voting_power.try_into()?, - name: None, - proposer_priority: value.proposer_priority.into(), - }) - } -} - -impl From for RawValidator { - fn from(value: Info) -> Self { - RawValidator { - address: value.address.into(), - pub_key: Some(value.pub_key.into()), - voting_power: value.power.into(), - proposer_priority: value.proposer_priority.into(), - } - } -} - impl Info { /// Return the voting power of the validator. pub fn power(&self) -> u64 { @@ -241,47 +166,16 @@ impl Info { #[derive(Clone, PartialEq)] pub struct SimpleValidator { /// Public key - pub pub_key: Option, + pub pub_key: PublicKey, /// Voting power pub voting_power: vote::Power, } -impl Protobuf for SimpleValidator {} - -impl TryFrom for SimpleValidator { - type Error = Error; - - fn try_from(value: RawSimpleValidator) -> Result { - Ok(SimpleValidator { - pub_key: value.pub_key, - voting_power: value.voting_power.try_into()?, - }) - } -} - -impl From for RawSimpleValidator { - fn from(value: SimpleValidator) -> Self { - RawSimpleValidator { - pub_key: value.pub_key, - voting_power: value.voting_power.into(), - } - } -} - /// Info -> SimpleValidator impl From<&Info> for SimpleValidator { fn from(info: &Info) -> SimpleValidator { - let sum = match &info.pub_key { - PublicKey::Ed25519(pk) => Some(tendermint_proto::crypto::public_key::Sum::Ed25519( - pk.as_bytes().to_vec(), - )), - #[cfg(feature = "secp256k1")] - PublicKey::Secp256k1(pk) => Some(tendermint_proto::crypto::public_key::Sum::Secp256k1( - pk.to_bytes().to_vec(), - )), - }; SimpleValidator { - pub_key: Some(tendermint_proto::crypto::PublicKey { sum }), + pub_key: info.pub_key, voting_power: info.power, } } @@ -291,7 +185,7 @@ impl Info { /// Returns the bytes to be hashed into the Merkle tree - /// the leaves of the tree. pub fn hash_bytes(&self) -> Vec { - SimpleValidator::from(self).encode_vec().unwrap() + Protobuf::::encode_vec(&SimpleValidator::from(self)).unwrap() } } @@ -335,28 +229,134 @@ pub struct Update { pub power: vote::Power, } -impl Protobuf for Update {} +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +tendermint_pb_modules! { + use pb::{ + abci::ValidatorUpdate as RawValidatorUpdate, + types::{ + SimpleValidator as RawSimpleValidator, Validator as RawValidator, + ValidatorSet as RawValidatorSet, + }, + }; + use super::{Info, Set, SimpleValidator, Update}; + use crate::{prelude::*, Error}; + + impl Protobuf for Set {} + + impl TryFrom for Set { + type Error = Error; + + fn try_from(value: RawValidatorSet) -> Result { + let validators = value + .validators + .into_iter() + .map(TryInto::try_into) + .collect::, _>>()?; + + let proposer = value.proposer.map(TryInto::try_into).transpose()?; + let validator_set = Self::new(validators, proposer); + + // Ensure that the raw voting power matches the computed one + let raw_voting_power = value.total_voting_power.try_into()?; + if raw_voting_power != validator_set.total_voting_power() { + return Err(Error::raw_voting_power_mismatch( + raw_voting_power, + validator_set.total_voting_power(), + )); + } + + Ok(validator_set) + } + } + + impl From for RawValidatorSet { + fn from(value: Set) -> Self { + RawValidatorSet { + validators: value.validators.into_iter().map(Into::into).collect(), + proposer: value.proposer.map(Into::into), + total_voting_power: value.total_voting_power.into(), + } + } + } -impl From for RawValidatorUpdate { - fn from(vu: Update) -> Self { - Self { - pub_key: Some(vu.pub_key.into()), - power: vu.power.into(), + impl TryFrom for Info { + type Error = Error; + + fn try_from(value: RawValidator) -> Result { + Ok(Info { + address: value.address.try_into()?, + pub_key: value + .pub_key + .ok_or_else(Error::missing_public_key)? + .try_into()?, + power: value.voting_power.try_into()?, + name: None, + proposer_priority: value.proposer_priority.into(), + }) + } + } + + impl From for RawValidator { + fn from(value: Info) -> Self { + RawValidator { + address: value.address.into(), + pub_key: Some(value.pub_key.into()), + voting_power: value.power.into(), + proposer_priority: value.proposer_priority.into(), + } + } + } + + impl Protobuf for SimpleValidator {} + + impl TryFrom for SimpleValidator { + type Error = Error; + + fn try_from(value: RawSimpleValidator) -> Result { + Ok(SimpleValidator { + pub_key: value.pub_key + .ok_or_else(Error::missing_public_key)? + .try_into()?, + voting_power: value.voting_power.try_into()?, + }) + } + } + + impl From for RawSimpleValidator { + fn from(value: SimpleValidator) -> Self { + RawSimpleValidator { + pub_key: Some(value.pub_key.into()), + voting_power: value.voting_power.into(), + } } } -} -impl TryFrom for Update { - type Error = Error; - - fn try_from(vu: RawValidatorUpdate) -> Result { - Ok(Self { - pub_key: vu - .pub_key - .ok_or_else(Error::missing_public_key)? - .try_into()?, - power: vu.power.try_into()?, - }) + impl Protobuf for Update {} + + impl From for RawValidatorUpdate { + fn from(vu: Update) -> Self { + Self { + pub_key: Some(vu.pub_key.into()), + power: vu.power.into(), + } + } + } + + impl TryFrom for Update { + type Error = Error; + + fn try_from(vu: RawValidatorUpdate) -> Result { + Ok(Self { + pub_key: vu + .pub_key + .ok_or_else(Error::missing_public_key)? + .try_into()?, + power: vu.power.try_into()?, + }) + } } } diff --git a/tendermint/src/vote.rs b/tendermint/src/vote.rs index 829c41aff..c0d90aa78 100644 --- a/tendermint/src/vote.rs +++ b/tendermint/src/vote.rs @@ -5,11 +5,7 @@ mod power; mod sign_vote; mod validator_index; -use core::{ - convert::{TryFrom, TryInto}, - fmt, - str::FromStr, -}; +use core::{fmt, str::FromStr}; use bytes::BufMut; use serde::{Deserialize, Serialize}; @@ -55,44 +51,50 @@ pub struct Vote { pub signature: Option, } -impl Protobuf for Vote {} - -impl TryFrom for Vote { - type Error = Error; - - fn try_from(value: RawVote) -> Result { - if value.timestamp.is_none() { - return Err(Error::missing_timestamp()); +tendermint_pb_modules! { + use super::Vote; + use crate::{prelude::*, block, Error, Signature}; + use pb::types::Vote as RawVote; + + impl Protobuf for Vote {} + + impl TryFrom for Vote { + type Error = Error; + + fn try_from(value: RawVote) -> Result { + if value.timestamp.is_none() { + return Err(Error::missing_timestamp()); + } + Ok(Vote { + vote_type: value.r#type.try_into()?, + height: value.height.try_into()?, + round: value.round.try_into()?, + // block_id can be nil in the Go implementation + block_id: value + .block_id + .map(TryInto::try_into) + .transpose()? + .filter(|i| i != &block::Id::default()), + timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, + validator_address: value.validator_address.try_into()?, + validator_index: value.validator_index.try_into()?, + signature: Signature::new(value.signature)?, + }) } - Ok(Vote { - vote_type: value.r#type.try_into()?, - height: value.height.try_into()?, - round: value.round.try_into()?, - // block_id can be nil in the Go implementation - block_id: value - .block_id - .map(TryInto::try_into) - .transpose()? - .filter(|i| i != &block::Id::default()), - timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, - validator_address: value.validator_address.try_into()?, - validator_index: value.validator_index.try_into()?, - signature: Signature::new(value.signature)?, - }) } -} -impl From for RawVote { - fn from(value: Vote) -> Self { - RawVote { - r#type: value.vote_type.into(), - height: value.height.into(), - round: value.round.into(), - block_id: value.block_id.map(Into::into), - timestamp: value.timestamp.map(Into::into), - validator_address: value.validator_address.into(), - validator_index: value.validator_index.into(), - signature: value.signature.map(|s| s.to_bytes()).unwrap_or_default(), + impl From for RawVote { + fn from(value: Vote) -> Self { + RawVote { + r#type: value.vote_type.into(), + height: value.height.into(), + round: value.round.into(), + block_id: value.block_id.map(Into::into), + timestamp: value.timestamp.map(Into::into), + validator_address: value.validator_address.into(), + validator_index: value.validator_index.into(), + signature: value.signature.map(|s| s.to_bytes()).unwrap_or_default(), + } } } } diff --git a/tendermint/src/vote/sign_vote.rs b/tendermint/src/vote/sign_vote.rs index 54caf1c87..7516e6041 100644 --- a/tendermint/src/vote/sign_vote.rs +++ b/tendermint/src/vote/sign_vote.rs @@ -340,58 +340,6 @@ mod tests { } } - #[test] - fn test_vote_rountrip_with_sig() { - let dt = datetime!(2017-12-25 03:00:01.234 UTC); - let vote = Vote { - validator_address: AccountId::try_from(vec![ - 0xa3, 0xb2, 0xcc, 0xdd, 0x71, 0x86, 0xf1, 0x68, 0x5f, 0x21, 0xf2, 0x48, 0x2a, 0xf4, - 0xfb, 0x34, 0x46, 0xa8, 0x4b, 0x35, - ]) - .unwrap(), - validator_index: ValidatorIndex::try_from(56789).unwrap(), - height: Height::from(12345_u32), - round: Round::from(2_u16), - timestamp: Some(dt.try_into().unwrap()), - vote_type: Type::Prevote, - block_id: Some(BlockId { - hash: Hash::from_hex_upper(Algorithm::Sha256, "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFA") - .unwrap(), // Hash::new(Algorithm::Sha256, - // b"hash".to_vec().as_slice()).unwrap(), - part_set_header: Header::new( - 1_000_000, - Hash::from_hex_upper(Algorithm::Sha256, "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFA") - .unwrap(), - ) - .unwrap(), - }), - // signature: None, - signature: Signature::new(vec![ - 130u8, 246, 183, 50, 153, 248, 28, 57, 51, 142, 55, 217, 194, 24, 134, 212, 233, - 100, 211, 10, 24, 174, 179, 117, 41, 65, 141, 134, 149, 239, 65, 174, 217, 42, 6, - 184, 112, 17, 7, 97, 255, 221, 252, 16, 60, 144, 30, 212, 167, 39, 67, 35, 118, - 192, 133, 130, 193, 115, 32, 206, 152, 91, 173, 10, - ]) - .unwrap(), - }; - let got = vote.encode_vec().unwrap(); - let v = Vote::decode_vec(&got).unwrap(); - - assert_eq!(v, vote); - // SignVoteRequest - { - let svr = SignVoteRequest { - vote, - chain_id: ChainId::from_str("test_chain_id").unwrap(), - }; - let mut got = vec![]; - let _have = svr.encode(&mut got); - - let svr2 = SignVoteRequest::decode(got.as_ref()).unwrap(); - assert_eq!(svr, svr2); - } - } - #[test] fn test_deserialization() { let encoded = vec![ @@ -437,4 +385,60 @@ mod tests { let got = SignVoteRequest::decode_vec(&encoded).unwrap(); assert_eq!(got, want); } + + tendermint_pb_modules! { + use super::*; + + #[test] + fn test_vote_rountrip_with_sig() { + let dt = datetime!(2017-12-25 03:00:01.234 UTC); + let vote = Vote { + validator_address: AccountId::try_from(vec![ + 0xa3, 0xb2, 0xcc, 0xdd, 0x71, 0x86, 0xf1, 0x68, 0x5f, 0x21, 0xf2, 0x48, 0x2a, 0xf4, + 0xfb, 0x34, 0x46, 0xa8, 0x4b, 0x35, + ]) + .unwrap(), + validator_index: ValidatorIndex::try_from(56789).unwrap(), + height: Height::from(12345_u32), + round: Round::from(2_u16), + timestamp: Some(dt.try_into().unwrap()), + vote_type: Type::Prevote, + block_id: Some(BlockId { + hash: Hash::from_hex_upper(Algorithm::Sha256, "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFA") + .unwrap(), // Hash::new(Algorithm::Sha256, + // b"hash".to_vec().as_slice()).unwrap(), + part_set_header: Header::new( + 1_000_000, + Hash::from_hex_upper(Algorithm::Sha256, "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFA") + .unwrap(), + ) + .unwrap(), + }), + // signature: None, + signature: Signature::new(vec![ + 130u8, 246, 183, 50, 153, 248, 28, 57, 51, 142, 55, 217, 194, 24, 134, 212, 233, + 100, 211, 10, 24, 174, 179, 117, 41, 65, 141, 134, 149, 239, 65, 174, 217, 42, 6, + 184, 112, 17, 7, 97, 255, 221, 252, 16, 60, 144, 30, 212, 167, 39, 67, 35, 118, + 192, 133, 130, 193, 115, 32, 206, 152, 91, 173, 10, + ]) + .unwrap(), + }; + let got = Protobuf::::encode_vec(&vote).unwrap(); + let v = >::decode_vec(&got).unwrap(); + + assert_eq!(v, vote); + // SignVoteRequest + { + let svr = SignVoteRequest { + vote, + chain_id: ChainId::from_str("test_chain_id").unwrap(), + }; + let mut got = vec![]; + let _have = svr.encode(&mut got); + + let svr2 = SignVoteRequest::decode(got.as_ref()).unwrap(); + assert_eq!(svr, svr2); + } + } + } } From 7414aa9bd72904b1f01431d5fa8aebcea1ad5e1f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Fri, 21 Oct 2022 20:03:18 +0300 Subject: [PATCH 09/77] Add ABCI response types for PrepareProposal, ProcessProposal --- .../src/abci/doc/request-prepareproposal.md | 2 +- .../src/abci/doc/request-processproposal.md | 2 +- .../src/abci/doc/response-prepareproposal.md | 1 + .../src/abci/doc/response-processproposal.md | 1 + tendermint/src/abci/request.rs | 4 +- tendermint/src/abci/response.rs | 184 +++++++++++++----- .../src/abci/response/prepare_proposal.rs | 34 ++++ .../src/abci/response/process_proposal.rs | 91 +++++++++ tendermint/src/error.rs | 3 + 9 files changed, 270 insertions(+), 52 deletions(-) create mode 100644 tendermint/src/abci/doc/response-prepareproposal.md create mode 100644 tendermint/src/abci/doc/response-processproposal.md create mode 100644 tendermint/src/abci/response/prepare_proposal.rs create mode 100644 tendermint/src/abci/response/process_proposal.rs diff --git a/tendermint/src/abci/doc/request-prepareproposal.md b/tendermint/src/abci/doc/request-prepareproposal.md index b76cbb647..d977f1758 100644 --- a/tendermint/src/abci/doc/request-prepareproposal.md +++ b/tendermint/src/abci/doc/request-prepareproposal.md @@ -1 +1 @@ -[ABCI documentation](https://github.com/tendermint/tendermint/blob/main/spec/abci/abci++_methods.md#prepareproposal) +[ABCI documentation](https://github.com/tendermint/tendermint/blob/v0.37.x/spec/abci/abci++_methods.md#prepareproposal) diff --git a/tendermint/src/abci/doc/request-processproposal.md b/tendermint/src/abci/doc/request-processproposal.md index b7474ce7f..1d32bf046 100644 --- a/tendermint/src/abci/doc/request-processproposal.md +++ b/tendermint/src/abci/doc/request-processproposal.md @@ -1 +1 @@ -[ABCI documentation](https://github.com/tendermint/tendermint/blob/main/spec/abci/abci++_methods.md#processproposal) +[ABCI documentation](https://github.com/tendermint/tendermint/blob/v0.37.x/spec/abci/abci++_methods.md#processproposal) diff --git a/tendermint/src/abci/doc/response-prepareproposal.md b/tendermint/src/abci/doc/response-prepareproposal.md new file mode 100644 index 000000000..d977f1758 --- /dev/null +++ b/tendermint/src/abci/doc/response-prepareproposal.md @@ -0,0 +1 @@ +[ABCI documentation](https://github.com/tendermint/tendermint/blob/v0.37.x/spec/abci/abci++_methods.md#prepareproposal) diff --git a/tendermint/src/abci/doc/response-processproposal.md b/tendermint/src/abci/doc/response-processproposal.md new file mode 100644 index 000000000..1d32bf046 --- /dev/null +++ b/tendermint/src/abci/doc/response-processproposal.md @@ -0,0 +1 @@ +[ABCI documentation](https://github.com/tendermint/tendermint/blob/v0.37.x/spec/abci/abci++_methods.md#processproposal) diff --git a/tendermint/src/abci/request.rs b/tendermint/src/abci/request.rs index 309565da2..91e8ceebf 100644 --- a/tendermint/src/abci/request.rs +++ b/tendermint/src/abci/request.rs @@ -292,10 +292,10 @@ mod v0_34 { Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), - Request::PrepareProposal(x) => { + Request::PrepareProposal(_) => { panic!("PrepareProposal should not be used with Tendermint 0.34") }, - Request::ProcessProposal(x) => { + Request::ProcessProposal(_) => { panic!("ProcessProposal should not be used with Tendermint 0.34") }, }; diff --git a/tendermint/src/abci/response.rs b/tendermint/src/abci/response.rs index 5b55a7116..2b506d48f 100644 --- a/tendermint/src/abci/response.rs +++ b/tendermint/src/abci/response.rs @@ -18,7 +18,6 @@ // This is also why certain submodules have #[allow(unused)] imports to bring // items into scope for doc links, rather than changing the doc links -- it // allows the doc comments to be copied without editing. -use core::convert::{TryFrom, TryInto}; // bring into scope for doc links #[allow(unused)] @@ -38,6 +37,8 @@ mod init_chain; mod list_snapshots; mod load_snapshot_chunk; mod offer_snapshot; +mod prepare_proposal; +mod process_proposal; mod query; mod set_option; @@ -54,6 +55,8 @@ pub use init_chain::InitChain; pub use list_snapshots::ListSnapshots; pub use load_snapshot_chunk::LoadSnapshotChunk; pub use offer_snapshot::OfferSnapshot; +pub use prepare_proposal::PrepareProposal; +pub use process_proposal::ProcessProposal; pub use query::Query; pub use set_option::SetOption; @@ -92,6 +95,10 @@ pub enum Response { LoadSnapshotChunk(LoadSnapshotChunk), #[doc = include_str!("doc/response-applysnapshotchunk.md")] ApplySnapshotChunk(ApplySnapshotChunk), + #[doc = include_str!("doc/response-prepareproposal.md")] + PrepareProposal(PrepareProposal), + #[doc = include_str!("doc/response-processproposal.md")] + ProcessProposal(ProcessProposal), } /// The consensus category of ABCI responses. @@ -238,58 +245,139 @@ impl TryFrom for SnapshotResponse { // Protobuf conversions // ============================================================================= -use tendermint_proto::{abci as pb, Protobuf}; +mod v0_34 { + use super::Response; + use crate::Error; + use tendermint_proto::v0_34::abci as pb; + use tendermint_proto::Protobuf; -impl From for pb::Response { - fn from(response: Response) -> pb::Response { - use pb::response::Value; - let value = match response { - Response::Exception(x) => Some(Value::Exception(x.into())), - Response::Echo(x) => Some(Value::Echo(x.into())), - Response::Flush => Some(Value::Flush(Default::default())), - Response::Info(x) => Some(Value::Info(x.into())), - Response::SetOption(x) => Some(Value::SetOption(x.into())), - Response::InitChain(x) => Some(Value::InitChain(x.into())), - Response::Query(x) => Some(Value::Query(x.into())), - Response::BeginBlock(x) => Some(Value::BeginBlock(x.into())), - Response::CheckTx(x) => Some(Value::CheckTx(x.into())), - Response::DeliverTx(x) => Some(Value::DeliverTx(x.into())), - Response::EndBlock(x) => Some(Value::EndBlock(x.into())), - Response::Commit(x) => Some(Value::Commit(x.into())), - Response::ListSnapshots(x) => Some(Value::ListSnapshots(x.into())), - Response::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), - Response::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), - Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), - }; - pb::Response { value } + impl From for pb::Response { + fn from(response: Response) -> pb::Response { + use pb::response::Value; + let value = match response { + Response::Exception(x) => Some(Value::Exception(x.into())), + Response::Echo(x) => Some(Value::Echo(x.into())), + Response::Flush => Some(Value::Flush(Default::default())), + Response::Info(x) => Some(Value::Info(x.into())), + Response::SetOption(x) => Some(Value::SetOption(x.into())), + Response::InitChain(x) => Some(Value::InitChain(x.into())), + Response::Query(x) => Some(Value::Query(x.into())), + Response::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Response::CheckTx(x) => Some(Value::CheckTx(x.into())), + Response::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Response::EndBlock(x) => Some(Value::EndBlock(x.into())), + Response::Commit(x) => Some(Value::Commit(x.into())), + Response::ListSnapshots(x) => Some(Value::ListSnapshots(x.into())), + Response::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Response::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + Response::PrepareProposal(_) => { + panic!("PrepareProposal should not be used with Tendermint 0.34") + }, + Response::ProcessProposal(_) => { + panic!("ProcessProposal should not be used with Tendermint 0.34") + }, + }; + pb::Response { value } + } } -} -impl TryFrom for Response { - type Error = Error; + impl TryFrom for Response { + type Error = Error; - fn try_from(response: pb::Response) -> Result { - use pb::response::Value; - match response.value { - Some(Value::Exception(x)) => Ok(Response::Exception(x.try_into()?)), - Some(Value::Echo(x)) => Ok(Response::Echo(x.try_into()?)), - Some(Value::Flush(_)) => Ok(Response::Flush), - Some(Value::Info(x)) => Ok(Response::Info(x.try_into()?)), - Some(Value::SetOption(x)) => Ok(Response::SetOption(x.try_into()?)), - Some(Value::InitChain(x)) => Ok(Response::InitChain(x.try_into()?)), - Some(Value::Query(x)) => Ok(Response::Query(x.try_into()?)), - Some(Value::BeginBlock(x)) => Ok(Response::BeginBlock(x.try_into()?)), - Some(Value::CheckTx(x)) => Ok(Response::CheckTx(x.try_into()?)), - Some(Value::DeliverTx(x)) => Ok(Response::DeliverTx(x.try_into()?)), - Some(Value::EndBlock(x)) => Ok(Response::EndBlock(x.try_into()?)), - Some(Value::Commit(x)) => Ok(Response::Commit(x.try_into()?)), - Some(Value::ListSnapshots(x)) => Ok(Response::ListSnapshots(x.try_into()?)), - Some(Value::OfferSnapshot(x)) => Ok(Response::OfferSnapshot(x.try_into()?)), - Some(Value::LoadSnapshotChunk(x)) => Ok(Response::LoadSnapshotChunk(x.try_into()?)), - Some(Value::ApplySnapshotChunk(x)) => Ok(Response::ApplySnapshotChunk(x.try_into()?)), - None => Err(crate::Error::missing_data()), + fn try_from(response: pb::Response) -> Result { + use pb::response::Value; + match response.value { + Some(Value::Exception(x)) => Ok(Response::Exception(x.try_into()?)), + Some(Value::Echo(x)) => Ok(Response::Echo(x.try_into()?)), + Some(Value::Flush(_)) => Ok(Response::Flush), + Some(Value::Info(x)) => Ok(Response::Info(x.try_into()?)), + Some(Value::SetOption(x)) => Ok(Response::SetOption(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Response::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Response::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Response::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Response::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Response::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Response::EndBlock(x.try_into()?)), + Some(Value::Commit(x)) => Ok(Response::Commit(x.try_into()?)), + Some(Value::ListSnapshots(x)) => Ok(Response::ListSnapshots(x.try_into()?)), + Some(Value::OfferSnapshot(x)) => Ok(Response::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Response::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => { + Ok(Response::ApplySnapshotChunk(x.try_into()?)) + }, + None => Err(crate::Error::missing_data()), + } } } + + impl Protobuf for Response {} } -impl Protobuf for Response {} +mod v0_37 { + use super::Response; + use crate::Error; + use tendermint_proto::v0_37::abci as pb; + use tendermint_proto::Protobuf; + + impl From for pb::Response { + fn from(response: Response) -> pb::Response { + use pb::response::Value; + let value = match response { + Response::Exception(x) => Some(Value::Exception(x.into())), + Response::Echo(x) => Some(Value::Echo(x.into())), + Response::Flush => Some(Value::Flush(Default::default())), + Response::Info(x) => Some(Value::Info(x.into())), + Response::InitChain(x) => Some(Value::InitChain(x.into())), + Response::Query(x) => Some(Value::Query(x.into())), + Response::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Response::CheckTx(x) => Some(Value::CheckTx(x.into())), + Response::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Response::EndBlock(x) => Some(Value::EndBlock(x.into())), + Response::Commit(x) => Some(Value::Commit(x.into())), + Response::ListSnapshots(x) => Some(Value::ListSnapshots(x.into())), + Response::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Response::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + Response::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), + Response::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), + Response::SetOption(x) => { + panic!("SetOption should not be used with Tendermint 0.37") + }, + }; + pb::Response { value } + } + } + + impl TryFrom for Response { + type Error = Error; + + fn try_from(response: pb::Response) -> Result { + use pb::response::Value; + match response.value { + Some(Value::Exception(x)) => Ok(Response::Exception(x.try_into()?)), + Some(Value::Echo(x)) => Ok(Response::Echo(x.try_into()?)), + Some(Value::Flush(_)) => Ok(Response::Flush), + Some(Value::Info(x)) => Ok(Response::Info(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Response::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Response::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Response::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Response::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Response::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Response::EndBlock(x.try_into()?)), + Some(Value::Commit(x)) => Ok(Response::Commit(x.try_into()?)), + Some(Value::ListSnapshots(x)) => Ok(Response::ListSnapshots(x.try_into()?)), + Some(Value::OfferSnapshot(x)) => Ok(Response::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Response::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => { + Ok(Response::ApplySnapshotChunk(x.try_into()?)) + }, + Some(Value::PrepareProposal(x)) => Ok(Response::PrepareProposal(x.try_into()?)), + Some(Value::ProcessProposal(x)) => Ok(Response::ProcessProposal(x.try_into()?)), + None => Err(crate::Error::missing_data()), + } + } + } + + impl Protobuf for Response {} +} diff --git a/tendermint/src/abci/response/prepare_proposal.rs b/tendermint/src/abci/response/prepare_proposal.rs new file mode 100644 index 000000000..d8facfed5 --- /dev/null +++ b/tendermint/src/abci/response/prepare_proposal.rs @@ -0,0 +1,34 @@ +use bytes::Bytes; + +use crate::prelude::*; + +#[doc = include_str!("../doc/response-prepareproposal.md")] +#[derive(Clone, Debug, PartialEq, Eq)] +pub struct PrepareProposal { + pub txs: Vec, +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +// PrepareProposal has been introduced in 0.37. + +use tendermint_proto::v0_37::abci as pb; +use tendermint_proto::Protobuf; + +impl From for pb::ResponsePrepareProposal { + fn from(value: PrepareProposal) -> Self { + Self { txs: value.txs } + } +} + +impl TryFrom for PrepareProposal { + type Error = crate::Error; + + fn try_from(message: pb::ResponsePrepareProposal) -> Result { + Ok(Self { txs: message.txs }) + } +} + +impl Protobuf for PrepareProposal {} diff --git a/tendermint/src/abci/response/process_proposal.rs b/tendermint/src/abci/response/process_proposal.rs new file mode 100644 index 000000000..acaf45ef9 --- /dev/null +++ b/tendermint/src/abci/response/process_proposal.rs @@ -0,0 +1,91 @@ +use crate::prelude::*; + +#[doc = include_str!("../doc/response-processproposal.md")] +#[derive(Copy, Clone, Debug, PartialEq, Eq)] +#[repr(i32)] +pub enum ProcessProposal { + Unknown = 0, + Accept = 1, + Reject = 2, +} + +impl Default for ProcessProposal { + #[inline] + fn default() -> Self { + ProcessProposal::Unknown + } +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +// ProcessProposal has been introduced in 0.37. + +use tendermint_proto::v0_37::abci as pb; +use tendermint_proto::Protobuf; + +impl From for pb::ResponseProcessProposal { + fn from(value: ProcessProposal) -> Self { + Self { + status: value as i32, + } + } +} + +impl TryFrom for ProcessProposal { + type Error = crate::Error; + + fn try_from(message: pb::ResponseProcessProposal) -> Result { + let value = match message.status { + 0 => ProcessProposal::Unknown, + 1 => ProcessProposal::Accept, + 2 => ProcessProposal::Reject, + _ => return Err(crate::Error::unsupported_process_proposal_status()), + }; + Ok(value) + } +} + +impl Protobuf for ProcessProposal {} + +#[cfg(test)] +mod tests { + use super::*; + use crate::error::ErrorDetail; + + use std::collections::HashMap; + + #[test] + fn all_status_values_are_covered() { + use pb::response_process_proposal::ProposalStatus::*; + + const FIRST_INVALID_STATUS: i32 = 3; + + let mut covered = HashMap::new(); + for v in [Unknown, Accept, Reject] { + // Match the generated enum values exhaustively + match v { + Unknown | Accept | Reject => { + covered.insert(v as i32, false); + }, + } + } + for status in 0..FIRST_INVALID_STATUS { + let message = pb::ResponseProcessProposal { status }; + let response: ProcessProposal = message.try_into().unwrap(); + assert_eq!(response as i32, status); + covered.insert(status, true); + } + assert!(covered.values().all(|&x| x)); + + let message = pb::ResponseProcessProposal { + status: FIRST_INVALID_STATUS, + }; + let err = ProcessProposal::try_from(message).err().unwrap(); + assert!(matches!( + err.0, + ErrorDetail::UnsupportedProcessProposalStatus(_), + )); + } +} diff --git a/tendermint/src/error.rs b/tendermint/src/error.rs index 0e01e2c9a..4118250b0 100644 --- a/tendermint/src/error.rs +++ b/tendermint/src/error.rs @@ -188,6 +188,9 @@ define_error! { UnsupportedOfferSnapshotChunkResult |_| { format_args!("unsupported OfferSnapshotChunkResult type" ) }, + UnsupportedProcessProposalStatus + |_| { format_args!("unsupported ProcessProposal status value" ) }, + RawVotingPowerMismatch { raw: vote::Power, computed: vote::Power } |e| { format_args!("mismatch between raw voting ({0:?}) and computed one ({1:?})", e.raw, e.computed) }, From 30408ed110fb5519b8b3c2c9d4f29987d6b3c1c2 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 24 Oct 2022 20:26:42 +0300 Subject: [PATCH 10/77] Multi-version protobuf conversions for response types --- .../src/abci/response/apply_snapshot_chunk.rs | 58 +++---- tendermint/src/abci/response/begin_block.rs | 44 +++--- tendermint/src/abci/response/check_tx.rs | 80 +++++----- tendermint/src/abci/response/commit.rs | 38 ++--- tendermint/src/abci/response/deliver_tx.rs | 68 ++++----- tendermint/src/abci/response/echo.rs | 34 ++--- tendermint/src/abci/response/end_block.rs | 70 ++++----- tendermint/src/abci/response/exception.rs | 34 ++--- tendermint/src/abci/response/info.rs | 52 ++++--- tendermint/src/abci/response/init_chain.rs | 58 +++---- .../src/abci/response/list_snapshots.rs | 52 +++---- .../src/abci/response/load_snapshot_chunk.rs | 34 ++--- .../src/abci/response/offer_snapshot.rs | 48 +++--- tendermint/src/abci/response/query.rs | 64 ++++---- tendermint/src/merkle/proof.rs | 144 +++++++++--------- 15 files changed, 444 insertions(+), 434 deletions(-) diff --git a/tendermint/src/abci/response/apply_snapshot_chunk.rs b/tendermint/src/abci/response/apply_snapshot_chunk.rs index b3502450a..94ff7586e 100644 --- a/tendermint/src/abci/response/apply_snapshot_chunk.rs +++ b/tendermint/src/abci/response/apply_snapshot_chunk.rs @@ -50,39 +50,39 @@ impl Default for ApplySnapshotChunkResult { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; +tendermint_pb_modules! { + use super::{ApplySnapshotChunk, ApplySnapshotChunkResult}; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseApplySnapshotChunk { - fn from(apply_snapshot_chunk: ApplySnapshotChunk) -> Self { - Self { - result: apply_snapshot_chunk.result as i32, - refetch_chunks: apply_snapshot_chunk.refetch_chunks, - reject_senders: apply_snapshot_chunk.reject_senders, + impl From for pb::abci::ResponseApplySnapshotChunk { + fn from(apply_snapshot_chunk: ApplySnapshotChunk) -> Self { + Self { + result: apply_snapshot_chunk.result as i32, + refetch_chunks: apply_snapshot_chunk.refetch_chunks, + reject_senders: apply_snapshot_chunk.reject_senders, + } } } -} -impl TryFrom for ApplySnapshotChunk { - type Error = crate::Error; + impl TryFrom for ApplySnapshotChunk { + type Error = crate::Error; - fn try_from(apply_snapshot_chunk: pb::ResponseApplySnapshotChunk) -> Result { - let result = match apply_snapshot_chunk.result { - 0 => ApplySnapshotChunkResult::Unknown, - 1 => ApplySnapshotChunkResult::Accept, - 2 => ApplySnapshotChunkResult::Abort, - 3 => ApplySnapshotChunkResult::Retry, - 4 => ApplySnapshotChunkResult::RetrySnapshot, - 5 => ApplySnapshotChunkResult::RejectSnapshot, - _ => return Err(crate::Error::unsupported_apply_snapshot_chunk_result()), - }; - Ok(Self { - result, - refetch_chunks: apply_snapshot_chunk.refetch_chunks, - reject_senders: apply_snapshot_chunk.reject_senders, - }) + fn try_from(apply_snapshot_chunk: pb::abci::ResponseApplySnapshotChunk) -> Result { + let result = match apply_snapshot_chunk.result { + 0 => ApplySnapshotChunkResult::Unknown, + 1 => ApplySnapshotChunkResult::Accept, + 2 => ApplySnapshotChunkResult::Abort, + 3 => ApplySnapshotChunkResult::Retry, + 4 => ApplySnapshotChunkResult::RetrySnapshot, + 5 => ApplySnapshotChunkResult::RejectSnapshot, + _ => return Err(crate::Error::unsupported_apply_snapshot_chunk_result()), + }; + Ok(Self { + result, + refetch_chunks: apply_snapshot_chunk.refetch_chunks, + reject_senders: apply_snapshot_chunk.reject_senders, + }) + } } -} -impl Protobuf for ApplySnapshotChunk {} + impl Protobuf for ApplySnapshotChunk {} +} diff --git a/tendermint/src/abci/response/begin_block.rs b/tendermint/src/abci/response/begin_block.rs index 1f1622ddf..01ac0d202 100644 --- a/tendermint/src/abci/response/begin_block.rs +++ b/tendermint/src/abci/response/begin_block.rs @@ -15,30 +15,30 @@ pub struct BeginBlock { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseBeginBlock { - fn from(begin_block: BeginBlock) -> Self { - Self { - events: begin_block.events.into_iter().map(Into::into).collect(), +tendermint_pb_modules! { + use super::BeginBlock; + + impl From for pb::abci::ResponseBeginBlock { + fn from(begin_block: BeginBlock) -> Self { + Self { + events: begin_block.events.into_iter().map(Into::into).collect(), + } } } -} -impl TryFrom for BeginBlock { - type Error = crate::Error; - - fn try_from(begin_block: pb::ResponseBeginBlock) -> Result { - Ok(Self { - events: begin_block - .events - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - }) + impl TryFrom for BeginBlock { + type Error = crate::Error; + + fn try_from(begin_block: pb::abci::ResponseBeginBlock) -> Result { + Ok(Self { + events: begin_block + .events + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } } -} -impl Protobuf for BeginBlock {} + impl Protobuf for BeginBlock {} +} diff --git a/tendermint/src/abci/response/check_tx.rs b/tendermint/src/abci/response/check_tx.rs index 3c730d2cf..355c1a330 100644 --- a/tendermint/src/abci/response/check_tx.rs +++ b/tendermint/src/abci/response/check_tx.rs @@ -50,50 +50,50 @@ pub struct CheckTx { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; +tendermint_pb_modules! { + use super::CheckTx; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseCheckTx { - fn from(check_tx: CheckTx) -> Self { - Self { - code: check_tx.code.into(), - data: check_tx.data, - log: check_tx.log, - info: check_tx.info, - gas_wanted: check_tx.gas_wanted, - gas_used: check_tx.gas_used, - events: check_tx.events.into_iter().map(Into::into).collect(), - codespace: check_tx.codespace, - sender: check_tx.sender, - priority: check_tx.priority, - mempool_error: check_tx.mempool_error, + impl From for pb::abci::ResponseCheckTx { + fn from(check_tx: CheckTx) -> Self { + Self { + code: check_tx.code.into(), + data: check_tx.data, + log: check_tx.log, + info: check_tx.info, + gas_wanted: check_tx.gas_wanted, + gas_used: check_tx.gas_used, + events: check_tx.events.into_iter().map(Into::into).collect(), + codespace: check_tx.codespace, + sender: check_tx.sender, + priority: check_tx.priority, + mempool_error: check_tx.mempool_error, + } } } -} -impl TryFrom for CheckTx { - type Error = crate::Error; + impl TryFrom for CheckTx { + type Error = crate::Error; - fn try_from(check_tx: pb::ResponseCheckTx) -> Result { - Ok(Self { - code: check_tx.code.into(), - data: check_tx.data, - log: check_tx.log, - info: check_tx.info, - gas_wanted: check_tx.gas_wanted, - gas_used: check_tx.gas_used, - events: check_tx - .events - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - codespace: check_tx.codespace, - sender: check_tx.sender, - priority: check_tx.priority, - mempool_error: check_tx.mempool_error, - }) + fn try_from(check_tx: pb::abci::ResponseCheckTx) -> Result { + Ok(Self { + code: check_tx.code.into(), + data: check_tx.data, + log: check_tx.log, + info: check_tx.info, + gas_wanted: check_tx.gas_wanted, + gas_used: check_tx.gas_used, + events: check_tx + .events + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + codespace: check_tx.codespace, + sender: check_tx.sender, + priority: check_tx.priority, + mempool_error: check_tx.mempool_error, + }) + } } -} -impl Protobuf for CheckTx {} + impl Protobuf for CheckTx {} +} diff --git a/tendermint/src/abci/response/commit.rs b/tendermint/src/abci/response/commit.rs index 5d6180da6..30ab4be87 100644 --- a/tendermint/src/abci/response/commit.rs +++ b/tendermint/src/abci/response/commit.rs @@ -18,28 +18,28 @@ pub struct Commit { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseCommit { - fn from(commit: Commit) -> Self { - Self { - data: commit.data, - retain_height: commit.retain_height.into(), +tendermint_pb_modules! { + use super::Commit; + + impl From for pb::abci::ResponseCommit { + fn from(commit: Commit) -> Self { + Self { + data: commit.data, + retain_height: commit.retain_height.into(), + } } } -} -impl TryFrom for Commit { - type Error = crate::Error; + impl TryFrom for Commit { + type Error = crate::Error; - fn try_from(commit: pb::ResponseCommit) -> Result { - Ok(Self { - data: commit.data, - retain_height: commit.retain_height.try_into()?, - }) + fn try_from(commit: pb::abci::ResponseCommit) -> Result { + Ok(Self { + data: commit.data, + retain_height: commit.retain_height.try_into()?, + }) + } } -} -impl Protobuf for Commit {} + impl Protobuf for Commit {} +} diff --git a/tendermint/src/abci/response/deliver_tx.rs b/tendermint/src/abci/response/deliver_tx.rs index 864461adf..8d269c6af 100644 --- a/tendermint/src/abci/response/deliver_tx.rs +++ b/tendermint/src/abci/response/deliver_tx.rs @@ -42,44 +42,44 @@ pub struct DeliverTx { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; +tendermint_pb_modules! { + use super::DeliverTx; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseDeliverTx { - fn from(deliver_tx: DeliverTx) -> Self { - Self { - code: deliver_tx.code.into(), - data: deliver_tx.data, - log: deliver_tx.log, - info: deliver_tx.info, - gas_wanted: deliver_tx.gas_wanted, - gas_used: deliver_tx.gas_used, - events: deliver_tx.events.into_iter().map(Into::into).collect(), - codespace: deliver_tx.codespace, + impl From for pb::abci::ResponseDeliverTx { + fn from(deliver_tx: DeliverTx) -> Self { + Self { + code: deliver_tx.code.into(), + data: deliver_tx.data, + log: deliver_tx.log, + info: deliver_tx.info, + gas_wanted: deliver_tx.gas_wanted, + gas_used: deliver_tx.gas_used, + events: deliver_tx.events.into_iter().map(Into::into).collect(), + codespace: deliver_tx.codespace, + } } } -} -impl TryFrom for DeliverTx { - type Error = crate::Error; + impl TryFrom for DeliverTx { + type Error = crate::Error; - fn try_from(deliver_tx: pb::ResponseDeliverTx) -> Result { - Ok(Self { - code: deliver_tx.code.into(), - data: deliver_tx.data, - log: deliver_tx.log, - info: deliver_tx.info, - gas_wanted: deliver_tx.gas_wanted, - gas_used: deliver_tx.gas_used, - events: deliver_tx - .events - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - codespace: deliver_tx.codespace, - }) + fn try_from(deliver_tx: pb::abci::ResponseDeliverTx) -> Result { + Ok(Self { + code: deliver_tx.code.into(), + data: deliver_tx.data, + log: deliver_tx.log, + info: deliver_tx.info, + gas_wanted: deliver_tx.gas_wanted, + gas_used: deliver_tx.gas_used, + events: deliver_tx + .events + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + codespace: deliver_tx.codespace, + }) + } } -} -impl Protobuf for DeliverTx {} + impl Protobuf for DeliverTx {} +} diff --git a/tendermint/src/abci/response/echo.rs b/tendermint/src/abci/response/echo.rs index 7e4777713..11daa5276 100644 --- a/tendermint/src/abci/response/echo.rs +++ b/tendermint/src/abci/response/echo.rs @@ -11,26 +11,26 @@ pub struct Echo { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseEcho { - fn from(echo: Echo) -> Self { - Self { - message: echo.message, +tendermint_pb_modules! { + use super::Echo; + + impl From for pb::abci::ResponseEcho { + fn from(echo: Echo) -> Self { + Self { + message: echo.message, + } } } -} -impl TryFrom for Echo { - type Error = crate::Error; + impl TryFrom for Echo { + type Error = crate::Error; - fn try_from(echo: pb::ResponseEcho) -> Result { - Ok(Self { - message: echo.message, - }) + fn try_from(echo: pb::abci::ResponseEcho) -> Result { + Ok(Self { + message: echo.message, + }) + } } -} -impl Protobuf for Echo {} + impl Protobuf for Echo {} +} diff --git a/tendermint/src/abci/response/end_block.rs b/tendermint/src/abci/response/end_block.rs index 4b4463cee..9f5ad4ebb 100644 --- a/tendermint/src/abci/response/end_block.rs +++ b/tendermint/src/abci/response/end_block.rs @@ -22,45 +22,45 @@ pub struct EndBlock { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; +tendermint_pb_modules! { + use super::EndBlock; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseEndBlock { - fn from(end_block: EndBlock) -> Self { - Self { - validator_updates: end_block - .validator_updates - .into_iter() - .map(Into::into) - .collect(), - consensus_param_updates: end_block.consensus_param_updates.map(Into::into), - events: end_block.events.into_iter().map(Into::into).collect(), + impl From for pb::abci::ResponseEndBlock { + fn from(end_block: EndBlock) -> Self { + Self { + validator_updates: end_block + .validator_updates + .into_iter() + .map(Into::into) + .collect(), + consensus_param_updates: end_block.consensus_param_updates.map(Into::into), + events: end_block.events.into_iter().map(Into::into).collect(), + } } } -} -impl TryFrom for EndBlock { - type Error = crate::Error; + impl TryFrom for EndBlock { + type Error = crate::Error; - fn try_from(end_block: pb::ResponseEndBlock) -> Result { - Ok(Self { - validator_updates: end_block - .validator_updates - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - consensus_param_updates: end_block - .consensus_param_updates - .map(TryInto::try_into) - .transpose()?, - events: end_block - .events - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - }) + fn try_from(end_block: pb::abci::ResponseEndBlock) -> Result { + Ok(Self { + validator_updates: end_block + .validator_updates + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + consensus_param_updates: end_block + .consensus_param_updates + .map(TryInto::try_into) + .transpose()?, + events: end_block + .events + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } } -} -impl Protobuf for EndBlock {} + impl Protobuf for EndBlock {} +} diff --git a/tendermint/src/abci/response/exception.rs b/tendermint/src/abci/response/exception.rs index a6e784147..d8035173d 100644 --- a/tendermint/src/abci/response/exception.rs +++ b/tendermint/src/abci/response/exception.rs @@ -11,26 +11,26 @@ pub struct Exception { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseException { - fn from(exception: Exception) -> Self { - Self { - error: exception.error, +tendermint_pb_modules! { + use super::Exception; + + impl From for pb::abci::ResponseException { + fn from(exception: Exception) -> Self { + Self { + error: exception.error, + } } } -} -impl TryFrom for Exception { - type Error = crate::Error; + impl TryFrom for Exception { + type Error = crate::Error; - fn try_from(exception: pb::ResponseException) -> Result { - Ok(Self { - error: exception.error, - }) + fn try_from(exception: pb::abci::ResponseException) -> Result { + Ok(Self { + error: exception.error, + }) + } } -} -impl Protobuf for Exception {} + impl Protobuf for Exception {} +} diff --git a/tendermint/src/abci/response/info.rs b/tendermint/src/abci/response/info.rs index b19705599..703ac4c8a 100644 --- a/tendermint/src/abci/response/info.rs +++ b/tendermint/src/abci/response/info.rs @@ -1,7 +1,5 @@ -use crate::{block, prelude::*, AppHash, Error}; -use core::convert::TryFrom; +use crate::{block, prelude::*, AppHash}; use tendermint_proto::abci as pb; -use tendermint_proto::Protobuf; use serde::{Deserialize, Serialize}; @@ -25,30 +23,34 @@ pub struct Info { // Protobuf conversions // ============================================================================= -impl From for pb::ResponseInfo { - fn from(info: Info) -> Self { - Self { - data: info.data, - version: info.version, - app_version: info.app_version, - last_block_height: info.last_block_height.into(), - last_block_app_hash: info.last_block_app_hash.into(), +tendermint_pb_modules! { + use super::Info; + + impl From for pb::abci::ResponseInfo { + fn from(info: Info) -> Self { + Self { + data: info.data, + version: info.version, + app_version: info.app_version, + last_block_height: info.last_block_height.into(), + last_block_app_hash: info.last_block_app_hash.into(), + } } } -} -impl TryFrom for Info { - type Error = Error; - - fn try_from(info: pb::ResponseInfo) -> Result { - Ok(Self { - data: info.data, - version: info.version, - app_version: info.app_version, - last_block_height: info.last_block_height.try_into()?, - last_block_app_hash: info.last_block_app_hash.try_into()?, - }) + impl TryFrom for Info { + type Error = crate::Error; + + fn try_from(info: pb::abci::ResponseInfo) -> Result { + Ok(Self { + data: info.data, + version: info.version, + app_version: info.app_version, + last_block_height: info.last_block_height.try_into()?, + last_block_app_hash: info.last_block_app_hash.try_into()?, + }) + } } -} -impl Protobuf for Info {} + impl Protobuf for Info {} +} diff --git a/tendermint/src/abci/response/init_chain.rs b/tendermint/src/abci/response/init_chain.rs index 0dc360c0b..c4a9946a3 100644 --- a/tendermint/src/abci/response/init_chain.rs +++ b/tendermint/src/abci/response/init_chain.rs @@ -24,37 +24,37 @@ pub struct InitChain { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseInitChain { - fn from(init_chain: InitChain) -> Self { - Self { - consensus_params: init_chain.consensus_params.map(Into::into), - validators: init_chain.validators.into_iter().map(Into::into).collect(), - app_hash: init_chain.app_hash.into(), +tendermint_pb_modules! { + use super::InitChain; + + impl From for pb::abci::ResponseInitChain { + fn from(init_chain: InitChain) -> Self { + Self { + consensus_params: init_chain.consensus_params.map(Into::into), + validators: init_chain.validators.into_iter().map(Into::into).collect(), + app_hash: init_chain.app_hash.into(), + } } } -} -impl TryFrom for InitChain { - type Error = crate::Error; - - fn try_from(init_chain: pb::ResponseInitChain) -> Result { - Ok(Self { - consensus_params: init_chain - .consensus_params - .map(TryInto::try_into) - .transpose()?, - validators: init_chain - .validators - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - app_hash: init_chain.app_hash.try_into()?, - }) + impl TryFrom for InitChain { + type Error = crate::Error; + + fn try_from(init_chain: pb::abci::ResponseInitChain) -> Result { + Ok(Self { + consensus_params: init_chain + .consensus_params + .map(TryInto::try_into) + .transpose()?, + validators: init_chain + .validators + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + app_hash: init_chain.app_hash.try_into()?, + }) + } } -} -impl Protobuf for InitChain {} + impl Protobuf for InitChain {} +} diff --git a/tendermint/src/abci/response/list_snapshots.rs b/tendermint/src/abci/response/list_snapshots.rs index 55a7a5f24..e195687e8 100644 --- a/tendermint/src/abci/response/list_snapshots.rs +++ b/tendermint/src/abci/response/list_snapshots.rs @@ -12,34 +12,34 @@ pub struct ListSnapshots { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseListSnapshots { - fn from(list_snapshots: ListSnapshots) -> Self { - Self { - snapshots: list_snapshots - .snapshots - .into_iter() - .map(Into::into) - .collect(), +tendermint_pb_modules! { + use super::ListSnapshots; + + impl From for pb::abci::ResponseListSnapshots { + fn from(list_snapshots: ListSnapshots) -> Self { + Self { + snapshots: list_snapshots + .snapshots + .into_iter() + .map(Into::into) + .collect(), + } } } -} - -impl TryFrom for ListSnapshots { - type Error = crate::Error; - fn try_from(list_snapshots: pb::ResponseListSnapshots) -> Result { - Ok(Self { - snapshots: list_snapshots - .snapshots - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - }) + impl TryFrom for ListSnapshots { + type Error = crate::Error; + + fn try_from(list_snapshots: pb::abci::ResponseListSnapshots) -> Result { + Ok(Self { + snapshots: list_snapshots + .snapshots + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } } -} -impl Protobuf for ListSnapshots {} + impl Protobuf for ListSnapshots {} +} diff --git a/tendermint/src/abci/response/load_snapshot_chunk.rs b/tendermint/src/abci/response/load_snapshot_chunk.rs index fb8f2c129..05546dc86 100644 --- a/tendermint/src/abci/response/load_snapshot_chunk.rs +++ b/tendermint/src/abci/response/load_snapshot_chunk.rs @@ -16,26 +16,26 @@ pub struct LoadSnapshotChunk { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseLoadSnapshotChunk { - fn from(load_snapshot_chunk: LoadSnapshotChunk) -> Self { - Self { - chunk: load_snapshot_chunk.chunk, +tendermint_pb_modules! { + use super::LoadSnapshotChunk; + + impl From for pb::abci::ResponseLoadSnapshotChunk { + fn from(load_snapshot_chunk: LoadSnapshotChunk) -> Self { + Self { + chunk: load_snapshot_chunk.chunk, + } } } -} -impl TryFrom for LoadSnapshotChunk { - type Error = crate::Error; + impl TryFrom for LoadSnapshotChunk { + type Error = crate::Error; - fn try_from(load_snapshot_chunk: pb::ResponseLoadSnapshotChunk) -> Result { - Ok(Self { - chunk: load_snapshot_chunk.chunk, - }) + fn try_from(load_snapshot_chunk: pb::abci::ResponseLoadSnapshotChunk) -> Result { + Ok(Self { + chunk: load_snapshot_chunk.chunk, + }) + } } -} -impl Protobuf for LoadSnapshotChunk {} + impl Protobuf for LoadSnapshotChunk {} +} diff --git a/tendermint/src/abci/response/offer_snapshot.rs b/tendermint/src/abci/response/offer_snapshot.rs index 47ee38861..97e3660ab 100644 --- a/tendermint/src/abci/response/offer_snapshot.rs +++ b/tendermint/src/abci/response/offer_snapshot.rs @@ -31,32 +31,32 @@ impl Default for OfferSnapshot { // Protobuf conversions // ============================================================================= -use core::convert::TryFrom; - -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseOfferSnapshot { - fn from(offer_snapshot: OfferSnapshot) -> Self { - Self { - result: offer_snapshot as i32, +tendermint_pb_modules! { + use super::OfferSnapshot; + + impl From for pb::abci::ResponseOfferSnapshot { + fn from(offer_snapshot: OfferSnapshot) -> Self { + Self { + result: offer_snapshot as i32, + } } } -} -impl TryFrom for OfferSnapshot { - type Error = crate::Error; - - fn try_from(offer_snapshot: pb::ResponseOfferSnapshot) -> Result { - Ok(match offer_snapshot.result { - 0 => OfferSnapshot::Unknown, - 1 => OfferSnapshot::Accept, - 2 => OfferSnapshot::Abort, - 3 => OfferSnapshot::Reject, - 4 => OfferSnapshot::RejectFormat, - 5 => OfferSnapshot::RejectSender, - _ => return Err(crate::Error::unsupported_offer_snapshot_chunk_result()), - }) + impl TryFrom for OfferSnapshot { + type Error = crate::Error; + + fn try_from(offer_snapshot: pb::abci::ResponseOfferSnapshot) -> Result { + Ok(match offer_snapshot.result { + 0 => OfferSnapshot::Unknown, + 1 => OfferSnapshot::Accept, + 2 => OfferSnapshot::Abort, + 3 => OfferSnapshot::Reject, + 4 => OfferSnapshot::RejectFormat, + 5 => OfferSnapshot::RejectSender, + _ => return Err(crate::Error::unsupported_offer_snapshot_chunk_result()), + }) + } } -} -impl Protobuf for OfferSnapshot {} + impl Protobuf for OfferSnapshot {} +} diff --git a/tendermint/src/abci/response/query.rs b/tendermint/src/abci/response/query.rs index 40fbc8beb..23bbe8b83 100644 --- a/tendermint/src/abci/response/query.rs +++ b/tendermint/src/abci/response/query.rs @@ -40,42 +40,42 @@ pub struct Query { // Protobuf conversions // ============================================================================= -use core::convert::{TryFrom, TryInto}; +tendermint_pb_modules! { + use super::Query; -use tendermint_proto::{abci as pb, Protobuf}; - -impl From for pb::ResponseQuery { - fn from(query: Query) -> Self { - Self { - code: query.code.into(), - log: query.log, - info: query.info, - index: query.index, - key: query.key, - value: query.value, - proof_ops: query.proof.map(Into::into), - height: query.height.into(), - codespace: query.codespace, + impl From for pb::abci::ResponseQuery { + fn from(query: Query) -> Self { + Self { + code: query.code.into(), + log: query.log, + info: query.info, + index: query.index, + key: query.key, + value: query.value, + proof_ops: query.proof.map(Into::into), + height: query.height.into(), + codespace: query.codespace, + } } } -} -impl TryFrom for Query { - type Error = crate::Error; + impl TryFrom for Query { + type Error = crate::Error; - fn try_from(query: pb::ResponseQuery) -> Result { - Ok(Self { - code: query.code.into(), - log: query.log, - info: query.info, - index: query.index, - key: query.key, - value: query.value, - proof: query.proof_ops.map(TryInto::try_into).transpose()?, - height: query.height.try_into()?, - codespace: query.codespace, - }) + fn try_from(query: pb::abci::ResponseQuery) -> Result { + Ok(Self { + code: query.code.into(), + log: query.log, + info: query.info, + index: query.index, + key: query.key, + value: query.value, + proof: query.proof_ops.map(TryInto::try_into).transpose()?, + height: query.height.try_into()?, + codespace: query.codespace, + }) + } } -} -impl Protobuf for Query {} + impl Protobuf for Query {} +} diff --git a/tendermint/src/merkle/proof.rs b/tendermint/src/merkle/proof.rs index df5ad2bdd..228708abc 100644 --- a/tendermint/src/merkle/proof.rs +++ b/tendermint/src/merkle/proof.rs @@ -1,13 +1,8 @@ //! Merkle proofs -use core::convert::TryFrom; use serde::{Deserialize, Serialize}; -use tendermint_proto::{ - crypto::{Proof as RawProof, ProofOp as RawProofOp, ProofOps as RawProofOps}, - Protobuf, -}; -use crate::{prelude::*, serializers, Error, Hash}; +use crate::{prelude::*, serializers, Hash}; #[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] #[serde(try_from = "RawProof", into = "RawProof")] @@ -47,86 +42,99 @@ pub struct ProofOp { pub data: Vec, } -impl Protobuf for Proof {} - -impl TryFrom for Proof { - type Error = Error; - - fn try_from(message: RawProof) -> Result { - Ok(Self { - total: message - .total - .try_into() - .map_err(Error::negative_proof_total)?, - index: message - .index - .try_into() - .map_err(Error::negative_proof_index)?, - leaf_hash: message.leaf_hash.try_into()?, - aunts: message - .aunts - .into_iter() - .map(TryInto::try_into) - .collect::>()?, - }) +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +tendermint_pb_modules! { + use super::{Proof, ProofOp, ProofOps}; + use crate::{prelude::*, Error}; + use pb::{ + crypto::{Proof as RawProof, ProofOp as RawProofOp, ProofOps as RawProofOps}, + }; + + impl Protobuf for Proof {} + + impl TryFrom for Proof { + type Error = Error; + + fn try_from(message: RawProof) -> Result { + Ok(Self { + total: message + .total + .try_into() + .map_err(Error::negative_proof_total)?, + index: message + .index + .try_into() + .map_err(Error::negative_proof_index)?, + leaf_hash: message.leaf_hash.try_into()?, + aunts: message + .aunts + .into_iter() + .map(TryInto::try_into) + .collect::>()?, + }) + } } -} -impl From for RawProof { - fn from(value: Proof) -> Self { - Self { - total: value - .total - .try_into() - .expect("number of items is too large"), - index: value.index.try_into().expect("index is too large"), - leaf_hash: value.leaf_hash.into(), - aunts: value.aunts.into_iter().map(Into::into).collect(), + impl From for RawProof { + fn from(value: Proof) -> Self { + Self { + total: value + .total + .try_into() + .expect("number of items is too large"), + index: value.index.try_into().expect("index is too large"), + leaf_hash: value.leaf_hash.into(), + aunts: value.aunts.into_iter().map(Into::into).collect(), + } } } -} -impl Protobuf for ProofOp {} + impl Protobuf for ProofOp {} + impl Protobuf for ProofOp {} -impl TryFrom for ProofOp { - type Error = Error; + impl TryFrom for ProofOp { + type Error = Error; - fn try_from(value: RawProofOp) -> Result { - Ok(Self { - field_type: value.r#type, - key: value.key, - data: value.data, - }) + fn try_from(value: RawProofOp) -> Result { + Ok(Self { + field_type: value.r#type, + key: value.key, + data: value.data, + }) + } } -} -impl From for RawProofOp { - fn from(value: ProofOp) -> Self { - RawProofOp { - r#type: value.field_type, - key: value.key, - data: value.data, + impl From for RawProofOp { + fn from(value: ProofOp) -> Self { + RawProofOp { + r#type: value.field_type, + key: value.key, + data: value.data, + } } } -} -impl Protobuf for ProofOps {} + impl Protobuf for ProofOps {} -impl TryFrom for ProofOps { - type Error = Error; + impl TryFrom for ProofOps { + type Error = Error; - fn try_from(value: RawProofOps) -> Result { - let ops: Result, _> = value.ops.into_iter().map(ProofOp::try_from).collect(); + fn try_from(value: RawProofOps) -> Result { + let ops: Result, _> = value.ops.into_iter().map(ProofOp::try_from).collect(); - Ok(Self { ops: ops? }) + Ok(Self { ops: ops? }) + } } -} -impl From for RawProofOps { - fn from(value: ProofOps) -> Self { - let ops: Vec = value.ops.into_iter().map(RawProofOp::from).collect(); + impl From for RawProofOps { + fn from(value: ProofOps) -> Self { + let ops: Vec = value.ops.into_iter().map(RawProofOp::from).collect(); - RawProofOps { ops } + RawProofOps { ops } + } } } From df285593d0fa6721599a64872647929bed8ddadf Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 24 Oct 2022 20:30:02 +0300 Subject: [PATCH 11/77] Fix conversion from account::Id to Bytes --- tendermint/src/account.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tendermint/src/account.rs b/tendermint/src/account.rs index 0fcc8cc71..0194cd64d 100644 --- a/tendermint/src/account.rs +++ b/tendermint/src/account.rs @@ -62,7 +62,7 @@ impl TryFrom for Id { impl From for Bytes { fn from(value: Id) -> Self { - value.as_bytes().into() + Bytes::copy_from_slice(value.as_bytes()) } } From ca50ce4d082e5a88759b018e13329934a3ec59c9 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 24 Oct 2022 20:48:56 +0300 Subject: [PATCH 12/77] Fix compiler warnings --- tendermint/src/abci/request.rs | 2 +- tendermint/src/abci/response.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/tendermint/src/abci/request.rs b/tendermint/src/abci/request.rs index 91e8ceebf..f37388995 100644 --- a/tendermint/src/abci/request.rs +++ b/tendermint/src/abci/request.rs @@ -362,7 +362,7 @@ mod v0_37 { Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), Request::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), Request::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), - Request::SetOption(x) => { + Request::SetOption(_) => { panic!("SetOption should not be used with Tendermint 0.37") }, }; diff --git a/tendermint/src/abci/response.rs b/tendermint/src/abci/response.rs index 2b506d48f..721ea2a5d 100644 --- a/tendermint/src/abci/response.rs +++ b/tendermint/src/abci/response.rs @@ -341,7 +341,7 @@ mod v0_37 { Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), Response::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), Response::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), - Response::SetOption(x) => { + Response::SetOption(_) => { panic!("SetOption should not be used with Tendermint 0.37") }, }; From 3277ac3a38e3eced400ce04e37c6d19870fda9d6 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 25 Oct 2022 13:47:21 +0300 Subject: [PATCH 13/77] light-client: Restore Supervisor::report_evidence Keep it as a stub to avoid more extensive changes. --- light-client/src/supervisor.rs | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/light-client/src/supervisor.rs b/light-client/src/supervisor.rs index 5be0a8346..14dad4b29 100644 --- a/light-client/src/supervisor.rs +++ b/light-client/src/supervisor.rs @@ -283,6 +283,21 @@ impl Supervisor { Ok(forked) } + /// Report the given evidence of a fork. + // TODO: rework to supply LightClientAttackEvidence data + fn report_evidence( + &mut self, + provider: PeerId, + _primary: &LightBlock, + _witness: &LightBlock, + ) -> Result<(), Error> { + self.evidence_reporter + .report(Evidence::LightClientAttackEvidence, provider) + .map_err(Error::io)?; + + Ok(()) + } + /// Perform fork detection with the given verified block and trusted block. fn detect_forks( &self, From 47e285b822baece50aa059d66352464c92c5b4e8 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 25 Oct 2022 17:20:34 +0300 Subject: [PATCH 14/77] Restore serialization of Block and Evidence Define hand-written Serialize/Deserialize impls for Evidence. --- proto/src/prost/v0_34/tendermint.types.rs | 3 - proto/src/prost/v0_37/tendermint.types.rs | 3 - proto/src/serializers.rs | 1 + proto/src/serializers/evidence.rs | 47 ++++++ tendermint/src/block.rs | 4 +- tendermint/src/evidence.rs | 173 ++-------------------- tools/proto-compiler/src/constants.rs | 6 +- 7 files changed, 62 insertions(+), 175 deletions(-) create mode 100644 proto/src/serializers/evidence.rs diff --git a/proto/src/prost/v0_34/tendermint.types.rs b/proto/src/prost/v0_34/tendermint.types.rs index 5e8de00a8..753c63469 100644 --- a/proto/src/prost/v0_34/tendermint.types.rs +++ b/proto/src/prost/v0_34/tendermint.types.rs @@ -389,8 +389,6 @@ pub struct EventDataRoundState { #[prost(string, tag="3")] pub step: ::prost::alloc::string::String, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Evidence { #[prost(oneof="evidence::Sum", tags="1, 2")] @@ -400,7 +398,6 @@ pub struct Evidence { pub mod evidence { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] - #[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { #[prost(message, tag="1")] diff --git a/proto/src/prost/v0_37/tendermint.types.rs b/proto/src/prost/v0_37/tendermint.types.rs index 7b205cede..bb5dce6c6 100644 --- a/proto/src/prost/v0_37/tendermint.types.rs +++ b/proto/src/prost/v0_37/tendermint.types.rs @@ -383,8 +383,6 @@ pub struct EventDataRoundState { #[prost(string, tag="3")] pub step: ::prost::alloc::string::String, } -#[derive(::serde::Deserialize, ::serde::Serialize)] -#[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Evidence { #[prost(oneof="evidence::Sum", tags="1, 2")] @@ -394,7 +392,6 @@ pub struct Evidence { pub mod evidence { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] - #[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { #[prost(message, tag="1")] diff --git a/proto/src/serializers.rs b/proto/src/serializers.rs index c506cb003..161833816 100644 --- a/proto/src/serializers.rs +++ b/proto/src/serializers.rs @@ -55,6 +55,7 @@ pub mod allow_null; pub mod bytes; +mod evidence; pub mod from_str; pub mod nullable; pub mod optional; diff --git a/proto/src/serializers/evidence.rs b/proto/src/serializers/evidence.rs new file mode 100644 index 000000000..7136455c5 --- /dev/null +++ b/proto/src/serializers/evidence.rs @@ -0,0 +1,47 @@ +mod v0_34 { + use crate::v0_34::types::{evidence, Evidence}; + use serde::{Deserialize, Deserializer, Serialize, Serializer}; + + impl<'de> Deserialize<'de> for Evidence { + fn deserialize(deserializer: D) -> Result + where + D: Deserializer<'de>, + { + let sum = Option::::deserialize(deserializer)?; + Ok(Self { sum }) + } + } + + impl Serialize for Evidence { + fn serialize(&self, serializer: S) -> Result + where + S: Serializer, + { + self.sum.serialize(serializer) + } + } +} + +mod v0_37 { + use crate::v0_37::types::{evidence, Evidence}; + use serde::{Deserialize, Deserializer, Serialize, Serializer}; + + impl<'de> Deserialize<'de> for Evidence { + fn deserialize(deserializer: D) -> Result + where + D: Deserializer<'de>, + { + let sum = Option::::deserialize(deserializer)?; + Ok(Self { sum }) + } + } + + impl Serialize for Evidence { + fn serialize(&self, serializer: S) -> Result + where + S: Serializer, + { + self.sum.serialize(serializer) + } + } +} diff --git a/tendermint/src/block.rs b/tendermint/src/block.rs index 845fd36cd..14c27a603 100644 --- a/tendermint/src/block.rs +++ b/tendermint/src/block.rs @@ -24,7 +24,7 @@ pub use self::{ round::*, size::Size, }; -use crate::{error::Error, evidence, prelude::*, serializers}; +use crate::{error::Error, evidence, prelude::*}; /// Blocks consist of a header, transactions, votes (the commit), and a list of /// evidence of malfeasance (i.e. signing conflicting votes). @@ -33,6 +33,7 @@ use crate::{error::Error, evidence, prelude::*, serializers}; // Default serialization - all fields serialize; used by /block endpoint #[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq)] #[non_exhaustive] +#[serde(try_from = "RawBlock", into = "RawBlock")] pub struct Block { /// Block header pub header: Header, @@ -41,7 +42,6 @@ pub struct Block { pub data: Vec>, /// Evidence of malfeasance - #[serde(with = "serializers::allow_null")] pub evidence: evidence::Data, /// Last commit diff --git a/tendermint/src/evidence.rs b/tendermint/src/evidence.rs index 6da571a53..beeb92495 100644 --- a/tendermint/src/evidence.rs +++ b/tendermint/src/evidence.rs @@ -7,7 +7,7 @@ use core::{ use serde::{Deserialize, Serialize}; use tendermint_proto::{ - google::protobuf::Duration as RawDuration, types::evidence::Sum as RawSum, Protobuf, + google::protobuf::Duration as RawDuration, types::Evidence as RawEvidence, Protobuf, }; use crate::{error::Error, prelude::*, serializers, vote::Power, Time, Vote}; @@ -18,7 +18,7 @@ use crate::{error::Error, prelude::*, serializers, vote::Power, Time, Vote}; /// /// #[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] -#[serde(try_from = "RawSum", into = "Option")] // Used by RPC /broadcast_evidence endpoint +#[serde(try_from = "RawEvidence", into = "RawEvidence")] // Used by RPC /broadcast_evidence endpoint pub enum Evidence { /// Duplicate vote evidence DuplicateVote(DuplicateVoteEvidence), @@ -120,188 +120,35 @@ pub struct Params { // Protobuf conversions // ============================================================================= -mod v0_34 { - use tendermint_proto::v0_37::types::{ +tendermint_pb_modules! { + use pb::types::{ evidence::Sum as RawSum, DuplicateVoteEvidence as RawDuplicateVoteEvidence, Evidence as RawEvidence, EvidenceList as RawEvidenceList, EvidenceParams as RawEvidenceParams, }; - use tendermint_proto::Protobuf; use super::{Data, DuplicateVoteEvidence, Evidence, Params}; use crate::{error::Error, prelude::*}; - impl TryFrom for Evidence { - type Error = Error; - - fn try_from(value: RawSum) -> Result { - use RawSum::*; - match value { - DuplicateVoteEvidence(ev) => Ok(Evidence::DuplicateVote(ev.try_into()?)), - LightClientAttackEvidence(_ev) => Ok(Evidence::LightClientAttackEvidence), - } - } - } - impl TryFrom for Evidence { type Error = Error; - fn try_from(value: RawEvidence) -> Result { - value - .sum - .ok_or_else(Error::invalid_evidence) - .and_then(TryInto::try_into) - } - } - - impl From for Option { - fn from(value: Evidence) -> Self { - match value { - Evidence::DuplicateVote(ev) => Some(RawSum::DuplicateVoteEvidence(ev.into())), - Evidence::LightClientAttackEvidence => None, - } - } - } - - impl From for RawEvidence { - fn from(value: Evidence) -> Self { - RawEvidence { sum: value.into() } - } - } - - impl TryFrom for DuplicateVoteEvidence { - type Error = Error; - - fn try_from(value: RawDuplicateVoteEvidence) -> Result { - Ok(Self { - vote_a: value - .vote_a - .ok_or_else(Error::missing_evidence)? - .try_into()?, - vote_b: value - .vote_b - .ok_or_else(Error::missing_evidence)? - .try_into()?, - total_voting_power: value.total_voting_power.try_into()?, - validator_power: value.validator_power.try_into()?, - timestamp: value - .timestamp - .ok_or_else(Error::missing_timestamp)? - .try_into()?, - }) - } - } - - impl From for RawDuplicateVoteEvidence { - fn from(value: DuplicateVoteEvidence) -> Self { - RawDuplicateVoteEvidence { - vote_a: Some(value.vote_a.into()), - vote_b: Some(value.vote_b.into()), - total_voting_power: value.total_voting_power.into(), - validator_power: value.total_voting_power.into(), - timestamp: Some(value.timestamp.into()), - } - } - } - - impl TryFrom for Data { - type Error = Error; - fn try_from(value: RawEvidenceList) -> Result { - let evidence = value - .evidence - .into_iter() - .map(TryInto::try_into) - .collect::, _>>()?; - Ok(Self(evidence)) - } - } - - impl From for RawEvidenceList { - fn from(value: Data) -> Self { - RawEvidenceList { - evidence: value.0.into_iter().map(Into::into).collect(), - } - } - } - - impl Protobuf for Params {} - - impl TryFrom for Params { - type Error = Error; - - fn try_from(value: RawEvidenceParams) -> Result { - Ok(Self { - max_age_num_blocks: value - .max_age_num_blocks - .try_into() - .map_err(Error::negative_max_age_num)?, - max_age_duration: value - .max_age_duration - .ok_or_else(Error::missing_max_age_duration)? - .try_into()?, - max_bytes: value.max_bytes, - }) - } - } - - impl From for RawEvidenceParams { - fn from(value: Params) -> Self { - Self { - // Todo: Implement proper domain types so this becomes infallible - max_age_num_blocks: value.max_age_num_blocks.try_into().unwrap(), - max_age_duration: Some(value.max_age_duration.into()), - max_bytes: value.max_bytes, - } - } - } -} - -mod v0_37 { - use tendermint_proto::v0_34::types::{ - evidence::Sum as RawSum, DuplicateVoteEvidence as RawDuplicateVoteEvidence, - Evidence as RawEvidence, EvidenceList as RawEvidenceList, - EvidenceParams as RawEvidenceParams, - }; - use tendermint_proto::Protobuf; - - use super::{Data, DuplicateVoteEvidence, Evidence, Params}; - use crate::{error::Error, prelude::*}; - - impl TryFrom for Evidence { - type Error = Error; - - fn try_from(value: RawSum) -> Result { + fn try_from(message: RawEvidence) -> Result { use RawSum::*; - match value { + match message.sum.ok_or_else(Error::invalid_evidence)? { DuplicateVoteEvidence(ev) => Ok(Evidence::DuplicateVote(ev.try_into()?)), LightClientAttackEvidence(_ev) => Ok(Evidence::LightClientAttackEvidence), } } } - impl TryFrom for Evidence { - type Error = Error; - - fn try_from(value: RawEvidence) -> Result { - value - .sum - .ok_or_else(Error::invalid_evidence) - .and_then(TryInto::try_into) - } - } - - impl From for Option { + impl From for RawEvidence { fn from(value: Evidence) -> Self { - match value { + let sum = match value { Evidence::DuplicateVote(ev) => Some(RawSum::DuplicateVoteEvidence(ev.into())), Evidence::LightClientAttackEvidence => None, - } - } - } - - impl From for RawEvidence { - fn from(value: Evidence) -> Self { - RawEvidence { sum: value.into() } + }; + RawEvidence { sum } } } diff --git a/tools/proto-compiler/src/constants.rs b/tools/proto-compiler/src/constants.rs index 98be71f53..d5a7928b4 100644 --- a/tools/proto-compiler/src/constants.rs +++ b/tools/proto-compiler/src/constants.rs @@ -53,7 +53,6 @@ const RENAME_SRPUBKEY: &str = r#"#[serde(rename = "tendermint/PubKeySr25519", wi const RENAME_DUPLICATEVOTE: &str = r#"#[serde(rename = "tendermint/DuplicateVoteEvidence")]"#; const RENAME_LIGHTCLIENTATTACK: &str = r#"#[serde(rename = "tendermint/LightClientAttackEvidence")]"#; -const EVIDENCE_VARIANT: &str = r#"#[serde(from = "crate::serializers::evidence::EvidenceVariant", into = "crate::serializers::evidence::EvidenceVariant")]"#; const ALIAS_VALIDATOR_POWER_QUOTED: &str = r#"#[serde(alias = "ValidatorPower", with = "crate::serializers::from_str")]"#; const ALIAS_TOTAL_VOTING_POWER_QUOTED: &str = @@ -72,8 +71,9 @@ pub static CUSTOM_TYPE_ATTRIBUTES: &[(&str, &str)] = &[ (".tendermint.types.BlockIDFlag", PRIMITIVE_ENUM), (".tendermint.types.Block", SERIALIZED), (".tendermint.types.Data", SERIALIZED), + (".tendermint.types.Evidence.sum", SERIALIZED), + (".tendermint.types.Evidence.sum", TYPE_TAG), (".tendermint.types.EvidenceList", SERIALIZED), - (".tendermint.types.Evidence", SERIALIZED), (".tendermint.types.DuplicateVoteEvidence", SERIALIZED), (".tendermint.types.Vote", SERIALIZED), (".tendermint.types.BlockID", SERIALIZED), @@ -88,14 +88,12 @@ pub static CUSTOM_TYPE_ATTRIBUTES: &[(&str, &str)] = &[ (".tendermint.types.ValidatorSet", SERIALIZED), (".tendermint.crypto.PublicKey", SERIALIZED), (".tendermint.crypto.PublicKey.sum", TYPE_TAG), - (".tendermint.types.Evidence.sum", TYPE_TAG), (".tendermint.abci.ResponseInfo", SERIALIZED), (".tendermint.types.CanonicalBlockID", SERIALIZED), (".tendermint.types.CanonicalPartSetHeader", SERIALIZED), (".tendermint.types.Validator", SERIALIZED), (".tendermint.types.CanonicalVote", SERIALIZED), (".tendermint.types.BlockMeta", SERIALIZED), - (".tendermint.types.Evidence", EVIDENCE_VARIANT), (".tendermint.types.TxProof", SERIALIZED), (".tendermint.crypto.Proof", SERIALIZED), ]; From 53a546c04c95d6b227c08e5fd22580359ba449b5 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 27 Oct 2022 12:55:32 +0300 Subject: [PATCH 15/77] Fix clippy lints --- tendermint/src/abci/event.rs | 4 ++-- tendermint/src/evidence.rs | 1 + tendermint/src/validator.rs | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/tendermint/src/abci/event.rs b/tendermint/src/abci/event.rs index 868c40602..f7c1aa7e2 100644 --- a/tendermint/src/abci/event.rs +++ b/tendermint/src/abci/event.rs @@ -212,8 +212,8 @@ mod v0_37 { impl From for pb::EventAttribute { fn from(event: EventAttribute) -> Self { Self { - key: event.key.into(), - value: event.value.into(), + key: event.key, + value: event.value, index: event.index, } } diff --git a/tendermint/src/evidence.rs b/tendermint/src/evidence.rs index beeb92495..39f98f559 100644 --- a/tendermint/src/evidence.rs +++ b/tendermint/src/evidence.rs @@ -19,6 +19,7 @@ use crate::{error::Error, prelude::*, serializers, vote::Power, Time, Vote}; /// #[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] #[serde(try_from = "RawEvidence", into = "RawEvidence")] // Used by RPC /broadcast_evidence endpoint +#[allow(clippy::large_enum_variant)] pub enum Evidence { /// Duplicate vote evidence DuplicateVote(DuplicateVoteEvidence), diff --git a/tendermint/src/validator.rs b/tendermint/src/validator.rs index 12d462c2a..cf250bb40 100644 --- a/tendermint/src/validator.rs +++ b/tendermint/src/validator.rs @@ -163,7 +163,7 @@ impl Info { /// nor the proposer priority, as that changes with every block even if the validator set didn't. /// It contains only the pubkey and the voting power. /// TODO: currently only works for Ed25519 pubkeys -#[derive(Clone, PartialEq)] +#[derive(Clone, PartialEq, Eq)] pub struct SimpleValidator { /// Public key pub pub_key: PublicKey, From 9b7089c9c60152a4958f255719632a7e89977500 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 27 Oct 2022 13:49:53 +0300 Subject: [PATCH 16/77] proto-compiler: Improve copying of generated files - Filter out the empty non-Tendermint files. - Improve use of the WalkDir iterator. - Use OS-agnostic path construction. --- tools/proto-compiler/src/functions.rs | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/tools/proto-compiler/src/functions.rs b/tools/proto-compiler/src/functions.rs index 03da98ccc..90f327c3e 100644 --- a/tools/proto-compiler/src/functions.rs +++ b/tools/proto-compiler/src/functions.rs @@ -166,20 +166,20 @@ pub fn copy_files(src_dir: &Path, target_dir: &Path) { // Copy new compiled files (prost does not use folder structures) let errors = WalkDir::new(src_dir) + .contents_first(true) .into_iter() - .filter_map(|e| e.ok()) - .filter(|e| e.file_type().is_file()) - .map(|e| { - copy( - e.path(), - std::path::Path::new(&format!( - "{}/{}", - &target_dir.display(), - &e.file_name().to_os_string().to_str().unwrap() - )), - ) + .filter_entry(|e| { + e.file_type().is_file() + && e.file_name() + .to_str() + .map(|name| name.starts_with("tendermint.")) + .unwrap_or(false) + }) + .map(|res| { + let e = res?; + copy(e.path(), target_dir.join(e.file_name())) }) - .filter_map(|e| e.err()) + .filter_map(|res| res.err()) .collect::>(); if !errors.is_empty() { From f40b6f4424918bdf6d6649613788a347c2a8bc7c Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 27 Oct 2022 13:50:53 +0300 Subject: [PATCH 17/77] proto: Regenerate v0_34 with v0.34.22 --- proto/src/tendermint/v0_34.rs | 2 +- tools/proto-compiler/src/constants.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/proto/src/tendermint/v0_34.rs b/proto/src/tendermint/v0_34.rs index 950815c7d..c9fa5e266 100644 --- a/proto/src/tendermint/v0_34.rs +++ b/proto/src/tendermint/v0_34.rs @@ -62,5 +62,5 @@ pub mod version { pub mod meta { pub const REPOSITORY: &str = "https://github.com/tendermint/tendermint"; - pub const COMMITISH: &str = "v0.34.21"; + pub const COMMITISH: &str = "v0.34.22"; } diff --git a/tools/proto-compiler/src/constants.rs b/tools/proto-compiler/src/constants.rs index d5a7928b4..0dc057b05 100644 --- a/tools/proto-compiler/src/constants.rs +++ b/tools/proto-compiler/src/constants.rs @@ -19,7 +19,7 @@ pub struct TendermintVersion { pub const TENDERMINT_VERSIONS: &[TendermintVersion] = &[ TendermintVersion { ident: "v0_34", - commitish: "v0.34.21", + commitish: "v0.34.22", }, TendermintVersion { ident: "v0_37", From 276bc6d349229d205240048bf1a54d3379393b56 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 9 Nov 2022 15:38:08 +0200 Subject: [PATCH 18/77] Add domain type for RemoteSignerError With multi-protocol stuff, it should be done properly and conversions defined from/to proto stuff. --- tendermint/src/privval.rs | 40 ++++ tendermint/src/proposal/sign_proposal.rs | 103 ++++----- tendermint/src/public_key/pub_key_response.rs | 47 +++-- tendermint/src/vote/sign_vote.rs | 198 +++++++++--------- 4 files changed, 221 insertions(+), 167 deletions(-) create mode 100644 tendermint/src/privval.rs diff --git a/tendermint/src/privval.rs b/tendermint/src/privval.rs new file mode 100644 index 000000000..dd1b92415 --- /dev/null +++ b/tendermint/src/privval.rs @@ -0,0 +1,40 @@ +//! Types used in the Privval protocol (Tendermint Core [ADR-063]) +//! +//! [ADR-063]: https://github.com/tendermint/tendermint/blob/main/docs/architecture/adr-063-privval-grpc.md + +use crate::prelude::*; + +#[derive(Clone, Debug, PartialEq)] +pub struct RemoteSignerError { + pub code: i32, + pub description: String, +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +tendermint_pb_modules! { + use super::RemoteSignerError; + use pb::privval::RemoteSignerError as RawRemoteSignerError; + + impl TryFrom for RemoteSignerError { + type Error = crate::Error; + + fn try_from(message: RawRemoteSignerError) -> Result { + Ok(Self { + code: message.code, + description: message.description, + }) + } + } + + impl From for RawRemoteSignerError { + fn from(value: RemoteSignerError) -> Self { + Self { + code: value.code, + description: value.description, + } + } + } +} diff --git a/tendermint/src/proposal/sign_proposal.rs b/tendermint/src/proposal/sign_proposal.rs index a78f8c813..16374f4a8 100644 --- a/tendermint/src/proposal/sign_proposal.rs +++ b/tendermint/src/proposal/sign_proposal.rs @@ -1,16 +1,8 @@ -use core::convert::{TryFrom, TryInto}; - use bytes::BufMut; -use tendermint_proto::{ - privval::{ - RemoteSignerError, SignProposalRequest as RawSignProposalRequest, - SignedProposalResponse as RawSignedProposalResponse, - }, - Error as ProtobufError, Protobuf, -}; +use tendermint_proto::Error as ProtobufError; use super::Proposal; -use crate::{chain::Id as ChainId, error::Error, prelude::*}; +use crate::{chain::Id as ChainId, prelude::*, privval::RemoteSignerError}; /// SignProposalRequest is a request to sign a proposal #[derive(Clone, PartialEq, Eq, Debug)] @@ -21,32 +13,6 @@ pub struct SignProposalRequest { pub chain_id: ChainId, } -impl Protobuf for SignProposalRequest {} -impl Protobuf for SignedProposalResponse {} - -impl TryFrom for SignProposalRequest { - type Error = Error; - - fn try_from(value: RawSignProposalRequest) -> Result { - if value.proposal.is_none() { - return Err(Error::no_proposal_found()); - } - Ok(SignProposalRequest { - proposal: Proposal::try_from(value.proposal.unwrap())?, - chain_id: ChainId::try_from(value.chain_id).unwrap(), - }) - } -} - -impl From for RawSignProposalRequest { - fn from(value: SignProposalRequest) -> Self { - RawSignProposalRequest { - proposal: Some(value.proposal.into()), - chain_id: value.chain_id.to_string(), - } - } -} - impl SignProposalRequest { /// Create signable bytes from Proposal. pub fn to_signable_bytes(&self, sign_bytes: &mut B) -> Result @@ -72,22 +38,61 @@ pub struct SignedProposalResponse { pub error: Option, } -impl TryFrom for SignedProposalResponse { - type Error = Error; +// ============================================================================= +// Protobuf conversions +// ============================================================================= - fn try_from(value: RawSignedProposalResponse) -> Result { - Ok(SignedProposalResponse { - proposal: value.proposal.map(TryInto::try_into).transpose()?, - error: value.error, - }) +tendermint_pb_modules! { + use pb::privval::{ + SignProposalRequest as RawSignProposalRequest, + SignedProposalResponse as RawSignedProposalResponse, + }; + use crate::{Error, chain::Id as ChainId, prelude::*}; + use super::{SignProposalRequest, SignedProposalResponse}; + + impl Protobuf for SignProposalRequest {} + impl Protobuf for SignedProposalResponse {} + + impl TryFrom for SignProposalRequest { + type Error = Error; + + fn try_from(value: RawSignProposalRequest) -> Result { + if value.proposal.is_none() { + return Err(Error::no_proposal_found()); + } + Ok(SignProposalRequest { + proposal: Proposal::try_from(value.proposal.unwrap())?, + chain_id: ChainId::try_from(value.chain_id).unwrap(), + }) + } + } + + impl From for RawSignProposalRequest { + fn from(value: SignProposalRequest) -> Self { + RawSignProposalRequest { + proposal: Some(value.proposal.into()), + chain_id: value.chain_id.to_string(), + } + } + } + + impl TryFrom for SignedProposalResponse { + type Error = Error; + + fn try_from(value: RawSignedProposalResponse) -> Result { + Ok(SignedProposalResponse { + proposal: value.proposal.map(TryInto::try_into).transpose()?, + error: value.error.map(TryInto::try_into).transpose()?, + }) + } } -} -impl From for RawSignedProposalResponse { - fn from(value: SignedProposalResponse) -> Self { - RawSignedProposalResponse { - proposal: value.proposal.map(Into::into), - error: value.error, + impl From for RawSignedProposalResponse { + fn from(value: SignedProposalResponse) -> Self { + RawSignedProposalResponse { + proposal: value.proposal.map(Into::into), + error: value.error.map(Into::into), + } } } } diff --git a/tendermint/src/public_key/pub_key_response.rs b/tendermint/src/public_key/pub_key_response.rs index bf337d848..5a00028f1 100644 --- a/tendermint/src/public_key/pub_key_response.rs +++ b/tendermint/src/public_key/pub_key_response.rs @@ -1,11 +1,4 @@ -use core::convert::{TryFrom, TryInto}; - -use tendermint_proto::{ - privval::{PubKeyResponse as RawPubKeyResponse, RemoteSignerError}, - Protobuf, -}; - -use crate::{Error, PublicKey}; +use crate::{privval::RemoteSignerError, PublicKey}; /// PubKeyResponse #[derive(Clone, PartialEq, Debug)] @@ -18,26 +11,34 @@ pub struct PubKeyResponse { pub error: Option, } -impl Protobuf for PubKeyResponse {} +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +tendermint_pb_modules! { + use super::PubKeyResponse; + use pb::privval::PubKeyResponse as RawPubKeyResponse; + + impl Protobuf for PubKeyResponse {} -impl TryFrom for PubKeyResponse { - type Error = Error; + impl TryFrom for PubKeyResponse { + type Error = crate::Error; - fn try_from(value: RawPubKeyResponse) -> Result { - Ok(PubKeyResponse { - pub_key: value.pub_key.map(TryInto::try_into).transpose()?, - error: value.error, - }) + fn try_from(value: RawPubKeyResponse) -> Result { + Ok(PubKeyResponse { + pub_key: value.pub_key.map(TryInto::try_into).transpose()?, + error: value.error.map(TryInto::try_into).transpose()?, + }) + } } -} -impl From for RawPubKeyResponse { - fn from(value: PubKeyResponse) -> Self { - RawPubKeyResponse { - pub_key: value.pub_key.map(Into::into), - error: value.error, + impl From for RawPubKeyResponse { + fn from(value: PubKeyResponse) -> Self { + RawPubKeyResponse { + pub_key: value.pub_key.map(Into::into), + error: value.error.map(Into::into), + } } } } - // Todo: write unit test diff --git a/tendermint/src/vote/sign_vote.rs b/tendermint/src/vote/sign_vote.rs index 7516e6041..22d688f9c 100644 --- a/tendermint/src/vote/sign_vote.rs +++ b/tendermint/src/vote/sign_vote.rs @@ -1,15 +1,7 @@ -use core::convert::{TryFrom, TryInto}; - use bytes::BufMut; -use tendermint_proto::{ - privval::{ - RemoteSignerError, SignVoteRequest as RawSignVoteRequest, - SignedVoteResponse as RawSignedVoteResponse, - }, - Error as ProtobufError, Protobuf, -}; +use tendermint_proto::Error as ProtobufError; -use crate::{chain, error::Error, prelude::*, Vote}; +use crate::{chain, prelude::*, privval::RemoteSignerError, Vote}; /// SignVoteRequest is a request to sign a vote #[derive(Clone, PartialEq, Eq, Debug)] @@ -20,29 +12,6 @@ pub struct SignVoteRequest { pub chain_id: chain::Id, } -impl Protobuf for SignVoteRequest {} - -impl TryFrom for SignVoteRequest { - type Error = Error; - - fn try_from(value: RawSignVoteRequest) -> Result { - let vote = value.vote.ok_or_else(Error::no_vote_found)?.try_into()?; - - let chain_id = value.chain_id.try_into()?; - - Ok(SignVoteRequest { vote, chain_id }) - } -} - -impl From for RawSignVoteRequest { - fn from(value: SignVoteRequest) -> Self { - RawSignVoteRequest { - vote: Some(value.vote.into()), - chain_id: value.chain_id.as_str().to_string(), - } - } -} - impl SignVoteRequest { /// Create signable bytes from Vote. pub fn to_signable_bytes(&self, sign_bytes: &mut B) -> Result @@ -68,24 +37,59 @@ pub struct SignedVoteResponse { pub error: Option, } -impl Protobuf for SignedVoteResponse {} +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +tendermint_pb_modules! { + use super::{SignVoteRequest, SignedVoteResponse}; + use crate::{Error, prelude::*}; + use pb::privval::{ + SignVoteRequest as RawSignVoteRequest, SignedVoteResponse as RawSignedVoteResponse, + }; + + impl Protobuf for SignVoteRequest {} + + impl TryFrom for SignVoteRequest { + type Error = Error; -impl TryFrom for SignedVoteResponse { - type Error = Error; + fn try_from(value: RawSignVoteRequest) -> Result { + let vote = value.vote.ok_or_else(Error::no_vote_found)?.try_into()?; - fn try_from(value: RawSignedVoteResponse) -> Result { - Ok(SignedVoteResponse { - vote: value.vote.map(TryFrom::try_from).transpose()?, - error: value.error, - }) + let chain_id = value.chain_id.try_into()?; + + Ok(SignVoteRequest { vote, chain_id }) + } } -} -impl From for RawSignedVoteResponse { - fn from(value: SignedVoteResponse) -> Self { - RawSignedVoteResponse { - vote: value.vote.map(Into::into), - error: value.error, + impl From for RawSignVoteRequest { + fn from(value: SignVoteRequest) -> Self { + RawSignVoteRequest { + vote: Some(value.vote.into()), + chain_id: value.chain_id.as_str().to_owned(), + } + } + } + + impl Protobuf for SignedVoteResponse {} + + impl TryFrom for SignedVoteResponse { + type Error = Error; + + fn try_from(value: RawSignedVoteResponse) -> Result { + Ok(SignedVoteResponse { + vote: value.vote.map(TryFrom::try_from).transpose()?, + error: value.error.map(TryFrom::try_from).transpose()?, + }) + } + } + + impl From for RawSignedVoteResponse { + fn from(value: SignedVoteResponse) -> Self { + RawSignedVoteResponse { + vote: value.vote.map(Into::into), + error: value.error.map(Into::into), + } } } } @@ -340,55 +344,57 @@ mod tests { } } - #[test] - fn test_deserialization() { - let encoded = vec![ - 10, 188, 1, 8, 1, 16, 185, 96, 24, 2, 34, 74, 10, 32, 222, 173, 190, 239, 222, 173, - 190, 239, 186, 251, 175, 186, 251, 175, 186, 250, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 18, 38, 8, 192, 132, 61, 18, 32, 0, 34, 68, 102, 136, 170, 204, 238, 17, - 51, 85, 119, 153, 187, 221, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 42, - 11, 8, 177, 211, 129, 210, 5, 16, 128, 157, 202, 111, 50, 20, 163, 178, 204, 221, 113, - 134, 241, 104, 95, 33, 242, 72, 42, 244, 251, 52, 70, 168, 75, 53, 56, 213, 187, 3, 66, - 64, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1, 18, 13, 116, 101, 115, 116, 95, 99, 104, 97, 105, 110, 95, 105, - 100, - ]; // Todo: Double-check the Go implementation, this was self-generated. - let dt = datetime!(2017-12-25 03:00:01.234 UTC); - let vote = Vote { - validator_address: AccountId::try_from(vec![ - 0xa3, 0xb2, 0xcc, 0xdd, 0x71, 0x86, 0xf1, 0x68, 0x5f, 0x21, 0xf2, 0x48, 0x2a, 0xf4, - 0xfb, 0x34, 0x46, 0xa8, 0x4b, 0x35, - ]) - .unwrap(), - validator_index: ValidatorIndex::try_from(56789).unwrap(), - height: Height::from(12345_u32), - round: Round::from(2_u16), - timestamp: Some(dt.try_into().unwrap()), - vote_type: Type::Prevote, - block_id: Some(BlockId { - hash: Hash::from_hex_upper(Algorithm::Sha256, "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFA") - .unwrap(), - part_set_header: Header::new( - 1_000_000, - Hash::from_hex_upper(Algorithm::Sha256, "0022446688AACCEE1133557799BBDDFF") - .unwrap(), - ) - .unwrap(), - }), - signature: Signature::new(vec![1; Ed25519Signature::BYTE_SIZE]).unwrap(), - }; - let want = SignVoteRequest { - vote, - chain_id: ChainId::from_str("test_chain_id").unwrap(), - }; - let got = SignVoteRequest::decode_vec(&encoded).unwrap(); - assert_eq!(got, want); - } - tendermint_pb_modules! { use super::*; + #[test] + fn test_deserialization() { + let encoded = vec![ + 10, 188, 1, 8, 1, 16, 185, 96, 24, 2, 34, 74, 10, 32, 222, 173, 190, 239, 222, 173, + 190, 239, 186, 251, 175, 186, 251, 175, 186, 250, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 18, 38, 8, 192, 132, 61, 18, 32, 0, 34, 68, 102, 136, 170, 204, 238, 17, + 51, 85, 119, 153, 187, 221, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 42, + 11, 8, 177, 211, 129, 210, 5, 16, 128, 157, 202, 111, 50, 20, 163, 178, 204, 221, 113, + 134, 241, 104, 95, 33, 242, 72, 42, 244, 251, 52, 70, 168, 75, 53, 56, 213, 187, 3, 66, + 64, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 18, 13, 116, 101, 115, 116, 95, 99, 104, 97, 105, 110, 95, 105, + 100, + ]; // Todo: Double-check the Go implementation, this was self-generated. + let dt = datetime!(2017-12-25 03:00:01.234 UTC); + let vote = Vote { + validator_address: AccountId::try_from(vec![ + 0xa3, 0xb2, 0xcc, 0xdd, 0x71, 0x86, 0xf1, 0x68, 0x5f, 0x21, 0xf2, 0x48, 0x2a, 0xf4, + 0xfb, 0x34, 0x46, 0xa8, 0x4b, 0x35, + ]) + .unwrap(), + validator_index: ValidatorIndex::try_from(56789).unwrap(), + height: Height::from(12345_u32), + round: Round::from(2_u16), + timestamp: Some(dt.try_into().unwrap()), + vote_type: Type::Prevote, + block_id: Some(BlockId { + hash: Hash::from_hex_upper(Algorithm::Sha256, "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFA") + .unwrap(), + part_set_header: Header::new( + 1_000_000, + Hash::from_hex_upper(Algorithm::Sha256, "0022446688AACCEE1133557799BBDDFF") + .unwrap(), + ) + .unwrap(), + }), + signature: Signature::new(vec![1; Ed25519Signature::BYTE_SIZE]).unwrap(), + }; + let want = SignVoteRequest { + vote, + chain_id: ChainId::from_str("test_chain_id").unwrap(), + }; + let got = >::decode_vec( + &encoded + ).unwrap(); + assert_eq!(got, want); + } + #[test] fn test_vote_rountrip_with_sig() { let dt = datetime!(2017-12-25 03:00:01.234 UTC); @@ -434,9 +440,11 @@ mod tests { chain_id: ChainId::from_str("test_chain_id").unwrap(), }; let mut got = vec![]; - let _have = svr.encode(&mut got); + let _have = Protobuf::::encode(&svr, &mut got); - let svr2 = SignVoteRequest::decode(got.as_ref()).unwrap(); + let svr2 = >::decode( + got.as_ref() + ).unwrap(); assert_eq!(svr, svr2); } } From 18f51e434cc8a293b00a80044973f49a0b5780dc Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 9 Nov 2022 21:02:11 +0200 Subject: [PATCH 19/77] Define more multi-protocol conversions Temporarily remove the import of crate::v0_37::* to the root of tendermint-proto. --- abci/src/application.rs | 2 +- abci/src/application/kvstore.rs | 2 +- abci/src/client.rs | 2 +- abci/src/codec.rs | 2 +- abci/src/error.rs | 2 +- abci/tests/echo_app.rs | 2 +- abci/tests/kvstore_app.rs | 2 +- proto/src/tendermint.rs | 1 - proto/tests/unit.rs | 6 +- tendermint/src/abci/response/info.rs | 2 +- tendermint/src/block.rs | 88 +++++---- tendermint/src/block/commit.rs | 65 +++--- tendermint/src/block/commit_sig.rs | 186 +++++++++--------- tendermint/src/block/header.rs | 4 +- tendermint/src/block/id.rs | 2 +- tendermint/src/block/meta.rs | 60 +++--- tendermint/src/block/parts.rs | 2 +- tendermint/src/block/signed_header.rs | 49 ++--- tendermint/src/evidence.rs | 6 +- tendermint/src/lib.rs | 1 + tendermint/src/merkle/proof.rs | 2 +- tendermint/src/proposal.rs | 179 +++++++++-------- tendermint/src/proposal/canonical_proposal.rs | 168 ++++++++-------- tendermint/src/proposal/sign_proposal.rs | 2 +- tendermint/src/proto_macros.rs | 2 + tendermint/src/public_key.rs | 97 ++++----- tendermint/src/public_key/pub_key_request.rs | 98 ++++----- tendermint/src/tx/proof.rs | 2 +- tendermint/src/validator.rs | 3 +- tendermint/src/vote.rs | 11 +- tendermint/src/vote/canonical_vote.rs | 168 ++++++++-------- tendermint/src/vote/sign_vote.rs | 130 ++++++------ 32 files changed, 702 insertions(+), 646 deletions(-) diff --git a/abci/src/application.rs b/abci/src/application.rs index bd8947864..2f4e8f503 100644 --- a/abci/src/application.rs +++ b/abci/src/application.rs @@ -5,7 +5,7 @@ pub mod echo; #[cfg(feature = "kvstore-app")] pub mod kvstore; -use tendermint_proto::abci::{ +use tendermint_proto::v0_37::abci::{ request::Value, response, Request, RequestApplySnapshotChunk, RequestBeginBlock, RequestCheckTx, RequestDeliverTx, RequestEcho, RequestEndBlock, RequestInfo, RequestInitChain, RequestLoadSnapshotChunk, RequestOfferSnapshot, RequestPrepareProposal, RequestProcessProposal, diff --git a/abci/src/application/kvstore.rs b/abci/src/application/kvstore.rs index 8336b71e1..641103714 100644 --- a/abci/src/application/kvstore.rs +++ b/abci/src/application/kvstore.rs @@ -6,7 +6,7 @@ use std::{ }; use bytes::BytesMut; -use tendermint_proto::abci::{ +use tendermint_proto::v0_37::abci::{ Event, EventAttribute, RequestCheckTx, RequestDeliverTx, RequestInfo, RequestQuery, ResponseCheckTx, ResponseCommit, ResponseDeliverTx, ResponseInfo, ResponseQuery, }; diff --git a/abci/src/client.rs b/abci/src/client.rs index a7a82be44..6fdb1de75 100644 --- a/abci/src/client.rs +++ b/abci/src/client.rs @@ -2,7 +2,7 @@ use std::net::{TcpStream, ToSocketAddrs}; -use tendermint_proto::abci::{ +use tendermint_proto::v0_37::abci::{ request, response, Request, RequestApplySnapshotChunk, RequestBeginBlock, RequestCheckTx, RequestCommit, RequestDeliverTx, RequestEcho, RequestEndBlock, RequestFlush, RequestInfo, RequestInitChain, RequestListSnapshots, RequestLoadSnapshotChunk, RequestOfferSnapshot, diff --git a/abci/src/codec.rs b/abci/src/codec.rs index ce85acd24..bd7796e1d 100644 --- a/abci/src/codec.rs +++ b/abci/src/codec.rs @@ -11,7 +11,7 @@ use std::{ use bytes::{Buf, BufMut, BytesMut}; use prost::Message; -use tendermint_proto::abci::{Request, Response}; +use tendermint_proto::v0_37::abci::{Request, Response}; use crate::error::Error; diff --git a/abci/src/error.rs b/abci/src/error.rs index dcdbb7e17..72b875d0e 100644 --- a/abci/src/error.rs +++ b/abci/src/error.rs @@ -1,7 +1,7 @@ //! tendermint-abci errors use flex_error::{define_error, DisplayError}; -use tendermint_proto::abci::response::Value; +use tendermint_proto::v0_37::abci::response::Value; define_error! { Error { diff --git a/abci/tests/echo_app.rs b/abci/tests/echo_app.rs index f0306099b..c2f07895b 100644 --- a/abci/tests/echo_app.rs +++ b/abci/tests/echo_app.rs @@ -3,7 +3,7 @@ #[cfg(all(feature = "client", feature = "echo-app"))] mod echo_app_integration { use tendermint_abci::{ClientBuilder, EchoApp, ServerBuilder}; - use tendermint_proto::abci::RequestEcho; + use tendermint_proto::v0_37::abci::RequestEcho; #[test] fn echo() { diff --git a/abci/tests/kvstore_app.rs b/abci/tests/kvstore_app.rs index 05c821483..998f167be 100644 --- a/abci/tests/kvstore_app.rs +++ b/abci/tests/kvstore_app.rs @@ -5,7 +5,7 @@ mod kvstore_app_integration { use std::thread; use tendermint_abci::{ClientBuilder, KeyValueStoreApp, ServerBuilder}; - use tendermint_proto::abci::{RequestDeliverTx, RequestEcho, RequestQuery}; + use tendermint_proto::v0_37::abci::{RequestDeliverTx, RequestEcho, RequestQuery}; #[test] fn happy_path() { diff --git a/proto/src/tendermint.rs b/proto/src/tendermint.rs index 4a8211a91..dfe07be1d 100644 --- a/proto/src/tendermint.rs +++ b/proto/src/tendermint.rs @@ -1,3 +1,2 @@ pub mod v0_34; pub mod v0_37; -pub use v0_37::*; diff --git a/proto/tests/unit.rs b/proto/tests/unit.rs index 1aa161c8e..d0bc59d4d 100644 --- a/proto/tests/unit.rs +++ b/proto/tests/unit.rs @@ -1,9 +1,7 @@ use core::convert::TryFrom; -use tendermint_proto::{ - types::{BlockId as RawBlockId, PartSetHeader as RawPartSetHeader}, - Protobuf, -}; +use tendermint_proto::v0_37::types::{BlockId as RawBlockId, PartSetHeader as RawPartSetHeader}; +use tendermint_proto::Protobuf; impl Protobuf for BlockId {} diff --git a/tendermint/src/abci/response/info.rs b/tendermint/src/abci/response/info.rs index 703ac4c8a..af2b98cea 100644 --- a/tendermint/src/abci/response/info.rs +++ b/tendermint/src/abci/response/info.rs @@ -1,5 +1,5 @@ use crate::{block, prelude::*, AppHash}; -use tendermint_proto::abci as pb; +use tendermint_proto::v0_37::abci as pb; use serde::{Deserialize, Serialize}; diff --git a/tendermint/src/block.rs b/tendermint/src/block.rs index 14c27a603..f0471c598 100644 --- a/tendermint/src/block.rs +++ b/tendermint/src/block.rs @@ -12,7 +12,7 @@ pub mod signed_header; mod size; use serde::{Deserialize, Serialize}; -use tendermint_proto::{types::Block as RawBlock, Protobuf}; +use tendermint_proto::v0_37::types::Block as RawBlock; pub use self::{ commit::*, @@ -48,49 +48,55 @@ pub struct Block { pub last_commit: Option, } -impl Protobuf for Block {} - -impl TryFrom for Block { - type Error = Error; - - fn try_from(value: RawBlock) -> Result { - let header: Header = value.header.ok_or_else(Error::missing_header)?.try_into()?; - // if last_commit is Commit::Default, it is considered nil by Go. - let last_commit = value - .last_commit - .map(TryInto::try_into) - .transpose()? - .filter(|c| c != &Commit::default()); - if last_commit.is_none() && header.height.value() != 1 { - return Err(Error::invalid_block( - "last_commit is empty on non-first block".to_string(), - )); +tendermint_pb_modules! { + use super::{Block, Header, Commit}; + use crate::{Error, prelude::*}; + use pb::types::Block as RawBlock; + + impl Protobuf for Block {} + + impl TryFrom for Block { + type Error = Error; + + fn try_from(value: RawBlock) -> Result { + let header: Header = value.header.ok_or_else(Error::missing_header)?.try_into()?; + // if last_commit is Commit::Default, it is considered nil by Go. + let last_commit = value + .last_commit + .map(TryInto::try_into) + .transpose()? + .filter(|c| c != &Commit::default()); + if last_commit.is_none() && header.height.value() != 1 { + return Err(Error::invalid_block( + "last_commit is empty on non-first block".to_string(), + )); + } + // Todo: Figure out requirements. + // if last_commit.is_some() && header.height.value() == 1 { + // return Err(Kind::InvalidFirstBlock.context("last_commit is not null on first + // height").into()); + //} + Ok(Block { + header, + data: value.data.ok_or_else(Error::missing_data)?.txs, + evidence: value + .evidence + .ok_or_else(Error::missing_evidence)? + .try_into()?, + last_commit, + }) } - // Todo: Figure out requirements. - // if last_commit.is_some() && header.height.value() == 1 { - // return Err(Kind::InvalidFirstBlock.context("last_commit is not null on first - // height").into()); - //} - Ok(Block { - header, - data: value.data.ok_or_else(Error::missing_data)?.txs, - evidence: value - .evidence - .ok_or_else(Error::missing_evidence)? - .try_into()?, - last_commit, - }) } -} -impl From for RawBlock { - fn from(value: Block) -> Self { - use tendermint_proto::types::Data as RawData; - RawBlock { - header: Some(value.header.into()), - data: Some(RawData { txs: value.data }), - evidence: Some(value.evidence.into()), - last_commit: value.last_commit.map(Into::into), + impl From for RawBlock { + fn from(value: Block) -> Self { + use pb::types::Data as RawData; + RawBlock { + header: Some(value.header.into()), + data: Some(RawData { txs: value.data }), + evidence: Some(value.evidence.into()), + last_commit: value.last_commit.map(Into::into), + } } } } diff --git a/tendermint/src/block/commit.rs b/tendermint/src/block/commit.rs index 2672a9efd..2a14e5bc0 100644 --- a/tendermint/src/block/commit.rs +++ b/tendermint/src/block/commit.rs @@ -1,13 +1,10 @@ //! Commits to a Tendermint blockchain -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; -use tendermint_proto::types::Commit as RawCommit; +use tendermint_proto::v0_37::types::Commit as RawCommit; use crate::{ block::{commit_sig::CommitSig, Height, Id, Round}, - error::Error, prelude::*, }; @@ -32,34 +29,44 @@ pub struct Commit { pub signatures: Vec, } -impl TryFrom for Commit { - type Error = Error; +tendermint_pb_modules! { + use super::Commit; + use crate::{ + block::commit_sig::CommitSig, + error::Error, + prelude::*, + }; + use pb::types::Commit as RawCommit; + + impl TryFrom for Commit { + type Error = Error; - fn try_from(value: RawCommit) -> Result { - let signatures: Result, Error> = value - .signatures - .into_iter() - .map(TryFrom::try_from) - .collect(); - Ok(Self { - height: value.height.try_into()?, - round: value.round.try_into()?, - block_id: value - .block_id - .ok_or_else(|| Error::invalid_block("missing block id".to_string()))? - .try_into()?, // gogoproto.nullable = false - signatures: signatures?, - }) + fn try_from(value: RawCommit) -> Result { + let signatures: Result, Error> = value + .signatures + .into_iter() + .map(TryFrom::try_from) + .collect(); + Ok(Self { + height: value.height.try_into()?, + round: value.round.try_into()?, + block_id: value + .block_id + .ok_or_else(|| Error::invalid_block("missing block id".to_string()))? + .try_into()?, // gogoproto.nullable = false + signatures: signatures?, + }) + } } -} -impl From for RawCommit { - fn from(value: Commit) -> Self { - RawCommit { - height: value.height.into(), - round: value.round.into(), - block_id: Some(value.block_id.into()), - signatures: value.signatures.into_iter().map(Into::into).collect(), + impl From for RawCommit { + fn from(value: Commit) -> Self { + RawCommit { + height: value.height.into(), + round: value.round.into(), + block_id: Some(value.block_id.into()), + signatures: value.signatures.into_iter().map(Into::into).collect(), + } } } } diff --git a/tendermint/src/block/commit_sig.rs b/tendermint/src/block/commit_sig.rs index a462366db..39c71cc1c 100644 --- a/tendermint/src/block/commit_sig.rs +++ b/tendermint/src/block/commit_sig.rs @@ -1,11 +1,6 @@ //! CommitSig within Commit -use core::convert::{TryFrom, TryInto}; - -use num_traits::ToPrimitive; -use tendermint_proto::types::{BlockIdFlag, CommitSig as RawCommitSig}; - -use crate::{account, error::Error, prelude::*, Signature, Time}; +use crate::{account, prelude::*, Signature, Time}; /// CommitSig represents a signature of a validator. /// It's a part of the Commit and can be used to reconstruct the vote set given the validator set. @@ -63,105 +58,112 @@ impl CommitSig { } } -// Todo: https://github.com/informalsystems/tendermint-rs/issues/259 - CommitSig Timestamp can be zero time -// Todo: https://github.com/informalsystems/tendermint-rs/issues/260 - CommitSig validator address missing in Absent vote -impl TryFrom for CommitSig { - type Error = Error; - - fn try_from(value: RawCommitSig) -> Result { - if value.block_id_flag == BlockIdFlag::Absent.to_i32().unwrap() { - if value.timestamp.is_some() { - let timestamp = value.timestamp.unwrap(); - // 0001-01-01T00:00:00.000Z translates to EPOCH-62135596800 seconds - if timestamp.nanos != 0 || timestamp.seconds != -62135596800 { - return Err(Error::invalid_timestamp( - "absent commitsig has non-zero timestamp".to_string(), +tendermint_pb_modules! { + use super::CommitSig; + use crate::{error::Error, prelude::*, Signature}; + use num_traits::ToPrimitive; + use pb::types::{BlockIdFlag, CommitSig as RawCommitSig}; + + // Todo: https://github.com/informalsystems/tendermint-rs/issues/259 - CommitSig Timestamp can be zero time + // Todo: https://github.com/informalsystems/tendermint-rs/issues/260 - CommitSig validator address missing in Absent vote + impl TryFrom for CommitSig { + type Error = Error; + + fn try_from(value: RawCommitSig) -> Result { + if value.block_id_flag == BlockIdFlag::Absent.to_i32().unwrap() { + if value.timestamp.is_some() { + let timestamp = value.timestamp.unwrap(); + // 0001-01-01T00:00:00.000Z translates to EPOCH-62135596800 seconds + if timestamp.nanos != 0 || timestamp.seconds != -62135596800 { + return Err(Error::invalid_timestamp( + "absent commitsig has non-zero timestamp".to_string(), + )); + } + } + + if !value.signature.is_empty() { + return Err(Error::invalid_signature( + "expected empty signature for absent commitsig".to_string(), )); } - } - if !value.signature.is_empty() { - return Err(Error::invalid_signature( - "expected empty signature for absent commitsig".to_string(), - )); + return Ok(CommitSig::BlockIdFlagAbsent); } - return Ok(CommitSig::BlockIdFlagAbsent); - } - - if value.block_id_flag == BlockIdFlag::Commit.to_i32().unwrap() { - if value.signature.is_empty() { - return Err(Error::invalid_signature( - "expected non-empty signature for regular commitsig".to_string(), - )); - } + if value.block_id_flag == BlockIdFlag::Commit.to_i32().unwrap() { + if value.signature.is_empty() { + return Err(Error::invalid_signature( + "expected non-empty signature for regular commitsig".to_string(), + )); + } - if value.validator_address.is_empty() { - return Err(Error::invalid_validator_address()); - } + if value.validator_address.is_empty() { + return Err(Error::invalid_validator_address()); + } - let timestamp = value - .timestamp - .ok_or_else(Error::missing_timestamp)? - .try_into()?; + let timestamp = value + .timestamp + .ok_or_else(Error::missing_timestamp)? + .try_into()?; - return Ok(CommitSig::BlockIdFlagCommit { - validator_address: value.validator_address.try_into()?, - timestamp, - signature: Signature::new(value.signature)?, - }); - } - if value.block_id_flag == BlockIdFlag::Nil.to_i32().unwrap() { - if value.signature.is_empty() { - return Err(Error::invalid_signature( - "nil commitsig has no signature".to_string(), - )); + return Ok(CommitSig::BlockIdFlagCommit { + validator_address: value.validator_address.try_into()?, + timestamp, + signature: Signature::new(value.signature)?, + }); } - if value.validator_address.is_empty() { - return Err(Error::invalid_validator_address()); + if value.block_id_flag == BlockIdFlag::Nil.to_i32().unwrap() { + if value.signature.is_empty() { + return Err(Error::invalid_signature( + "nil commitsig has no signature".to_string(), + )); + } + if value.validator_address.is_empty() { + return Err(Error::invalid_validator_address()); + } + return Ok(CommitSig::BlockIdFlagNil { + validator_address: value.validator_address.try_into()?, + timestamp: value + .timestamp + .ok_or_else(Error::missing_timestamp)? + .try_into()?, + signature: Signature::new(value.signature)?, + }); } - return Ok(CommitSig::BlockIdFlagNil { - validator_address: value.validator_address.try_into()?, - timestamp: value - .timestamp - .ok_or_else(Error::missing_timestamp)? - .try_into()?, - signature: Signature::new(value.signature)?, - }); + Err(Error::block_id_flag()) } - Err(Error::block_id_flag()) } -} -impl From for RawCommitSig { - fn from(commit: CommitSig) -> RawCommitSig { - match commit { - CommitSig::BlockIdFlagAbsent => RawCommitSig { - block_id_flag: BlockIdFlag::Absent.to_i32().unwrap(), - validator_address: Vec::new(), - timestamp: None, - signature: Vec::new(), - }, - CommitSig::BlockIdFlagNil { - validator_address, - timestamp, - signature, - } => RawCommitSig { - block_id_flag: BlockIdFlag::Nil.to_i32().unwrap(), - validator_address: validator_address.into(), - timestamp: Some(timestamp.into()), - signature: signature.map(|s| s.to_bytes()).unwrap_or_default(), - }, - CommitSig::BlockIdFlagCommit { - validator_address, - timestamp, - signature, - } => RawCommitSig { - block_id_flag: BlockIdFlag::Commit.to_i32().unwrap(), - validator_address: validator_address.into(), - timestamp: Some(timestamp.into()), - signature: signature.map(|s| s.to_bytes()).unwrap_or_default(), - }, + impl From for RawCommitSig { + fn from(commit: CommitSig) -> RawCommitSig { + match commit { + CommitSig::BlockIdFlagAbsent => RawCommitSig { + block_id_flag: BlockIdFlag::Absent.to_i32().unwrap(), + validator_address: Vec::new(), + timestamp: None, + signature: Vec::new(), + }, + CommitSig::BlockIdFlagNil { + validator_address, + timestamp, + signature, + } => RawCommitSig { + block_id_flag: BlockIdFlag::Nil.to_i32().unwrap(), + validator_address: validator_address.into(), + timestamp: Some(timestamp.into()), + signature: signature.map(|s| s.to_bytes()).unwrap_or_default(), + }, + CommitSig::BlockIdFlagCommit { + validator_address, + timestamp, + signature, + } => RawCommitSig { + block_id_flag: BlockIdFlag::Commit.to_i32().unwrap(), + validator_address: validator_address.into(), + timestamp: Some(timestamp.into()), + signature: signature.map(|s| s.to_bytes()).unwrap_or_default(), + }, + } } } } diff --git a/tendermint/src/block/header.rs b/tendermint/src/block/header.rs index cc99443b5..f5e3440df 100644 --- a/tendermint/src/block/header.rs +++ b/tendermint/src/block/header.rs @@ -1,11 +1,11 @@ //! Block headers use serde::{Deserialize, Serialize}; -use tendermint_proto::{ +use tendermint_proto::v0_37::{ types::{BlockId as RawBlockId, Header as RawHeader}, version::Consensus as RawConsensusVersion, - Protobuf, }; +use tendermint_proto::Protobuf; use crate::{ account, block, chain, merkle::simple_hash_from_byte_vectors, prelude::*, AppHash, Hash, Time, diff --git a/tendermint/src/block/id.rs b/tendermint/src/block/id.rs index fc29bb506..c88f7a1a4 100644 --- a/tendermint/src/block/id.rs +++ b/tendermint/src/block/id.rs @@ -4,7 +4,7 @@ use core::{ }; use serde::{Deserialize, Serialize}; -use tendermint_proto::types::BlockId as RawBlockId; +use tendermint_proto::v0_37::types::BlockId as RawBlockId; use crate::{ block::parts::Header as PartSetHeader, diff --git a/tendermint/src/block/meta.rs b/tendermint/src/block/meta.rs index 71c72f2da..4dbed2cdb 100644 --- a/tendermint/src/block/meta.rs +++ b/tendermint/src/block/meta.rs @@ -1,12 +1,10 @@ //! Block metadata -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; -use tendermint_proto::types::BlockMeta as RawMeta; +use tendermint_proto::v0_37::types::BlockMeta as RawMeta; use super::{Header, Id}; -use crate::{error::Error, prelude::*}; +use crate::prelude::*; /// Block metadata - Todo: implement constructor and getters #[derive(Serialize, Deserialize, Clone, Debug)] @@ -25,32 +23,38 @@ pub struct Meta { pub num_txs: i64, } -impl TryFrom for Meta { - type Error = Error; - - fn try_from(value: RawMeta) -> Result { - Ok(Meta { - block_id: value - .block_id - .ok_or_else(|| Error::invalid_block("no block_id".to_string()))? - .try_into()?, - block_size: value.block_size, - header: value - .header - .ok_or_else(|| Error::invalid_block("no header".to_string()))? - .try_into()?, - num_txs: value.num_txs, - }) +tendermint_pb_modules! { + use super::Meta; + use crate::{error::Error, prelude::*}; + use pb::types::BlockMeta as RawMeta; + + impl TryFrom for Meta { + type Error = Error; + + fn try_from(value: RawMeta) -> Result { + Ok(Meta { + block_id: value + .block_id + .ok_or_else(|| Error::invalid_block("no block_id".to_string()))? + .try_into()?, + block_size: value.block_size, + header: value + .header + .ok_or_else(|| Error::invalid_block("no header".to_string()))? + .try_into()?, + num_txs: value.num_txs, + }) + } } -} -impl From for RawMeta { - fn from(value: Meta) -> Self { - RawMeta { - block_id: Some(value.block_id.into()), - block_size: value.block_size, - header: Some(value.header.into()), - num_txs: value.num_txs, + impl From for RawMeta { + fn from(value: Meta) -> Self { + RawMeta { + block_id: Some(value.block_id.into()), + block_size: value.block_size, + header: Some(value.header.into()), + num_txs: value.num_txs, + } } } } diff --git a/tendermint/src/block/parts.rs b/tendermint/src/block/parts.rs index 19d6fdf2d..7635034f4 100644 --- a/tendermint/src/block/parts.rs +++ b/tendermint/src/block/parts.rs @@ -1,7 +1,7 @@ //! Block parts use serde::{Deserialize, Serialize}; -use tendermint_proto::types::PartSetHeader as RawPartSetHeader; +use tendermint_proto::v0_37::types::PartSetHeader as RawPartSetHeader; use crate::{error::Error, prelude::*, Hash}; diff --git a/tendermint/src/block/signed_header.rs b/tendermint/src/block/signed_header.rs index de2fc3ec2..4cd852920 100644 --- a/tendermint/src/block/signed_header.rs +++ b/tendermint/src/block/signed_header.rs @@ -1,10 +1,9 @@ //! SignedHeader contains commit and and block header. //! It is what the rpc endpoint /commit returns and hence can be used by a //! light client. -use core::convert::{TryFrom, TryInto}; use serde::{Deserialize, Serialize}; -use tendermint_proto::{types::SignedHeader as RawSignedHeader, Protobuf}; +use tendermint_proto::v0_37::types::SignedHeader as RawSignedHeader; use crate::{block, Error}; @@ -19,32 +18,38 @@ pub struct SignedHeader { pub commit: block::Commit, } -impl TryFrom for SignedHeader { - type Error = Error; +tendermint_pb_modules! { + use super::SignedHeader; + use crate::Error; + use pb::types::SignedHeader as RawSignedHeader; - fn try_from(value: RawSignedHeader) -> Result { - let header = value - .header - .ok_or_else(Error::invalid_signed_header)? - .try_into()?; - let commit = value - .commit - .ok_or_else(Error::invalid_signed_header)? - .try_into()?; - Self::new(header, commit) // Additional checks + impl TryFrom for SignedHeader { + type Error = Error; + + fn try_from(value: RawSignedHeader) -> Result { + let header = value + .header + .ok_or_else(Error::invalid_signed_header)? + .try_into()?; + let commit = value + .commit + .ok_or_else(Error::invalid_signed_header)? + .try_into()?; + Self::new(header, commit) // Additional checks + } } -} -impl From for RawSignedHeader { - fn from(value: SignedHeader) -> Self { - RawSignedHeader { - header: Some(value.header.into()), - commit: Some(value.commit.into()), + impl From for RawSignedHeader { + fn from(value: SignedHeader) -> Self { + RawSignedHeader { + header: Some(value.header.into()), + commit: Some(value.commit.into()), + } } } -} -impl Protobuf for SignedHeader {} + impl Protobuf for SignedHeader {} +} impl SignedHeader { /// Constructor. diff --git a/tendermint/src/evidence.rs b/tendermint/src/evidence.rs index 39f98f559..af735007a 100644 --- a/tendermint/src/evidence.rs +++ b/tendermint/src/evidence.rs @@ -6,9 +6,9 @@ use core::{ }; use serde::{Deserialize, Serialize}; -use tendermint_proto::{ - google::protobuf::Duration as RawDuration, types::Evidence as RawEvidence, Protobuf, -}; +use tendermint_proto::google::protobuf::Duration as RawDuration; +use tendermint_proto::v0_37::types::Evidence as RawEvidence; +use tendermint_proto::Protobuf; use crate::{error::Error, prelude::*, serializers, vote::Power, Time, Vote}; diff --git a/tendermint/src/lib.rs b/tendermint/src/lib.rs index a6abfddd2..434e3157f 100644 --- a/tendermint/src/lib.rs +++ b/tendermint/src/lib.rs @@ -43,6 +43,7 @@ mod moniker; pub mod node; mod prelude; pub mod private_key; +pub mod privval; pub mod proposal; pub mod public_key; pub mod serializers; diff --git a/tendermint/src/merkle/proof.rs b/tendermint/src/merkle/proof.rs index 228708abc..903c1471c 100644 --- a/tendermint/src/merkle/proof.rs +++ b/tendermint/src/merkle/proof.rs @@ -1,6 +1,7 @@ //! Merkle proofs use serde::{Deserialize, Serialize}; +use tendermint_proto::v0_37::crypto::Proof as RawProof; use crate::{prelude::*, serializers, Hash}; @@ -93,7 +94,6 @@ tendermint_pb_modules! { } impl Protobuf for ProofOp {} - impl Protobuf for ProofOp {} impl TryFrom for ProofOp { type Error = Error; diff --git a/tendermint/src/proposal.rs b/tendermint/src/proposal.rs index a5334529b..10c832b5a 100644 --- a/tendermint/src/proposal.rs +++ b/tendermint/src/proposal.rs @@ -4,19 +4,17 @@ mod canonical_proposal; mod msg_type; mod sign_proposal; -use core::convert::{TryFrom, TryInto}; - use bytes::BufMut; pub use msg_type::Type; pub use sign_proposal::{SignProposalRequest, SignedProposalResponse}; -use tendermint_proto::{types::Proposal as RawProposal, Error as ProtobufError, Protobuf}; +use tendermint_proto::v0_37::types::CanonicalProposal as RawCanonicalProposal; +use tendermint_proto::{Error as ProtobufError, Protobuf}; pub use self::canonical_proposal::CanonicalProposal; use crate::{ block::{Height, Id as BlockId, Round}, chain::Id as ChainId, consensus::State, - error::Error, prelude::*, Signature, Time, }; @@ -40,41 +38,47 @@ pub struct Proposal { pub signature: Option, } -impl Protobuf for Proposal {} - -impl TryFrom for Proposal { - type Error = Error; - - fn try_from(value: RawProposal) -> Result { - if value.pol_round < -1 { - return Err(Error::negative_pol_round()); +tendermint_pb_modules! { + use super::Proposal; + use crate::{Signature, Error, block::Round}; + use pb::types::Proposal as RawProposal; + + impl Protobuf for Proposal {} + + impl TryFrom for Proposal { + type Error = Error; + + fn try_from(value: RawProposal) -> Result { + if value.pol_round < -1 { + return Err(Error::negative_pol_round()); + } + let pol_round = match value.pol_round { + -1 => None, + n => Some(Round::try_from(n)?), + }; + Ok(Proposal { + msg_type: value.r#type.try_into()?, + height: value.height.try_into()?, + round: value.round.try_into()?, + pol_round, + block_id: value.block_id.map(TryInto::try_into).transpose()?, + timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, + signature: Signature::new(value.signature)?, + }) } - let pol_round = match value.pol_round { - -1 => None, - n => Some(Round::try_from(n)?), - }; - Ok(Proposal { - msg_type: value.r#type.try_into()?, - height: value.height.try_into()?, - round: value.round.try_into()?, - pol_round, - block_id: value.block_id.map(TryInto::try_into).transpose()?, - timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, - signature: Signature::new(value.signature)?, - }) } -} -impl From for RawProposal { - fn from(value: Proposal) -> Self { - RawProposal { - r#type: value.msg_type.into(), - height: value.height.into(), - round: value.round.into(), - pol_round: value.pol_round.map_or(-1, Into::into), - block_id: value.block_id.map(Into::into), - timestamp: value.timestamp.map(Into::into), - signature: value.signature.map(|s| s.to_bytes()).unwrap_or_default(), + impl From for RawProposal { + fn from(value: Proposal) -> Self { + RawProposal { + r#type: value.msg_type.into(), + height: value.height.into(), + round: value.round.into(), + pol_round: value.pol_round.map_or(-1, Into::into), + block_id: value.block_id.map(Into::into), + timestamp: value.timestamp.map(Into::into), + signature: value.signature.map(|s| s.to_bytes()).unwrap_or_default(), + } } } } @@ -89,13 +93,15 @@ impl Proposal { where B: BufMut, { - CanonicalProposal::new(self.clone(), chain_id).encode_length_delimited(sign_bytes)?; + let canonical = CanonicalProposal::new(self.clone(), chain_id); + Protobuf::::encode_length_delimited(&canonical, sign_bytes)?; Ok(true) } /// Create signable vector from Proposal. pub fn to_signable_vec(&self, chain_id: ChainId) -> Result, ProtobufError> { - CanonicalProposal::new(self.clone(), chain_id).encode_length_delimited_vec() + let canonical = CanonicalProposal::new(self.clone(), chain_id); + Protobuf::::encode_length_delimited_vec(&canonical) } /// Consensus state from this proposal - This doesn't seem to be used anywhere. @@ -115,9 +121,8 @@ impl Proposal { #[cfg(test)] mod tests { - use core::{convert::TryInto, str::FromStr}; + use core::str::FromStr; - use tendermint_proto::Protobuf; use time::macros::datetime; use crate::{ @@ -294,53 +299,57 @@ mod tests { assert_eq!(got, want) } - #[test] - fn test_deserialization() { - let dt = datetime!(2018-02-11 07:09:22.765 UTC); - let proposal = Proposal { - msg_type: Type::Proposal, - height: Height::from(12345_u32), - round: Round::from(23456_u16), - timestamp: Some(dt.try_into().unwrap()), - - pol_round: None, - block_id: Some(BlockId { - hash: Hash::from_hex_upper( - Algorithm::Sha256, - "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFADEADBEEFDEADBEEFBAFBAFBAFBAFBAFA", - ) - .unwrap(), - part_set_header: Header::new( - 65535, - Hash::from_hex_upper( + tendermint_pb_modules! { + use super::*; + + #[test] + fn test_deserialization() { + let dt = datetime!(2018-02-11 07:09:22.765 UTC); + let proposal = Proposal { + msg_type: Type::Proposal, + height: Height::from(12345_u32), + round: Round::from(23456_u16), + timestamp: Some(dt.try_into().unwrap()), + + pol_round: None, + block_id: Some(BlockId { + hash: Hash::from_hex_upper( Algorithm::Sha256, - "0022446688AACCEE1133557799BBDDFF0022446688AACCEE1133557799BBDDFF", + "DEADBEEFDEADBEEFBAFBAFBAFBAFBAFADEADBEEFDEADBEEFBAFBAFBAFBAFBAFA", ) .unwrap(), - ) - .unwrap(), - }), - signature: Some(dummy_signature()), - }; - let want = SignProposalRequest { - proposal, - chain_id: ChainId::from_str("test_chain_id").unwrap(), - }; - - let data = vec![ - 10, 176, 1, 8, 32, 16, 185, 96, 24, 160, 183, 1, 32, 255, 255, 255, 255, 255, 255, 255, - 255, 255, 1, 42, 74, 10, 32, 222, 173, 190, 239, 222, 173, 190, 239, 186, 251, 175, - 186, 251, 175, 186, 250, 222, 173, 190, 239, 222, 173, 190, 239, 186, 251, 175, 186, - 251, 175, 186, 250, 18, 38, 8, 255, 255, 3, 18, 32, 0, 34, 68, 102, 136, 170, 204, 238, - 17, 51, 85, 119, 153, 187, 221, 255, 0, 34, 68, 102, 136, 170, 204, 238, 17, 51, 85, - 119, 153, 187, 221, 255, 50, 12, 8, 162, 216, 255, 211, 5, 16, 192, 242, 227, 236, 2, - 58, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 13, 116, 101, 115, 116, 95, 99, 104, 97, 105, 110, 95, - 105, 100, - ]; - - let have = SignProposalRequest::decode_vec(&data).unwrap(); - assert_eq!(have, want); + part_set_header: Header::new( + 65535, + Hash::from_hex_upper( + Algorithm::Sha256, + "0022446688AACCEE1133557799BBDDFF0022446688AACCEE1133557799BBDDFF", + ) + .unwrap(), + ) + .unwrap(), + }), + signature: Some(dummy_signature()), + }; + let want = SignProposalRequest { + proposal, + chain_id: ChainId::from_str("test_chain_id").unwrap(), + }; + + let data = vec![ + 10, 176, 1, 8, 32, 16, 185, 96, 24, 160, 183, 1, 32, 255, 255, 255, 255, 255, 255, 255, + 255, 255, 1, 42, 74, 10, 32, 222, 173, 190, 239, 222, 173, 190, 239, 186, 251, 175, + 186, 251, 175, 186, 250, 222, 173, 190, 239, 222, 173, 190, 239, 186, 251, 175, 186, + 251, 175, 186, 250, 18, 38, 8, 255, 255, 3, 18, 32, 0, 34, 68, 102, 136, 170, 204, 238, + 17, 51, 85, 119, 153, 187, 221, 255, 0, 34, 68, 102, 136, 170, 204, 238, 17, 51, 85, + 119, 153, 187, 221, 255, 50, 12, 8, 162, 216, 255, 211, 5, 16, 192, 242, 227, 236, 2, + 58, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 13, 116, 101, 115, 116, 95, 99, 104, 97, 105, 110, 95, + 105, 100, + ]; + + let have = >::decode_vec(&data).unwrap(); + assert_eq!(have, want); + } } } diff --git a/tendermint/src/proposal/canonical_proposal.rs b/tendermint/src/proposal/canonical_proposal.rs index d8346cadf..7113e9ca6 100644 --- a/tendermint/src/proposal/canonical_proposal.rs +++ b/tendermint/src/proposal/canonical_proposal.rs @@ -1,14 +1,9 @@ //! CanonicalProposal -use core::convert::{TryFrom, TryInto}; - -use tendermint_proto::{types::CanonicalProposal as RawCanonicalProposal, Protobuf}; - use super::Type; use crate::{ block::{Height, Id as BlockId, Round}, chain::Id as ChainId, - error::Error, prelude::*, Time, }; @@ -32,53 +27,64 @@ pub struct CanonicalProposal { pub chain_id: ChainId, } -impl Protobuf for CanonicalProposal {} +tendermint_pb_modules! { + use crate::{ + block::{Id as BlockId, Round}, + chain::Id as ChainId, + error::Error, + prelude::*, + }; + use super::CanonicalProposal; + use pb::types::CanonicalProposal as RawCanonicalProposal; -impl TryFrom for CanonicalProposal { - type Error = Error; + impl Protobuf for CanonicalProposal {} - fn try_from(value: RawCanonicalProposal) -> Result { - if value.pol_round < -1 { - return Err(Error::negative_pol_round()); + impl TryFrom for CanonicalProposal { + type Error = Error; + + fn try_from(value: RawCanonicalProposal) -> Result { + if value.pol_round < -1 { + return Err(Error::negative_pol_round()); + } + let round = Round::try_from(i32::try_from(value.round).map_err(Error::integer_overflow)?)?; + let pol_round = match value.pol_round { + -1 => None, + n => Some(Round::try_from( + i32::try_from(n).map_err(Error::integer_overflow)?, + )?), + }; + // If the Hash is empty in BlockId, the BlockId should be empty. + // See: https://github.com/informalsystems/tendermint-rs/issues/663 + let block_id = value.block_id.filter(|i| !i.hash.is_empty()); + Ok(CanonicalProposal { + msg_type: value.r#type.try_into()?, + height: value.height.try_into()?, + round, + pol_round, + block_id: block_id.map(TryInto::try_into).transpose()?, + timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, + chain_id: ChainId::try_from(value.chain_id).unwrap(), + }) } - let round = Round::try_from(i32::try_from(value.round).map_err(Error::integer_overflow)?)?; - let pol_round = match value.pol_round { - -1 => None, - n => Some(Round::try_from( - i32::try_from(n).map_err(Error::integer_overflow)?, - )?), - }; - // If the Hash is empty in BlockId, the BlockId should be empty. - // See: https://github.com/informalsystems/tendermint-rs/issues/663 - let block_id = value.block_id.filter(|i| !i.hash.is_empty()); - Ok(CanonicalProposal { - msg_type: value.r#type.try_into()?, - height: value.height.try_into()?, - round, - pol_round, - block_id: block_id.map(TryInto::try_into).transpose()?, - timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, - chain_id: ChainId::try_from(value.chain_id).unwrap(), - }) } -} -impl From for RawCanonicalProposal { - fn from(value: CanonicalProposal) -> Self { - // If the Hash is empty in BlockId, the BlockId should be empty. - // See: https://github.com/informalsystems/tendermint-rs/issues/663 - let block_id = value.block_id.filter(|i| i != &BlockId::default()); - RawCanonicalProposal { - r#type: value.msg_type.into(), - height: value.height.into(), - round: i32::from(value.round) as i64, - pol_round: match value.pol_round { - None => -1, - Some(p) => i32::from(p) as i64, - }, - block_id: block_id.map(Into::into), - timestamp: value.timestamp.map(Into::into), - chain_id: value.chain_id.as_str().to_string(), + impl From for RawCanonicalProposal { + fn from(value: CanonicalProposal) -> Self { + // If the Hash is empty in BlockId, the BlockId should be empty. + // See: https://github.com/informalsystems/tendermint-rs/issues/663 + let block_id = value.block_id.filter(|i| i != &BlockId::default()); + RawCanonicalProposal { + r#type: value.msg_type.into(), + height: value.height.into(), + round: i32::from(value.round) as i64, + pol_round: match value.pol_round { + None => -1, + Some(p) => i32::from(p) as i64, + }, + block_id: block_id.map(Into::into), + timestamp: value.timestamp.map(Into::into), + chain_id: value.chain_id.as_str().to_string(), + } } } } @@ -100,42 +106,42 @@ impl CanonicalProposal { #[cfg(test)] mod tests { - use core::convert::TryFrom; - - use tendermint_proto::types::{ - CanonicalBlockId as RawCanonicalBlockId, - CanonicalPartSetHeader as RawCanonicalPartSetHeader, - CanonicalProposal as RawCanonicalProposal, - }; + tendermint_pb_modules! { + use pb::types::{ + CanonicalBlockId as RawCanonicalBlockId, + CanonicalPartSetHeader as RawCanonicalPartSetHeader, + CanonicalProposal as RawCanonicalProposal, + }; - use crate::{ - prelude::*, - proposal::{canonical_proposal::CanonicalProposal, Type}, - }; + use crate::{ + prelude::*, + proposal::{canonical_proposal::CanonicalProposal, Type}, + }; - #[test] - fn canonical_proposal_domain_checks() { - // RawCanonicalProposal with edge cases to test domain knowledge - // pol_round = -1 should decode to None - // block_id with empty hash should decode to None - let proto_cp = RawCanonicalProposal { - r#type: 32, - height: 2, - round: 4, - pol_round: -1, - block_id: Some(RawCanonicalBlockId { - hash: vec![], - part_set_header: Some(RawCanonicalPartSetHeader { - total: 1, - hash: vec![1], + #[test] + fn canonical_proposal_domain_checks() { + // RawCanonicalProposal with edge cases to test domain knowledge + // pol_round = -1 should decode to None + // block_id with empty hash should decode to None + let proto_cp = RawCanonicalProposal { + r#type: 32, + height: 2, + round: 4, + pol_round: -1, + block_id: Some(RawCanonicalBlockId { + hash: vec![], + part_set_header: Some(RawCanonicalPartSetHeader { + total: 1, + hash: vec![1], + }), }), - }), - timestamp: None, - chain_id: "testchain".to_string(), - }; - let cp = CanonicalProposal::try_from(proto_cp).unwrap(); - assert_eq!(cp.msg_type, Type::Proposal); - assert!(cp.pol_round.is_none()); - assert!(cp.block_id.is_none()); + timestamp: None, + chain_id: "testchain".to_string(), + }; + let cp = CanonicalProposal::try_from(proto_cp).unwrap(); + assert_eq!(cp.msg_type, Type::Proposal); + assert!(cp.pol_round.is_none()); + assert!(cp.block_id.is_none()); + } } } diff --git a/tendermint/src/proposal/sign_proposal.rs b/tendermint/src/proposal/sign_proposal.rs index 16374f4a8..9c3e4a0e7 100644 --- a/tendermint/src/proposal/sign_proposal.rs +++ b/tendermint/src/proposal/sign_proposal.rs @@ -47,7 +47,7 @@ tendermint_pb_modules! { SignProposalRequest as RawSignProposalRequest, SignedProposalResponse as RawSignedProposalResponse, }; - use crate::{Error, chain::Id as ChainId, prelude::*}; + use crate::{Error, Proposal, chain::Id as ChainId, prelude::*}; use super::{SignProposalRequest, SignedProposalResponse}; impl Protobuf for SignProposalRequest {} diff --git a/tendermint/src/proto_macros.rs b/tendermint/src/proto_macros.rs index 1fb5d55a6..49948a02b 100644 --- a/tendermint/src/proto_macros.rs +++ b/tendermint/src/proto_macros.rs @@ -6,12 +6,14 @@ macro_rules! tendermint_pb_modules { } => { mod v0_34 { use tendermint_proto::v0_34 as pb; + #[allow(unused_imports)] use tendermint_proto::Protobuf; $($contents)* } mod v0_37 { use tendermint_proto::v0_37 as pb; + #[allow(unused_imports)] use tendermint_proto::Protobuf; $($contents)* diff --git a/tendermint/src/public_key.rs b/tendermint/src/public_key.rs index 779c406ef..46e7b97fc 100644 --- a/tendermint/src/public_key.rs +++ b/tendermint/src/public_key.rs @@ -445,7 +445,6 @@ mod tests { use core::convert::TryFrom; use subtle_encoding::hex; - use tendermint_proto::Protobuf; use super::{PublicKey, Signature, TendermintKey}; use crate::{prelude::*, public_key::PubKeyResponse}; @@ -512,50 +511,58 @@ mod tests { assert_eq!(reserialized_json.as_str(), json_string); } - #[test] - fn test_ed25519_pubkey_msg() { - // test-vector generated from Go - // import ( - // "fmt" - // "github.com/tendermint/tendermint/proto/tendermint/crypto" - // "github.com/tendermint/tendermint/proto/tendermint/privval" - // ) - // - // func ed25519_key() { - // pkr := &privval.PubKeyResponse{ - // PubKey: &crypto.PublicKey{ - // Sum: &crypto.PublicKey_Ed25519{Ed25519: []byte{ - // 215, 90, 152, 1, 130, 177, 10, 183, 213, 75, 254, 211, 201, 100, 7, 58, - // 14, 225, 114, 243, 218, 166, 35, 37, 175, 2, 26, 104, 247, 7, 81, 26, - // }, - // }, - // }, - // Error: nil, - // } - // pbpk, _ := pkr.Marshal() - // fmt.Printf("%#v\n", pbpk) - // - // } - let encoded = vec![ - 0xa, 0x22, 0xa, 0x20, 0xd7, 0x5a, 0x98, 0x1, 0x82, 0xb1, 0xa, 0xb7, 0xd5, 0x4b, 0xfe, - 0xd3, 0xc9, 0x64, 0x7, 0x3a, 0xe, 0xe1, 0x72, 0xf3, 0xda, 0xa6, 0x23, 0x25, 0xaf, 0x2, - 0x1a, 0x68, 0xf7, 0x7, 0x51, 0x1a, - ]; - - let msg = PubKeyResponse { - pub_key: Some( - PublicKey::from_raw_ed25519(&[ - 215, 90, 152, 1, 130, 177, 10, 183, 213, 75, 254, 211, 201, 100, 7, 58, 14, - 225, 114, 243, 218, 166, 35, 37, 175, 2, 26, 104, 247, 7, 81, 26, - ]) - .unwrap(), - ), - error: None, - }; - let got = msg.encode_vec().unwrap(); - - assert_eq!(got, encoded); - assert_eq!(PubKeyResponse::decode_vec(&encoded).unwrap(), msg); + tendermint_pb_modules! { + use super::*; + use pb::privval::PubKeyResponse as RawPubKeyResponse; + + #[test] + fn test_ed25519_pubkey_msg() { + // test-vector generated from Go + // import ( + // "fmt" + // "github.com/tendermint/tendermint/proto/tendermint/crypto" + // "github.com/tendermint/tendermint/proto/tendermint/privval" + // ) + // + // func ed25519_key() { + // pkr := &privval.PubKeyResponse{ + // PubKey: &crypto.PublicKey{ + // Sum: &crypto.PublicKey_Ed25519{Ed25519: []byte{ + // 215, 90, 152, 1, 130, 177, 10, 183, 213, 75, 254, 211, 201, 100, 7, 58, + // 14, 225, 114, 243, 218, 166, 35, 37, 175, 2, 26, 104, 247, 7, 81, 26, + // }, + // }, + // }, + // Error: nil, + // } + // pbpk, _ := pkr.Marshal() + // fmt.Printf("%#v\n", pbpk) + // + // } + let encoded = vec![ + 0xa, 0x22, 0xa, 0x20, 0xd7, 0x5a, 0x98, 0x1, 0x82, 0xb1, 0xa, 0xb7, 0xd5, 0x4b, 0xfe, + 0xd3, 0xc9, 0x64, 0x7, 0x3a, 0xe, 0xe1, 0x72, 0xf3, 0xda, 0xa6, 0x23, 0x25, 0xaf, 0x2, + 0x1a, 0x68, 0xf7, 0x7, 0x51, 0x1a, + ]; + + let msg = PubKeyResponse { + pub_key: Some( + PublicKey::from_raw_ed25519(&[ + 215, 90, 152, 1, 130, 177, 10, 183, 213, 75, 254, 211, 201, 100, 7, 58, 14, + 225, 114, 243, 218, 166, 35, 37, 175, 2, 26, 104, 247, 7, 81, 26, + ]) + .unwrap(), + ), + error: None, + }; + let got = Protobuf::::encode_vec(&msg).unwrap(); + + assert_eq!(got, encoded); + let decoded = >::decode_vec( + &encoded + ).unwrap(); + assert_eq!(decoded, msg); + } } // From https://datatracker.ietf.org/doc/html/rfc8032#section-7.1 diff --git a/tendermint/src/public_key/pub_key_request.rs b/tendermint/src/public_key/pub_key_request.rs index a83a163db..c6ee31eb9 100644 --- a/tendermint/src/public_key/pub_key_request.rs +++ b/tendermint/src/public_key/pub_key_request.rs @@ -1,8 +1,4 @@ -use core::convert::TryFrom; - -use tendermint_proto::{privval::PubKeyRequest as RawPubKeyRequest, Protobuf}; - -use crate::{chain::Id as ChainId, prelude::*, Error}; +use crate::{chain::Id as ChainId, prelude::*}; /// PubKeyRequest requests the consensus public key from the remote signer. #[derive(Clone, PartialEq, Eq, Debug)] @@ -11,63 +7,69 @@ pub struct PubKeyRequest { pub chain_id: ChainId, } -impl Protobuf for PubKeyRequest {} +tendermint_pb_modules! { + use super::PubKeyRequest; + use crate::{chain::Id as ChainId, prelude::*}; + use pb::privval::PubKeyRequest as RawPubKeyRequest; + + impl Protobuf for PubKeyRequest {} -impl TryFrom for PubKeyRequest { - type Error = Error; + impl TryFrom for PubKeyRequest { + type Error = crate::Error; - fn try_from(value: RawPubKeyRequest) -> Result { - Ok(PubKeyRequest { - chain_id: ChainId::try_from(value.chain_id)?, - }) + fn try_from(value: RawPubKeyRequest) -> Result { + Ok(PubKeyRequest { + chain_id: ChainId::try_from(value.chain_id)?, + }) + } } -} -impl From for RawPubKeyRequest { - fn from(value: PubKeyRequest) -> Self { - RawPubKeyRequest { - chain_id: value.chain_id.as_str().to_string(), + impl From for RawPubKeyRequest { + fn from(value: PubKeyRequest) -> Self { + RawPubKeyRequest { + chain_id: value.chain_id.as_str().to_string(), + } } } } #[cfg(test)] mod tests { - use core::str::FromStr; - - use tendermint_proto::Protobuf; - - use super::PubKeyRequest; - use crate::{chain::Id as ChainId, prelude::*}; + tendermint_pb_modules! { + use super::super::PubKeyRequest; + use pb::privval::PubKeyRequest as RawPubKeyRequest; + use crate::{chain::Id as ChainId, prelude::*}; + use core::str::FromStr; - #[test] - fn test_empty_pubkey_msg() { - // test-vector generated via the following go code: - // import ( - // "fmt" - // "github.com/tendermint/tendermint/proto/tendermint/privval" - // ) - // func ed25519_empty() { - // pkr := &privval.PubKeyRequest{ - // ChainId: "A", - // } - // pbpk, _ := pkr.Marshal() - // fmt.Printf("%#v\n", pbpk) - // - // } + #[test] + fn test_empty_pubkey_msg() { + // test-vector generated via the following go code: + // import ( + // "fmt" + // "github.com/tendermint/tendermint/proto/tendermint/privval" + // ) + // func ed25519_empty() { + // pkr := &privval.PubKeyRequest{ + // ChainId: "A", + // } + // pbpk, _ := pkr.Marshal() + // fmt.Printf("%#v\n", pbpk) + // + // } - let want: Vec = vec![10, 1, 65]; - let msg = PubKeyRequest { - chain_id: ChainId::from_str("A").unwrap(), - }; - let mut got = vec![]; - let _have = msg.encode(&mut got); + let want: Vec = vec![10, 1, 65]; + let msg = PubKeyRequest { + chain_id: ChainId::from_str("A").unwrap(), + }; + let mut got = vec![]; + Protobuf::::encode(&msg, &mut got).unwrap(); - assert_eq!(got, want); + assert_eq!(got, want); - match PubKeyRequest::decode(want.as_ref()) { - Ok(have) => assert_eq!(have, msg), - Err(err) => panic!("{}", err.to_string()), + match >::decode(want.as_ref()) { + Ok(have) => assert_eq!(have, msg), + Err(err) => panic!("{}", err.to_string()), + } } } } diff --git a/tendermint/src/tx/proof.rs b/tendermint/src/tx/proof.rs index 7d8abfa7a..98af54590 100644 --- a/tendermint/src/tx/proof.rs +++ b/tendermint/src/tx/proof.rs @@ -1,5 +1,5 @@ use serde::{Deserialize, Serialize}; -use tendermint_proto::types::TxProof as RawTxProof; +use tendermint_proto::v0_37::types::TxProof as RawTxProof; use tendermint_proto::Protobuf; use crate::{merkle, prelude::*, Error, Hash}; diff --git a/tendermint/src/validator.rs b/tendermint/src/validator.rs index cf250bb40..f8b99f5f9 100644 --- a/tendermint/src/validator.rs +++ b/tendermint/src/validator.rs @@ -1,7 +1,8 @@ //! Tendermint validators use serde::{Deserialize, Serialize}; -use tendermint_proto::{types::SimpleValidator as RawSimpleValidator, Protobuf}; +use tendermint_proto::v0_37::types::SimpleValidator as RawSimpleValidator; +use tendermint_proto::Protobuf; use crate::{ account, hash::Hash, merkle, prelude::*, public_key::deserialize_public_key, vote, Error, diff --git a/tendermint/src/vote.rs b/tendermint/src/vote.rs index c0d90aa78..3bb791f9d 100644 --- a/tendermint/src/vote.rs +++ b/tendermint/src/vote.rs @@ -9,7 +9,8 @@ use core::{fmt, str::FromStr}; use bytes::BufMut; use serde::{Deserialize, Serialize}; -use tendermint_proto::{types::Vote as RawVote, Error as ProtobufError, Protobuf}; +use tendermint_proto::v0_37::types::{CanonicalVote as RawCanonicalVote, Vote as RawVote}; +use tendermint_proto::{Error as ProtobufError, Protobuf}; pub use self::{ canonical_vote::CanonicalVote, power::Power, sign_vote::*, validator_index::ValidatorIndex, @@ -130,13 +131,15 @@ impl Vote { where B: BufMut, { - CanonicalVote::new(self.clone(), chain_id).encode_length_delimited(sign_bytes)?; + let canonical = CanonicalVote::new(self.clone(), chain_id); + Protobuf::::encode_length_delimited(&canonical, sign_bytes)?; Ok(true) } /// Create signable vector from Vote. pub fn to_signable_vec(&self, chain_id: ChainId) -> Result, ProtobufError> { - CanonicalVote::new(self.clone(), chain_id).encode_length_delimited_vec() + let canonical = CanonicalVote::new(self.clone(), chain_id); + Protobuf::::encode_length_delimited_vec(&canonical) } /// Consensus state from this vote - This doesn't seem to be used anywhere. @@ -215,7 +218,7 @@ impl SignedVote { /// Return the bytes (of the canonicalized vote) that were signed. pub fn sign_bytes(&self) -> Vec { - self.vote.encode_length_delimited_vec().unwrap() + Protobuf::::encode_length_delimited_vec(&self.vote).unwrap() } /// Return the actual signature on the canonicalized vote. diff --git a/tendermint/src/vote/canonical_vote.rs b/tendermint/src/vote/canonical_vote.rs index 363129003..c3afd918d 100644 --- a/tendermint/src/vote/canonical_vote.rs +++ b/tendermint/src/vote/canonical_vote.rs @@ -1,9 +1,7 @@ -use core::convert::{TryFrom, TryInto}; - use serde::{Deserialize, Serialize}; -use tendermint_proto::{types::CanonicalVote as RawCanonicalVote, Protobuf}; +use tendermint_proto::v0_37::types::CanonicalVote as RawCanonicalVote; -use crate::{block, chain::Id as ChainId, error::Error, prelude::*, Time}; +use crate::{block, chain::Id as ChainId, prelude::*, Time}; /// CanonicalVote is used for protobuf encoding a Vote #[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq)] @@ -29,43 +27,50 @@ pub struct CanonicalVote { pub chain_id: ChainId, } -impl Protobuf for CanonicalVote {} - -impl TryFrom for CanonicalVote { - type Error = Error; - - fn try_from(value: RawCanonicalVote) -> Result { - if value.timestamp.is_none() { - return Err(Error::missing_timestamp()); +tendermint_pb_modules! { + use super::CanonicalVote; + use crate::Error; + use crate::{block, chain::Id as ChainId, prelude::*}; + use pb::types::CanonicalVote as RawCanonicalVote; + + impl Protobuf for CanonicalVote {} + + impl TryFrom for CanonicalVote { + type Error = Error; + + fn try_from(value: RawCanonicalVote) -> Result { + if value.timestamp.is_none() { + return Err(Error::missing_timestamp()); + } + let _val: i32 = value.round.try_into().map_err(Error::integer_overflow)?; + + // If the Hash is empty in BlockId, the BlockId should be empty. + // See: https://github.com/informalsystems/tendermint-rs/issues/663 + let block_id = value.block_id.filter(|i| !i.hash.is_empty()); + Ok(CanonicalVote { + vote_type: value.r#type.try_into()?, + height: value.height.try_into()?, + round: (value.round as i32).try_into()?, + block_id: block_id.map(|b| b.try_into()).transpose()?, + timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, + chain_id: ChainId::try_from(value.chain_id)?, + }) } - let _val: i32 = value.round.try_into().map_err(Error::integer_overflow)?; - - // If the Hash is empty in BlockId, the BlockId should be empty. - // See: https://github.com/informalsystems/tendermint-rs/issues/663 - let block_id = value.block_id.filter(|i| !i.hash.is_empty()); - Ok(CanonicalVote { - vote_type: value.r#type.try_into()?, - height: value.height.try_into()?, - round: (value.round as i32).try_into()?, - block_id: block_id.map(|b| b.try_into()).transpose()?, - timestamp: value.timestamp.map(|t| t.try_into()).transpose()?, - chain_id: ChainId::try_from(value.chain_id)?, - }) } -} -impl From for RawCanonicalVote { - fn from(value: CanonicalVote) -> Self { - // If the Hash is empty in BlockId, the BlockId should be empty. - // See: https://github.com/informalsystems/tendermint-rs/issues/663 - let block_id = value.block_id.filter(|i| i != &block::Id::default()); - RawCanonicalVote { - r#type: value.vote_type.into(), - height: value.height.into(), - round: value.round.value().into(), - block_id: block_id.map(Into::into), - timestamp: value.timestamp.map(Into::into), - chain_id: value.chain_id.to_string(), + impl From for RawCanonicalVote { + fn from(value: CanonicalVote) -> Self { + // If the Hash is empty in BlockId, the BlockId should be empty. + // See: https://github.com/informalsystems/tendermint-rs/issues/663 + let block_id = value.block_id.filter(|i| i != &block::Id::default()); + RawCanonicalVote { + r#type: value.vote_type.into(), + height: value.height.into(), + round: value.round.value().into(), + block_id: block_id.map(Into::into), + timestamp: value.timestamp.map(Into::into), + chain_id: value.chain_id.to_string(), + } } } } @@ -86,52 +91,51 @@ impl CanonicalVote { #[cfg(test)] mod tests { - use core::convert::TryFrom; - use tendermint_proto::{ - google::protobuf::Timestamp, - types::{ + tendermint_pb_modules! { + use tendermint_proto::google::protobuf::Timestamp; + use pb::types::{ CanonicalBlockId as RawCanonicalBlockId, - CanonicalPartSetHeader as RawCanonicalPartSetHeader, CanonicalVote as RawCanonicalVote, - }, - }; - - use crate::{ - prelude::*, - vote::{canonical_vote::CanonicalVote, Type}, - }; - - #[test] - fn canonical_vote_domain_checks() { - // RawCanonicalVote with edge cases to test domain knowledge - // block_id with empty hash should decode to None - // timestamp at EPOCH is still considered valid time - let proto_cp = RawCanonicalVote { - r#type: 1, - height: 2, - round: 4, - block_id: Some(RawCanonicalBlockId { - hash: vec![], - part_set_header: Some(RawCanonicalPartSetHeader { - total: 1, - hash: vec![1], - }), - }), - timestamp: Some(Timestamp { - seconds: 0, - nanos: 0, - }), - chain_id: "testchain".to_string(), + CanonicalPartSetHeader as RawCanonicalPartSetHeader, + CanonicalVote as RawCanonicalVote, }; - let cp = CanonicalVote::try_from(proto_cp).unwrap(); - assert_eq!(cp.vote_type, Type::Prevote); - assert!(cp.block_id.is_none()); - assert!(cp.timestamp.is_some()); - - // No timestamp is not acceptable - // See: https://github.com/informalsystems/tendermint-rs/issues/649 - let mut proto_cp: RawCanonicalVote = cp.into(); - proto_cp.timestamp = None; - assert!(CanonicalVote::try_from(proto_cp).is_err()); + use crate::{ + prelude::*, + vote::{canonical_vote::CanonicalVote, Type}, + }; + + #[test] + fn canonical_vote_domain_checks() { + // RawCanonicalVote with edge cases to test domain knowledge + // block_id with empty hash should decode to None + // timestamp at EPOCH is still considered valid time + let proto_cp = RawCanonicalVote { + r#type: 1, + height: 2, + round: 4, + block_id: Some(RawCanonicalBlockId { + hash: vec![], + part_set_header: Some(RawCanonicalPartSetHeader { + total: 1, + hash: vec![1], + }), + }), + timestamp: Some(Timestamp { + seconds: 0, + nanos: 0, + }), + chain_id: "testchain".to_string(), + }; + let cp = CanonicalVote::try_from(proto_cp).unwrap(); + assert_eq!(cp.vote_type, Type::Prevote); + assert!(cp.block_id.is_none()); + assert!(cp.timestamp.is_some()); + + // No timestamp is not acceptable + // See: https://github.com/informalsystems/tendermint-rs/issues/649 + let mut proto_cp: RawCanonicalVote = cp.into(); + proto_cp.timestamp = None; + assert!(CanonicalVote::try_from(proto_cp).is_err()); + } } } diff --git a/tendermint/src/vote/sign_vote.rs b/tendermint/src/vote/sign_vote.rs index 22d688f9c..c1bcbcd66 100644 --- a/tendermint/src/vote/sign_vote.rs +++ b/tendermint/src/vote/sign_vote.rs @@ -102,7 +102,6 @@ mod tests { }; use std::println; - use tendermint_proto::Protobuf; use time::macros::datetime; use crate::{ @@ -276,76 +275,77 @@ mod tests { assert_eq!(got, want); } - #[test] - fn test_sign_bytes_compatibility() { - let cv = CanonicalVote::new(Vote::default(), ChainId::try_from("A").unwrap()); - let mut got = vec![]; - // SignBytes are encoded using MarshalBinary and not MarshalBinaryBare - cv.encode_length_delimited(&mut got).unwrap(); - let want = vec![ - 0x10, 0x8, 0x1, 0x11, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2a, 0x0, 0x32, 0x1, - 0x41, - ]; // Todo: Get these bytes from Go. During protobuf upgrade we didn't get to generate them. - assert_eq!(got, want); + tendermint_pb_modules! { + use super::*; + use pb::types::CanonicalVote as RawCanonicalVote; - // with proper (fixed size) height and round (Precommit): - { - let vt_precommit = Vote { - height: Height::from(1_u32), - round: Round::from(1_u16), - vote_type: Type::Precommit, - ..Default::default() - }; - println!("{:?}", vt_precommit); - let cv_precommit = CanonicalVote::new(vt_precommit, ChainId::try_from("A").unwrap()); - let got = cv_precommit.encode_vec().unwrap(); + #[test] + fn test_sign_bytes_compatibility() { + let cv = CanonicalVote::new(Vote::default(), ChainId::try_from("A").unwrap()); + let mut got = vec![]; + // SignBytes are encoded using MarshalBinary and not MarshalBinaryBare + Protobuf::::encode_length_delimited(&cv, &mut got).unwrap(); let want = vec![ - 0x8, // (field_number << 3) | wire_type - 0x2, // PrecommitType - 0x11, // (field_number << 3) | wire_type - 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // height - 0x19, // (field_number << 3) | wire_type - 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // round - 0x2a, // (field_number << 3) | wire_type - 0x0, // timestamp - 0x32, // (field_number << 3) | wire_type - // remaining fields (chain ID): - 0x1, 0x41, - ]; + 0x10, 0x8, 0x1, 0x11, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2a, 0x0, 0x32, 0x1, + 0x41, + ]; // Todo: Get these bytes from Go. During protobuf upgrade we didn't get to generate them. assert_eq!(got, want); - } - // with proper (fixed size) height and round (Prevote): - { - let vt_prevote = Vote { - height: Height::from(1_u32), - round: Round::from(1_u16), - vote_type: Type::Prevote, - ..Default::default() - }; - - let cv_prevote = CanonicalVote::new(vt_prevote, ChainId::try_from("A").unwrap()); - let got = cv_prevote.encode_vec().unwrap(); + // with proper (fixed size) height and round (Precommit): + { + let vt_precommit = Vote { + height: Height::from(1_u32), + round: Round::from(1_u16), + vote_type: Type::Precommit, + ..Default::default() + }; + println!("{:?}", vt_precommit); + let cv_precommit = CanonicalVote::new(vt_precommit, ChainId::try_from("A").unwrap()); + let got = Protobuf::::encode_vec(&cv_precommit).unwrap(); + let want = vec![ + 0x8, // (field_number << 3) | wire_type + 0x2, // PrecommitType + 0x11, // (field_number << 3) | wire_type + 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // height + 0x19, // (field_number << 3) | wire_type + 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // round + 0x2a, // (field_number << 3) | wire_type + 0x0, // timestamp + 0x32, // (field_number << 3) | wire_type + // remaining fields (chain ID): + 0x1, 0x41, + ]; + assert_eq!(got, want); + } + // with proper (fixed size) height and round (Prevote): + { + let vt_prevote = Vote { + height: Height::from(1_u32), + round: Round::from(1_u16), + vote_type: Type::Prevote, + ..Default::default() + }; - let want = vec![ - 0x8, // (field_number << 3) | wire_type - 0x1, // PrevoteType - 0x11, // (field_number << 3) | wire_type - 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // height - 0x19, // (field_number << 3) | wire_type - 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // round - 0x2a, // (field_number << 3) | wire_type - 0x0, // timestamp - 0x32, // (field_number << 3) | wire_type - // remaining fields (chain ID): - 0x1, 0x41, - ]; - assert_eq!(got, want); + let cv_prevote = CanonicalVote::new(vt_prevote, ChainId::try_from("A").unwrap()); + + let got = Protobuf::::encode_vec(&cv_prevote).unwrap(); + + let want = vec![ + 0x8, // (field_number << 3) | wire_type + 0x1, // PrevoteType + 0x11, // (field_number << 3) | wire_type + 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // height + 0x19, // (field_number << 3) | wire_type + 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, // round + 0x2a, // (field_number << 3) | wire_type + 0x0, // timestamp + 0x32, // (field_number << 3) | wire_type + // remaining fields (chain ID): + 0x1, 0x41, + ]; + assert_eq!(got, want); + } } - } - - tendermint_pb_modules! { - use super::*; #[test] fn test_deserialization() { From b18264ebc61babdee89aa20e426329721aeda254 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 14 Nov 2022 16:10:26 +0200 Subject: [PATCH 20/77] p2p: version-qualify dependencies on protobuf Where there are direct dependencies on the proto definitions, clarify them with the protocol version for later audit. --- p2p/src/secret_connection.rs | 2 +- p2p/src/secret_connection/amino_types.rs | 4 ++-- p2p/src/secret_connection/protocol.rs | 2 +- test/src/test/unit/p2p/secret_connection.rs | 2 +- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/p2p/src/secret_connection.rs b/p2p/src/secret_connection.rs index 17269ab78..272219764 100644 --- a/p2p/src/secret_connection.rs +++ b/p2p/src/secret_connection.rs @@ -20,7 +20,7 @@ use ed25519_dalek::{self as ed25519, Signer, Verifier}; use merlin::Transcript; use rand_core::OsRng; use subtle::ConstantTimeEq; -use tendermint_proto as proto; +use tendermint_proto::v0_37 as proto; use tendermint_std_ext::TryClone; use x25519_dalek::{EphemeralSecret, PublicKey as EphemeralPublic}; diff --git a/p2p/src/secret_connection/amino_types.rs b/p2p/src/secret_connection/amino_types.rs index 31cceafe9..ca3315516 100644 --- a/p2p/src/secret_connection/amino_types.rs +++ b/p2p/src/secret_connection/amino_types.rs @@ -4,7 +4,7 @@ use core::convert::TryFrom; use ed25519_dalek as ed25519; use prost_derive::Message; -use tendermint_proto as proto; +use tendermint_proto::v0_37 as proto; use crate::error::Error; @@ -35,7 +35,7 @@ impl AuthSigMessage { } } -impl TryFrom for tendermint_proto::p2p::AuthSigMessage { +impl TryFrom for proto::p2p::AuthSigMessage { type Error = Error; fn try_from(amino_msg: AuthSigMessage) -> Result { diff --git a/p2p/src/secret_connection/protocol.rs b/p2p/src/secret_connection/protocol.rs index b17f4ca51..005a2ee9f 100644 --- a/p2p/src/secret_connection/protocol.rs +++ b/p2p/src/secret_connection/protocol.rs @@ -4,7 +4,7 @@ use std::convert::TryInto; use ed25519_dalek as ed25519; use prost::Message as _; -use tendermint_proto as proto; +use tendermint_proto::v0_37 as proto; use x25519_dalek::PublicKey as EphemeralPublic; #[cfg(feature = "amino")] diff --git a/test/src/test/unit/p2p/secret_connection.rs b/test/src/test/unit/p2p/secret_connection.rs index ddcb551f6..2f141c185 100644 --- a/test/src/test/unit/p2p/secret_connection.rs +++ b/test/src/test/unit/p2p/secret_connection.rs @@ -7,7 +7,7 @@ use std::{ use ed25519_dalek::{self as ed25519}; use rand_core::OsRng; use tendermint_p2p::secret_connection::{sort32, Handshake, SecretConnection, Version}; -use tendermint_proto as proto; +use tendermint_proto::v0_37 as proto; use x25519_dalek::PublicKey as EphemeralPublic; use crate::pipe; From d1a76a9803408a21e23b26dfa61d07d47362e130 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 14 Nov 2022 16:25:18 +0200 Subject: [PATCH 21/77] Make clippy happy --- tendermint/src/privval.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tendermint/src/privval.rs b/tendermint/src/privval.rs index dd1b92415..f4fa9af83 100644 --- a/tendermint/src/privval.rs +++ b/tendermint/src/privval.rs @@ -4,7 +4,7 @@ use crate::prelude::*; -#[derive(Clone, Debug, PartialEq)] +#[derive(Clone, Debug, PartialEq, Eq)] pub struct RemoteSignerError { pub code: i32, pub description: String, From d397090c1fe0f09a1080e1bbcc2aed42531df329 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 16 Nov 2022 12:06:17 +0200 Subject: [PATCH 22/77] Derive Eq where clippy suggests --- tendermint/src/proposal/sign_proposal.rs | 2 +- tendermint/src/public_key/pub_key_response.rs | 2 +- tendermint/src/vote/sign_vote.rs | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tendermint/src/proposal/sign_proposal.rs b/tendermint/src/proposal/sign_proposal.rs index 9c3e4a0e7..fb4f0ff21 100644 --- a/tendermint/src/proposal/sign_proposal.rs +++ b/tendermint/src/proposal/sign_proposal.rs @@ -30,7 +30,7 @@ impl SignProposalRequest { } /// SignedProposalResponse is response containing a signed proposal or an error -#[derive(Clone, PartialEq, Debug)] +#[derive(Clone, PartialEq, Eq, Debug)] pub struct SignedProposalResponse { /// Proposal pub proposal: Option, diff --git a/tendermint/src/public_key/pub_key_response.rs b/tendermint/src/public_key/pub_key_response.rs index 5a00028f1..e974912f1 100644 --- a/tendermint/src/public_key/pub_key_response.rs +++ b/tendermint/src/public_key/pub_key_response.rs @@ -1,7 +1,7 @@ use crate::{privval::RemoteSignerError, PublicKey}; /// PubKeyResponse -#[derive(Clone, PartialEq, Debug)] +#[derive(Clone, PartialEq, Eq, Debug)] // Todo: either pub_key OR error is present pub struct PubKeyResponse { /// Public key diff --git a/tendermint/src/vote/sign_vote.rs b/tendermint/src/vote/sign_vote.rs index c1bcbcd66..234a813cc 100644 --- a/tendermint/src/vote/sign_vote.rs +++ b/tendermint/src/vote/sign_vote.rs @@ -29,7 +29,7 @@ impl SignVoteRequest { } /// SignedVoteResponse is a response containing a signed vote or an error -#[derive(Clone, PartialEq, Debug)] +#[derive(Clone, PartialEq, Eq, Debug)] pub struct SignedVoteResponse { /// Optional Vote pub vote: Option, From 4796bc416fa0c0db84f75efa4bacf69fc511a394 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 21 Nov 2022 15:45:27 +0200 Subject: [PATCH 23/77] tendermint: version-specific Request and Response Separate Request and Response definitions pertaining to protocol versions v0.34 and v0.37, namespaced in top-level modules v0_34 and v0_37 respectively. --- tendermint/src/abci.rs | 7 +- tendermint/src/abci/request.rs | 330 ++------------------------ tendermint/src/abci/response.rs | 276 +-------------------- tendermint/src/lib.rs | 3 + tendermint/src/v0_34.rs | 1 + tendermint/src/v0_34/abci.rs | 5 + tendermint/src/v0_34/abci/request.rs | 219 +++++++++++++++++ tendermint/src/v0_34/abci/response.rs | 196 +++++++++++++++ tendermint/src/v0_37.rs | 1 + tendermint/src/v0_37/abci.rs | 5 + tendermint/src/v0_37/abci/request.rs | 223 +++++++++++++++++ tendermint/src/v0_37/abci/response.rs | 200 ++++++++++++++++ 12 files changed, 873 insertions(+), 593 deletions(-) create mode 100644 tendermint/src/v0_34.rs create mode 100644 tendermint/src/v0_34/abci.rs create mode 100644 tendermint/src/v0_34/abci/request.rs create mode 100644 tendermint/src/v0_34/abci/response.rs create mode 100644 tendermint/src/v0_37.rs create mode 100644 tendermint/src/v0_37/abci.rs create mode 100644 tendermint/src/v0_37/abci/request.rs create mode 100644 tendermint/src/v0_37/abci/response.rs diff --git a/tendermint/src/abci.rs b/tendermint/src/abci.rs index 2ea41b9d9..72a179ff7 100644 --- a/tendermint/src/abci.rs +++ b/tendermint/src/abci.rs @@ -44,12 +44,15 @@ pub mod request; pub mod response; pub mod types; +pub use crate::v0_37::abci::request::Request; +pub use crate::v0_37::abci::response::Response; + pub use event::{Event, EventAttribute, EventAttributeIndexExt}; #[doc(inline)] pub use self::{ code::Code, kind::MethodKind, - request::{ConsensusRequest, InfoRequest, MempoolRequest, Request, SnapshotRequest}, - response::{ConsensusResponse, InfoResponse, MempoolResponse, Response, SnapshotResponse}, + request::{ConsensusRequest, InfoRequest, MempoolRequest, SnapshotRequest}, + response::{ConsensusResponse, InfoResponse, MempoolResponse, SnapshotResponse}, }; diff --git a/tendermint/src/abci/request.rs b/tendermint/src/abci/request.rs index f37388995..7e3e8c307 100644 --- a/tendermint/src/abci/request.rs +++ b/tendermint/src/abci/request.rs @@ -18,28 +18,25 @@ // This is also why certain submodules have #[allow(unused)] imports to bring // items into scope for doc links, rather than changing the doc links -- it // allows the doc comments to be copied without editing. -use core::convert::TryFrom; // bring into scope for doc links #[allow(unused)] use super::types::Snapshot; -use super::MethodKind; -use crate::{prelude::*, Error}; -mod apply_snapshot_chunk; -mod begin_block; -mod check_tx; -mod deliver_tx; -mod echo; -mod end_block; -mod info; -mod init_chain; -mod load_snapshot_chunk; -mod offer_snapshot; -mod prepare_proposal; -mod process_proposal; -mod query; -mod set_option; +pub(super) mod apply_snapshot_chunk; +pub(super) mod begin_block; +pub(super) mod check_tx; +pub(super) mod deliver_tx; +pub(super) mod echo; +pub(super) mod end_block; +pub(super) mod info; +pub(super) mod init_chain; +pub(super) mod load_snapshot_chunk; +pub(super) mod offer_snapshot; +pub(super) mod prepare_proposal; +pub(super) mod process_proposal; +pub(super) mod query; +pub(super) mod set_option; pub use apply_snapshot_chunk::ApplySnapshotChunk; pub use begin_block::BeginBlock; @@ -56,72 +53,6 @@ pub use process_proposal::ProcessProposal; pub use query::Query; pub use set_option::SetOption; -/// All possible ABCI requests. -#[allow(clippy::large_enum_variant)] -#[derive(Clone, PartialEq, Eq, Debug)] -pub enum Request { - #[doc = include_str!("doc/request-echo.md")] - Echo(Echo), - #[doc = include_str!("doc/request-flush.md")] - Flush, - #[doc = include_str!("doc/request-info.md")] - Info(Info), - #[doc = include_str!("doc/request-setoption.md")] - SetOption(SetOption), - #[doc = include_str!("doc/request-initchain.md")] - InitChain(InitChain), - #[doc = include_str!("doc/request-query.md")] - Query(Query), - #[doc = include_str!("doc/request-beginblock.md")] - BeginBlock(BeginBlock), - #[doc = include_str!("doc/request-checktx.md")] - CheckTx(CheckTx), - #[doc = include_str!("doc/request-delivertx.md")] - DeliverTx(DeliverTx), - #[doc = include_str!("doc/request-endblock.md")] - EndBlock(EndBlock), - #[doc = include_str!("doc/request-commit.md")] - Commit, - #[doc = include_str!("doc/request-listsnapshots.md")] - ListSnapshots, - #[doc = include_str!("doc/request-offersnapshot.md")] - OfferSnapshot(OfferSnapshot), - #[doc = include_str!("doc/request-loadsnapshotchunk.md")] - LoadSnapshotChunk(LoadSnapshotChunk), - #[doc = include_str!("doc/request-applysnapshotchunk.md")] - ApplySnapshotChunk(ApplySnapshotChunk), - #[doc = include_str!("doc/request-prepareproposal.md")] - PrepareProposal(PrepareProposal), - #[doc = include_str!("doc/request-processproposal.md")] - ProcessProposal(ProcessProposal), -} - -impl Request { - /// Get the method kind for this request. - pub fn kind(&self) -> MethodKind { - use Request::*; - match self { - Flush => MethodKind::Flush, - InitChain(_) => MethodKind::Consensus, - BeginBlock(_) => MethodKind::Consensus, - DeliverTx(_) => MethodKind::Consensus, - EndBlock(_) => MethodKind::Consensus, - Commit => MethodKind::Consensus, - PrepareProposal(_) => MethodKind::Consensus, - ProcessProposal(_) => MethodKind::Consensus, - CheckTx(_) => MethodKind::Mempool, - ListSnapshots => MethodKind::Snapshot, - OfferSnapshot(_) => MethodKind::Snapshot, - LoadSnapshotChunk(_) => MethodKind::Snapshot, - ApplySnapshotChunk(_) => MethodKind::Snapshot, - Info(_) => MethodKind::Info, - Query(_) => MethodKind::Info, - Echo(_) => MethodKind::Info, - SetOption(_) => MethodKind::Info, - } - } -} - /// The consensus category of ABCI requests. #[allow(clippy::large_enum_variant)] #[derive(Clone, PartialEq, Eq, Debug)] @@ -138,32 +69,6 @@ pub enum ConsensusRequest { Commit, } -impl From for Request { - fn from(req: ConsensusRequest) -> Self { - match req { - ConsensusRequest::InitChain(x) => Self::InitChain(x), - ConsensusRequest::BeginBlock(x) => Self::BeginBlock(x), - ConsensusRequest::DeliverTx(x) => Self::DeliverTx(x), - ConsensusRequest::EndBlock(x) => Self::EndBlock(x), - ConsensusRequest::Commit => Self::Commit, - } - } -} - -impl TryFrom for ConsensusRequest { - type Error = Error; - fn try_from(req: Request) -> Result { - match req { - Request::InitChain(x) => Ok(Self::InitChain(x)), - Request::BeginBlock(x) => Ok(Self::BeginBlock(x)), - Request::DeliverTx(x) => Ok(Self::DeliverTx(x)), - Request::EndBlock(x) => Ok(Self::EndBlock(x)), - Request::Commit => Ok(Self::Commit), - _ => Err(Error::invalid_abci_request_type()), - } - } -} - /// The mempool category of ABCI requests. #[derive(Clone, PartialEq, Eq, Debug)] pub enum MempoolRequest { @@ -171,24 +76,6 @@ pub enum MempoolRequest { CheckTx(CheckTx), } -impl From for Request { - fn from(req: MempoolRequest) -> Self { - match req { - MempoolRequest::CheckTx(x) => Self::CheckTx(x), - } - } -} - -impl TryFrom for MempoolRequest { - type Error = Error; - fn try_from(req: Request) -> Result { - match req { - Request::CheckTx(x) => Ok(Self::CheckTx(x)), - _ => Err(Error::invalid_abci_request_type()), - } - } -} - /// The info category of ABCI requests. #[derive(Clone, PartialEq, Eq, Debug)] pub enum InfoRequest { @@ -202,30 +89,6 @@ pub enum InfoRequest { SetOption(SetOption), } -impl From for Request { - fn from(req: InfoRequest) -> Self { - match req { - InfoRequest::Info(x) => Self::Info(x), - InfoRequest::Query(x) => Self::Query(x), - InfoRequest::Echo(x) => Self::Echo(x), - InfoRequest::SetOption(x) => Self::SetOption(x), - } - } -} - -impl TryFrom for InfoRequest { - type Error = Error; - fn try_from(req: Request) -> Result { - match req { - Request::Info(x) => Ok(Self::Info(x)), - Request::Query(x) => Ok(Self::Query(x)), - Request::Echo(x) => Ok(Self::Echo(x)), - Request::SetOption(x) => Ok(Self::SetOption(x)), - _ => Err(Error::invalid_abci_request_type()), - } - } -} - /// The snapshot category of ABCI requests. #[derive(Clone, PartialEq, Eq, Debug)] pub enum SnapshotRequest { @@ -238,168 +101,3 @@ pub enum SnapshotRequest { #[doc = include_str!("doc/request-applysnapshotchunk.md")] ApplySnapshotChunk(ApplySnapshotChunk), } - -impl From for Request { - fn from(req: SnapshotRequest) -> Self { - match req { - SnapshotRequest::ListSnapshots => Self::ListSnapshots, - SnapshotRequest::OfferSnapshot(x) => Self::OfferSnapshot(x), - SnapshotRequest::LoadSnapshotChunk(x) => Self::LoadSnapshotChunk(x), - SnapshotRequest::ApplySnapshotChunk(x) => Self::ApplySnapshotChunk(x), - } - } -} - -impl TryFrom for SnapshotRequest { - type Error = Error; - fn try_from(req: Request) -> Result { - match req { - Request::ListSnapshots => Ok(Self::ListSnapshots), - Request::OfferSnapshot(x) => Ok(Self::OfferSnapshot(x)), - Request::LoadSnapshotChunk(x) => Ok(Self::LoadSnapshotChunk(x)), - Request::ApplySnapshotChunk(x) => Ok(Self::ApplySnapshotChunk(x)), - _ => Err(Error::invalid_abci_request_type()), - } - } -} - -// ============================================================================= -// Protobuf conversions -// ============================================================================= - -mod v0_34 { - use super::Request; - use crate::{prelude::*, Error}; - use tendermint_proto::v0_34::abci as pb; - use tendermint_proto::Protobuf; - - impl From for pb::Request { - fn from(request: Request) -> pb::Request { - use pb::request::Value; - let value = match request { - Request::Echo(x) => Some(Value::Echo(x.into())), - Request::Flush => Some(Value::Flush(Default::default())), - Request::Info(x) => Some(Value::Info(x.into())), - Request::SetOption(x) => Some(Value::SetOption(x.into())), - Request::InitChain(x) => Some(Value::InitChain(x.into())), - Request::Query(x) => Some(Value::Query(x.into())), - Request::BeginBlock(x) => Some(Value::BeginBlock(x.into())), - Request::CheckTx(x) => Some(Value::CheckTx(x.into())), - Request::DeliverTx(x) => Some(Value::DeliverTx(x.into())), - Request::EndBlock(x) => Some(Value::EndBlock(x.into())), - Request::Commit => Some(Value::Commit(Default::default())), - Request::ListSnapshots => Some(Value::ListSnapshots(Default::default())), - Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), - Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), - Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), - Request::PrepareProposal(_) => { - panic!("PrepareProposal should not be used with Tendermint 0.34") - }, - Request::ProcessProposal(_) => { - panic!("ProcessProposal should not be used with Tendermint 0.34") - }, - }; - pb::Request { value } - } - } - - impl TryFrom for Request { - type Error = Error; - - fn try_from(request: pb::Request) -> Result { - use pb::request::Value; - match request.value { - Some(Value::Echo(x)) => Ok(Request::Echo(x.try_into()?)), - Some(Value::Flush(pb::RequestFlush {})) => Ok(Request::Flush), - Some(Value::Info(x)) => Ok(Request::Info(x.try_into()?)), - Some(Value::SetOption(x)) => Ok(Request::SetOption(x.try_into()?)), - Some(Value::InitChain(x)) => Ok(Request::InitChain(x.try_into()?)), - Some(Value::Query(x)) => Ok(Request::Query(x.try_into()?)), - Some(Value::BeginBlock(x)) => Ok(Request::BeginBlock(x.try_into()?)), - Some(Value::CheckTx(x)) => Ok(Request::CheckTx(x.try_into()?)), - Some(Value::DeliverTx(x)) => Ok(Request::DeliverTx(x.try_into()?)), - Some(Value::EndBlock(x)) => Ok(Request::EndBlock(x.try_into()?)), - Some(Value::Commit(pb::RequestCommit {})) => Ok(Request::Commit), - Some(Value::ListSnapshots(pb::RequestListSnapshots {})) => { - Ok(Request::ListSnapshots) - }, - Some(Value::OfferSnapshot(x)) => Ok(Request::OfferSnapshot(x.try_into()?)), - Some(Value::LoadSnapshotChunk(x)) => Ok(Request::LoadSnapshotChunk(x.try_into()?)), - Some(Value::ApplySnapshotChunk(x)) => { - Ok(Request::ApplySnapshotChunk(x.try_into()?)) - }, - None => Err(crate::Error::missing_data()), - } - } - } - - impl Protobuf for Request {} -} - -mod v0_37 { - use super::Request; - use crate::{prelude::*, Error}; - use tendermint_proto::v0_37::abci as pb; - use tendermint_proto::Protobuf; - - impl From for pb::Request { - fn from(request: Request) -> pb::Request { - use pb::request::Value; - let value = match request { - Request::Echo(x) => Some(Value::Echo(x.into())), - Request::Flush => Some(Value::Flush(Default::default())), - Request::Info(x) => Some(Value::Info(x.into())), - Request::InitChain(x) => Some(Value::InitChain(x.into())), - Request::Query(x) => Some(Value::Query(x.into())), - Request::BeginBlock(x) => Some(Value::BeginBlock(x.into())), - Request::CheckTx(x) => Some(Value::CheckTx(x.into())), - Request::DeliverTx(x) => Some(Value::DeliverTx(x.into())), - Request::EndBlock(x) => Some(Value::EndBlock(x.into())), - Request::Commit => Some(Value::Commit(Default::default())), - Request::ListSnapshots => Some(Value::ListSnapshots(Default::default())), - Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), - Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), - Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), - Request::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), - Request::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), - Request::SetOption(_) => { - panic!("SetOption should not be used with Tendermint 0.37") - }, - }; - pb::Request { value } - } - } - - impl TryFrom for Request { - type Error = Error; - - fn try_from(request: pb::Request) -> Result { - use pb::request::Value; - match request.value { - Some(Value::Echo(x)) => Ok(Request::Echo(x.try_into()?)), - Some(Value::Flush(pb::RequestFlush {})) => Ok(Request::Flush), - Some(Value::Info(x)) => Ok(Request::Info(x.try_into()?)), - Some(Value::InitChain(x)) => Ok(Request::InitChain(x.try_into()?)), - Some(Value::Query(x)) => Ok(Request::Query(x.try_into()?)), - Some(Value::BeginBlock(x)) => Ok(Request::BeginBlock(x.try_into()?)), - Some(Value::CheckTx(x)) => Ok(Request::CheckTx(x.try_into()?)), - Some(Value::DeliverTx(x)) => Ok(Request::DeliverTx(x.try_into()?)), - Some(Value::EndBlock(x)) => Ok(Request::EndBlock(x.try_into()?)), - Some(Value::Commit(pb::RequestCommit {})) => Ok(Request::Commit), - Some(Value::ListSnapshots(pb::RequestListSnapshots {})) => { - Ok(Request::ListSnapshots) - }, - Some(Value::OfferSnapshot(x)) => Ok(Request::OfferSnapshot(x.try_into()?)), - Some(Value::LoadSnapshotChunk(x)) => Ok(Request::LoadSnapshotChunk(x.try_into()?)), - Some(Value::ApplySnapshotChunk(x)) => { - Ok(Request::ApplySnapshotChunk(x.try_into()?)) - }, - Some(Value::PrepareProposal(x)) => Ok(Request::PrepareProposal(x.try_into()?)), - Some(Value::ProcessProposal(x)) => Ok(Request::ProcessProposal(x.try_into()?)), - None => Err(crate::Error::missing_data()), - } - } - } - - impl Protobuf for Request {} -} diff --git a/tendermint/src/abci/response.rs b/tendermint/src/abci/response.rs index 721ea2a5d..feb2613c0 100644 --- a/tendermint/src/abci/response.rs +++ b/tendermint/src/abci/response.rs @@ -22,7 +22,7 @@ // bring into scope for doc links #[allow(unused)] use super::types::Snapshot; -use crate::{prelude::*, Error}; +use crate::prelude::*; mod apply_snapshot_chunk; mod begin_block; @@ -60,47 +60,6 @@ pub use process_proposal::ProcessProposal; pub use query::Query; pub use set_option::SetOption; -/// All possible ABCI responses. -#[derive(Clone, PartialEq, Eq, Debug)] -pub enum Response { - #[doc = include_str!("doc/response-exception.md")] - Exception(Exception), - #[doc = include_str!("doc/response-echo.md")] - Echo(Echo), - #[doc = include_str!("doc/response-flush.md")] - Flush, - #[doc = include_str!("doc/response-info.md")] - Info(Info), - #[doc = include_str!("doc/response-setoption.md")] - SetOption(SetOption), - #[doc = include_str!("doc/response-initchain.md")] - InitChain(InitChain), - #[doc = include_str!("doc/response-query.md")] - Query(Query), - #[doc = include_str!("doc/response-beginblock.md")] - BeginBlock(BeginBlock), - #[doc = include_str!("doc/response-checktx.md")] - CheckTx(CheckTx), - #[doc = include_str!("doc/response-delivertx.md")] - DeliverTx(DeliverTx), - #[doc = include_str!("doc/response-endblock.md")] - EndBlock(EndBlock), - #[doc = include_str!("doc/response-commit.md")] - Commit(Commit), - #[doc = include_str!("doc/response-listsnapshots.md")] - ListSnapshots(ListSnapshots), - #[doc = include_str!("doc/response-offersnapshot.md")] - OfferSnapshot(OfferSnapshot), - #[doc = include_str!("doc/response-loadsnapshotchunk.md")] - LoadSnapshotChunk(LoadSnapshotChunk), - #[doc = include_str!("doc/response-applysnapshotchunk.md")] - ApplySnapshotChunk(ApplySnapshotChunk), - #[doc = include_str!("doc/response-prepareproposal.md")] - PrepareProposal(PrepareProposal), - #[doc = include_str!("doc/response-processproposal.md")] - ProcessProposal(ProcessProposal), -} - /// The consensus category of ABCI responses. #[derive(Clone, PartialEq, Eq, Debug)] pub enum ConsensusResponse { @@ -116,32 +75,6 @@ pub enum ConsensusResponse { Commit(Commit), } -impl From for Response { - fn from(req: ConsensusResponse) -> Self { - match req { - ConsensusResponse::InitChain(x) => Self::InitChain(x), - ConsensusResponse::BeginBlock(x) => Self::BeginBlock(x), - ConsensusResponse::DeliverTx(x) => Self::DeliverTx(x), - ConsensusResponse::EndBlock(x) => Self::EndBlock(x), - ConsensusResponse::Commit(x) => Self::Commit(x), - } - } -} - -impl TryFrom for ConsensusResponse { - type Error = Error; - fn try_from(req: Response) -> Result { - match req { - Response::InitChain(x) => Ok(Self::InitChain(x)), - Response::BeginBlock(x) => Ok(Self::BeginBlock(x)), - Response::DeliverTx(x) => Ok(Self::DeliverTx(x)), - Response::EndBlock(x) => Ok(Self::EndBlock(x)), - Response::Commit(x) => Ok(Self::Commit(x)), - _ => Err(Error::invalid_abci_response_type()), - } - } -} - /// The mempool category of ABCI responses. #[derive(Clone, PartialEq, Eq, Debug)] pub enum MempoolResponse { @@ -149,24 +82,6 @@ pub enum MempoolResponse { CheckTx(CheckTx), } -impl From for Response { - fn from(req: MempoolResponse) -> Self { - match req { - MempoolResponse::CheckTx(x) => Self::CheckTx(x), - } - } -} - -impl TryFrom for MempoolResponse { - type Error = Error; - fn try_from(req: Response) -> Result { - match req { - Response::CheckTx(x) => Ok(Self::CheckTx(x)), - _ => Err(Error::invalid_abci_response_type()), - } - } -} - /// The info category of ABCI responses. #[derive(Clone, PartialEq, Eq, Debug)] pub enum InfoResponse { @@ -180,30 +95,6 @@ pub enum InfoResponse { SetOption(SetOption), } -impl From for Response { - fn from(req: InfoResponse) -> Self { - match req { - InfoResponse::Echo(x) => Self::Echo(x), - InfoResponse::Info(x) => Self::Info(x), - InfoResponse::Query(x) => Self::Query(x), - InfoResponse::SetOption(x) => Self::SetOption(x), - } - } -} - -impl TryFrom for InfoResponse { - type Error = Error; - fn try_from(req: Response) -> Result { - match req { - Response::Echo(x) => Ok(Self::Echo(x)), - Response::Info(x) => Ok(Self::Info(x)), - Response::Query(x) => Ok(Self::Query(x)), - Response::SetOption(x) => Ok(Self::SetOption(x)), - _ => Err(Error::invalid_abci_response_type()), - } - } -} - /// The snapshot category of ABCI responses. #[derive(Clone, PartialEq, Eq, Debug)] pub enum SnapshotResponse { @@ -216,168 +107,3 @@ pub enum SnapshotResponse { #[doc = include_str!("doc/response-applysnapshotchunk.md")] ApplySnapshotChunk(ApplySnapshotChunk), } - -impl From for Response { - fn from(req: SnapshotResponse) -> Self { - match req { - SnapshotResponse::ListSnapshots(x) => Self::ListSnapshots(x), - SnapshotResponse::OfferSnapshot(x) => Self::OfferSnapshot(x), - SnapshotResponse::LoadSnapshotChunk(x) => Self::LoadSnapshotChunk(x), - SnapshotResponse::ApplySnapshotChunk(x) => Self::ApplySnapshotChunk(x), - } - } -} - -impl TryFrom for SnapshotResponse { - type Error = Error; - fn try_from(req: Response) -> Result { - match req { - Response::ListSnapshots(x) => Ok(Self::ListSnapshots(x)), - Response::OfferSnapshot(x) => Ok(Self::OfferSnapshot(x)), - Response::LoadSnapshotChunk(x) => Ok(Self::LoadSnapshotChunk(x)), - Response::ApplySnapshotChunk(x) => Ok(Self::ApplySnapshotChunk(x)), - _ => Err(Error::invalid_abci_response_type()), - } - } -} - -// ============================================================================= -// Protobuf conversions -// ============================================================================= - -mod v0_34 { - use super::Response; - use crate::Error; - use tendermint_proto::v0_34::abci as pb; - use tendermint_proto::Protobuf; - - impl From for pb::Response { - fn from(response: Response) -> pb::Response { - use pb::response::Value; - let value = match response { - Response::Exception(x) => Some(Value::Exception(x.into())), - Response::Echo(x) => Some(Value::Echo(x.into())), - Response::Flush => Some(Value::Flush(Default::default())), - Response::Info(x) => Some(Value::Info(x.into())), - Response::SetOption(x) => Some(Value::SetOption(x.into())), - Response::InitChain(x) => Some(Value::InitChain(x.into())), - Response::Query(x) => Some(Value::Query(x.into())), - Response::BeginBlock(x) => Some(Value::BeginBlock(x.into())), - Response::CheckTx(x) => Some(Value::CheckTx(x.into())), - Response::DeliverTx(x) => Some(Value::DeliverTx(x.into())), - Response::EndBlock(x) => Some(Value::EndBlock(x.into())), - Response::Commit(x) => Some(Value::Commit(x.into())), - Response::ListSnapshots(x) => Some(Value::ListSnapshots(x.into())), - Response::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), - Response::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), - Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), - Response::PrepareProposal(_) => { - panic!("PrepareProposal should not be used with Tendermint 0.34") - }, - Response::ProcessProposal(_) => { - panic!("ProcessProposal should not be used with Tendermint 0.34") - }, - }; - pb::Response { value } - } - } - - impl TryFrom for Response { - type Error = Error; - - fn try_from(response: pb::Response) -> Result { - use pb::response::Value; - match response.value { - Some(Value::Exception(x)) => Ok(Response::Exception(x.try_into()?)), - Some(Value::Echo(x)) => Ok(Response::Echo(x.try_into()?)), - Some(Value::Flush(_)) => Ok(Response::Flush), - Some(Value::Info(x)) => Ok(Response::Info(x.try_into()?)), - Some(Value::SetOption(x)) => Ok(Response::SetOption(x.try_into()?)), - Some(Value::InitChain(x)) => Ok(Response::InitChain(x.try_into()?)), - Some(Value::Query(x)) => Ok(Response::Query(x.try_into()?)), - Some(Value::BeginBlock(x)) => Ok(Response::BeginBlock(x.try_into()?)), - Some(Value::CheckTx(x)) => Ok(Response::CheckTx(x.try_into()?)), - Some(Value::DeliverTx(x)) => Ok(Response::DeliverTx(x.try_into()?)), - Some(Value::EndBlock(x)) => Ok(Response::EndBlock(x.try_into()?)), - Some(Value::Commit(x)) => Ok(Response::Commit(x.try_into()?)), - Some(Value::ListSnapshots(x)) => Ok(Response::ListSnapshots(x.try_into()?)), - Some(Value::OfferSnapshot(x)) => Ok(Response::OfferSnapshot(x.try_into()?)), - Some(Value::LoadSnapshotChunk(x)) => Ok(Response::LoadSnapshotChunk(x.try_into()?)), - Some(Value::ApplySnapshotChunk(x)) => { - Ok(Response::ApplySnapshotChunk(x.try_into()?)) - }, - None => Err(crate::Error::missing_data()), - } - } - } - - impl Protobuf for Response {} -} - -mod v0_37 { - use super::Response; - use crate::Error; - use tendermint_proto::v0_37::abci as pb; - use tendermint_proto::Protobuf; - - impl From for pb::Response { - fn from(response: Response) -> pb::Response { - use pb::response::Value; - let value = match response { - Response::Exception(x) => Some(Value::Exception(x.into())), - Response::Echo(x) => Some(Value::Echo(x.into())), - Response::Flush => Some(Value::Flush(Default::default())), - Response::Info(x) => Some(Value::Info(x.into())), - Response::InitChain(x) => Some(Value::InitChain(x.into())), - Response::Query(x) => Some(Value::Query(x.into())), - Response::BeginBlock(x) => Some(Value::BeginBlock(x.into())), - Response::CheckTx(x) => Some(Value::CheckTx(x.into())), - Response::DeliverTx(x) => Some(Value::DeliverTx(x.into())), - Response::EndBlock(x) => Some(Value::EndBlock(x.into())), - Response::Commit(x) => Some(Value::Commit(x.into())), - Response::ListSnapshots(x) => Some(Value::ListSnapshots(x.into())), - Response::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), - Response::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), - Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), - Response::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), - Response::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), - Response::SetOption(_) => { - panic!("SetOption should not be used with Tendermint 0.37") - }, - }; - pb::Response { value } - } - } - - impl TryFrom for Response { - type Error = Error; - - fn try_from(response: pb::Response) -> Result { - use pb::response::Value; - match response.value { - Some(Value::Exception(x)) => Ok(Response::Exception(x.try_into()?)), - Some(Value::Echo(x)) => Ok(Response::Echo(x.try_into()?)), - Some(Value::Flush(_)) => Ok(Response::Flush), - Some(Value::Info(x)) => Ok(Response::Info(x.try_into()?)), - Some(Value::InitChain(x)) => Ok(Response::InitChain(x.try_into()?)), - Some(Value::Query(x)) => Ok(Response::Query(x.try_into()?)), - Some(Value::BeginBlock(x)) => Ok(Response::BeginBlock(x.try_into()?)), - Some(Value::CheckTx(x)) => Ok(Response::CheckTx(x.try_into()?)), - Some(Value::DeliverTx(x)) => Ok(Response::DeliverTx(x.try_into()?)), - Some(Value::EndBlock(x)) => Ok(Response::EndBlock(x.try_into()?)), - Some(Value::Commit(x)) => Ok(Response::Commit(x.try_into()?)), - Some(Value::ListSnapshots(x)) => Ok(Response::ListSnapshots(x.try_into()?)), - Some(Value::OfferSnapshot(x)) => Ok(Response::OfferSnapshot(x.try_into()?)), - Some(Value::LoadSnapshotChunk(x)) => Ok(Response::LoadSnapshotChunk(x.try_into()?)), - Some(Value::ApplySnapshotChunk(x)) => { - Ok(Response::ApplySnapshotChunk(x.try_into()?)) - }, - Some(Value::PrepareProposal(x)) => Ok(Response::PrepareProposal(x.try_into()?)), - Some(Value::ProcessProposal(x)) => Ok(Response::ProcessProposal(x.try_into()?)), - None => Err(crate::Error::missing_data()), - } - } - } - - impl Protobuf for Response {} -} diff --git a/tendermint/src/lib.rs b/tendermint/src/lib.rs index 434e3157f..3edcfaa4e 100644 --- a/tendermint/src/lib.rs +++ b/tendermint/src/lib.rs @@ -56,6 +56,9 @@ pub mod validator; mod version; pub mod vote; +pub mod v0_34; +pub mod v0_37; + #[cfg(test)] mod test; diff --git a/tendermint/src/v0_34.rs b/tendermint/src/v0_34.rs new file mode 100644 index 000000000..c52eb0a4c --- /dev/null +++ b/tendermint/src/v0_34.rs @@ -0,0 +1 @@ +pub mod abci; diff --git a/tendermint/src/v0_34/abci.rs b/tendermint/src/v0_34/abci.rs new file mode 100644 index 000000000..601e534df --- /dev/null +++ b/tendermint/src/v0_34/abci.rs @@ -0,0 +1,5 @@ +pub mod request; +pub mod response; + +pub use request::Request; +pub use response::Response; diff --git a/tendermint/src/v0_34/abci/request.rs b/tendermint/src/v0_34/abci/request.rs new file mode 100644 index 000000000..cea3ba016 --- /dev/null +++ b/tendermint/src/v0_34/abci/request.rs @@ -0,0 +1,219 @@ +use tendermint_proto::v0_34::abci as pb; +use tendermint_proto::Protobuf; + +use crate::abci::request::{ConsensusRequest, InfoRequest, MempoolRequest, SnapshotRequest}; +use crate::abci::MethodKind; +use crate::Error; + +pub use crate::abci::request::{ + ApplySnapshotChunk, BeginBlock, CheckTx, CheckTxKind, DeliverTx, Echo, EndBlock, Info, + InitChain, LoadSnapshotChunk, OfferSnapshot, Query, SetOption, +}; + +/// All possible ABCI requests. +#[allow(clippy::large_enum_variant)] +#[derive(Clone, PartialEq, Eq, Debug)] +pub enum Request { + #[doc = include_str!("../../abci/doc/request-echo.md")] + Echo(Echo), + #[doc = include_str!("../../abci/doc/request-flush.md")] + Flush, + #[doc = include_str!("../../abci/doc/request-info.md")] + Info(Info), + #[doc = include_str!("../../abci/doc/request-setoption.md")] + SetOption(SetOption), + #[doc = include_str!("../../abci/doc/request-initchain.md")] + InitChain(InitChain), + #[doc = include_str!("../../abci/doc/request-query.md")] + Query(Query), + #[doc = include_str!("../../abci/doc/request-beginblock.md")] + BeginBlock(BeginBlock), + #[doc = include_str!("../../abci/doc/request-checktx.md")] + CheckTx(CheckTx), + #[doc = include_str!("../../abci/doc/request-delivertx.md")] + DeliverTx(DeliverTx), + #[doc = include_str!("../../abci/doc/request-endblock.md")] + EndBlock(EndBlock), + #[doc = include_str!("../../abci/doc/request-commit.md")] + Commit, + #[doc = include_str!("../../abci/doc/request-listsnapshots.md")] + ListSnapshots, + #[doc = include_str!("../../abci/doc/request-offersnapshot.md")] + OfferSnapshot(OfferSnapshot), + #[doc = include_str!("../../abci/doc/request-loadsnapshotchunk.md")] + LoadSnapshotChunk(LoadSnapshotChunk), + #[doc = include_str!("../../abci/doc/request-applysnapshotchunk.md")] + ApplySnapshotChunk(ApplySnapshotChunk), +} + +impl Request { + /// Get the method kind for this request. + pub fn kind(&self) -> MethodKind { + use Request::*; + match self { + Flush => MethodKind::Flush, + InitChain(_) => MethodKind::Consensus, + BeginBlock(_) => MethodKind::Consensus, + DeliverTx(_) => MethodKind::Consensus, + EndBlock(_) => MethodKind::Consensus, + Commit => MethodKind::Consensus, + CheckTx(_) => MethodKind::Mempool, + ListSnapshots => MethodKind::Snapshot, + OfferSnapshot(_) => MethodKind::Snapshot, + LoadSnapshotChunk(_) => MethodKind::Snapshot, + ApplySnapshotChunk(_) => MethodKind::Snapshot, + Info(_) => MethodKind::Info, + Query(_) => MethodKind::Info, + Echo(_) => MethodKind::Info, + SetOption(_) => MethodKind::Info, + } + } +} + +impl From for Request { + fn from(req: ConsensusRequest) -> Self { + match req { + ConsensusRequest::InitChain(x) => Self::InitChain(x), + ConsensusRequest::BeginBlock(x) => Self::BeginBlock(x), + ConsensusRequest::DeliverTx(x) => Self::DeliverTx(x), + ConsensusRequest::EndBlock(x) => Self::EndBlock(x), + ConsensusRequest::Commit => Self::Commit, + } + } +} + +impl TryFrom for ConsensusRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::InitChain(x) => Ok(Self::InitChain(x)), + Request::BeginBlock(x) => Ok(Self::BeginBlock(x)), + Request::DeliverTx(x) => Ok(Self::DeliverTx(x)), + Request::EndBlock(x) => Ok(Self::EndBlock(x)), + Request::Commit => Ok(Self::Commit), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +impl From for Request { + fn from(req: MempoolRequest) -> Self { + match req { + MempoolRequest::CheckTx(x) => Self::CheckTx(x), + } + } +} + +impl TryFrom for MempoolRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::CheckTx(x) => Ok(Self::CheckTx(x)), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +impl From for Request { + fn from(req: InfoRequest) -> Self { + match req { + InfoRequest::Info(x) => Self::Info(x), + InfoRequest::Query(x) => Self::Query(x), + InfoRequest::Echo(x) => Self::Echo(x), + InfoRequest::SetOption(x) => Self::SetOption(x), + } + } +} + +impl TryFrom for InfoRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::Info(x) => Ok(Self::Info(x)), + Request::Query(x) => Ok(Self::Query(x)), + Request::Echo(x) => Ok(Self::Echo(x)), + Request::SetOption(x) => Ok(Self::SetOption(x)), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +impl From for Request { + fn from(req: SnapshotRequest) -> Self { + match req { + SnapshotRequest::ListSnapshots => Self::ListSnapshots, + SnapshotRequest::OfferSnapshot(x) => Self::OfferSnapshot(x), + SnapshotRequest::LoadSnapshotChunk(x) => Self::LoadSnapshotChunk(x), + SnapshotRequest::ApplySnapshotChunk(x) => Self::ApplySnapshotChunk(x), + } + } +} + +impl TryFrom for SnapshotRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::ListSnapshots => Ok(Self::ListSnapshots), + Request::OfferSnapshot(x) => Ok(Self::OfferSnapshot(x)), + Request::LoadSnapshotChunk(x) => Ok(Self::LoadSnapshotChunk(x)), + Request::ApplySnapshotChunk(x) => Ok(Self::ApplySnapshotChunk(x)), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +impl From for pb::Request { + fn from(request: Request) -> pb::Request { + use pb::request::Value; + let value = match request { + Request::Echo(x) => Some(Value::Echo(x.into())), + Request::Flush => Some(Value::Flush(Default::default())), + Request::Info(x) => Some(Value::Info(x.into())), + Request::SetOption(x) => Some(Value::SetOption(x.into())), + Request::InitChain(x) => Some(Value::InitChain(x.into())), + Request::Query(x) => Some(Value::Query(x.into())), + Request::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Request::CheckTx(x) => Some(Value::CheckTx(x.into())), + Request::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Request::EndBlock(x) => Some(Value::EndBlock(x.into())), + Request::Commit => Some(Value::Commit(Default::default())), + Request::ListSnapshots => Some(Value::ListSnapshots(Default::default())), + Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + }; + pb::Request { value } + } +} + +impl TryFrom for Request { + type Error = Error; + + fn try_from(request: pb::Request) -> Result { + use pb::request::Value; + match request.value { + Some(Value::Echo(x)) => Ok(Request::Echo(x.try_into()?)), + Some(Value::Flush(pb::RequestFlush {})) => Ok(Request::Flush), + Some(Value::Info(x)) => Ok(Request::Info(x.try_into()?)), + Some(Value::SetOption(x)) => Ok(Request::SetOption(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Request::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Request::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Request::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Request::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Request::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Request::EndBlock(x.try_into()?)), + Some(Value::Commit(pb::RequestCommit {})) => Ok(Request::Commit), + Some(Value::ListSnapshots(pb::RequestListSnapshots {})) => Ok(Request::ListSnapshots), + Some(Value::OfferSnapshot(x)) => Ok(Request::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Request::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => Ok(Request::ApplySnapshotChunk(x.try_into()?)), + None => Err(crate::Error::missing_data()), + } + } +} + +impl Protobuf for Request {} diff --git a/tendermint/src/v0_34/abci/response.rs b/tendermint/src/v0_34/abci/response.rs new file mode 100644 index 000000000..5efdf1466 --- /dev/null +++ b/tendermint/src/v0_34/abci/response.rs @@ -0,0 +1,196 @@ +pub use crate::abci::response::{ + ApplySnapshotChunk, BeginBlock, CheckTx, Commit, DeliverTx, Echo, EndBlock, Exception, Info, + InitChain, ListSnapshots, LoadSnapshotChunk, OfferSnapshot, Query, SetOption, +}; +use crate::abci::response::{ConsensusResponse, InfoResponse, MempoolResponse, SnapshotResponse}; +use crate::Error; + +/// All possible ABCI responses for this protocol version. +#[derive(Clone, PartialEq, Eq, Debug)] +pub enum Response { + #[doc = include_str!("../../abci/doc/response-exception.md")] + Exception(Exception), + #[doc = include_str!("../../abci/doc/response-echo.md")] + Echo(Echo), + #[doc = include_str!("../../abci/doc/response-flush.md")] + Flush, + #[doc = include_str!("../../abci/doc/response-info.md")] + Info(Info), + #[doc = include_str!("../../abci/doc/response-setoption.md")] + SetOption(SetOption), + #[doc = include_str!("../../abci/doc/response-initchain.md")] + InitChain(InitChain), + #[doc = include_str!("../../abci/doc/response-query.md")] + Query(Query), + #[doc = include_str!("../../abci/doc/response-beginblock.md")] + BeginBlock(BeginBlock), + #[doc = include_str!("../../abci/doc/response-checktx.md")] + CheckTx(CheckTx), + #[doc = include_str!("../../abci/doc/response-delivertx.md")] + DeliverTx(DeliverTx), + #[doc = include_str!("../../abci/doc/response-endblock.md")] + EndBlock(EndBlock), + #[doc = include_str!("../../abci/doc/response-commit.md")] + Commit(Commit), + #[doc = include_str!("../../abci/doc/response-listsnapshots.md")] + ListSnapshots(ListSnapshots), + #[doc = include_str!("../../abci/doc/response-offersnapshot.md")] + OfferSnapshot(OfferSnapshot), + #[doc = include_str!("../../abci/doc/response-loadsnapshotchunk.md")] + LoadSnapshotChunk(LoadSnapshotChunk), + #[doc = include_str!("../../abci/doc/response-applysnapshotchunk.md")] + ApplySnapshotChunk(ApplySnapshotChunk), +} + +impl From for Response { + fn from(req: ConsensusResponse) -> Self { + match req { + ConsensusResponse::InitChain(x) => Self::InitChain(x), + ConsensusResponse::BeginBlock(x) => Self::BeginBlock(x), + ConsensusResponse::DeliverTx(x) => Self::DeliverTx(x), + ConsensusResponse::EndBlock(x) => Self::EndBlock(x), + ConsensusResponse::Commit(x) => Self::Commit(x), + } + } +} + +impl TryFrom for ConsensusResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::InitChain(x) => Ok(Self::InitChain(x)), + Response::BeginBlock(x) => Ok(Self::BeginBlock(x)), + Response::DeliverTx(x) => Ok(Self::DeliverTx(x)), + Response::EndBlock(x) => Ok(Self::EndBlock(x)), + Response::Commit(x) => Ok(Self::Commit(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +impl From for Response { + fn from(req: MempoolResponse) -> Self { + match req { + MempoolResponse::CheckTx(x) => Self::CheckTx(x), + } + } +} + +impl TryFrom for MempoolResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::CheckTx(x) => Ok(Self::CheckTx(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +impl From for Response { + fn from(req: InfoResponse) -> Self { + match req { + InfoResponse::Echo(x) => Self::Echo(x), + InfoResponse::Info(x) => Self::Info(x), + InfoResponse::Query(x) => Self::Query(x), + InfoResponse::SetOption(x) => Self::SetOption(x), + } + } +} + +impl TryFrom for InfoResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::Echo(x) => Ok(Self::Echo(x)), + Response::Info(x) => Ok(Self::Info(x)), + Response::Query(x) => Ok(Self::Query(x)), + Response::SetOption(x) => Ok(Self::SetOption(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +impl From for Response { + fn from(req: SnapshotResponse) -> Self { + match req { + SnapshotResponse::ListSnapshots(x) => Self::ListSnapshots(x), + SnapshotResponse::OfferSnapshot(x) => Self::OfferSnapshot(x), + SnapshotResponse::LoadSnapshotChunk(x) => Self::LoadSnapshotChunk(x), + SnapshotResponse::ApplySnapshotChunk(x) => Self::ApplySnapshotChunk(x), + } + } +} + +impl TryFrom for SnapshotResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::ListSnapshots(x) => Ok(Self::ListSnapshots(x)), + Response::OfferSnapshot(x) => Ok(Self::OfferSnapshot(x)), + Response::LoadSnapshotChunk(x) => Ok(Self::LoadSnapshotChunk(x)), + Response::ApplySnapshotChunk(x) => Ok(Self::ApplySnapshotChunk(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +use tendermint_proto::v0_34::abci as pb; +use tendermint_proto::Protobuf; + +impl From for pb::Response { + fn from(response: Response) -> pb::Response { + use pb::response::Value; + let value = match response { + Response::Exception(x) => Some(Value::Exception(x.into())), + Response::Echo(x) => Some(Value::Echo(x.into())), + Response::Flush => Some(Value::Flush(Default::default())), + Response::Info(x) => Some(Value::Info(x.into())), + Response::SetOption(x) => Some(Value::SetOption(x.into())), + Response::InitChain(x) => Some(Value::InitChain(x.into())), + Response::Query(x) => Some(Value::Query(x.into())), + Response::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Response::CheckTx(x) => Some(Value::CheckTx(x.into())), + Response::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Response::EndBlock(x) => Some(Value::EndBlock(x.into())), + Response::Commit(x) => Some(Value::Commit(x.into())), + Response::ListSnapshots(x) => Some(Value::ListSnapshots(x.into())), + Response::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Response::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + }; + pb::Response { value } + } +} + +impl TryFrom for Response { + type Error = Error; + + fn try_from(response: pb::Response) -> Result { + use pb::response::Value; + match response.value { + Some(Value::Exception(x)) => Ok(Response::Exception(x.try_into()?)), + Some(Value::Echo(x)) => Ok(Response::Echo(x.try_into()?)), + Some(Value::Flush(_)) => Ok(Response::Flush), + Some(Value::Info(x)) => Ok(Response::Info(x.try_into()?)), + Some(Value::SetOption(x)) => Ok(Response::SetOption(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Response::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Response::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Response::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Response::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Response::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Response::EndBlock(x.try_into()?)), + Some(Value::Commit(x)) => Ok(Response::Commit(x.try_into()?)), + Some(Value::ListSnapshots(x)) => Ok(Response::ListSnapshots(x.try_into()?)), + Some(Value::OfferSnapshot(x)) => Ok(Response::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Response::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => Ok(Response::ApplySnapshotChunk(x.try_into()?)), + None => Err(crate::Error::missing_data()), + } + } +} + +impl Protobuf for Response {} diff --git a/tendermint/src/v0_37.rs b/tendermint/src/v0_37.rs new file mode 100644 index 000000000..c52eb0a4c --- /dev/null +++ b/tendermint/src/v0_37.rs @@ -0,0 +1 @@ +pub mod abci; diff --git a/tendermint/src/v0_37/abci.rs b/tendermint/src/v0_37/abci.rs new file mode 100644 index 000000000..601e534df --- /dev/null +++ b/tendermint/src/v0_37/abci.rs @@ -0,0 +1,5 @@ +pub mod request; +pub mod response; + +pub use request::Request; +pub use response::Response; diff --git a/tendermint/src/v0_37/abci/request.rs b/tendermint/src/v0_37/abci/request.rs new file mode 100644 index 000000000..faf52830c --- /dev/null +++ b/tendermint/src/v0_37/abci/request.rs @@ -0,0 +1,223 @@ +use tendermint_proto::v0_37::abci as pb; +use tendermint_proto::Protobuf; + +use crate::abci::request::{ConsensusRequest, InfoRequest, MempoolRequest, SnapshotRequest}; +use crate::abci::MethodKind; +use crate::Error; + +pub use crate::abci::request::{ + ApplySnapshotChunk, BeginBlock, CheckTx, CheckTxKind, DeliverTx, Echo, EndBlock, Info, + InitChain, LoadSnapshotChunk, OfferSnapshot, PrepareProposal, ProcessProposal, Query, +}; + +/// All possible ABCI requests. +#[allow(clippy::large_enum_variant)] +#[derive(Clone, PartialEq, Eq, Debug)] +pub enum Request { + #[doc = include_str!("../../abci/doc/request-echo.md")] + Echo(Echo), + #[doc = include_str!("../../abci/doc/request-flush.md")] + Flush, + #[doc = include_str!("../../abci/doc/request-info.md")] + Info(Info), + #[doc = include_str!("../../abci/doc/request-initchain.md")] + InitChain(InitChain), + #[doc = include_str!("../../abci/doc/request-query.md")] + Query(Query), + #[doc = include_str!("../../abci/doc/request-beginblock.md")] + BeginBlock(BeginBlock), + #[doc = include_str!("../../abci/doc/request-checktx.md")] + CheckTx(CheckTx), + #[doc = include_str!("../../abci/doc/request-delivertx.md")] + DeliverTx(DeliverTx), + #[doc = include_str!("../../abci/doc/request-endblock.md")] + EndBlock(EndBlock), + #[doc = include_str!("../../abci/doc/request-commit.md")] + Commit, + #[doc = include_str!("../../abci/doc/request-listsnapshots.md")] + ListSnapshots, + #[doc = include_str!("../../abci/doc/request-offersnapshot.md")] + OfferSnapshot(OfferSnapshot), + #[doc = include_str!("../../abci/doc/request-loadsnapshotchunk.md")] + LoadSnapshotChunk(LoadSnapshotChunk), + #[doc = include_str!("../../abci/doc/request-applysnapshotchunk.md")] + ApplySnapshotChunk(ApplySnapshotChunk), + #[doc = include_str!("../../abci/doc/request-prepareproposal.md")] + PrepareProposal(PrepareProposal), + #[doc = include_str!("../../abci/doc/request-processproposal.md")] + ProcessProposal(ProcessProposal), +} + +impl Request { + /// Get the method kind for this request. + pub fn kind(&self) -> MethodKind { + use Request::*; + match self { + Flush => MethodKind::Flush, + InitChain(_) => MethodKind::Consensus, + BeginBlock(_) => MethodKind::Consensus, + DeliverTx(_) => MethodKind::Consensus, + EndBlock(_) => MethodKind::Consensus, + Commit => MethodKind::Consensus, + PrepareProposal(_) => MethodKind::Consensus, + ProcessProposal(_) => MethodKind::Consensus, + CheckTx(_) => MethodKind::Mempool, + ListSnapshots => MethodKind::Snapshot, + OfferSnapshot(_) => MethodKind::Snapshot, + LoadSnapshotChunk(_) => MethodKind::Snapshot, + ApplySnapshotChunk(_) => MethodKind::Snapshot, + Info(_) => MethodKind::Info, + Query(_) => MethodKind::Info, + Echo(_) => MethodKind::Info, + } + } +} + +impl From for Request { + fn from(req: ConsensusRequest) -> Self { + match req { + ConsensusRequest::InitChain(x) => Self::InitChain(x), + ConsensusRequest::BeginBlock(x) => Self::BeginBlock(x), + ConsensusRequest::DeliverTx(x) => Self::DeliverTx(x), + ConsensusRequest::EndBlock(x) => Self::EndBlock(x), + ConsensusRequest::Commit => Self::Commit, + } + } +} + +impl TryFrom for ConsensusRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::InitChain(x) => Ok(Self::InitChain(x)), + Request::BeginBlock(x) => Ok(Self::BeginBlock(x)), + Request::DeliverTx(x) => Ok(Self::DeliverTx(x)), + Request::EndBlock(x) => Ok(Self::EndBlock(x)), + Request::Commit => Ok(Self::Commit), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +impl From for Request { + fn from(req: MempoolRequest) -> Self { + match req { + MempoolRequest::CheckTx(x) => Self::CheckTx(x), + } + } +} + +impl TryFrom for MempoolRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::CheckTx(x) => Ok(Self::CheckTx(x)), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +impl From for Request { + fn from(req: InfoRequest) -> Self { + match req { + InfoRequest::Info(x) => Self::Info(x), + InfoRequest::Query(x) => Self::Query(x), + InfoRequest::Echo(x) => Self::Echo(x), + InfoRequest::SetOption(_) => panic!("cannot be used with v0.37"), + } + } +} + +impl TryFrom for InfoRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::Info(x) => Ok(Self::Info(x)), + Request::Query(x) => Ok(Self::Query(x)), + Request::Echo(x) => Ok(Self::Echo(x)), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +impl From for Request { + fn from(req: SnapshotRequest) -> Self { + match req { + SnapshotRequest::ListSnapshots => Self::ListSnapshots, + SnapshotRequest::OfferSnapshot(x) => Self::OfferSnapshot(x), + SnapshotRequest::LoadSnapshotChunk(x) => Self::LoadSnapshotChunk(x), + SnapshotRequest::ApplySnapshotChunk(x) => Self::ApplySnapshotChunk(x), + } + } +} + +impl TryFrom for SnapshotRequest { + type Error = Error; + fn try_from(req: Request) -> Result { + match req { + Request::ListSnapshots => Ok(Self::ListSnapshots), + Request::OfferSnapshot(x) => Ok(Self::OfferSnapshot(x)), + Request::LoadSnapshotChunk(x) => Ok(Self::LoadSnapshotChunk(x)), + Request::ApplySnapshotChunk(x) => Ok(Self::ApplySnapshotChunk(x)), + _ => Err(Error::invalid_abci_request_type()), + } + } +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +impl From for pb::Request { + fn from(request: Request) -> pb::Request { + use pb::request::Value; + let value = match request { + Request::Echo(x) => Some(Value::Echo(x.into())), + Request::Flush => Some(Value::Flush(Default::default())), + Request::Info(x) => Some(Value::Info(x.into())), + Request::InitChain(x) => Some(Value::InitChain(x.into())), + Request::Query(x) => Some(Value::Query(x.into())), + Request::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Request::CheckTx(x) => Some(Value::CheckTx(x.into())), + Request::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Request::EndBlock(x) => Some(Value::EndBlock(x.into())), + Request::Commit => Some(Value::Commit(Default::default())), + Request::ListSnapshots => Some(Value::ListSnapshots(Default::default())), + Request::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Request::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Request::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + Request::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), + Request::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), + }; + pb::Request { value } + } +} + +impl TryFrom for Request { + type Error = Error; + + fn try_from(request: pb::Request) -> Result { + use pb::request::Value; + match request.value { + Some(Value::Echo(x)) => Ok(Request::Echo(x.try_into()?)), + Some(Value::Flush(pb::RequestFlush {})) => Ok(Request::Flush), + Some(Value::Info(x)) => Ok(Request::Info(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Request::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Request::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Request::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Request::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Request::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Request::EndBlock(x.try_into()?)), + Some(Value::Commit(pb::RequestCommit {})) => Ok(Request::Commit), + Some(Value::ListSnapshots(pb::RequestListSnapshots {})) => Ok(Request::ListSnapshots), + Some(Value::OfferSnapshot(x)) => Ok(Request::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Request::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => Ok(Request::ApplySnapshotChunk(x.try_into()?)), + Some(Value::PrepareProposal(x)) => Ok(Request::PrepareProposal(x.try_into()?)), + Some(Value::ProcessProposal(x)) => Ok(Request::ProcessProposal(x.try_into()?)), + None => Err(crate::Error::missing_data()), + } + } +} + +impl Protobuf for Request {} diff --git a/tendermint/src/v0_37/abci/response.rs b/tendermint/src/v0_37/abci/response.rs new file mode 100644 index 000000000..bfe7de822 --- /dev/null +++ b/tendermint/src/v0_37/abci/response.rs @@ -0,0 +1,200 @@ +pub use crate::abci::response::{ + ApplySnapshotChunk, BeginBlock, CheckTx, Commit, DeliverTx, Echo, EndBlock, Exception, Info, + InitChain, ListSnapshots, LoadSnapshotChunk, OfferSnapshot, PrepareProposal, ProcessProposal, + Query, +}; +use crate::abci::response::{ConsensusResponse, InfoResponse, MempoolResponse, SnapshotResponse}; +use crate::Error; + +/// All possible ABCI responses for this protocol version. +#[derive(Clone, PartialEq, Eq, Debug)] +pub enum Response { + #[doc = include_str!("../../abci/doc/response-exception.md")] + Exception(Exception), + #[doc = include_str!("../../abci/doc/response-echo.md")] + Echo(Echo), + #[doc = include_str!("../../abci/doc/response-flush.md")] + Flush, + #[doc = include_str!("../../abci/doc/response-info.md")] + Info(Info), + #[doc = include_str!("../../abci/doc/response-initchain.md")] + InitChain(InitChain), + #[doc = include_str!("../../abci/doc/response-query.md")] + Query(Query), + #[doc = include_str!("../../abci/doc/response-beginblock.md")] + BeginBlock(BeginBlock), + #[doc = include_str!("../../abci/doc/response-checktx.md")] + CheckTx(CheckTx), + #[doc = include_str!("../../abci/doc/response-delivertx.md")] + DeliverTx(DeliverTx), + #[doc = include_str!("../../abci/doc/response-endblock.md")] + EndBlock(EndBlock), + #[doc = include_str!("../../abci/doc/response-commit.md")] + Commit(Commit), + #[doc = include_str!("../../abci/doc/response-listsnapshots.md")] + ListSnapshots(ListSnapshots), + #[doc = include_str!("../../abci/doc/response-offersnapshot.md")] + OfferSnapshot(OfferSnapshot), + #[doc = include_str!("../../abci/doc/response-loadsnapshotchunk.md")] + LoadSnapshotChunk(LoadSnapshotChunk), + #[doc = include_str!("../../abci/doc/response-applysnapshotchunk.md")] + ApplySnapshotChunk(ApplySnapshotChunk), + #[doc = include_str!("../../abci/doc/response-prepareproposal.md")] + PrepareProposal(PrepareProposal), + #[doc = include_str!("../../abci/doc/response-processproposal.md")] + ProcessProposal(ProcessProposal), +} + +impl From for Response { + fn from(req: ConsensusResponse) -> Self { + match req { + ConsensusResponse::InitChain(x) => Self::InitChain(x), + ConsensusResponse::BeginBlock(x) => Self::BeginBlock(x), + ConsensusResponse::DeliverTx(x) => Self::DeliverTx(x), + ConsensusResponse::EndBlock(x) => Self::EndBlock(x), + ConsensusResponse::Commit(x) => Self::Commit(x), + } + } +} + +impl TryFrom for ConsensusResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::InitChain(x) => Ok(Self::InitChain(x)), + Response::BeginBlock(x) => Ok(Self::BeginBlock(x)), + Response::DeliverTx(x) => Ok(Self::DeliverTx(x)), + Response::EndBlock(x) => Ok(Self::EndBlock(x)), + Response::Commit(x) => Ok(Self::Commit(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +impl From for Response { + fn from(req: MempoolResponse) -> Self { + match req { + MempoolResponse::CheckTx(x) => Self::CheckTx(x), + } + } +} + +impl TryFrom for MempoolResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::CheckTx(x) => Ok(Self::CheckTx(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +impl From for Response { + fn from(req: InfoResponse) -> Self { + match req { + InfoResponse::Echo(x) => Self::Echo(x), + InfoResponse::Info(x) => Self::Info(x), + InfoResponse::Query(x) => Self::Query(x), + InfoResponse::SetOption(_) => panic!("cannot be used with v0.37"), + } + } +} + +impl TryFrom for InfoResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::Echo(x) => Ok(Self::Echo(x)), + Response::Info(x) => Ok(Self::Info(x)), + Response::Query(x) => Ok(Self::Query(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +impl From for Response { + fn from(req: SnapshotResponse) -> Self { + match req { + SnapshotResponse::ListSnapshots(x) => Self::ListSnapshots(x), + SnapshotResponse::OfferSnapshot(x) => Self::OfferSnapshot(x), + SnapshotResponse::LoadSnapshotChunk(x) => Self::LoadSnapshotChunk(x), + SnapshotResponse::ApplySnapshotChunk(x) => Self::ApplySnapshotChunk(x), + } + } +} + +impl TryFrom for SnapshotResponse { + type Error = Error; + fn try_from(req: Response) -> Result { + match req { + Response::ListSnapshots(x) => Ok(Self::ListSnapshots(x)), + Response::OfferSnapshot(x) => Ok(Self::OfferSnapshot(x)), + Response::LoadSnapshotChunk(x) => Ok(Self::LoadSnapshotChunk(x)), + Response::ApplySnapshotChunk(x) => Ok(Self::ApplySnapshotChunk(x)), + _ => Err(Error::invalid_abci_response_type()), + } + } +} + +// ============================================================================= +// Protobuf conversions +// ============================================================================= + +use tendermint_proto::v0_37::abci as pb; +use tendermint_proto::Protobuf; + +impl From for pb::Response { + fn from(response: Response) -> pb::Response { + use pb::response::Value; + let value = match response { + Response::Exception(x) => Some(Value::Exception(x.into())), + Response::Echo(x) => Some(Value::Echo(x.into())), + Response::Flush => Some(Value::Flush(Default::default())), + Response::Info(x) => Some(Value::Info(x.into())), + Response::InitChain(x) => Some(Value::InitChain(x.into())), + Response::Query(x) => Some(Value::Query(x.into())), + Response::BeginBlock(x) => Some(Value::BeginBlock(x.into())), + Response::CheckTx(x) => Some(Value::CheckTx(x.into())), + Response::DeliverTx(x) => Some(Value::DeliverTx(x.into())), + Response::EndBlock(x) => Some(Value::EndBlock(x.into())), + Response::Commit(x) => Some(Value::Commit(x.into())), + Response::ListSnapshots(x) => Some(Value::ListSnapshots(x.into())), + Response::OfferSnapshot(x) => Some(Value::OfferSnapshot(x.into())), + Response::LoadSnapshotChunk(x) => Some(Value::LoadSnapshotChunk(x.into())), + Response::ApplySnapshotChunk(x) => Some(Value::ApplySnapshotChunk(x.into())), + Response::PrepareProposal(x) => Some(Value::PrepareProposal(x.into())), + Response::ProcessProposal(x) => Some(Value::ProcessProposal(x.into())), + }; + pb::Response { value } + } +} + +impl TryFrom for Response { + type Error = Error; + + fn try_from(response: pb::Response) -> Result { + use pb::response::Value; + match response.value { + Some(Value::Exception(x)) => Ok(Response::Exception(x.try_into()?)), + Some(Value::Echo(x)) => Ok(Response::Echo(x.try_into()?)), + Some(Value::Flush(_)) => Ok(Response::Flush), + Some(Value::Info(x)) => Ok(Response::Info(x.try_into()?)), + Some(Value::InitChain(x)) => Ok(Response::InitChain(x.try_into()?)), + Some(Value::Query(x)) => Ok(Response::Query(x.try_into()?)), + Some(Value::BeginBlock(x)) => Ok(Response::BeginBlock(x.try_into()?)), + Some(Value::CheckTx(x)) => Ok(Response::CheckTx(x.try_into()?)), + Some(Value::DeliverTx(x)) => Ok(Response::DeliverTx(x.try_into()?)), + Some(Value::EndBlock(x)) => Ok(Response::EndBlock(x.try_into()?)), + Some(Value::Commit(x)) => Ok(Response::Commit(x.try_into()?)), + Some(Value::ListSnapshots(x)) => Ok(Response::ListSnapshots(x.try_into()?)), + Some(Value::OfferSnapshot(x)) => Ok(Response::OfferSnapshot(x.try_into()?)), + Some(Value::LoadSnapshotChunk(x)) => Ok(Response::LoadSnapshotChunk(x.try_into()?)), + Some(Value::ApplySnapshotChunk(x)) => Ok(Response::ApplySnapshotChunk(x.try_into()?)), + Some(Value::PrepareProposal(x)) => Ok(Response::PrepareProposal(x.try_into()?)), + Some(Value::ProcessProposal(x)) => Ok(Response::ProcessProposal(x.try_into()?)), + None => Err(crate::Error::missing_data()), + } + } +} + +impl Protobuf for Response {} From 9730636c86d4be447ffef7d90b6e6d4fb3a9c0a0 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 28 Nov 2022 14:09:03 +0200 Subject: [PATCH 24/77] Remove last version aliases of Request, Response Need to check where we depend in downstream branches. --- tendermint/src/abci.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tendermint/src/abci.rs b/tendermint/src/abci.rs index 72a179ff7..3fa4de415 100644 --- a/tendermint/src/abci.rs +++ b/tendermint/src/abci.rs @@ -44,8 +44,8 @@ pub mod request; pub mod response; pub mod types; -pub use crate::v0_37::abci::request::Request; -pub use crate::v0_37::abci::response::Response; +// pub use crate::v0_37::abci::request::Request; +// pub use crate::v0_37::abci::response::Response; pub use event::{Event, EventAttribute, EventAttributeIndexExt}; From d7ee353f16d08326f01750994bf95d1f2a6e6440 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Sun, 18 Dec 2022 20:11:25 +0200 Subject: [PATCH 25/77] Re-generate protos with prost-build 0.11.4 Also update v0_34 to 0.34.24. --- proto/src/prost/v0_34/tendermint.abci.rs | 409 +++++++++------- .../src/prost/v0_34/tendermint.blockchain.rs | 32 +- proto/src/prost/v0_34/tendermint.consensus.rs | 127 ++--- proto/src/prost/v0_34/tendermint.crypto.rs | 49 +- proto/src/prost/v0_34/tendermint.libs.bits.rs | 5 +- proto/src/prost/v0_34/tendermint.mempool.rs | 9 +- proto/src/prost/v0_34/tendermint.p2p.rs | 81 ++-- proto/src/prost/v0_34/tendermint.privval.rs | 61 ++- proto/src/prost/v0_34/tendermint.rpc.grpc.rs | 22 +- proto/src/prost/v0_34/tendermint.state.rs | 56 ++- proto/src/prost/v0_34/tendermint.statesync.rs | 45 +- proto/src/prost/v0_34/tendermint.store.rs | 5 +- proto/src/prost/v0_34/tendermint.types.rs | 269 ++++++----- proto/src/prost/v0_34/tendermint.version.rs | 10 +- proto/src/prost/v0_37/tendermint.abci.rs | 453 ++++++++++-------- proto/src/prost/v0_37/tendermint.blocksync.rs | 32 +- proto/src/prost/v0_37/tendermint.consensus.rs | 127 ++--- proto/src/prost/v0_37/tendermint.crypto.rs | 49 +- proto/src/prost/v0_37/tendermint.libs.bits.rs | 5 +- proto/src/prost/v0_37/tendermint.mempool.rs | 9 +- proto/src/prost/v0_37/tendermint.p2p.rs | 81 ++-- proto/src/prost/v0_37/tendermint.privval.rs | 61 ++- proto/src/prost/v0_37/tendermint.rpc.grpc.rs | 22 +- proto/src/prost/v0_37/tendermint.state.rs | 56 ++- proto/src/prost/v0_37/tendermint.statesync.rs | 45 +- proto/src/prost/v0_37/tendermint.store.rs | 5 +- proto/src/prost/v0_37/tendermint.types.rs | 267 ++++++----- proto/src/prost/v0_37/tendermint.version.rs | 10 +- proto/src/tendermint.rs | 1 + proto/src/tendermint/v0_34.rs | 2 +- tools/proto-compiler/Cargo.toml | 2 +- tools/proto-compiler/src/constants.rs | 2 +- 32 files changed, 1361 insertions(+), 1048 deletions(-) diff --git a/proto/src/prost/v0_34/tendermint.abci.rs b/proto/src/prost/v0_34/tendermint.abci.rs index 04e96b7df..240575c56 100644 --- a/proto/src/prost/v0_34/tendermint.abci.rs +++ b/proto/src/prost/v0_34/tendermint.abci.rs @@ -1,378 +1,413 @@ -// This file is copied from -// NOTE: When using custom types, mind the warnings. -// - -// ---------------------------------------- -// Request types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Request { - #[prost(oneof="request::Value", tags="1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15")] + #[prost( + oneof = "request::Value", + tags = "1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15" + )] pub value: ::core::option::Option, } /// Nested message and enum types in `Request`. pub mod request { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Echo(super::RequestEcho), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] Flush(super::RequestFlush), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Info(super::RequestInfo), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] SetOption(super::RequestSetOption), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] InitChain(super::RequestInitChain), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] Query(super::RequestQuery), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] BeginBlock(super::RequestBeginBlock), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] CheckTx(super::RequestCheckTx), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] DeliverTx(super::RequestDeliverTx), - #[prost(message, tag="10")] + #[prost(message, tag = "10")] EndBlock(super::RequestEndBlock), - #[prost(message, tag="11")] + #[prost(message, tag = "11")] Commit(super::RequestCommit), - #[prost(message, tag="12")] + #[prost(message, tag = "12")] ListSnapshots(super::RequestListSnapshots), - #[prost(message, tag="13")] + #[prost(message, tag = "13")] OfferSnapshot(super::RequestOfferSnapshot), - #[prost(message, tag="14")] + #[prost(message, tag = "14")] LoadSnapshotChunk(super::RequestLoadSnapshotChunk), - #[prost(message, tag="15")] + #[prost(message, tag = "15")] ApplySnapshotChunk(super::RequestApplySnapshotChunk), } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEcho { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub message: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestFlush { -} +pub struct RequestFlush {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInfo { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] pub block_version: u64, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] pub p2p_version: u64, } /// nondeterministic +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestSetOption { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub key: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub value: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInitChain { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub time: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] pub app_state_bytes: ::prost::bytes::Bytes, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub initial_height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestQuery { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub data: ::prost::bytes::Bytes, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub path: ::prost::alloc::string::String, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub height: i64, - #[prost(bool, tag="4")] + #[prost(bool, tag = "4")] pub prove: bool, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestBeginBlock { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub hash: ::prost::bytes::Bytes, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub header: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub last_commit_info: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] pub byzantine_validators: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestCheckTx { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub tx: ::prost::bytes::Bytes, - #[prost(enumeration="CheckTxType", tag="2")] + #[prost(enumeration = "CheckTxType", tag = "2")] pub r#type: i32, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestDeliverTx { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub tx: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEndBlock { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestCommit { -} +pub struct RequestCommit {} /// lists available snapshots +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestListSnapshots { -} +pub struct RequestListSnapshots {} /// offers a snapshot to the application +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestOfferSnapshot { /// snapshot offered by peers - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub snapshot: ::core::option::Option, /// light client-verified app hash for snapshot height - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub app_hash: ::prost::bytes::Bytes, } /// loads a snapshot chunk +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestLoadSnapshotChunk { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunk: u32, } /// Applies a snapshot chunk +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestApplySnapshotChunk { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub index: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub chunk: ::prost::bytes::Bytes, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub sender: ::prost::alloc::string::String, } -// ---------------------------------------- -// Response types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Response { - #[prost(oneof="response::Value", tags="1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16")] + #[prost( + oneof = "response::Value", + tags = "1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16" + )] pub value: ::core::option::Option, } /// Nested message and enum types in `Response`. pub mod response { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Exception(super::ResponseException), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] Echo(super::ResponseEcho), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Flush(super::ResponseFlush), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] Info(super::ResponseInfo), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] SetOption(super::ResponseSetOption), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] InitChain(super::ResponseInitChain), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] Query(super::ResponseQuery), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] BeginBlock(super::ResponseBeginBlock), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] CheckTx(super::ResponseCheckTx), - #[prost(message, tag="10")] + #[prost(message, tag = "10")] DeliverTx(super::ResponseDeliverTx), - #[prost(message, tag="11")] + #[prost(message, tag = "11")] EndBlock(super::ResponseEndBlock), - #[prost(message, tag="12")] + #[prost(message, tag = "12")] Commit(super::ResponseCommit), - #[prost(message, tag="13")] + #[prost(message, tag = "13")] ListSnapshots(super::ResponseListSnapshots), - #[prost(message, tag="14")] + #[prost(message, tag = "14")] OfferSnapshot(super::ResponseOfferSnapshot), - #[prost(message, tag="15")] + #[prost(message, tag = "15")] LoadSnapshotChunk(super::ResponseLoadSnapshotChunk), - #[prost(message, tag="16")] + #[prost(message, tag = "16")] ApplySnapshotChunk(super::ResponseApplySnapshotChunk), } } /// nondeterministic +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseException { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub error: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEcho { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub message: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct ResponseFlush { -} +pub struct ResponseFlush {} #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseInfo { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] #[serde(default)] pub data: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] #[serde(default)] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] #[serde(with = "crate::serializers::from_str", default)] pub app_version: u64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str", default)] pub last_block_height: i64, - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] #[serde(default)] #[serde(skip_serializing_if = "bytes::Bytes::is_empty")] pub last_block_app_hash: ::prost::bytes::Bytes, } /// nondeterministic +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseSetOption { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, /// bytes data = 2; - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseInitChain { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes="bytes", tag="3")] + #[prost(bytes = "bytes", tag = "3")] pub app_hash: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseQuery { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, /// bytes data = 2; // use "value" instead. /// /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub index: i64, - #[prost(bytes="bytes", tag="6")] + #[prost(bytes = "bytes", tag = "6")] pub key: ::prost::bytes::Bytes, - #[prost(bytes="bytes", tag="7")] + #[prost(bytes = "bytes", tag = "7")] pub value: ::prost::bytes::Bytes, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub proof_ops: ::core::option::Option, - #[prost(int64, tag="9")] + #[prost(int64, tag = "9")] pub height: i64, - #[prost(string, tag="10")] + #[prost(string, tag = "10")] pub codespace: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseBeginBlock { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub events: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCheckTx { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub gas_wanted: i64, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub gas_used: i64, - #[prost(message, repeated, tag="7")] + #[prost(message, repeated, tag = "7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag="8")] + #[prost(string, tag = "8")] pub codespace: ::prost::alloc::string::String, - #[prost(string, tag="9")] + #[prost(string, tag = "9")] pub sender: ::prost::alloc::string::String, - #[prost(int64, tag="10")] + #[prost(int64, tag = "10")] pub priority: i64, /// mempool_error is set by Tendermint. /// ABCI applictions creating a ResponseCheckTX should not set mempool_error. - #[prost(string, tag="11")] + #[prost(string, tag = "11")] pub mempool_error: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseDeliverTx { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub gas_wanted: i64, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub gas_used: i64, /// nondeterministic - #[prost(message, repeated, tag="7")] + #[prost(message, repeated, tag = "7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag="8")] + #[prost(string, tag = "8")] pub codespace: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEndBlock { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub validator_updates: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub consensus_param_updates: ::core::option::Option, - #[prost(message, repeated, tag="3")] + #[prost(message, repeated, tag = "3")] pub events: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCommit { /// reserve 1 - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub retain_height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseListSnapshots { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub snapshots: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseOfferSnapshot { - #[prost(enumeration="response_offer_snapshot::Result", tag="1")] + #[prost(enumeration = "response_offer_snapshot::Result", tag = "1")] pub result: i32, } /// Nested message and enum types in `ResponseOfferSnapshot`. pub mod response_offer_snapshot { - #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[derive( + Clone, + Copy, + Debug, + PartialEq, + Eq, + Hash, + PartialOrd, + Ord, + ::prost::Enumeration + )] #[repr(i32)] pub enum Result { /// Unknown result, abort all snapshot restoration @@ -405,25 +440,37 @@ pub mod response_offer_snapshot { } } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseLoadSnapshotChunk { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub chunk: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseApplySnapshotChunk { - #[prost(enumeration="response_apply_snapshot_chunk::Result", tag="1")] + #[prost(enumeration = "response_apply_snapshot_chunk::Result", tag = "1")] pub result: i32, /// Chunks to refetch and reapply - #[prost(uint32, repeated, tag="2")] + #[prost(uint32, repeated, tag = "2")] pub refetch_chunks: ::prost::alloc::vec::Vec, /// Chunk senders to reject and ban - #[prost(string, repeated, tag="3")] + #[prost(string, repeated, tag = "3")] pub reject_senders: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// Nested message and enum types in `ResponseApplySnapshotChunk`. pub mod response_apply_snapshot_chunk { - #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[derive( + Clone, + Copy, + Debug, + PartialEq, + Eq, + Hash, + PartialOrd, + Ord, + ::prost::Enumeration + )] #[repr(i32)] pub enum Result { /// Unknown result, abort all snapshot restoration @@ -456,143 +503,145 @@ pub mod response_apply_snapshot_chunk { } } } -// ---------------------------------------- -// Misc. - /// ConsensusParams contains all consensus-relevant parameters /// that can be adjusted by the abci app +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ConsensusParams { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub validator: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub version: ::core::option::Option, } /// BlockParams contains limits on the block size. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockParams { /// Note: must be greater than 0 - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_bytes: i64, /// Note: must be greater or equal to -1 - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub max_gas: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct LastCommitInfo { - #[prost(int32, tag="1")] + #[prost(int32, tag = "1")] pub round: i32, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub votes: ::prost::alloc::vec::Vec, } /// Event allows application developers to attach additional information to /// ResponseBeginBlock, ResponseEndBlock, ResponseCheckTx and ResponseDeliverTx. /// Later, transactions may be queried using these events. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Event { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub r#type: ::prost::alloc::string::String, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub attributes: ::prost::alloc::vec::Vec, } /// EventAttribute is a single key-value pair, associated with an event. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EventAttribute { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub key: ::prost::bytes::Bytes, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub value: ::prost::bytes::Bytes, /// nondeterministic - #[prost(bool, tag="3")] + #[prost(bool, tag = "3")] pub index: bool, } /// TxResult contains results of executing the transaction. /// /// One usage is indexing transaction results. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TxResult { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub index: u32, - #[prost(bytes="bytes", tag="3")] + #[prost(bytes = "bytes", tag = "3")] pub tx: ::prost::bytes::Bytes, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub result: ::core::option::Option, } -// ---------------------------------------- -// Blockchain Types - /// Validator +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Validator { /// The first 20 bytes of SHA256(public key) - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub address: ::prost::bytes::Bytes, /// PubKey pub_key = 2 \[(gogoproto.nullable)=false\]; /// /// The voting power - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub power: i64, } /// ValidatorUpdate +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorUpdate { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub power: i64, } /// VoteInfo +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub validator: ::core::option::Option, - #[prost(bool, tag="2")] + #[prost(bool, tag = "2")] pub signed_last_block: bool, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Evidence { - #[prost(enumeration="EvidenceType", tag="1")] + #[prost(enumeration = "EvidenceType", tag = "1")] pub r#type: i32, /// The offending validator - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub validator: ::core::option::Option, /// The height when the offense occurred - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub height: i64, /// The corresponding time where the offense occurred - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub time: ::core::option::Option, /// Total voting power of the validator set in case the ABCI application does /// not store historical validators. /// - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub total_voting_power: i64, } -// ---------------------------------------- -// State Sync Types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Snapshot { /// The height at which the snapshot was taken - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, /// The application-specific snapshot format - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, /// Number of chunks in the snapshot - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunks: u32, /// Arbitrary snapshot hash, equal only if identical - #[prost(bytes="bytes", tag="4")] + #[prost(bytes = "bytes", tag = "4")] pub hash: ::prost::bytes::Bytes, /// Arbitrary application metadata - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] pub metadata: ::prost::bytes::Bytes, } #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] diff --git a/proto/src/prost/v0_34/tendermint.blockchain.rs b/proto/src/prost/v0_34/tendermint.blockchain.rs index 492aa692e..4480ece49 100644 --- a/proto/src/prost/v0_34/tendermint.blockchain.rs +++ b/proto/src/prost/v0_34/tendermint.blockchain.rs @@ -1,51 +1,57 @@ /// BlockRequest requests a block for a specific height +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockRequest { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } /// NoBlockResponse informs the node that the peer does not have block at the requested height +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NoBlockResponse { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } /// BlockResponse returns block to the requested +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block: ::core::option::Option, } /// StatusRequest requests the status of a peer. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct StatusRequest { -} +pub struct StatusRequest {} /// StatusResponse is a peer response to inform their status. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct StatusResponse { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub base: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4, 5")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] BlockRequest(super::BlockRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] NoBlockResponse(super::NoBlockResponse), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] BlockResponse(super::BlockResponse), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] StatusRequest(super::StatusRequest), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] StatusResponse(super::StatusResponse), } } diff --git a/proto/src/prost/v0_34/tendermint.consensus.rs b/proto/src/prost/v0_34/tendermint.consensus.rs index 6f3fe8624..95237cc78 100644 --- a/proto/src/prost/v0_34/tendermint.consensus.rs +++ b/proto/src/prost/v0_34/tendermint.consensus.rs @@ -1,184 +1,201 @@ /// NewRoundStep is sent for every step taken in the ConsensusState. /// For every height/round/step transition +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NewRoundStep { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub step: u32, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub seconds_since_start_time: i64, - #[prost(int32, tag="5")] + #[prost(int32, tag = "5")] pub last_commit_round: i32, } /// NewValidBlock is sent when a validator observes a valid block B in some round r, /// i.e., there is a Proposal for block B and 2/3+ prevotes for the block B in the round r. /// In case the block is also committed, then IsCommit flag is set to true. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NewValidBlock { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub block_part_set_header: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_parts: ::core::option::Option, - #[prost(bool, tag="5")] + #[prost(bool, tag = "5")] pub is_commit: bool, } /// Proposal is sent when a new block is proposed. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proposal { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub proposal: ::core::option::Option, } /// ProposalPOL is sent when a previous proposal is re-proposed. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProposalPol { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub proposal_pol_round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proposal_pol: ::core::option::Option, } /// BlockPart is sent when gossipping a piece of the proposed block. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockPart { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub part: ::core::option::Option, } /// Vote is sent when voting for a proposal (or lack thereof). +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Vote { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote: ::core::option::Option, } /// HasVote is sent to indicate that a particular vote has been received. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct HasVote { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(enumeration="super::types::SignedMsgType", tag="3")] + #[prost(enumeration = "super::types::SignedMsgType", tag = "3")] pub r#type: i32, - #[prost(int32, tag="4")] + #[prost(int32, tag = "4")] pub index: i32, } /// VoteSetMaj23 is sent to indicate that a given BlockID has seen +2/3 votes. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteSetMaj23 { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(enumeration="super::types::SignedMsgType", tag="3")] + #[prost(enumeration = "super::types::SignedMsgType", tag = "3")] pub r#type: i32, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, } /// VoteSetBits is sent to communicate the bit-array of votes seen for the BlockID. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteSetBits { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(enumeration="super::types::SignedMsgType", tag="3")] + #[prost(enumeration = "super::types::SignedMsgType", tag = "3")] pub r#type: i32, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub votes: ::core::option::Option, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5, 6, 7, 8, 9")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4, 5, 6, 7, 8, 9")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] NewRoundStep(super::NewRoundStep), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] NewValidBlock(super::NewValidBlock), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Proposal(super::Proposal), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] ProposalPol(super::ProposalPol), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] BlockPart(super::BlockPart), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] Vote(super::Vote), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] HasVote(super::HasVote), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] VoteSetMaj23(super::VoteSetMaj23), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] VoteSetBits(super::VoteSetBits), } } /// MsgInfo are msgs from the reactor which may update the state +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct MsgInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub msg: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub peer_id: ::prost::alloc::string::String, } /// TimeoutInfo internally generated messages which may update the state +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TimeoutInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub duration: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, - #[prost(uint32, tag="4")] + #[prost(uint32, tag = "4")] pub step: u32, } /// EndHeight marks the end of the given height inside WAL. /// @internal used by scripts/wal2json util. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EndHeight { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct WalMessage { - #[prost(oneof="wal_message::Sum", tags="1, 2, 3, 4")] + #[prost(oneof = "wal_message::Sum", tags = "1, 2, 3, 4")] pub sum: ::core::option::Option, } /// Nested message and enum types in `WALMessage`. pub mod wal_message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] EventDataRoundState(super::super::types::EventDataRoundState), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] MsgInfo(super::MsgInfo), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] TimeoutInfo(super::TimeoutInfo), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] EndHeight(super::EndHeight), } } /// TimedWALMessage wraps WALMessage and adds Time for debugging purposes. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TimedWalMessage { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub time: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub msg: ::core::option::Option, } diff --git a/proto/src/prost/v0_34/tendermint.crypto.rs b/proto/src/prost/v0_34/tendermint.crypto.rs index 0fac07973..fed646029 100644 --- a/proto/src/prost/v0_34/tendermint.crypto.rs +++ b/proto/src/prost/v0_34/tendermint.crypto.rs @@ -1,73 +1,86 @@ #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proof { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] #[serde(with = "crate::serializers::from_str")] pub total: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub index: i64, - #[prost(bytes="vec", tag="3")] + #[prost(bytes = "vec", tag = "3")] #[serde(with = "crate::serializers::bytes::base64string")] pub leaf_hash: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", repeated, tag="4")] + #[prost(bytes = "vec", repeated, tag = "4")] #[serde(with = "crate::serializers::bytes::vec_base64string")] pub aunts: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValueOp { /// Encoded in ProofOp.Key. - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] pub key: ::prost::alloc::vec::Vec, /// To encode in ProofOp.Data - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub proof: ::core::option::Option, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DominoOp { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub key: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub input: ::prost::alloc::string::String, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub output: ::prost::alloc::string::String, } /// ProofOp defines an operation used for calculating Merkle root /// The data could be arbitrary format, providing nessecary data /// for example neighbouring node hash +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProofOp { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub r#type: ::prost::alloc::string::String, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub key: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", tag="3")] + #[prost(bytes = "vec", tag = "3")] pub data: ::prost::alloc::vec::Vec, } /// ProofOps is Merkle proof defined by the list of ProofOps +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProofOps { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub ops: ::prost::alloc::vec::Vec, } /// PublicKey defines the keys available for use with Tendermint Validators #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PublicKey { - #[prost(oneof="public_key::Sum", tags="1, 2")] + #[prost(oneof = "public_key::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `PublicKey`. pub mod public_key { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(bytes, tag="1")] - #[serde(rename = "tendermint/PubKeyEd25519", with = "crate::serializers::bytes::base64string")] + #[prost(bytes, tag = "1")] + #[serde( + rename = "tendermint/PubKeyEd25519", + with = "crate::serializers::bytes::base64string" + )] Ed25519(::prost::alloc::vec::Vec), - #[prost(bytes, tag="2")] - #[serde(rename = "tendermint/PubKeySecp256k1", with = "crate::serializers::bytes::base64string")] + #[prost(bytes, tag = "2")] + #[serde( + rename = "tendermint/PubKeySecp256k1", + with = "crate::serializers::bytes::base64string" + )] Secp256k1(::prost::alloc::vec::Vec), } } diff --git a/proto/src/prost/v0_34/tendermint.libs.bits.rs b/proto/src/prost/v0_34/tendermint.libs.bits.rs index 47eee3773..460876d21 100644 --- a/proto/src/prost/v0_34/tendermint.libs.bits.rs +++ b/proto/src/prost/v0_34/tendermint.libs.bits.rs @@ -1,8 +1,9 @@ #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BitArray { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub bits: i64, - #[prost(uint64, repeated, tag="2")] + #[prost(uint64, repeated, tag = "2")] pub elems: ::prost::alloc::vec::Vec, } diff --git a/proto/src/prost/v0_34/tendermint.mempool.rs b/proto/src/prost/v0_34/tendermint.mempool.rs index af22801ba..9fec1376b 100644 --- a/proto/src/prost/v0_34/tendermint.mempool.rs +++ b/proto/src/prost/v0_34/tendermint.mempool.rs @@ -1,18 +1,21 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Txs { - #[prost(bytes="vec", repeated, tag="1")] + #[prost(bytes = "vec", repeated, tag = "1")] pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1")] + #[prost(oneof = "message::Sum", tags = "1")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Txs(super::Txs), } } diff --git a/proto/src/prost/v0_34/tendermint.p2p.rs b/proto/src/prost/v0_34/tendermint.p2p.rs index 4b81d0be0..bfaa808cb 100644 --- a/proto/src/prost/v0_34/tendermint.p2p.rs +++ b/proto/src/prost/v0_34/tendermint.p2p.rs @@ -1,106 +1,117 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPing { -} +pub struct PacketPing {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPong { -} +pub struct PacketPong {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PacketMsg { - #[prost(int32, tag="1")] + #[prost(int32, tag = "1")] pub channel_id: i32, - #[prost(bool, tag="2")] + #[prost(bool, tag = "2")] pub eof: bool, - #[prost(bytes="vec", tag="3")] + #[prost(bytes = "vec", tag = "3")] pub data: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Packet { - #[prost(oneof="packet::Sum", tags="1, 2, 3")] + #[prost(oneof = "packet::Sum", tags = "1, 2, 3")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Packet`. pub mod packet { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] PacketPing(super::PacketPing), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] PacketPong(super::PacketPong), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] PacketMsg(super::PacketMsg), } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct AuthSigMessage { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub sig: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NetAddress { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub id: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub ip: ::prost::alloc::string::String, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub port: u32, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProtocolVersion { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub p2p: u64, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] pub block: u64, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] pub app: u64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub protocol_version: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub default_node_id: ::prost::alloc::string::String, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub listen_addr: ::prost::alloc::string::String, - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub network: ::prost::alloc::string::String, - #[prost(string, tag="5")] + #[prost(string, tag = "5")] pub version: ::prost::alloc::string::String, - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] pub channels: ::prost::alloc::vec::Vec, - #[prost(string, tag="7")] + #[prost(string, tag = "7")] pub moniker: ::prost::alloc::string::String, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub other: ::core::option::Option, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfoOther { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub tx_index: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub rpc_address: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PexRequest { -} +pub struct PexRequest {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PexAddrs { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub addrs: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2")] + #[prost(oneof = "message::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] PexRequest(super::PexRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] PexAddrs(super::PexAddrs), } } diff --git a/proto/src/prost/v0_34/tendermint.privval.rs b/proto/src/prost/v0_34/tendermint.privval.rs index 892a10bbf..1fae1cbee 100644 --- a/proto/src/prost/v0_34/tendermint.privval.rs +++ b/proto/src/prost/v0_34/tendermint.privval.rs @@ -1,88 +1,97 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RemoteSignerError { - #[prost(int32, tag="1")] + #[prost(int32, tag = "1")] pub code: i32, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub description: ::prost::alloc::string::String, } /// PubKeyRequest requests the consensus public key from the remote signer. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PubKeyRequest { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub chain_id: ::prost::alloc::string::String, } /// PubKeyResponse is a response message containing the public key. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PubKeyResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub error: ::core::option::Option, } /// SignVoteRequest is a request to sign a vote +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignVoteRequest { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, } /// SignedVoteResponse is a response containing a signed vote or an error +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignedVoteResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub error: ::core::option::Option, } /// SignProposalRequest is a request to sign a proposal +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignProposalRequest { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub proposal: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, } /// SignedProposalResponse is response containing a signed proposal or an error +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignedProposalResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub proposal: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub error: ::core::option::Option, } /// PingRequest is a request to confirm that the connection is alive. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PingRequest { -} +pub struct PingRequest {} /// PingResponse is a response to confirm that the connection is alive. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PingResponse { -} +pub struct PingResponse {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5, 6, 7, 8")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4, 5, 6, 7, 8")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] PubKeyRequest(super::PubKeyRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] PubKeyResponse(super::PubKeyResponse), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] SignVoteRequest(super::SignVoteRequest), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] SignedVoteResponse(super::SignedVoteResponse), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] SignProposalRequest(super::SignProposalRequest), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] SignedProposalResponse(super::SignedProposalResponse), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] PingRequest(super::PingRequest), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] PingResponse(super::PingResponse), } } diff --git a/proto/src/prost/v0_34/tendermint.rpc.grpc.rs b/proto/src/prost/v0_34/tendermint.rpc.grpc.rs index 4739bccac..5630cb50c 100644 --- a/proto/src/prost/v0_34/tendermint.rpc.grpc.rs +++ b/proto/src/prost/v0_34/tendermint.rpc.grpc.rs @@ -1,24 +1,20 @@ -// ---------------------------------------- -// Request types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestPing { -} +pub struct RequestPing {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestBroadcastTx { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] pub tx: ::prost::alloc::vec::Vec, } -// ---------------------------------------- -// Response types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct ResponsePing { -} +pub struct ResponsePing {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseBroadcastTx { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub check_tx: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub deliver_tx: ::core::option::Option, } diff --git a/proto/src/prost/v0_34/tendermint.state.rs b/proto/src/prost/v0_34/tendermint.state.rs index c996b31a5..dd006a2c6 100644 --- a/proto/src/prost/v0_34/tendermint.state.rs +++ b/proto/src/prost/v0_34/tendermint.state.rs @@ -1,60 +1,66 @@ /// ABCIResponses retains the responses /// of the various ABCI calls during block processing. /// It is persisted to disk for each height before calling Commit. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct AbciResponses { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub deliver_txs: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub end_block: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub begin_block: ::core::option::Option, } /// ValidatorsInfo represents the latest validator set, or the last height it changed +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorsInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub validator_set: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub last_height_changed: i64, } /// ConsensusParamsInfo represents the latest consensus params, or the last height it changed +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ConsensusParamsInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub consensus_params: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub last_height_changed: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct AbciResponsesInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub abci_responses: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Version { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub consensus: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub software: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct State { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub version: ::core::option::Option, /// immutable - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(int64, tag="14")] + #[prost(int64, tag = "14")] pub initial_height: i64, /// LastBlockHeight=0 at genesis (ie. block(H=0) does not exist) - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub last_block_height: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub last_block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub last_block_time: ::core::option::Option, /// LastValidators is used to validate block.LastCommit. /// Validators are persisted to the database separately every time they change, @@ -62,24 +68,24 @@ pub struct State { /// Note that if s.LastBlockHeight causes a valset change, /// we set s.LastHeightValidatorsChanged = s.LastBlockHeight + 1 + 1 /// Extra +1 due to nextValSet delay. - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub next_validators: ::core::option::Option, - #[prost(message, optional, tag="7")] + #[prost(message, optional, tag = "7")] pub validators: ::core::option::Option, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub last_validators: ::core::option::Option, - #[prost(int64, tag="9")] + #[prost(int64, tag = "9")] pub last_height_validators_changed: i64, /// Consensus parameters used for validating blocks. /// Changes returned by EndBlock and updated after Commit. - #[prost(message, optional, tag="10")] + #[prost(message, optional, tag = "10")] pub consensus_params: ::core::option::Option, - #[prost(int64, tag="11")] + #[prost(int64, tag = "11")] pub last_height_consensus_params_changed: i64, /// Merkle root of the results from executing prev block - #[prost(bytes="vec", tag="12")] + #[prost(bytes = "vec", tag = "12")] pub last_results_hash: ::prost::alloc::vec::Vec, /// the latest AppHash we've received from calling abci.Commit() - #[prost(bytes="vec", tag="13")] + #[prost(bytes = "vec", tag = "13")] pub app_hash: ::prost::alloc::vec::Vec, } diff --git a/proto/src/prost/v0_34/tendermint.statesync.rs b/proto/src/prost/v0_34/tendermint.statesync.rs index 593bd0222..a2ad034e3 100644 --- a/proto/src/prost/v0_34/tendermint.statesync.rs +++ b/proto/src/prost/v0_34/tendermint.statesync.rs @@ -1,57 +1,62 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] SnapshotsRequest(super::SnapshotsRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] SnapshotsResponse(super::SnapshotsResponse), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] ChunkRequest(super::ChunkRequest), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] ChunkResponse(super::ChunkResponse), } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct SnapshotsRequest { -} +pub struct SnapshotsRequest {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SnapshotsResponse { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunks: u32, - #[prost(bytes="vec", tag="4")] + #[prost(bytes = "vec", tag = "4")] pub hash: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", tag="5")] + #[prost(bytes = "vec", tag = "5")] pub metadata: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ChunkRequest { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub index: u32, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ChunkResponse { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub index: u32, - #[prost(bytes="vec", tag="4")] + #[prost(bytes = "vec", tag = "4")] pub chunk: ::prost::alloc::vec::Vec, - #[prost(bool, tag="5")] + #[prost(bool, tag = "5")] pub missing: bool, } diff --git a/proto/src/prost/v0_34/tendermint.store.rs b/proto/src/prost/v0_34/tendermint.store.rs index a4c2799d9..98d20b0fc 100644 --- a/proto/src/prost/v0_34/tendermint.store.rs +++ b/proto/src/prost/v0_34/tendermint.store.rs @@ -1,7 +1,8 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockStoreState { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub base: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, } diff --git a/proto/src/prost/v0_34/tendermint.types.rs b/proto/src/prost/v0_34/tendermint.types.rs index 753c63469..66c081611 100644 --- a/proto/src/prost/v0_34/tendermint.types.rs +++ b/proto/src/prost/v0_34/tendermint.types.rs @@ -1,256 +1,270 @@ #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorSet { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub validators: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub proposer: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub total_voting_power: i64, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Validator { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(alias = "power", with = "crate::serializers::from_str")] pub voting_power: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str", default)] pub proposer_priority: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SimpleValidator { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub voting_power: i64, } /// PartsetHeader #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PartSetHeader { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] #[serde(with = "crate::serializers::part_set_header_total")] pub total: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Part { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub index: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub bytes: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proof: ::core::option::Option, } /// BlockID #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockId { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } -// -------------------------------- - /// Header defines the structure of a Tendermint block header. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Header { /// basic block info - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub version: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] #[serde(with = "crate::serializers::optional")] pub time: ::core::option::Option, /// prev block info - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub last_block_id: ::core::option::Option, /// hashes of block data /// /// commit from validators from the last block - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_commit_hash: ::prost::alloc::vec::Vec, /// transactions - #[prost(bytes="vec", tag="7")] + #[prost(bytes = "vec", tag = "7")] #[serde(with = "crate::serializers::bytes::hexstring")] pub data_hash: ::prost::alloc::vec::Vec, /// hashes from the app output from the prev block /// /// validators for the current block - #[prost(bytes="vec", tag="8")] + #[prost(bytes = "vec", tag = "8")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validators_hash: ::prost::alloc::vec::Vec, /// validators for the next block - #[prost(bytes="vec", tag="9")] + #[prost(bytes = "vec", tag = "9")] #[serde(with = "crate::serializers::bytes::hexstring")] pub next_validators_hash: ::prost::alloc::vec::Vec, /// consensus params for current block - #[prost(bytes="vec", tag="10")] + #[prost(bytes = "vec", tag = "10")] #[serde(with = "crate::serializers::bytes::hexstring")] pub consensus_hash: ::prost::alloc::vec::Vec, /// state after txs from the previous block - #[prost(bytes="vec", tag="11")] + #[prost(bytes = "vec", tag = "11")] #[serde(with = "crate::serializers::bytes::hexstring")] pub app_hash: ::prost::alloc::vec::Vec, /// root hash of all results from the txs from the previous block - #[prost(bytes="vec", tag="12")] + #[prost(bytes = "vec", tag = "12")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_results_hash: ::prost::alloc::vec::Vec, /// consensus info /// /// evidence included in the block - #[prost(bytes="vec", tag="13")] + #[prost(bytes = "vec", tag = "13")] #[serde(with = "crate::serializers::bytes::hexstring")] pub evidence_hash: ::prost::alloc::vec::Vec, /// original proposer of the block - #[prost(bytes="vec", tag="14")] + #[prost(bytes = "vec", tag = "14")] #[serde(with = "crate::serializers::bytes::hexstring")] pub proposer_address: ::prost::alloc::vec::Vec, } /// Data contains the set of transactions included in the block #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Data { /// Txs that will be applied by state @ block.Height+1. /// NOTE: not all txs here are valid. We're just agreeing on the order first. /// This means that block.AppHash does not include these txs. - #[prost(bytes="vec", repeated, tag="1")] + #[prost(bytes = "vec", repeated, tag = "1")] #[serde(with = "crate::serializers::txs")] pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } /// Vote represents a prevote, precommit, or commit vote from validators for /// consensus. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Vote { - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, /// zero if vote is nil. - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] #[serde(with = "crate::serializers::optional")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(int32, tag="7")] + #[prost(int32, tag = "7")] pub validator_index: i32, - #[prost(bytes="vec", tag="8")] + #[prost(bytes = "vec", tag = "8")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } /// Commit contains the evidence that a block was committed by a set of validators. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Commit { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub block_id: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] #[serde(with = "crate::serializers::nullable")] pub signatures: ::prost::alloc::vec::Vec, } /// CommitSig is a part of the Vote included in a Commit. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CommitSig { - #[prost(enumeration="BlockIdFlag", tag="1")] + #[prost(enumeration = "BlockIdFlag", tag = "1")] pub block_id_flag: i32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] #[serde(with = "crate::serializers::optional")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="4")] + #[prost(bytes = "vec", tag = "4")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proposal { - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, - #[prost(int32, tag="4")] + #[prost(int32, tag = "4")] pub pol_round: i32, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="7")] + #[prost(bytes = "vec", tag = "7")] pub signature: ::prost::alloc::vec::Vec, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignedHeader { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub commit: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct LightBlock { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub signed_header: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub validator_set: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockMeta { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block_id: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub block_size: i64, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub header: ::core::option::Option
, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str")] pub num_txs: i64, } /// TxProof represents a Merkle proof of the presence of a transaction in the Merkle tree. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TxProof { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub root_hash: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::base64string")] pub data: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proof: ::core::option::Option, } /// BlockIdFlag indicates which BlcokID the signature is for @@ -304,215 +318,232 @@ impl SignedMsgType { } /// ConsensusParams contains consensus critical parameters that determine the /// validity of blocks. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ConsensusParams { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub validator: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub version: ::core::option::Option, } /// BlockParams contains limits on the block size. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockParams { /// Max block size, in bytes. /// Note: must be greater than 0 - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_bytes: i64, /// Max gas per block. /// Note: must be greater or equal to -1 - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub max_gas: i64, /// Minimum time increment between consecutive blocks (in milliseconds) If the /// block header timestamp is ahead of the system clock, decrease this value. /// /// Not exposed to the application. - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub time_iota_ms: i64, } /// EvidenceParams determine how we handle evidence of malfeasance. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EvidenceParams { /// Max age of evidence, in blocks. /// /// The basic formula for calculating this is: MaxAgeDuration / {average block /// time}. - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_age_num_blocks: i64, /// Max age of evidence, in time. /// /// It should correspond with an app's "unbonding period" or other similar /// mechanism for handling [Nothing-At-Stake /// attacks](). - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub max_age_duration: ::core::option::Option, /// This sets the maximum size of total evidence in bytes that can be committed in a single block. /// and should fall comfortably under the max block bytes. /// Default is 1048576 or 1MB - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(with = "crate::serializers::from_str", default)] pub max_bytes: i64, } /// ValidatorParams restrict the public key types validators can use. /// NOTE: uses ABCI pubkey naming, not Amino names. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorParams { - #[prost(string, repeated, tag="1")] + #[prost(string, repeated, tag = "1")] pub pub_key_types: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// VersionParams contains the ABCI application version. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VersionParams { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub app_version: u64, } /// HashedParams is a subset of ConsensusParams. /// /// It is hashed into the Header.ConsensusHash. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct HashedParams { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub block_max_bytes: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub block_max_gas: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EventDataRoundState { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub step: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Evidence { - #[prost(oneof="evidence::Sum", tags="1, 2")] + #[prost(oneof = "evidence::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Evidence`. pub mod evidence { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] #[serde(rename = "tendermint/DuplicateVoteEvidence")] DuplicateVoteEvidence(super::DuplicateVoteEvidence), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] #[serde(rename = "tendermint/LightClientAttackEvidence")] LightClientAttackEvidence(super::LightClientAttackEvidence), } } /// DuplicateVoteEvidence contains evidence of a validator signed two conflicting votes. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DuplicateVoteEvidence { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote_a: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub vote_b: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(alias = "TotalVotingPower", with = "crate::serializers::from_str")] pub total_voting_power: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(alias = "ValidatorPower", with = "crate::serializers::from_str")] pub validator_power: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] #[serde(alias = "Timestamp")] pub timestamp: ::core::option::Option, } /// LightClientAttackEvidence contains evidence of a set of validators attempting to mislead a light client. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct LightClientAttackEvidence { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub conflicting_block: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub common_height: i64, - #[prost(message, repeated, tag="3")] + #[prost(message, repeated, tag = "3")] pub byzantine_validators: ::prost::alloc::vec::Vec, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub total_voting_power: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub timestamp: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EvidenceList { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] #[serde(with = "crate::serializers::nullable")] pub evidence: ::prost::alloc::vec::Vec, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Block { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub data: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub last_commit: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalBlockId { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalPartSetHeader { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub total: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub hash: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalProposal { /// type alias for byte - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="2")] + #[prost(sfixed64, tag = "2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="3")] + #[prost(sfixed64, tag = "3")] pub round: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub pol_round: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub timestamp: ::core::option::Option, - #[prost(string, tag="7")] + #[prost(string, tag = "7")] pub chain_id: ::prost::alloc::string::String, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalVote { /// type alias for byte - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="2")] + #[prost(sfixed64, tag = "2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="3")] + #[prost(sfixed64, tag = "3")] pub round: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub timestamp: ::core::option::Option, - #[prost(string, tag="6")] + #[prost(string, tag = "6")] pub chain_id: ::prost::alloc::string::String, } diff --git a/proto/src/prost/v0_34/tendermint.version.rs b/proto/src/prost/v0_34/tendermint.version.rs index bd1227266..8a77a26fc 100644 --- a/proto/src/prost/v0_34/tendermint.version.rs +++ b/proto/src/prost/v0_34/tendermint.version.rs @@ -1,23 +1,25 @@ /// App includes the protocol and software version for the application. /// This information is included in ResponseInfo. The App.Protocol can be /// updated in ResponseEndBlock. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct App { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub protocol: u64, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub software: ::prost::alloc::string::String, } /// Consensus captures the consensus rules for processing a block in the blockchain, /// including all blockchain data structures and the rules of the application's /// state transition machine. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Consensus { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] #[serde(with = "crate::serializers::from_str")] pub block: u64, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] #[serde(with = "crate::serializers::from_str", default)] pub app: u64, } diff --git a/proto/src/prost/v0_37/tendermint.abci.rs b/proto/src/prost/v0_37/tendermint.abci.rs index 8a62bb862..acccf14ad 100644 --- a/proto/src/prost/v0_37/tendermint.abci.rs +++ b/proto/src/prost/v0_37/tendermint.abci.rs @@ -1,409 +1,444 @@ -// This file is copied from -// NOTE: When using custom types, mind the warnings. -// - -// ---------------------------------------- -// Request types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Request { - #[prost(oneof="request::Value", tags="1, 2, 3, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17")] + #[prost( + oneof = "request::Value", + tags = "1, 2, 3, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17" + )] pub value: ::core::option::Option, } /// Nested message and enum types in `Request`. pub mod request { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Echo(super::RequestEcho), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] Flush(super::RequestFlush), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Info(super::RequestInfo), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] InitChain(super::RequestInitChain), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] Query(super::RequestQuery), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] BeginBlock(super::RequestBeginBlock), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] CheckTx(super::RequestCheckTx), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] DeliverTx(super::RequestDeliverTx), - #[prost(message, tag="10")] + #[prost(message, tag = "10")] EndBlock(super::RequestEndBlock), - #[prost(message, tag="11")] + #[prost(message, tag = "11")] Commit(super::RequestCommit), - #[prost(message, tag="12")] + #[prost(message, tag = "12")] ListSnapshots(super::RequestListSnapshots), - #[prost(message, tag="13")] + #[prost(message, tag = "13")] OfferSnapshot(super::RequestOfferSnapshot), - #[prost(message, tag="14")] + #[prost(message, tag = "14")] LoadSnapshotChunk(super::RequestLoadSnapshotChunk), - #[prost(message, tag="15")] + #[prost(message, tag = "15")] ApplySnapshotChunk(super::RequestApplySnapshotChunk), - #[prost(message, tag="16")] + #[prost(message, tag = "16")] PrepareProposal(super::RequestPrepareProposal), - #[prost(message, tag="17")] + #[prost(message, tag = "17")] ProcessProposal(super::RequestProcessProposal), } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEcho { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub message: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestFlush { -} +pub struct RequestFlush {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInfo { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] pub block_version: u64, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] pub p2p_version: u64, - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub abci_version: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestInitChain { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub time: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] pub app_state_bytes: ::prost::bytes::Bytes, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub initial_height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestQuery { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub data: ::prost::bytes::Bytes, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub path: ::prost::alloc::string::String, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub height: i64, - #[prost(bool, tag="4")] + #[prost(bool, tag = "4")] pub prove: bool, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestBeginBlock { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub hash: ::prost::bytes::Bytes, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub header: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub last_commit_info: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] pub byzantine_validators: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestCheckTx { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub tx: ::prost::bytes::Bytes, - #[prost(enumeration="CheckTxType", tag="2")] + #[prost(enumeration = "CheckTxType", tag = "2")] pub r#type: i32, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestDeliverTx { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub tx: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestEndBlock { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestCommit { -} +pub struct RequestCommit {} /// lists available snapshots +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestListSnapshots { -} +pub struct RequestListSnapshots {} /// offers a snapshot to the application +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestOfferSnapshot { /// snapshot offered by peers - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub snapshot: ::core::option::Option, /// light client-verified app hash for snapshot height - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub app_hash: ::prost::bytes::Bytes, } /// loads a snapshot chunk +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestLoadSnapshotChunk { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunk: u32, } /// Applies a snapshot chunk +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestApplySnapshotChunk { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub index: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub chunk: ::prost::bytes::Bytes, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub sender: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestPrepareProposal { /// the modified transactions cannot exceed this size. - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_tx_bytes: i64, /// txs is an array of transactions that will be included in a block, /// sent to the app for possible modifications. - #[prost(bytes="bytes", repeated, tag="2")] + #[prost(bytes = "bytes", repeated, tag = "2")] pub txs: ::prost::alloc::vec::Vec<::prost::bytes::Bytes>, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub local_last_commit: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] pub misbehavior: ::prost::alloc::vec::Vec, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub height: i64, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub time: ::core::option::Option, - #[prost(bytes="bytes", tag="7")] + #[prost(bytes = "bytes", tag = "7")] pub next_validators_hash: ::prost::bytes::Bytes, /// address of the public key of the validator proposing the block. - #[prost(bytes="bytes", tag="8")] + #[prost(bytes = "bytes", tag = "8")] pub proposer_address: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestProcessProposal { - #[prost(bytes="bytes", repeated, tag="1")] + #[prost(bytes = "bytes", repeated, tag = "1")] pub txs: ::prost::alloc::vec::Vec<::prost::bytes::Bytes>, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub proposed_last_commit: ::core::option::Option, - #[prost(message, repeated, tag="3")] + #[prost(message, repeated, tag = "3")] pub misbehavior: ::prost::alloc::vec::Vec, /// hash is the merkle root hash of the fields of the proposed block. - #[prost(bytes="bytes", tag="4")] + #[prost(bytes = "bytes", tag = "4")] pub hash: ::prost::bytes::Bytes, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub height: i64, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub time: ::core::option::Option, - #[prost(bytes="bytes", tag="7")] + #[prost(bytes = "bytes", tag = "7")] pub next_validators_hash: ::prost::bytes::Bytes, /// address of the public key of the original proposer of the block. - #[prost(bytes="bytes", tag="8")] + #[prost(bytes = "bytes", tag = "8")] pub proposer_address: ::prost::bytes::Bytes, } -// ---------------------------------------- -// Response types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Response { - #[prost(oneof="response::Value", tags="1, 2, 3, 4, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18")] + #[prost( + oneof = "response::Value", + tags = "1, 2, 3, 4, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18" + )] pub value: ::core::option::Option, } /// Nested message and enum types in `Response`. pub mod response { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Value { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Exception(super::ResponseException), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] Echo(super::ResponseEcho), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Flush(super::ResponseFlush), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] Info(super::ResponseInfo), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] InitChain(super::ResponseInitChain), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] Query(super::ResponseQuery), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] BeginBlock(super::ResponseBeginBlock), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] CheckTx(super::ResponseCheckTx), - #[prost(message, tag="10")] + #[prost(message, tag = "10")] DeliverTx(super::ResponseDeliverTx), - #[prost(message, tag="11")] + #[prost(message, tag = "11")] EndBlock(super::ResponseEndBlock), - #[prost(message, tag="12")] + #[prost(message, tag = "12")] Commit(super::ResponseCommit), - #[prost(message, tag="13")] + #[prost(message, tag = "13")] ListSnapshots(super::ResponseListSnapshots), - #[prost(message, tag="14")] + #[prost(message, tag = "14")] OfferSnapshot(super::ResponseOfferSnapshot), - #[prost(message, tag="15")] + #[prost(message, tag = "15")] LoadSnapshotChunk(super::ResponseLoadSnapshotChunk), - #[prost(message, tag="16")] + #[prost(message, tag = "16")] ApplySnapshotChunk(super::ResponseApplySnapshotChunk), - #[prost(message, tag="17")] + #[prost(message, tag = "17")] PrepareProposal(super::ResponsePrepareProposal), - #[prost(message, tag="18")] + #[prost(message, tag = "18")] ProcessProposal(super::ResponseProcessProposal), } } /// nondeterministic +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseException { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub error: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEcho { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub message: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct ResponseFlush { -} +pub struct ResponseFlush {} #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseInfo { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] #[serde(default)] pub data: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] #[serde(default)] pub version: ::prost::alloc::string::String, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] #[serde(with = "crate::serializers::from_str", default)] pub app_version: u64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str", default)] pub last_block_height: i64, - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] #[serde(default)] #[serde(skip_serializing_if = "bytes::Bytes::is_empty")] pub last_block_app_hash: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseInitChain { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub consensus_params: ::core::option::Option, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub validators: ::prost::alloc::vec::Vec, - #[prost(bytes="bytes", tag="3")] + #[prost(bytes = "bytes", tag = "3")] pub app_hash: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseQuery { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, /// bytes data = 2; // use "value" instead. /// /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub index: i64, - #[prost(bytes="bytes", tag="6")] + #[prost(bytes = "bytes", tag = "6")] pub key: ::prost::bytes::Bytes, - #[prost(bytes="bytes", tag="7")] + #[prost(bytes = "bytes", tag = "7")] pub value: ::prost::bytes::Bytes, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub proof_ops: ::core::option::Option, - #[prost(int64, tag="9")] + #[prost(int64, tag = "9")] pub height: i64, - #[prost(string, tag="10")] + #[prost(string, tag = "10")] pub codespace: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseBeginBlock { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub events: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCheckTx { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub gas_wanted: i64, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub gas_used: i64, - #[prost(message, repeated, tag="7")] + #[prost(message, repeated, tag = "7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag="8")] + #[prost(string, tag = "8")] pub codespace: ::prost::alloc::string::String, - #[prost(string, tag="9")] + #[prost(string, tag = "9")] pub sender: ::prost::alloc::string::String, - #[prost(int64, tag="10")] + #[prost(int64, tag = "10")] pub priority: i64, /// mempool_error is set by Tendermint. /// ABCI applictions creating a ResponseCheckTX should not set mempool_error. - #[prost(string, tag="11")] + #[prost(string, tag = "11")] pub mempool_error: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseDeliverTx { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub code: u32, - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, /// nondeterministic - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub log: ::prost::alloc::string::String, /// nondeterministic - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub info: ::prost::alloc::string::String, - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub gas_wanted: i64, - #[prost(int64, tag="6")] + #[prost(int64, tag = "6")] pub gas_used: i64, /// nondeterministic - #[prost(message, repeated, tag="7")] + #[prost(message, repeated, tag = "7")] pub events: ::prost::alloc::vec::Vec, - #[prost(string, tag="8")] + #[prost(string, tag = "8")] pub codespace: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseEndBlock { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub validator_updates: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub consensus_param_updates: ::core::option::Option, - #[prost(message, repeated, tag="3")] + #[prost(message, repeated, tag = "3")] pub events: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseCommit { /// reserve 1 - #[prost(bytes="bytes", tag="2")] + #[prost(bytes = "bytes", tag = "2")] pub data: ::prost::bytes::Bytes, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub retain_height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseListSnapshots { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub snapshots: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseOfferSnapshot { - #[prost(enumeration="response_offer_snapshot::Result", tag="1")] + #[prost(enumeration = "response_offer_snapshot::Result", tag = "1")] pub result: i32, } /// Nested message and enum types in `ResponseOfferSnapshot`. pub mod response_offer_snapshot { - #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[derive( + Clone, + Copy, + Debug, + PartialEq, + Eq, + Hash, + PartialOrd, + Ord, + ::prost::Enumeration + )] #[repr(i32)] pub enum Result { /// Unknown result, abort all snapshot restoration @@ -436,25 +471,37 @@ pub mod response_offer_snapshot { } } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseLoadSnapshotChunk { - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub chunk: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseApplySnapshotChunk { - #[prost(enumeration="response_apply_snapshot_chunk::Result", tag="1")] + #[prost(enumeration = "response_apply_snapshot_chunk::Result", tag = "1")] pub result: i32, /// Chunks to refetch and reapply - #[prost(uint32, repeated, tag="2")] + #[prost(uint32, repeated, tag = "2")] pub refetch_chunks: ::prost::alloc::vec::Vec, /// Chunk senders to reject and ban - #[prost(string, repeated, tag="3")] + #[prost(string, repeated, tag = "3")] pub reject_senders: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// Nested message and enum types in `ResponseApplySnapshotChunk`. pub mod response_apply_snapshot_chunk { - #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[derive( + Clone, + Copy, + Debug, + PartialEq, + Eq, + Hash, + PartialOrd, + Ord, + ::prost::Enumeration + )] #[repr(i32)] pub enum Result { /// Unknown result, abort all snapshot restoration @@ -487,19 +534,31 @@ pub mod response_apply_snapshot_chunk { } } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponsePrepareProposal { - #[prost(bytes="bytes", repeated, tag="1")] + #[prost(bytes = "bytes", repeated, tag = "1")] pub txs: ::prost::alloc::vec::Vec<::prost::bytes::Bytes>, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseProcessProposal { - #[prost(enumeration="response_process_proposal::ProposalStatus", tag="1")] + #[prost(enumeration = "response_process_proposal::ProposalStatus", tag = "1")] pub status: i32, } /// Nested message and enum types in `ResponseProcessProposal`. pub mod response_process_proposal { - #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] + #[derive( + Clone, + Copy, + Debug, + PartialEq, + Eq, + Hash, + PartialOrd, + Ord, + ::prost::Enumeration + )] #[repr(i32)] pub enum ProposalStatus { Unknown = 0, @@ -520,140 +579,142 @@ pub mod response_process_proposal { } } } -// ---------------------------------------- -// Misc. - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CommitInfo { - #[prost(int32, tag="1")] + #[prost(int32, tag = "1")] pub round: i32, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub votes: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ExtendedCommitInfo { /// The round at which the block proposer decided in the previous height. - #[prost(int32, tag="1")] + #[prost(int32, tag = "1")] pub round: i32, /// List of validators' addresses in the last validator set with their voting /// information, including vote extensions. - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub votes: ::prost::alloc::vec::Vec, } /// Event allows application developers to attach additional information to /// ResponseBeginBlock, ResponseEndBlock, ResponseCheckTx and ResponseDeliverTx. /// Later, transactions may be queried using these events. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Event { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub r#type: ::prost::alloc::string::String, - #[prost(message, repeated, tag="2")] + #[prost(message, repeated, tag = "2")] pub attributes: ::prost::alloc::vec::Vec, } /// EventAttribute is a single key-value pair, associated with an event. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EventAttribute { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub key: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub value: ::prost::alloc::string::String, /// nondeterministic - #[prost(bool, tag="3")] + #[prost(bool, tag = "3")] pub index: bool, } /// TxResult contains results of executing the transaction. /// /// One usage is indexing transaction results. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TxResult { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub index: u32, - #[prost(bytes="bytes", tag="3")] + #[prost(bytes = "bytes", tag = "3")] pub tx: ::prost::bytes::Bytes, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub result: ::core::option::Option, } -// ---------------------------------------- -// Blockchain Types - /// Validator +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Validator { /// The first 20 bytes of SHA256(public key) - #[prost(bytes="bytes", tag="1")] + #[prost(bytes = "bytes", tag = "1")] pub address: ::prost::bytes::Bytes, /// PubKey pub_key = 2 \[(gogoproto.nullable)=false\]; /// /// The voting power - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub power: i64, } /// ValidatorUpdate +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorUpdate { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub power: i64, } /// VoteInfo +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub validator: ::core::option::Option, - #[prost(bool, tag="2")] + #[prost(bool, tag = "2")] pub signed_last_block: bool, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ExtendedVoteInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub validator: ::core::option::Option, - #[prost(bool, tag="2")] + #[prost(bool, tag = "2")] pub signed_last_block: bool, /// Reserved for future use - #[prost(bytes="bytes", tag="3")] + #[prost(bytes = "bytes", tag = "3")] pub vote_extension: ::prost::bytes::Bytes, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Misbehavior { - #[prost(enumeration="MisbehaviorType", tag="1")] + #[prost(enumeration = "MisbehaviorType", tag = "1")] pub r#type: i32, /// The offending validator - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub validator: ::core::option::Option, /// The height when the offense occurred - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub height: i64, /// The corresponding time where the offense occurred - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub time: ::core::option::Option, /// Total voting power of the validator set in case the ABCI application does /// not store historical validators. /// - #[prost(int64, tag="5")] + #[prost(int64, tag = "5")] pub total_voting_power: i64, } -// ---------------------------------------- -// State Sync Types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Snapshot { /// The height at which the snapshot was taken - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, /// The application-specific snapshot format - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, /// Number of chunks in the snapshot - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunks: u32, /// Arbitrary snapshot hash, equal only if identical - #[prost(bytes="bytes", tag="4")] + #[prost(bytes = "bytes", tag = "4")] pub hash: ::prost::bytes::Bytes, /// Arbitrary application metadata - #[prost(bytes="bytes", tag="5")] + #[prost(bytes = "bytes", tag = "5")] pub metadata: ::prost::bytes::Bytes, } #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord, ::prost::Enumeration)] diff --git a/proto/src/prost/v0_37/tendermint.blocksync.rs b/proto/src/prost/v0_37/tendermint.blocksync.rs index 492aa692e..4480ece49 100644 --- a/proto/src/prost/v0_37/tendermint.blocksync.rs +++ b/proto/src/prost/v0_37/tendermint.blocksync.rs @@ -1,51 +1,57 @@ /// BlockRequest requests a block for a specific height +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockRequest { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } /// NoBlockResponse informs the node that the peer does not have block at the requested height +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NoBlockResponse { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } /// BlockResponse returns block to the requested +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block: ::core::option::Option, } /// StatusRequest requests the status of a peer. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct StatusRequest { -} +pub struct StatusRequest {} /// StatusResponse is a peer response to inform their status. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct StatusResponse { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub base: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4, 5")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] BlockRequest(super::BlockRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] NoBlockResponse(super::NoBlockResponse), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] BlockResponse(super::BlockResponse), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] StatusRequest(super::StatusRequest), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] StatusResponse(super::StatusResponse), } } diff --git a/proto/src/prost/v0_37/tendermint.consensus.rs b/proto/src/prost/v0_37/tendermint.consensus.rs index 6f3fe8624..95237cc78 100644 --- a/proto/src/prost/v0_37/tendermint.consensus.rs +++ b/proto/src/prost/v0_37/tendermint.consensus.rs @@ -1,184 +1,201 @@ /// NewRoundStep is sent for every step taken in the ConsensusState. /// For every height/round/step transition +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NewRoundStep { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub step: u32, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub seconds_since_start_time: i64, - #[prost(int32, tag="5")] + #[prost(int32, tag = "5")] pub last_commit_round: i32, } /// NewValidBlock is sent when a validator observes a valid block B in some round r, /// i.e., there is a Proposal for block B and 2/3+ prevotes for the block B in the round r. /// In case the block is also committed, then IsCommit flag is set to true. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NewValidBlock { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub block_part_set_header: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_parts: ::core::option::Option, - #[prost(bool, tag="5")] + #[prost(bool, tag = "5")] pub is_commit: bool, } /// Proposal is sent when a new block is proposed. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proposal { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub proposal: ::core::option::Option, } /// ProposalPOL is sent when a previous proposal is re-proposed. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProposalPol { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub proposal_pol_round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proposal_pol: ::core::option::Option, } /// BlockPart is sent when gossipping a piece of the proposed block. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockPart { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub part: ::core::option::Option, } /// Vote is sent when voting for a proposal (or lack thereof). +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Vote { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote: ::core::option::Option, } /// HasVote is sent to indicate that a particular vote has been received. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct HasVote { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(enumeration="super::types::SignedMsgType", tag="3")] + #[prost(enumeration = "super::types::SignedMsgType", tag = "3")] pub r#type: i32, - #[prost(int32, tag="4")] + #[prost(int32, tag = "4")] pub index: i32, } /// VoteSetMaj23 is sent to indicate that a given BlockID has seen +2/3 votes. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteSetMaj23 { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(enumeration="super::types::SignedMsgType", tag="3")] + #[prost(enumeration = "super::types::SignedMsgType", tag = "3")] pub r#type: i32, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, } /// VoteSetBits is sent to communicate the bit-array of votes seen for the BlockID. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VoteSetBits { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(enumeration="super::types::SignedMsgType", tag="3")] + #[prost(enumeration = "super::types::SignedMsgType", tag = "3")] pub r#type: i32, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub votes: ::core::option::Option, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5, 6, 7, 8, 9")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4, 5, 6, 7, 8, 9")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] NewRoundStep(super::NewRoundStep), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] NewValidBlock(super::NewValidBlock), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] Proposal(super::Proposal), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] ProposalPol(super::ProposalPol), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] BlockPart(super::BlockPart), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] Vote(super::Vote), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] HasVote(super::HasVote), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] VoteSetMaj23(super::VoteSetMaj23), - #[prost(message, tag="9")] + #[prost(message, tag = "9")] VoteSetBits(super::VoteSetBits), } } /// MsgInfo are msgs from the reactor which may update the state +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct MsgInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub msg: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub peer_id: ::prost::alloc::string::String, } /// TimeoutInfo internally generated messages which may update the state +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TimeoutInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub duration: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, - #[prost(uint32, tag="4")] + #[prost(uint32, tag = "4")] pub step: u32, } /// EndHeight marks the end of the given height inside WAL. /// @internal used by scripts/wal2json util. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EndHeight { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct WalMessage { - #[prost(oneof="wal_message::Sum", tags="1, 2, 3, 4")] + #[prost(oneof = "wal_message::Sum", tags = "1, 2, 3, 4")] pub sum: ::core::option::Option, } /// Nested message and enum types in `WALMessage`. pub mod wal_message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] EventDataRoundState(super::super::types::EventDataRoundState), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] MsgInfo(super::MsgInfo), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] TimeoutInfo(super::TimeoutInfo), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] EndHeight(super::EndHeight), } } /// TimedWALMessage wraps WALMessage and adds Time for debugging purposes. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TimedWalMessage { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub time: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub msg: ::core::option::Option, } diff --git a/proto/src/prost/v0_37/tendermint.crypto.rs b/proto/src/prost/v0_37/tendermint.crypto.rs index 0fac07973..fed646029 100644 --- a/proto/src/prost/v0_37/tendermint.crypto.rs +++ b/proto/src/prost/v0_37/tendermint.crypto.rs @@ -1,73 +1,86 @@ #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proof { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] #[serde(with = "crate::serializers::from_str")] pub total: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub index: i64, - #[prost(bytes="vec", tag="3")] + #[prost(bytes = "vec", tag = "3")] #[serde(with = "crate::serializers::bytes::base64string")] pub leaf_hash: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", repeated, tag="4")] + #[prost(bytes = "vec", repeated, tag = "4")] #[serde(with = "crate::serializers::bytes::vec_base64string")] pub aunts: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValueOp { /// Encoded in ProofOp.Key. - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] pub key: ::prost::alloc::vec::Vec, /// To encode in ProofOp.Data - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub proof: ::core::option::Option, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DominoOp { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub key: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub input: ::prost::alloc::string::String, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub output: ::prost::alloc::string::String, } /// ProofOp defines an operation used for calculating Merkle root /// The data could be arbitrary format, providing nessecary data /// for example neighbouring node hash +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProofOp { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub r#type: ::prost::alloc::string::String, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub key: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", tag="3")] + #[prost(bytes = "vec", tag = "3")] pub data: ::prost::alloc::vec::Vec, } /// ProofOps is Merkle proof defined by the list of ProofOps +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProofOps { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub ops: ::prost::alloc::vec::Vec, } /// PublicKey defines the keys available for use with Tendermint Validators #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PublicKey { - #[prost(oneof="public_key::Sum", tags="1, 2")] + #[prost(oneof = "public_key::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `PublicKey`. pub mod public_key { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(bytes, tag="1")] - #[serde(rename = "tendermint/PubKeyEd25519", with = "crate::serializers::bytes::base64string")] + #[prost(bytes, tag = "1")] + #[serde( + rename = "tendermint/PubKeyEd25519", + with = "crate::serializers::bytes::base64string" + )] Ed25519(::prost::alloc::vec::Vec), - #[prost(bytes, tag="2")] - #[serde(rename = "tendermint/PubKeySecp256k1", with = "crate::serializers::bytes::base64string")] + #[prost(bytes, tag = "2")] + #[serde( + rename = "tendermint/PubKeySecp256k1", + with = "crate::serializers::bytes::base64string" + )] Secp256k1(::prost::alloc::vec::Vec), } } diff --git a/proto/src/prost/v0_37/tendermint.libs.bits.rs b/proto/src/prost/v0_37/tendermint.libs.bits.rs index 47eee3773..460876d21 100644 --- a/proto/src/prost/v0_37/tendermint.libs.bits.rs +++ b/proto/src/prost/v0_37/tendermint.libs.bits.rs @@ -1,8 +1,9 @@ #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BitArray { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub bits: i64, - #[prost(uint64, repeated, tag="2")] + #[prost(uint64, repeated, tag = "2")] pub elems: ::prost::alloc::vec::Vec, } diff --git a/proto/src/prost/v0_37/tendermint.mempool.rs b/proto/src/prost/v0_37/tendermint.mempool.rs index af22801ba..9fec1376b 100644 --- a/proto/src/prost/v0_37/tendermint.mempool.rs +++ b/proto/src/prost/v0_37/tendermint.mempool.rs @@ -1,18 +1,21 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Txs { - #[prost(bytes="vec", repeated, tag="1")] + #[prost(bytes = "vec", repeated, tag = "1")] pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1")] + #[prost(oneof = "message::Sum", tags = "1")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] Txs(super::Txs), } } diff --git a/proto/src/prost/v0_37/tendermint.p2p.rs b/proto/src/prost/v0_37/tendermint.p2p.rs index 4b81d0be0..bfaa808cb 100644 --- a/proto/src/prost/v0_37/tendermint.p2p.rs +++ b/proto/src/prost/v0_37/tendermint.p2p.rs @@ -1,106 +1,117 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPing { -} +pub struct PacketPing {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PacketPong { -} +pub struct PacketPong {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PacketMsg { - #[prost(int32, tag="1")] + #[prost(int32, tag = "1")] pub channel_id: i32, - #[prost(bool, tag="2")] + #[prost(bool, tag = "2")] pub eof: bool, - #[prost(bytes="vec", tag="3")] + #[prost(bytes = "vec", tag = "3")] pub data: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Packet { - #[prost(oneof="packet::Sum", tags="1, 2, 3")] + #[prost(oneof = "packet::Sum", tags = "1, 2, 3")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Packet`. pub mod packet { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] PacketPing(super::PacketPing), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] PacketPong(super::PacketPong), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] PacketMsg(super::PacketMsg), } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct AuthSigMessage { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub sig: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct NetAddress { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub id: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub ip: ::prost::alloc::string::String, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub port: u32, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ProtocolVersion { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub p2p: u64, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] pub block: u64, - #[prost(uint64, tag="3")] + #[prost(uint64, tag = "3")] pub app: u64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub protocol_version: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub default_node_id: ::prost::alloc::string::String, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub listen_addr: ::prost::alloc::string::String, - #[prost(string, tag="4")] + #[prost(string, tag = "4")] pub network: ::prost::alloc::string::String, - #[prost(string, tag="5")] + #[prost(string, tag = "5")] pub version: ::prost::alloc::string::String, - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] pub channels: ::prost::alloc::vec::Vec, - #[prost(string, tag="7")] + #[prost(string, tag = "7")] pub moniker: ::prost::alloc::string::String, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub other: ::core::option::Option, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DefaultNodeInfoOther { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub tx_index: ::prost::alloc::string::String, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub rpc_address: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PexRequest { -} +pub struct PexRequest {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PexAddrs { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub addrs: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2")] + #[prost(oneof = "message::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] PexRequest(super::PexRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] PexAddrs(super::PexAddrs), } } diff --git a/proto/src/prost/v0_37/tendermint.privval.rs b/proto/src/prost/v0_37/tendermint.privval.rs index 892a10bbf..1fae1cbee 100644 --- a/proto/src/prost/v0_37/tendermint.privval.rs +++ b/proto/src/prost/v0_37/tendermint.privval.rs @@ -1,88 +1,97 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RemoteSignerError { - #[prost(int32, tag="1")] + #[prost(int32, tag = "1")] pub code: i32, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub description: ::prost::alloc::string::String, } /// PubKeyRequest requests the consensus public key from the remote signer. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PubKeyRequest { - #[prost(string, tag="1")] + #[prost(string, tag = "1")] pub chain_id: ::prost::alloc::string::String, } /// PubKeyResponse is a response message containing the public key. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PubKeyResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub error: ::core::option::Option, } /// SignVoteRequest is a request to sign a vote +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignVoteRequest { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, } /// SignedVoteResponse is a response containing a signed vote or an error +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignedVoteResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub error: ::core::option::Option, } /// SignProposalRequest is a request to sign a proposal +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignProposalRequest { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub proposal: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, } /// SignedProposalResponse is response containing a signed proposal or an error +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignedProposalResponse { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub proposal: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub error: ::core::option::Option, } /// PingRequest is a request to confirm that the connection is alive. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PingRequest { -} +pub struct PingRequest {} /// PingResponse is a response to confirm that the connection is alive. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct PingResponse { -} +pub struct PingResponse {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4, 5, 6, 7, 8")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4, 5, 6, 7, 8")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] PubKeyRequest(super::PubKeyRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] PubKeyResponse(super::PubKeyResponse), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] SignVoteRequest(super::SignVoteRequest), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] SignedVoteResponse(super::SignedVoteResponse), - #[prost(message, tag="5")] + #[prost(message, tag = "5")] SignProposalRequest(super::SignProposalRequest), - #[prost(message, tag="6")] + #[prost(message, tag = "6")] SignedProposalResponse(super::SignedProposalResponse), - #[prost(message, tag="7")] + #[prost(message, tag = "7")] PingRequest(super::PingRequest), - #[prost(message, tag="8")] + #[prost(message, tag = "8")] PingResponse(super::PingResponse), } } diff --git a/proto/src/prost/v0_37/tendermint.rpc.grpc.rs b/proto/src/prost/v0_37/tendermint.rpc.grpc.rs index 4739bccac..5630cb50c 100644 --- a/proto/src/prost/v0_37/tendermint.rpc.grpc.rs +++ b/proto/src/prost/v0_37/tendermint.rpc.grpc.rs @@ -1,24 +1,20 @@ -// ---------------------------------------- -// Request types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct RequestPing { -} +pub struct RequestPing {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct RequestBroadcastTx { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] pub tx: ::prost::alloc::vec::Vec, } -// ---------------------------------------- -// Response types - +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct ResponsePing { -} +pub struct ResponsePing {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ResponseBroadcastTx { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub check_tx: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub deliver_tx: ::core::option::Option, } diff --git a/proto/src/prost/v0_37/tendermint.state.rs b/proto/src/prost/v0_37/tendermint.state.rs index c996b31a5..dd006a2c6 100644 --- a/proto/src/prost/v0_37/tendermint.state.rs +++ b/proto/src/prost/v0_37/tendermint.state.rs @@ -1,60 +1,66 @@ /// ABCIResponses retains the responses /// of the various ABCI calls during block processing. /// It is persisted to disk for each height before calling Commit. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct AbciResponses { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub deliver_txs: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub end_block: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub begin_block: ::core::option::Option, } /// ValidatorsInfo represents the latest validator set, or the last height it changed +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorsInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub validator_set: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub last_height_changed: i64, } /// ConsensusParamsInfo represents the latest consensus params, or the last height it changed +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ConsensusParamsInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub consensus_params: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub last_height_changed: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct AbciResponsesInfo { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub abci_responses: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Version { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub consensus: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub software: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct State { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub version: ::core::option::Option, /// immutable - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(int64, tag="14")] + #[prost(int64, tag = "14")] pub initial_height: i64, /// LastBlockHeight=0 at genesis (ie. block(H=0) does not exist) - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub last_block_height: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub last_block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub last_block_time: ::core::option::Option, /// LastValidators is used to validate block.LastCommit. /// Validators are persisted to the database separately every time they change, @@ -62,24 +68,24 @@ pub struct State { /// Note that if s.LastBlockHeight causes a valset change, /// we set s.LastHeightValidatorsChanged = s.LastBlockHeight + 1 + 1 /// Extra +1 due to nextValSet delay. - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub next_validators: ::core::option::Option, - #[prost(message, optional, tag="7")] + #[prost(message, optional, tag = "7")] pub validators: ::core::option::Option, - #[prost(message, optional, tag="8")] + #[prost(message, optional, tag = "8")] pub last_validators: ::core::option::Option, - #[prost(int64, tag="9")] + #[prost(int64, tag = "9")] pub last_height_validators_changed: i64, /// Consensus parameters used for validating blocks. /// Changes returned by EndBlock and updated after Commit. - #[prost(message, optional, tag="10")] + #[prost(message, optional, tag = "10")] pub consensus_params: ::core::option::Option, - #[prost(int64, tag="11")] + #[prost(int64, tag = "11")] pub last_height_consensus_params_changed: i64, /// Merkle root of the results from executing prev block - #[prost(bytes="vec", tag="12")] + #[prost(bytes = "vec", tag = "12")] pub last_results_hash: ::prost::alloc::vec::Vec, /// the latest AppHash we've received from calling abci.Commit() - #[prost(bytes="vec", tag="13")] + #[prost(bytes = "vec", tag = "13")] pub app_hash: ::prost::alloc::vec::Vec, } diff --git a/proto/src/prost/v0_37/tendermint.statesync.rs b/proto/src/prost/v0_37/tendermint.statesync.rs index 593bd0222..a2ad034e3 100644 --- a/proto/src/prost/v0_37/tendermint.statesync.rs +++ b/proto/src/prost/v0_37/tendermint.statesync.rs @@ -1,57 +1,62 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Message { - #[prost(oneof="message::Sum", tags="1, 2, 3, 4")] + #[prost(oneof = "message::Sum", tags = "1, 2, 3, 4")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Message`. pub mod message { + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] SnapshotsRequest(super::SnapshotsRequest), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] SnapshotsResponse(super::SnapshotsResponse), - #[prost(message, tag="3")] + #[prost(message, tag = "3")] ChunkRequest(super::ChunkRequest), - #[prost(message, tag="4")] + #[prost(message, tag = "4")] ChunkResponse(super::ChunkResponse), } } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] -pub struct SnapshotsRequest { -} +pub struct SnapshotsRequest {} +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SnapshotsResponse { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub chunks: u32, - #[prost(bytes="vec", tag="4")] + #[prost(bytes = "vec", tag = "4")] pub hash: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", tag="5")] + #[prost(bytes = "vec", tag = "5")] pub metadata: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ChunkRequest { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub index: u32, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ChunkResponse { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub height: u64, - #[prost(uint32, tag="2")] + #[prost(uint32, tag = "2")] pub format: u32, - #[prost(uint32, tag="3")] + #[prost(uint32, tag = "3")] pub index: u32, - #[prost(bytes="vec", tag="4")] + #[prost(bytes = "vec", tag = "4")] pub chunk: ::prost::alloc::vec::Vec, - #[prost(bool, tag="5")] + #[prost(bool, tag = "5")] pub missing: bool, } diff --git a/proto/src/prost/v0_37/tendermint.store.rs b/proto/src/prost/v0_37/tendermint.store.rs index a4c2799d9..98d20b0fc 100644 --- a/proto/src/prost/v0_37/tendermint.store.rs +++ b/proto/src/prost/v0_37/tendermint.store.rs @@ -1,7 +1,8 @@ +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockStoreState { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub base: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, } diff --git a/proto/src/prost/v0_37/tendermint.types.rs b/proto/src/prost/v0_37/tendermint.types.rs index bb5dce6c6..3b93c0932 100644 --- a/proto/src/prost/v0_37/tendermint.types.rs +++ b/proto/src/prost/v0_37/tendermint.types.rs @@ -1,256 +1,270 @@ #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorSet { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] pub validators: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub proposer: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] pub total_voting_power: i64, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Validator { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(alias = "power", with = "crate::serializers::from_str")] pub voting_power: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str", default)] pub proposer_priority: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SimpleValidator { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub pub_key: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub voting_power: i64, } /// PartsetHeader #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct PartSetHeader { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] #[serde(with = "crate::serializers::part_set_header_total")] pub total: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Part { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub index: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub bytes: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proof: ::core::option::Option, } /// BlockID #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockId { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } -// -------------------------------- - /// Header defines the structure of a Tendermint block header. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Header { /// basic block info - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub version: ::core::option::Option, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub chain_id: ::prost::alloc::string::String, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] #[serde(with = "crate::serializers::optional")] pub time: ::core::option::Option, /// prev block info - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub last_block_id: ::core::option::Option, /// hashes of block data /// /// commit from validators from the last block - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_commit_hash: ::prost::alloc::vec::Vec, /// transactions - #[prost(bytes="vec", tag="7")] + #[prost(bytes = "vec", tag = "7")] #[serde(with = "crate::serializers::bytes::hexstring")] pub data_hash: ::prost::alloc::vec::Vec, /// hashes from the app output from the prev block /// /// validators for the current block - #[prost(bytes="vec", tag="8")] + #[prost(bytes = "vec", tag = "8")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validators_hash: ::prost::alloc::vec::Vec, /// validators for the next block - #[prost(bytes="vec", tag="9")] + #[prost(bytes = "vec", tag = "9")] #[serde(with = "crate::serializers::bytes::hexstring")] pub next_validators_hash: ::prost::alloc::vec::Vec, /// consensus params for current block - #[prost(bytes="vec", tag="10")] + #[prost(bytes = "vec", tag = "10")] #[serde(with = "crate::serializers::bytes::hexstring")] pub consensus_hash: ::prost::alloc::vec::Vec, /// state after txs from the previous block - #[prost(bytes="vec", tag="11")] + #[prost(bytes = "vec", tag = "11")] #[serde(with = "crate::serializers::bytes::hexstring")] pub app_hash: ::prost::alloc::vec::Vec, /// root hash of all results from the txs from the previous block - #[prost(bytes="vec", tag="12")] + #[prost(bytes = "vec", tag = "12")] #[serde(with = "crate::serializers::bytes::hexstring")] pub last_results_hash: ::prost::alloc::vec::Vec, /// consensus info /// /// evidence included in the block - #[prost(bytes="vec", tag="13")] + #[prost(bytes = "vec", tag = "13")] #[serde(with = "crate::serializers::bytes::hexstring")] pub evidence_hash: ::prost::alloc::vec::Vec, /// original proposer of the block - #[prost(bytes="vec", tag="14")] + #[prost(bytes = "vec", tag = "14")] #[serde(with = "crate::serializers::bytes::hexstring")] pub proposer_address: ::prost::alloc::vec::Vec, } /// Data contains the set of transactions included in the block #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Data { /// Txs that will be applied by state @ block.Height+1. /// NOTE: not all txs here are valid. We're just agreeing on the order first. /// This means that block.AppHash does not include these txs. - #[prost(bytes="vec", repeated, tag="1")] + #[prost(bytes = "vec", repeated, tag = "1")] #[serde(with = "crate::serializers::txs")] pub txs: ::prost::alloc::vec::Vec<::prost::alloc::vec::Vec>, } /// Vote represents a prevote, precommit, or commit vote from validators for /// consensus. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Vote { - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, /// zero if vote is nil. - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] #[serde(with = "crate::serializers::optional")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="6")] + #[prost(bytes = "vec", tag = "6")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(int32, tag="7")] + #[prost(int32, tag = "7")] pub validator_index: i32, - #[prost(bytes="vec", tag="8")] + #[prost(bytes = "vec", tag = "8")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } /// Commit contains the evidence that a block was committed by a set of validators. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Commit { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] #[serde(with = "crate::serializers::from_str")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub block_id: ::core::option::Option, - #[prost(message, repeated, tag="4")] + #[prost(message, repeated, tag = "4")] #[serde(with = "crate::serializers::nullable")] pub signatures: ::prost::alloc::vec::Vec, } /// CommitSig is a part of the Vote included in a Commit. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CommitSig { - #[prost(enumeration="BlockIdFlag", tag="1")] + #[prost(enumeration = "BlockIdFlag", tag = "1")] pub block_id_flag: i32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::hexstring")] pub validator_address: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] #[serde(with = "crate::serializers::optional")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="4")] + #[prost(bytes = "vec", tag = "4")] #[serde(with = "crate::serializers::bytes::base64string")] pub signature: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Proposal { - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub height: i64, - #[prost(int32, tag="3")] + #[prost(int32, tag = "3")] pub round: i32, - #[prost(int32, tag="4")] + #[prost(int32, tag = "4")] pub pol_round: i32, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub timestamp: ::core::option::Option, - #[prost(bytes="vec", tag="7")] + #[prost(bytes = "vec", tag = "7")] pub signature: ::prost::alloc::vec::Vec, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct SignedHeader { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub commit: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct LightBlock { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub signed_header: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub validator_set: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockMeta { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block_id: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] #[serde(with = "crate::serializers::from_str")] pub block_size: i64, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub header: ::core::option::Option
, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(with = "crate::serializers::from_str")] pub num_txs: i64, } /// TxProof represents a Merkle proof of the presence of a transaction in the Merkle tree. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct TxProof { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] #[serde(with = "crate::serializers::bytes::hexstring")] pub root_hash: ::prost::alloc::vec::Vec, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] #[serde(with = "crate::serializers::bytes::base64string")] pub data: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub proof: ::core::option::Option, } /// BlockIdFlag indicates which BlcokID the signature is for @@ -304,209 +318,226 @@ impl SignedMsgType { } /// ConsensusParams contains consensus critical parameters that determine the /// validity of blocks. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ConsensusParams { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub block: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub validator: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub version: ::core::option::Option, } /// BlockParams contains limits on the block size. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct BlockParams { /// Max block size, in bytes. /// Note: must be greater than 0 - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_bytes: i64, /// Max gas per block. /// Note: must be greater or equal to -1 - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub max_gas: i64, } /// EvidenceParams determine how we handle evidence of malfeasance. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EvidenceParams { /// Max age of evidence, in blocks. /// /// The basic formula for calculating this is: MaxAgeDuration / {average block /// time}. - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub max_age_num_blocks: i64, /// Max age of evidence, in time. /// /// It should correspond with an app's "unbonding period" or other similar /// mechanism for handling [Nothing-At-Stake /// attacks](). - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub max_age_duration: ::core::option::Option, /// This sets the maximum size of total evidence in bytes that can be committed in a single block. /// and should fall comfortably under the max block bytes. /// Default is 1048576 or 1MB - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(with = "crate::serializers::from_str", default)] pub max_bytes: i64, } /// ValidatorParams restrict the public key types validators can use. /// NOTE: uses ABCI pubkey naming, not Amino names. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct ValidatorParams { - #[prost(string, repeated, tag="1")] + #[prost(string, repeated, tag = "1")] pub pub_key_types: ::prost::alloc::vec::Vec<::prost::alloc::string::String>, } /// VersionParams contains the ABCI application version. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct VersionParams { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub app: u64, } /// HashedParams is a subset of ConsensusParams. /// /// It is hashed into the Header.ConsensusHash. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct HashedParams { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub block_max_bytes: i64, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub block_max_gas: i64, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EventDataRoundState { - #[prost(int64, tag="1")] + #[prost(int64, tag = "1")] pub height: i64, - #[prost(int32, tag="2")] + #[prost(int32, tag = "2")] pub round: i32, - #[prost(string, tag="3")] + #[prost(string, tag = "3")] pub step: ::prost::alloc::string::String, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Evidence { - #[prost(oneof="evidence::Sum", tags="1, 2")] + #[prost(oneof = "evidence::Sum", tags = "1, 2")] pub sum: ::core::option::Option, } /// Nested message and enum types in `Evidence`. pub mod evidence { #[derive(::serde::Deserialize, ::serde::Serialize)] #[serde(tag = "type", content = "value")] + #[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Oneof)] pub enum Sum { - #[prost(message, tag="1")] + #[prost(message, tag = "1")] #[serde(rename = "tendermint/DuplicateVoteEvidence")] DuplicateVoteEvidence(super::DuplicateVoteEvidence), - #[prost(message, tag="2")] + #[prost(message, tag = "2")] #[serde(rename = "tendermint/LightClientAttackEvidence")] LightClientAttackEvidence(super::LightClientAttackEvidence), } } /// DuplicateVoteEvidence contains evidence of a validator signed two conflicting votes. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct DuplicateVoteEvidence { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub vote_a: ::core::option::Option, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub vote_b: ::core::option::Option, - #[prost(int64, tag="3")] + #[prost(int64, tag = "3")] #[serde(alias = "TotalVotingPower", with = "crate::serializers::from_str")] pub total_voting_power: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] #[serde(alias = "ValidatorPower", with = "crate::serializers::from_str")] pub validator_power: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] #[serde(alias = "Timestamp")] pub timestamp: ::core::option::Option, } /// LightClientAttackEvidence contains evidence of a set of validators attempting to mislead a light client. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct LightClientAttackEvidence { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub conflicting_block: ::core::option::Option, - #[prost(int64, tag="2")] + #[prost(int64, tag = "2")] pub common_height: i64, - #[prost(message, repeated, tag="3")] + #[prost(message, repeated, tag = "3")] pub byzantine_validators: ::prost::alloc::vec::Vec, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub total_voting_power: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub timestamp: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct EvidenceList { - #[prost(message, repeated, tag="1")] + #[prost(message, repeated, tag = "1")] #[serde(with = "crate::serializers::nullable")] pub evidence: ::prost::alloc::vec::Vec, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Block { - #[prost(message, optional, tag="1")] + #[prost(message, optional, tag = "1")] pub header: ::core::option::Option
, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] pub data: ::core::option::Option, - #[prost(message, optional, tag="3")] + #[prost(message, optional, tag = "3")] pub evidence: ::core::option::Option, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub last_commit: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalBlockId { - #[prost(bytes="vec", tag="1")] + #[prost(bytes = "vec", tag = "1")] pub hash: ::prost::alloc::vec::Vec, - #[prost(message, optional, tag="2")] + #[prost(message, optional, tag = "2")] #[serde(alias = "parts")] pub part_set_header: ::core::option::Option, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalPartSetHeader { - #[prost(uint32, tag="1")] + #[prost(uint32, tag = "1")] pub total: u32, - #[prost(bytes="vec", tag="2")] + #[prost(bytes = "vec", tag = "2")] pub hash: ::prost::alloc::vec::Vec, } +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalProposal { /// type alias for byte - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="2")] + #[prost(sfixed64, tag = "2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="3")] + #[prost(sfixed64, tag = "3")] pub round: i64, - #[prost(int64, tag="4")] + #[prost(int64, tag = "4")] pub pol_round: i64, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="6")] + #[prost(message, optional, tag = "6")] pub timestamp: ::core::option::Option, - #[prost(string, tag="7")] + #[prost(string, tag = "7")] pub chain_id: ::prost::alloc::string::String, } #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct CanonicalVote { /// type alias for byte - #[prost(enumeration="SignedMsgType", tag="1")] + #[prost(enumeration = "SignedMsgType", tag = "1")] pub r#type: i32, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="2")] + #[prost(sfixed64, tag = "2")] pub height: i64, /// canonicalization requires fixed size encoding here - #[prost(sfixed64, tag="3")] + #[prost(sfixed64, tag = "3")] pub round: i64, - #[prost(message, optional, tag="4")] + #[prost(message, optional, tag = "4")] pub block_id: ::core::option::Option, - #[prost(message, optional, tag="5")] + #[prost(message, optional, tag = "5")] pub timestamp: ::core::option::Option, - #[prost(string, tag="6")] + #[prost(string, tag = "6")] pub chain_id: ::prost::alloc::string::String, } diff --git a/proto/src/prost/v0_37/tendermint.version.rs b/proto/src/prost/v0_37/tendermint.version.rs index bd1227266..8a77a26fc 100644 --- a/proto/src/prost/v0_37/tendermint.version.rs +++ b/proto/src/prost/v0_37/tendermint.version.rs @@ -1,23 +1,25 @@ /// App includes the protocol and software version for the application. /// This information is included in ResponseInfo. The App.Protocol can be /// updated in ResponseEndBlock. +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct App { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] pub protocol: u64, - #[prost(string, tag="2")] + #[prost(string, tag = "2")] pub software: ::prost::alloc::string::String, } /// Consensus captures the consensus rules for processing a block in the blockchain, /// including all blockchain data structures and the rules of the application's /// state transition machine. #[derive(::serde::Deserialize, ::serde::Serialize)] +#[allow(clippy::derive_partial_eq_without_eq)] #[derive(Clone, PartialEq, ::prost::Message)] pub struct Consensus { - #[prost(uint64, tag="1")] + #[prost(uint64, tag = "1")] #[serde(with = "crate::serializers::from_str")] pub block: u64, - #[prost(uint64, tag="2")] + #[prost(uint64, tag = "2")] #[serde(with = "crate::serializers::from_str", default)] pub app: u64, } diff --git a/proto/src/tendermint.rs b/proto/src/tendermint.rs index dfe07be1d..4a8211a91 100644 --- a/proto/src/tendermint.rs +++ b/proto/src/tendermint.rs @@ -1,2 +1,3 @@ pub mod v0_34; pub mod v0_37; +pub use v0_37::*; diff --git a/proto/src/tendermint/v0_34.rs b/proto/src/tendermint/v0_34.rs index c9fa5e266..2457ed879 100644 --- a/proto/src/tendermint/v0_34.rs +++ b/proto/src/tendermint/v0_34.rs @@ -62,5 +62,5 @@ pub mod version { pub mod meta { pub const REPOSITORY: &str = "https://github.com/tendermint/tendermint"; - pub const COMMITISH: &str = "v0.34.22"; + pub const COMMITISH: &str = "v0.34.24"; } diff --git a/tools/proto-compiler/Cargo.toml b/tools/proto-compiler/Cargo.toml index 1e5806428..c33065869 100644 --- a/tools/proto-compiler/Cargo.toml +++ b/tools/proto-compiler/Cargo.toml @@ -7,7 +7,7 @@ publish = false [dependencies] walkdir = { version = "2.3" } -prost-build = { version = "0.11" } +prost-build = { version = "0.11.4" } git2 = { version = "0.13" } tempfile = { version = "3.2.0" } subtle-encoding = { version = "0.5" } diff --git a/tools/proto-compiler/src/constants.rs b/tools/proto-compiler/src/constants.rs index 0dc057b05..556f9d8b4 100644 --- a/tools/proto-compiler/src/constants.rs +++ b/tools/proto-compiler/src/constants.rs @@ -19,7 +19,7 @@ pub struct TendermintVersion { pub const TENDERMINT_VERSIONS: &[TendermintVersion] = &[ TendermintVersion { ident: "v0_34", - commitish: "v0.34.22", + commitish: "v0.34.24", }, TendermintVersion { ident: "v0_37", From 0bea5cf6ced26d63085b32c0ce0b2ad8d96e4b1e Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 19 Dec 2022 17:24:38 +0200 Subject: [PATCH 26/77] rpc: add endpoints header and header_by_hash Provided by v0.37 nodes. --- rpc/src/endpoint.rs | 2 ++ rpc/src/endpoint/header.rs | 41 ++++++++++++++++++++++++++ rpc/src/endpoint/header_by_hash.rs | 47 ++++++++++++++++++++++++++++++ rpc/src/method.rs | 10 +++++++ 4 files changed, 100 insertions(+) create mode 100644 rpc/src/endpoint/header.rs create mode 100644 rpc/src/endpoint/header_by_hash.rs diff --git a/rpc/src/endpoint.rs b/rpc/src/endpoint.rs index 2e749aaa6..f04c2a0df 100644 --- a/rpc/src/endpoint.rs +++ b/rpc/src/endpoint.rs @@ -13,6 +13,8 @@ pub mod consensus_params; pub mod consensus_state; pub mod evidence; pub mod genesis; +pub mod header; +pub mod header_by_hash; pub mod health; pub mod net_info; pub mod status; diff --git a/rpc/src/endpoint/header.rs b/rpc/src/endpoint/header.rs new file mode 100644 index 000000000..373f9d346 --- /dev/null +++ b/rpc/src/endpoint/header.rs @@ -0,0 +1,41 @@ +//! `/header` endpoint JSON-RPC wrapper + +use serde::{Deserialize, Serialize}; +use tendermint::block::{self, Header}; + +/// Get information about a specific block +#[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] +pub struct Request { + /// Height of the block header to request. + /// + /// If no height is provided, it will fetch results for the latest block. + pub height: Option, +} + +impl Request { + /// Create a new request for header information about a particular block + pub fn new(height: block::Height) -> Self { + Self { + height: Some(height), + } + } +} + +impl crate::Request for Request { + type Response = Response; + + fn method(&self) -> crate::Method { + crate::Method::Header + } +} + +impl crate::SimpleRequest for Request {} + +/// Header response +#[derive(Clone, Debug, Deserialize, Serialize)] +pub struct Response { + /// Header data + pub header: Header, +} + +impl crate::Response for Response {} diff --git a/rpc/src/endpoint/header_by_hash.rs b/rpc/src/endpoint/header_by_hash.rs new file mode 100644 index 000000000..0406942e4 --- /dev/null +++ b/rpc/src/endpoint/header_by_hash.rs @@ -0,0 +1,47 @@ +//! `/header_by_hash` endpoint JSON-RPC wrapper + +use serde::{Deserialize, Serialize}; +use tendermint::{block::Header, Hash}; + +/// Get information about a specific block by its hash +#[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] +pub struct Request { + /// Hash of the block to request. + /// + /// If no hash is provided, it will return no header (as if the hash + /// did not match any block). + /// + /// Serialized internally into a hex-encoded string before sending to + /// the RPC server. + #[serde(default)] + #[serde(with = "crate::serializers::option_hash")] + pub hash: Option, +} + +impl Request { + /// Create a new request for information about a particular block + pub fn new>(hash: H) -> Self { + Self { + hash: Some(hash.into()), + } + } +} + +impl crate::Request for Request { + type Response = Response; + + fn method(&self) -> crate::Method { + crate::Method::HeaderByHash + } +} + +impl crate::SimpleRequest for Request {} + +/// Header response +#[derive(Clone, Debug, Deserialize, Serialize)] +pub struct Response { + /// Header data + pub header: Option
, +} + +impl crate::Response for Response {} diff --git a/rpc/src/method.rs b/rpc/src/method.rs index aaffd85c6..b6d663ffe 100644 --- a/rpc/src/method.rs +++ b/rpc/src/method.rs @@ -56,6 +56,12 @@ pub enum Method { /// Get genesis file Genesis, + /// Get block header + Header, + + /// Get block header by hash + HeaderByHash, + /// Get health info Health, @@ -103,6 +109,8 @@ impl Method { Method::ConsensusParams => "consensus_params", Method::ConsensusState => "consensus_state", Method::Genesis => "genesis", + Method::Header => "header", + Method::HeaderByHash => "header_by_hash", Method::Health => "health", Method::NetInfo => "net_info", Method::Status => "status", @@ -125,6 +133,8 @@ impl FromStr for Method { "block" => Method::Block, "block_by_hash" => Method::BlockByHash, "block_results" => Method::BlockResults, + "header" => Method::Header, + "header_by_hash" => Method::HeaderByHash, "block_search" => Method::BlockSearch, "blockchain" => Method::Blockchain, "broadcast_evidence" => Method::BroadcastEvidence, From d7e71009316d97c9eb101c0433bd3b2694384a2b Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 19 Dec 2022 17:47:02 +0200 Subject: [PATCH 27/77] rpc: Separate Client traits for v0.34 and v0.37 Add new endpoints /header and /header_by_hash to the v0_37::Client trait, and re-export it as new crate::Client. --- rpc/src/client.rs | 291 ----------------------------- rpc/src/client/transport/http.rs | 15 +- rpc/src/client/transport/mock.rs | 82 ++++++-- rpc/src/lib.rs | 12 +- rpc/src/v0_34.rs | 3 + rpc/src/v0_34/client.rs | 294 +++++++++++++++++++++++++++++ rpc/src/v0_37.rs | 3 + rpc/src/v0_37/client.rs | 310 +++++++++++++++++++++++++++++++ 8 files changed, 693 insertions(+), 317 deletions(-) create mode 100644 rpc/src/v0_34.rs create mode 100644 rpc/src/v0_34/client.rs create mode 100644 rpc/src/v0_37.rs create mode 100644 rpc/src/v0_37/client.rs diff --git a/rpc/src/client.rs b/rpc/src/client.rs index 403baa5a4..e3c2eb63f 100644 --- a/rpc/src/client.rs +++ b/rpc/src/client.rs @@ -5,12 +5,7 @@ pub use subscription::{Subscription, SubscriptionClient}; pub mod sync; mod transport; -use core::{fmt, time::Duration}; -use async_trait::async_trait; -use serde::{de::DeserializeOwned, Serialize}; -use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; -use tokio::time; #[cfg(feature = "http-client")] pub use transport::http::{HttpClient, HttpClientUrl}; pub use transport::mock::{MockClient, MockRequestMatcher, MockRequestMethodMatcher}; @@ -18,289 +13,3 @@ pub use transport::mock::{MockClient, MockRequestMatcher, MockRequestMethodMatch pub use transport::websocket::{ WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig, }; - -use crate::{ - endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, - paging::Paging, - prelude::*, - query::Query, - Error, Order, SimpleRequest, -}; - -/// Provides lightweight access to the Tendermint RPC. It gives access to all -/// endpoints with the exception of the event subscription-related ones. -/// -/// To access event subscription capabilities, use a client that implements the -/// [`SubscriptionClient`] trait. -/// -/// [`SubscriptionClient`]: trait.SubscriptionClient.html -#[async_trait] -pub trait Client { - /// `/abci_info`: get information about the ABCI application. - async fn abci_info(&self) -> Result { - Ok(self.perform(abci_info::Request).await?.response) - } - - /// `/abci_query`: query the ABCI application - async fn abci_query( - &self, - path: Option, - data: V, - height: Option, - prove: bool, - ) -> Result - where - V: Into> + Send, - { - Ok(self - .perform(abci_query::Request::new(path, data, height, prove)) - .await? - .response) - } - - /// `/block`: get block at a given height. - async fn block(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(block::Request::new(height.into())).await - } - - /// `/block_by_hash`: get block by hash. - async fn block_by_hash( - &self, - hash: tendermint::Hash, - ) -> Result { - self.perform(block_by_hash::Request::new(hash)).await - } - - /// `/block`: get the latest block. - async fn latest_block(&self) -> Result { - self.perform(block::Request::default()).await - } - - /// `/block_results`: get ABCI results for a block at a particular height. - async fn block_results(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(block_results::Request::new(height.into())) - .await - } - - /// `/block_results`: get ABCI results for the latest block. - async fn latest_block_results(&self) -> Result { - self.perform(block_results::Request::default()).await - } - - /// `/block_search`: search for blocks by BeginBlock and EndBlock events. - async fn block_search( - &self, - query: Query, - page: u32, - per_page: u8, - order: Order, - ) -> Result { - self.perform(block_search::Request::new(query, page, per_page, order)) - .await - } - - /// `/blockchain`: get block headers for `min` <= `height` <= `max`. - /// - /// Block headers are returned in descending order (highest first). - /// - /// Returns at most 20 items. - async fn blockchain(&self, min: H, max: H) -> Result - where - H: Into + Send, - { - // TODO(tarcieri): return errors for invalid params before making request? - self.perform(blockchain::Request::new(min.into(), max.into())) - .await - } - - /// `/broadcast_tx_async`: broadcast a transaction, returning immediately. - async fn broadcast_tx_async(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_async::Request::new(tx)).await - } - - /// `/broadcast_tx_sync`: broadcast a transaction, returning the response - /// from `CheckTx`. - async fn broadcast_tx_sync(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_sync::Request::new(tx)).await - } - - /// `/broadcast_tx_commit`: broadcast a transaction, returning the response - /// from `DeliverTx`. - async fn broadcast_tx_commit(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_commit::Request::new(tx)).await - } - - /// `/commit`: get block commit at a given height. - async fn commit(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(commit::Request::new(height.into())).await - } - - /// `/consensus_params`: get current consensus parameters at the specified - /// height. - async fn consensus_params(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(consensus_params::Request::new(Some(height.into()))) - .await - } - - /// `/consensus_state`: get current consensus state - async fn consensus_state(&self) -> Result { - self.perform(consensus_state::Request::new()).await - } - - // TODO(thane): Simplify once validators endpoint removes pagination. - /// `/validators`: get validators a given height. - async fn validators(&self, height: H, paging: Paging) -> Result - where - H: Into + Send, - { - let height = height.into(); - match paging { - Paging::Default => { - self.perform(validators::Request::new(Some(height), None, None)) - .await - }, - Paging::Specific { - page_number, - per_page, - } => { - self.perform(validators::Request::new( - Some(height), - Some(page_number), - Some(per_page), - )) - .await - }, - Paging::All => { - let mut page_num = 1_usize; - let mut validators = Vec::new(); - let per_page = DEFAULT_VALIDATORS_PER_PAGE.into(); - loop { - let response = self - .perform(validators::Request::new( - Some(height), - Some(page_num.into()), - Some(per_page), - )) - .await?; - validators.extend(response.validators); - if validators.len() as i32 == response.total { - return Ok(validators::Response::new( - response.block_height, - validators, - response.total, - )); - } - page_num += 1; - } - }, - } - } - - /// `/consensus_params`: get the latest consensus parameters. - async fn latest_consensus_params(&self) -> Result { - self.perform(consensus_params::Request::new(None)).await - } - - /// `/commit`: get the latest block commit - async fn latest_commit(&self) -> Result { - self.perform(commit::Request::default()).await - } - - /// `/health`: get node health. - /// - /// Returns empty result (200 OK) on success, no response in case of an error. - async fn health(&self) -> Result<(), Error> { - self.perform(health::Request).await?; - Ok(()) - } - - /// `/genesis`: get genesis file. - async fn genesis(&self) -> Result, Error> - where - AppState: fmt::Debug + Serialize + DeserializeOwned + Send, - { - Ok(self.perform(genesis::Request::default()).await?.genesis) - } - - /// `/net_info`: obtain information about P2P and other network connections. - async fn net_info(&self) -> Result { - self.perform(net_info::Request).await - } - - /// `/status`: get Tendermint status including node info, pubkey, latest - /// block hash, app hash, block height and time. - async fn status(&self) -> Result { - self.perform(status::Request).await - } - - /// `/broadcast_evidence`: broadcast an evidence. - async fn broadcast_evidence(&self, e: Evidence) -> Result { - self.perform(evidence::Request::new(e)).await - } - - /// `/tx`: find transaction by hash. - async fn tx(&self, hash: Hash, prove: bool) -> Result { - self.perform(tx::Request::new(hash, prove)).await - } - - /// `/tx_search`: search for transactions with their results. - async fn tx_search( - &self, - query: Query, - prove: bool, - page: u32, - per_page: u8, - order: Order, - ) -> Result { - self.perform(tx_search::Request::new(query, prove, page, per_page, order)) - .await - } - - /// Poll the `/health` endpoint until it returns a successful result or - /// the given `timeout` has elapsed. - async fn wait_until_healthy(&self, timeout: T) -> Result<(), Error> - where - T: Into + Send, - { - let timeout = timeout.into(); - let poll_interval = Duration::from_millis(200); - let mut attempts_remaining = timeout.as_millis() / poll_interval.as_millis(); - - while self.health().await.is_err() { - if attempts_remaining == 0 { - return Err(Error::timeout(timeout)); - } - - attempts_remaining -= 1; - time::sleep(poll_interval).await; - } - - Ok(()) - } - - /// Perform a request against the RPC endpoint - async fn perform(&self, request: R) -> Result - where - R: SimpleRequest; -} diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index ffc2551c4..87cb4aed3 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -8,7 +8,8 @@ use core::{ use async_trait::async_trait; use tendermint_config::net; -use crate::{client::Client, prelude::*, Error, Scheme, SimpleRequest, Url}; +use crate::{prelude::*, Error, Scheme, SimpleRequest, Url}; +use crate::{v0_34, v0_37}; /// A JSON-RPC/HTTP Tendermint RPC client (implements [`crate::Client`]). /// @@ -83,7 +84,17 @@ impl HttpClient { } #[async_trait] -impl Client for HttpClient { +impl v0_34::Client for HttpClient { + async fn perform(&self, request: R) -> Result + where + R: SimpleRequest, + { + self.inner.perform(request).await + } +} + +#[async_trait] +impl v0_37::Client for HttpClient { async fn perform(&self, request: R) -> Result where R: SimpleRequest, diff --git a/rpc/src/client/transport/mock.rs b/rpc/src/client/transport/mock.rs index 125540633..6739b61d0 100644 --- a/rpc/src/client/transport/mock.rs +++ b/rpc/src/client/transport/mock.rs @@ -14,8 +14,9 @@ use crate::{ prelude::*, query::Query, utils::uuid_str, - Client, Error, Method, Request, Response, Subscription, SubscriptionClient, + Error, Method, Request, Response, Subscription, SubscriptionClient, }; +use crate::{v0_34, v0_37}; /// A mock client implementation for use in testing. /// @@ -59,7 +60,19 @@ pub struct MockClient { } #[async_trait] -impl Client for MockClient { +impl v0_34::Client for MockClient { + async fn perform(&self, request: R) -> Result + where + R: Request, + { + self.matcher + .response_for(request) + .ok_or_else(Error::mismatch_response)? + } +} + +#[async_trait] +impl v0_37::Client for MockClient { async fn perform(&self, request: R) -> Result where R: Request, @@ -257,25 +270,54 @@ mod test { Event::from_string(&read_json_fixture(name).await).unwrap() } - #[tokio::test] - async fn mock_client() { - let abci_info_fixture = read_json_fixture("abci_info").await; - let block_fixture = read_json_fixture("block_at_height_10").await; - let matcher = MockRequestMethodMatcher::default() - .map(Method::AbciInfo, Ok(abci_info_fixture)) - .map(Method::Block, Ok(block_fixture)); - let (client, driver) = MockClient::new(matcher); - let driver_hdl = tokio::spawn(async move { driver.run().await }); - - let abci_info = client.abci_info().await.unwrap(); - assert_eq!("{\"size\":0}".to_string(), abci_info.data); - - let block = client.block(Height::from(10_u32)).await.unwrap().block; - assert_eq!(Height::from(10_u32), block.header.height); - assert_eq!("dockerchain".parse::().unwrap(), block.header.chain_id); + mod v0_34 { + use super::*; + use crate::v0_34::Client; + #[tokio::test] + async fn mock_client() { + let abci_info_fixture = read_json_fixture("abci_info").await; + let block_fixture = read_json_fixture("block_at_height_10").await; + let matcher = MockRequestMethodMatcher::default() + .map(Method::AbciInfo, Ok(abci_info_fixture)) + .map(Method::Block, Ok(block_fixture)); + let (client, driver) = MockClient::new(matcher); + let driver_hdl = tokio::spawn(async move { driver.run().await }); + + let abci_info = client.abci_info().await.unwrap(); + assert_eq!("{\"size\":0}".to_string(), abci_info.data); + + let block = client.block(Height::from(10_u32)).await.unwrap().block; + assert_eq!(Height::from(10_u32), block.header.height); + assert_eq!("dockerchain".parse::().unwrap(), block.header.chain_id); + + client.close(); + driver_hdl.await.unwrap().unwrap(); + } + } - client.close(); - driver_hdl.await.unwrap().unwrap(); + mod v0_37 { + use super::*; + use crate::v0_37::Client; + #[tokio::test] + async fn mock_client() { + let abci_info_fixture = read_json_fixture("abci_info").await; + let block_fixture = read_json_fixture("block_at_height_10").await; + let matcher = MockRequestMethodMatcher::default() + .map(Method::AbciInfo, Ok(abci_info_fixture)) + .map(Method::Block, Ok(block_fixture)); + let (client, driver) = MockClient::new(matcher); + let driver_hdl = tokio::spawn(async move { driver.run().await }); + + let abci_info = client.abci_info().await.unwrap(); + assert_eq!("{\"size\":0}".to_string(), abci_info.data); + + let block = client.block(Height::from(10_u32)).await.unwrap().block; + assert_eq!(Height::from(10_u32), block.header.height); + assert_eq!("dockerchain".parse::().unwrap(), block.header.chain_id); + + client.close(); + driver_hdl.await.unwrap().unwrap(); + } } #[tokio::test] diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index 4b9e6f1a3..e2f16ed99 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -34,13 +34,12 @@ mod prelude; #[cfg(any(feature = "http-client", feature = "websocket-client"))] mod client; +#[cfg(feature = "http-client")] +pub use client::{HttpClient, HttpClientUrl}; #[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use client::{ - Client, MockClient, MockRequestMatcher, MockRequestMethodMatcher, Subscription, - SubscriptionClient, + MockClient, MockRequestMatcher, MockRequestMethodMatcher, Subscription, SubscriptionClient, }; -#[cfg(feature = "http-client")] -pub use client::{HttpClient, HttpClientUrl}; #[cfg(feature = "websocket-client")] pub use client::{WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig}; @@ -60,6 +59,11 @@ pub mod serializers; mod utils; mod version; +pub mod v0_34; +pub mod v0_37; + +pub use v0_37::Client; + pub use error::Error; pub use id::Id; pub use method::Method; diff --git a/rpc/src/v0_34.rs b/rpc/src/v0_34.rs new file mode 100644 index 000000000..a864b1a17 --- /dev/null +++ b/rpc/src/v0_34.rs @@ -0,0 +1,3 @@ +mod client; + +pub use client::Client; diff --git a/rpc/src/v0_34/client.rs b/rpc/src/v0_34/client.rs new file mode 100644 index 000000000..3d617b402 --- /dev/null +++ b/rpc/src/v0_34/client.rs @@ -0,0 +1,294 @@ +//! The v0.34 RPC client interface. + +use core::{fmt, time::Duration}; + +use async_trait::async_trait; +use serde::{de::DeserializeOwned, Serialize}; +use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; +use tokio::time; + +use crate::{ + endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, + paging::Paging, + prelude::*, + query::Query, + Error, Order, SimpleRequest, +}; + +/// Provides lightweight access to the Tendermint RPC. It gives access to all +/// endpoints with the exception of the event subscription-related ones. +/// +/// To access event subscription capabilities, use a client that implements the +/// [`SubscriptionClient`] trait. +/// +/// [`SubscriptionClient`]: trait.SubscriptionClient.html +#[async_trait] +pub trait Client { + /// `/abci_info`: get information about the ABCI application. + async fn abci_info(&self) -> Result { + Ok(self.perform(abci_info::Request).await?.response) + } + + /// `/abci_query`: query the ABCI application + async fn abci_query( + &self, + path: Option, + data: V, + height: Option, + prove: bool, + ) -> Result + where + V: Into> + Send, + { + Ok(self + .perform(abci_query::Request::new(path, data, height, prove)) + .await? + .response) + } + + /// `/block`: get block at a given height. + async fn block(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(block::Request::new(height.into())).await + } + + /// `/block_by_hash`: get block by hash. + async fn block_by_hash( + &self, + hash: tendermint::Hash, + ) -> Result { + self.perform(block_by_hash::Request::new(hash)).await + } + + /// `/block`: get the latest block. + async fn latest_block(&self) -> Result { + self.perform(block::Request::default()).await + } + + /// `/block_results`: get ABCI results for a block at a particular height. + async fn block_results(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(block_results::Request::new(height.into())) + .await + } + + /// `/block_results`: get ABCI results for the latest block. + async fn latest_block_results(&self) -> Result { + self.perform(block_results::Request::default()).await + } + + /// `/block_search`: search for blocks by BeginBlock and EndBlock events. + async fn block_search( + &self, + query: Query, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + self.perform(block_search::Request::new(query, page, per_page, order)) + .await + } + + /// `/blockchain`: get block headers for `min` <= `height` <= `max`. + /// + /// Block headers are returned in descending order (highest first). + /// + /// Returns at most 20 items. + async fn blockchain(&self, min: H, max: H) -> Result + where + H: Into + Send, + { + // TODO(tarcieri): return errors for invalid params before making request? + self.perform(blockchain::Request::new(min.into(), max.into())) + .await + } + + /// `/broadcast_tx_async`: broadcast a transaction, returning immediately. + async fn broadcast_tx_async(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_async::Request::new(tx)).await + } + + /// `/broadcast_tx_sync`: broadcast a transaction, returning the response + /// from `CheckTx`. + async fn broadcast_tx_sync(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_sync::Request::new(tx)).await + } + + /// `/broadcast_tx_commit`: broadcast a transaction, returning the response + /// from `DeliverTx`. + async fn broadcast_tx_commit(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_commit::Request::new(tx)).await + } + + /// `/commit`: get block commit at a given height. + async fn commit(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(commit::Request::new(height.into())).await + } + + /// `/consensus_params`: get current consensus parameters at the specified + /// height. + async fn consensus_params(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(consensus_params::Request::new(Some(height.into()))) + .await + } + + /// `/consensus_state`: get current consensus state + async fn consensus_state(&self) -> Result { + self.perform(consensus_state::Request::new()).await + } + + // TODO(thane): Simplify once validators endpoint removes pagination. + /// `/validators`: get validators a given height. + async fn validators(&self, height: H, paging: Paging) -> Result + where + H: Into + Send, + { + let height = height.into(); + match paging { + Paging::Default => { + self.perform(validators::Request::new(Some(height), None, None)) + .await + }, + Paging::Specific { + page_number, + per_page, + } => { + self.perform(validators::Request::new( + Some(height), + Some(page_number), + Some(per_page), + )) + .await + }, + Paging::All => { + let mut page_num = 1_usize; + let mut validators = Vec::new(); + let per_page = DEFAULT_VALIDATORS_PER_PAGE.into(); + loop { + let response = self + .perform(validators::Request::new( + Some(height), + Some(page_num.into()), + Some(per_page), + )) + .await?; + validators.extend(response.validators); + if validators.len() as i32 == response.total { + return Ok(validators::Response::new( + response.block_height, + validators, + response.total, + )); + } + page_num += 1; + } + }, + } + } + + /// `/consensus_params`: get the latest consensus parameters. + async fn latest_consensus_params(&self) -> Result { + self.perform(consensus_params::Request::new(None)).await + } + + /// `/commit`: get the latest block commit + async fn latest_commit(&self) -> Result { + self.perform(commit::Request::default()).await + } + + /// `/health`: get node health. + /// + /// Returns empty result (200 OK) on success, no response in case of an error. + async fn health(&self) -> Result<(), Error> { + self.perform(health::Request).await?; + Ok(()) + } + + /// `/genesis`: get genesis file. + async fn genesis(&self) -> Result, Error> + where + AppState: fmt::Debug + Serialize + DeserializeOwned + Send, + { + Ok(self.perform(genesis::Request::default()).await?.genesis) + } + + /// `/net_info`: obtain information about P2P and other network connections. + async fn net_info(&self) -> Result { + self.perform(net_info::Request).await + } + + /// `/status`: get Tendermint status including node info, pubkey, latest + /// block hash, app hash, block height and time. + async fn status(&self) -> Result { + self.perform(status::Request).await + } + + /// `/broadcast_evidence`: broadcast an evidence. + async fn broadcast_evidence(&self, e: Evidence) -> Result { + self.perform(evidence::Request::new(e)).await + } + + /// `/tx`: find transaction by hash. + async fn tx(&self, hash: Hash, prove: bool) -> Result { + self.perform(tx::Request::new(hash, prove)).await + } + + /// `/tx_search`: search for transactions with their results. + async fn tx_search( + &self, + query: Query, + prove: bool, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + self.perform(tx_search::Request::new(query, prove, page, per_page, order)) + .await + } + + /// Poll the `/health` endpoint until it returns a successful result or + /// the given `timeout` has elapsed. + async fn wait_until_healthy(&self, timeout: T) -> Result<(), Error> + where + T: Into + Send, + { + let timeout = timeout.into(); + let poll_interval = Duration::from_millis(200); + let mut attempts_remaining = timeout.as_millis() / poll_interval.as_millis(); + + while self.health().await.is_err() { + if attempts_remaining == 0 { + return Err(Error::timeout(timeout)); + } + + attempts_remaining -= 1; + time::sleep(poll_interval).await; + } + + Ok(()) + } + + /// Perform a request against the RPC endpoint + async fn perform(&self, request: R) -> Result + where + R: SimpleRequest; +} diff --git a/rpc/src/v0_37.rs b/rpc/src/v0_37.rs new file mode 100644 index 000000000..a864b1a17 --- /dev/null +++ b/rpc/src/v0_37.rs @@ -0,0 +1,3 @@ +mod client; + +pub use client::Client; diff --git a/rpc/src/v0_37/client.rs b/rpc/src/v0_37/client.rs new file mode 100644 index 000000000..40daf5e67 --- /dev/null +++ b/rpc/src/v0_37/client.rs @@ -0,0 +1,310 @@ +//! The v0.37 RPC client interface. + +use core::{fmt, time::Duration}; + +use async_trait::async_trait; +use serde::{de::DeserializeOwned, Serialize}; +use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; +use tokio::time; + +use crate::{ + endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, + paging::Paging, + prelude::*, + query::Query, + Error, Order, SimpleRequest, +}; + +/// Provides lightweight access to the Tendermint RPC. It gives access to all +/// endpoints with the exception of the event subscription-related ones. +/// +/// To access event subscription capabilities, use a client that implements the +/// [`SubscriptionClient`] trait. +/// +/// [`SubscriptionClient`]: trait.SubscriptionClient.html +#[async_trait] +pub trait Client { + /// `/abci_info`: get information about the ABCI application. + async fn abci_info(&self) -> Result { + Ok(self.perform(abci_info::Request).await?.response) + } + + /// `/abci_query`: query the ABCI application + async fn abci_query( + &self, + path: Option, + data: V, + height: Option, + prove: bool, + ) -> Result + where + V: Into> + Send, + { + Ok(self + .perform(abci_query::Request::new(path, data, height, prove)) + .await? + .response) + } + + /// `/block`: get block at a given height. + async fn block(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(block::Request::new(height.into())).await + } + + /// `/block_by_hash`: get block by hash. + async fn block_by_hash( + &self, + hash: tendermint::Hash, + ) -> Result { + self.perform(block_by_hash::Request::new(hash)).await + } + + /// `/block`: get the latest block. + async fn latest_block(&self) -> Result { + self.perform(block::Request::default()).await + } + + /// `/header`: get block header at a given height. + async fn header(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(header::Request::new(height.into())).await + } + + /// `/header_by_hash`: get block by hash. + async fn header_by_hash( + &self, + hash: tendermint::Hash, + ) -> Result { + self.perform(header_by_hash::Request::new(hash)).await + } + + /// `/block_results`: get ABCI results for a block at a particular height. + async fn block_results(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(block_results::Request::new(height.into())) + .await + } + + /// `/block_results`: get ABCI results for the latest block. + async fn latest_block_results(&self) -> Result { + self.perform(block_results::Request::default()).await + } + + /// `/block_search`: search for blocks by BeginBlock and EndBlock events. + async fn block_search( + &self, + query: Query, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + self.perform(block_search::Request::new(query, page, per_page, order)) + .await + } + + /// `/blockchain`: get block headers for `min` <= `height` <= `max`. + /// + /// Block headers are returned in descending order (highest first). + /// + /// Returns at most 20 items. + async fn blockchain(&self, min: H, max: H) -> Result + where + H: Into + Send, + { + // TODO(tarcieri): return errors for invalid params before making request? + self.perform(blockchain::Request::new(min.into(), max.into())) + .await + } + + /// `/broadcast_tx_async`: broadcast a transaction, returning immediately. + async fn broadcast_tx_async(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_async::Request::new(tx)).await + } + + /// `/broadcast_tx_sync`: broadcast a transaction, returning the response + /// from `CheckTx`. + async fn broadcast_tx_sync(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_sync::Request::new(tx)).await + } + + /// `/broadcast_tx_commit`: broadcast a transaction, returning the response + /// from `DeliverTx`. + async fn broadcast_tx_commit(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_commit::Request::new(tx)).await + } + + /// `/commit`: get block commit at a given height. + async fn commit(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(commit::Request::new(height.into())).await + } + + /// `/consensus_params`: get current consensus parameters at the specified + /// height. + async fn consensus_params(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(consensus_params::Request::new(Some(height.into()))) + .await + } + + /// `/consensus_state`: get current consensus state + async fn consensus_state(&self) -> Result { + self.perform(consensus_state::Request::new()).await + } + + // TODO(thane): Simplify once validators endpoint removes pagination. + /// `/validators`: get validators a given height. + async fn validators(&self, height: H, paging: Paging) -> Result + where + H: Into + Send, + { + let height = height.into(); + match paging { + Paging::Default => { + self.perform(validators::Request::new(Some(height), None, None)) + .await + }, + Paging::Specific { + page_number, + per_page, + } => { + self.perform(validators::Request::new( + Some(height), + Some(page_number), + Some(per_page), + )) + .await + }, + Paging::All => { + let mut page_num = 1_usize; + let mut validators = Vec::new(); + let per_page = DEFAULT_VALIDATORS_PER_PAGE.into(); + loop { + let response = self + .perform(validators::Request::new( + Some(height), + Some(page_num.into()), + Some(per_page), + )) + .await?; + validators.extend(response.validators); + if validators.len() as i32 == response.total { + return Ok(validators::Response::new( + response.block_height, + validators, + response.total, + )); + } + page_num += 1; + } + }, + } + } + + /// `/consensus_params`: get the latest consensus parameters. + async fn latest_consensus_params(&self) -> Result { + self.perform(consensus_params::Request::new(None)).await + } + + /// `/commit`: get the latest block commit + async fn latest_commit(&self) -> Result { + self.perform(commit::Request::default()).await + } + + /// `/health`: get node health. + /// + /// Returns empty result (200 OK) on success, no response in case of an error. + async fn health(&self) -> Result<(), Error> { + self.perform(health::Request).await?; + Ok(()) + } + + /// `/genesis`: get genesis file. + async fn genesis(&self) -> Result, Error> + where + AppState: fmt::Debug + Serialize + DeserializeOwned + Send, + { + Ok(self.perform(genesis::Request::default()).await?.genesis) + } + + /// `/net_info`: obtain information about P2P and other network connections. + async fn net_info(&self) -> Result { + self.perform(net_info::Request).await + } + + /// `/status`: get Tendermint status including node info, pubkey, latest + /// block hash, app hash, block height and time. + async fn status(&self) -> Result { + self.perform(status::Request).await + } + + /// `/broadcast_evidence`: broadcast an evidence. + async fn broadcast_evidence(&self, e: Evidence) -> Result { + self.perform(evidence::Request::new(e)).await + } + + /// `/tx`: find transaction by hash. + async fn tx(&self, hash: Hash, prove: bool) -> Result { + self.perform(tx::Request::new(hash, prove)).await + } + + /// `/tx_search`: search for transactions with their results. + async fn tx_search( + &self, + query: Query, + prove: bool, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + self.perform(tx_search::Request::new(query, prove, page, per_page, order)) + .await + } + + /// Poll the `/health` endpoint until it returns a successful result or + /// the given `timeout` has elapsed. + async fn wait_until_healthy(&self, timeout: T) -> Result<(), Error> + where + T: Into + Send, + { + let timeout = timeout.into(); + let poll_interval = Duration::from_millis(200); + let mut attempts_remaining = timeout.as_millis() / poll_interval.as_millis(); + + while self.health().await.is_err() { + if attempts_remaining == 0 { + return Err(Error::timeout(timeout)); + } + + attempts_remaining -= 1; + time::sleep(poll_interval).await; + } + + Ok(()) + } + + /// Perform a request against the RPC endpoint + async fn perform(&self, request: R) -> Result + where + R: SimpleRequest; +} From 6a2446101a51ac86de3d09d2103f0200c6035ea8 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 19 Dec 2022 17:58:01 +0200 Subject: [PATCH 28/77] rpc: feature-gate the Client traits The same way as the old Client trait was. --- rpc/src/lib.rs | 1 + rpc/src/v0_34.rs | 2 ++ rpc/src/v0_37.rs | 2 ++ 3 files changed, 5 insertions(+) diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index e2f16ed99..95bd9a0d2 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -62,6 +62,7 @@ mod version; pub mod v0_34; pub mod v0_37; +#[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use v0_37::Client; pub use error::Error; diff --git a/rpc/src/v0_34.rs b/rpc/src/v0_34.rs index a864b1a17..81ee4d6bc 100644 --- a/rpc/src/v0_34.rs +++ b/rpc/src/v0_34.rs @@ -1,3 +1,5 @@ +#![cfg(any(feature = "http-client", feature = "websocket-client"))] + mod client; pub use client::Client; diff --git a/rpc/src/v0_37.rs b/rpc/src/v0_37.rs index a864b1a17..81ee4d6bc 100644 --- a/rpc/src/v0_37.rs +++ b/rpc/src/v0_37.rs @@ -1,3 +1,5 @@ +#![cfg(any(feature = "http-client", feature = "websocket-client"))] + mod client; pub use client::Client; From a00a69dda4f4eeee633814edbcb75e22fb9df2ea Mon Sep 17 00:00:00 2001 From: xla Date: Sat, 24 Dec 2022 10:29:05 +0100 Subject: [PATCH 29/77] xla/multi-tc-versionsupport/fix (#1254) --- config/tests/mod.rs | 8 ++++---- light-client/src/builder/light_client.rs | 1 + p2p/src/secret_connection.rs | 2 +- proto/src/serializers/bytes.rs | 12 ++++++------ proto/src/serializers/txs.rs | 2 +- rpc/src/client/transport/mock.rs | 2 +- rpc/src/client/transport/websocket.rs | 2 +- rpc/src/serializers/tm_hash_base64.rs | 2 +- rpc/src/serializers/tx_hash_base64.rs | 2 +- tendermint/src/abci.rs | 4 ++-- .../src/abci/doc/request-applysnapshotchunk.md | 4 ++-- tendermint/src/abci/doc/request-offersnapshot.md | 4 ++-- tendermint/src/abci/doc/response-offersnapshot.md | 4 ++-- tendermint/src/abci/request.rs | 3 --- tendermint/src/abci/response.rs | 4 ---- tendermint/src/hash.rs | 2 +- tendermint/src/public_key.rs | 4 ++-- testgen/src/tester.rs | 6 +++--- 18 files changed, 31 insertions(+), 37 deletions(-) diff --git a/config/tests/mod.rs b/config/tests/mod.rs index 031e44470..8d67c14dd 100644 --- a/config/tests/mod.rs +++ b/config/tests/mod.rs @@ -19,7 +19,7 @@ fn read_fixture(name: &str) -> String { #[test] fn config_toml_parser() { let config_toml = read_fixture("config.toml"); - let config = TendermintConfig::parse_toml(&config_toml).unwrap(); + let config = TendermintConfig::parse_toml(config_toml).unwrap(); // main base config options @@ -206,7 +206,7 @@ fn config_toml_parser() { #[test] fn node_key_parser() { let raw_node_key = read_fixture("node_key.json"); - let node_key = NodeKey::parse_json(&raw_node_key).unwrap(); + let node_key = NodeKey::parse_json(raw_node_key).unwrap(); assert_eq!( node_key.node_id().to_string(), "1a7b6bcf3d6fb055ab3aebca415847531b626699" @@ -217,7 +217,7 @@ fn node_key_parser() { #[test] fn priv_validator_json_parser() { let raw_priv_validator_key = read_fixture("priv_validator_key.json"); - let priv_validator_key = PrivValidatorKey::parse_json(&raw_priv_validator_key).unwrap(); + let priv_validator_key = PrivValidatorKey::parse_json(raw_priv_validator_key).unwrap(); assert_eq!( priv_validator_key.consensus_pubkey().to_hex(), "F26BF4B2A2E84CEB7A53C3F1AE77408779B20064782FBADBDF0E365959EE4534" @@ -229,7 +229,7 @@ fn priv_validator_json_parser() { #[test] fn parsing_roundtrip() { let config_toml = read_fixture("config.toml"); - let config = TendermintConfig::parse_toml(&config_toml).unwrap(); + let config = TendermintConfig::parse_toml(config_toml).unwrap(); let written_config_toml = toml::to_string(&config).unwrap(); let written_config = TendermintConfig::parse_toml(&written_config_toml).unwrap(); diff --git a/light-client/src/builder/light_client.rs b/light-client/src/builder/light_client.rs index a428a5a2b..46b383c14 100644 --- a/light-client/src/builder/light_client.rs +++ b/light-client/src/builder/light_client.rs @@ -82,6 +82,7 @@ impl LightClientBuilder { options: Options, timeout: Option, ) -> Self { + #[allow(clippy::box_default)] Self::custom( peer_id, options, diff --git a/p2p/src/secret_connection.rs b/p2p/src/secret_connection.rs index 272219764..75d104e5f 100644 --- a/p2p/src/secret_connection.rs +++ b/p2p/src/secret_connection.rs @@ -648,7 +648,7 @@ fn read_and_decrypt( if chunk_length as usize > DATA_MAX_SIZE { return Err(io::Error::new( io::ErrorKind::Other, - format!("chunk is too big: {}! max: {}", chunk_length, DATA_MAX_SIZE), + format!("chunk is too big: {chunk_length}! max: {DATA_MAX_SIZE}"), )); } diff --git a/proto/src/serializers/bytes.rs b/proto/src/serializers/bytes.rs index d1c5c28dd..f27ce4c03 100644 --- a/proto/src/serializers/bytes.rs +++ b/proto/src/serializers/bytes.rs @@ -43,8 +43,8 @@ pub mod base64string { D: Deserializer<'de>, Vec: Into, { - let string = Option::::deserialize(deserializer)?.unwrap_or_default(); - let v = base64::decode(&string).map_err(serde::de::Error::custom)?; + let s = Option::::deserialize(deserializer)?.unwrap_or_default(); + let v = base64::decode(s).map_err(serde::de::Error::custom)?; Ok(v.into()) } @@ -54,7 +54,7 @@ pub mod base64string { D: Deserializer<'de>, { let s = Option::::deserialize(deserializer)?.unwrap_or_default(); - String::from_utf8(base64::decode(&s).map_err(serde::de::Error::custom)?) + String::from_utf8(base64::decode(s).map_err(serde::de::Error::custom)?) .map_err(serde::de::Error::custom) } @@ -85,7 +85,7 @@ pub mod vec_base64string { Option::>::deserialize(deserializer)? .unwrap_or_default() .into_iter() - .map(|s| base64::decode(&s).map_err(serde::de::Error::custom)) + .map(|s| base64::decode(s).map_err(serde::de::Error::custom)) .collect() } @@ -117,8 +117,8 @@ pub mod option_base64string { where D: Deserializer<'de>, { - let string = Option::::deserialize(deserializer)?.unwrap_or_default(); - base64::decode(&string).map_err(serde::de::Error::custom) + let s = Option::::deserialize(deserializer)?.unwrap_or_default(); + base64::decode(s).map_err(serde::de::Error::custom) } /// Serialize from `T` into `Option` diff --git a/proto/src/serializers/txs.rs b/proto/src/serializers/txs.rs index fb5d46f54..44594c743 100644 --- a/proto/src/serializers/txs.rs +++ b/proto/src/serializers/txs.rs @@ -19,7 +19,7 @@ where } value_vec_base64string .into_iter() - .map(|s| base64::decode(&s).map_err(serde::de::Error::custom)) + .map(|s| base64::decode(s).map_err(serde::de::Error::custom)) .collect() } diff --git a/rpc/src/client/transport/mock.rs b/rpc/src/client/transport/mock.rs index 6739b61d0..f9f3f6e64 100644 --- a/rpc/src/client/transport/mock.rs +++ b/rpc/src/client/transport/mock.rs @@ -267,7 +267,7 @@ mod test { } async fn read_event(name: &str) -> Event { - Event::from_string(&read_json_fixture(name).await).unwrap() + Event::from_string(read_json_fixture(name).await).unwrap() } mod v0_34 { diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 217b17efb..26fc349db 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -1155,7 +1155,7 @@ mod test { } async fn read_event(name: &str) -> Event { - Event::from_string(&read_json_fixture(name).await).unwrap() + Event::from_string(read_json_fixture(name).await).unwrap() } #[tokio::test] diff --git a/rpc/src/serializers/tm_hash_base64.rs b/rpc/src/serializers/tm_hash_base64.rs index b8626a825..b57e33c3e 100644 --- a/rpc/src/serializers/tm_hash_base64.rs +++ b/rpc/src/serializers/tm_hash_base64.rs @@ -12,7 +12,7 @@ where D: Deserializer<'de>, { let s = Option::::deserialize(deserializer)?.unwrap_or_default(); - let decoded = base64::decode(&s).map_err(serde::de::Error::custom)?; + let decoded = base64::decode(s).map_err(serde::de::Error::custom)?; if decoded.len() != SHA256_HASH_SIZE { return Err(serde::de::Error::custom( "unexpected transaction length for hash", diff --git a/rpc/src/serializers/tx_hash_base64.rs b/rpc/src/serializers/tx_hash_base64.rs index feded9a5c..aa289fd07 100644 --- a/rpc/src/serializers/tx_hash_base64.rs +++ b/rpc/src/serializers/tx_hash_base64.rs @@ -12,7 +12,7 @@ where D: Deserializer<'de>, { let s = Option::::deserialize(deserializer)?.unwrap_or_default(); - let decoded = base64::decode(&s).map_err(serde::de::Error::custom)?; + let decoded = base64::decode(s).map_err(serde::de::Error::custom)?; let hash = Hash::from_bytes(Algorithm::Sha256, &decoded).map_err(serde::de::Error::custom)?; Ok(hash) } diff --git a/tendermint/src/abci.rs b/tendermint/src/abci.rs index 3fa4de415..72a179ff7 100644 --- a/tendermint/src/abci.rs +++ b/tendermint/src/abci.rs @@ -44,8 +44,8 @@ pub mod request; pub mod response; pub mod types; -// pub use crate::v0_37::abci::request::Request; -// pub use crate::v0_37::abci::response::Response; +pub use crate::v0_37::abci::request::Request; +pub use crate::v0_37::abci::response::Response; pub use event::{Event, EventAttribute, EventAttributeIndexExt}; diff --git a/tendermint/src/abci/doc/request-applysnapshotchunk.md b/tendermint/src/abci/doc/request-applysnapshotchunk.md index fe1c35598..d79d42e57 100644 --- a/tendermint/src/abci/doc/request-applysnapshotchunk.md +++ b/tendermint/src/abci/doc/request-applysnapshotchunk.md @@ -5,7 +5,7 @@ appropriate. Tendermint will not do this unless instructed by the application. The application may want to verify each chunk, e.g., by attaching chunk -hashes in [`Snapshot::metadata`] and/or incrementally verifying contents +hashes in `Snapshot::metadata` and/or incrementally verifying contents against `app_hash`. When all chunks have been accepted, Tendermint will make an ABCI [`Info`] @@ -18,4 +18,4 @@ because no suitable peers are available), it will reject the snapshot and try a different one via `OfferSnapshot`. The application should be prepared to reset and accept it or abort as appropriate. -[ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#applysnapshotchunk) \ No newline at end of file +[ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#applysnapshotchunk) diff --git a/tendermint/src/abci/doc/request-offersnapshot.md b/tendermint/src/abci/doc/request-offersnapshot.md index db0e60b17..41303e0d9 100644 --- a/tendermint/src/abci/doc/request-offersnapshot.md +++ b/tendermint/src/abci/doc/request-offersnapshot.md @@ -13,8 +13,8 @@ additional verification schemes to avoid denial-of-service attacks. The verified `app_hash` is automatically checked against the restored application at the end of snapshot restoration. -See also the [`Snapshot`] data type and the [ABCI state sync documentation][ssd]. +See also the `Snapshot` data type and the [ABCI state sync documentation][ssd]. [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#offersnapshot) -[ssd]: https://docs.tendermint.com/master/spec/abci/apps.html#state-sync \ No newline at end of file +[ssd]: https://docs.tendermint.com/master/spec/abci/apps.html#state-sync diff --git a/tendermint/src/abci/doc/response-offersnapshot.md b/tendermint/src/abci/doc/response-offersnapshot.md index 0da7a66fa..42f0d076c 100644 --- a/tendermint/src/abci/doc/response-offersnapshot.md +++ b/tendermint/src/abci/doc/response-offersnapshot.md @@ -1,7 +1,7 @@ Returns the application's response to a snapshot offer. -See also the [`Snapshot`] data type and the [ABCI state sync documentation][ssd]. +See also the [`OfferSnapshot`] data type and the [ABCI state sync documentation][ssd]. [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#offersnapshot) -[ssd]: https://docs.tendermint.com/master/spec/abci/apps.html#state-sync \ No newline at end of file +[ssd]: https://docs.tendermint.com/master/spec/abci/apps.html#state-sync diff --git a/tendermint/src/abci/request.rs b/tendermint/src/abci/request.rs index 7e3e8c307..a582b2ec0 100644 --- a/tendermint/src/abci/request.rs +++ b/tendermint/src/abci/request.rs @@ -1,8 +1,5 @@ //! ABCI requests and request data. //! -//! The [`Request`] enum records all possible ABCI requests. Requests that -//! contain data are modeled as a separate struct, to avoid duplication of field -//! definitions. // IMPORTANT NOTE ON DOCUMENTATION: // diff --git a/tendermint/src/abci/response.rs b/tendermint/src/abci/response.rs index feb2613c0..17ead4ae6 100644 --- a/tendermint/src/abci/response.rs +++ b/tendermint/src/abci/response.rs @@ -1,8 +1,4 @@ //! ABCI responses and response data. -//! -//! The [`Response`] enum records all possible ABCI responses. Responses that -//! contain data are modeled as a separate struct, to avoid duplication of field -//! definitions. // IMPORTANT NOTE ON DOCUMENTATION: // diff --git a/tendermint/src/hash.rs b/tendermint/src/hash.rs index b7c7deae5..e55229313 100644 --- a/tendermint/src/hash.rs +++ b/tendermint/src/hash.rs @@ -234,7 +234,7 @@ impl TryFrom for AppHash { type Error = Error; fn try_from(value: Bytes) -> Result { - Ok(AppHash(value.into())) + Ok(AppHash(value.to_vec())) } } impl From for Bytes { diff --git a/tendermint/src/public_key.rs b/tendermint/src/public_key.rs index 46e7b97fc..294adf994 100644 --- a/tendermint/src/public_key.rs +++ b/tendermint/src/public_key.rs @@ -425,7 +425,7 @@ where { use de::Error; let encoded = String::deserialize(deserializer)?; - let bytes = base64::decode(&encoded).map_err(D::Error::custom)?; + let bytes = base64::decode(encoded).map_err(D::Error::custom)?; Ed25519::from_bytes(&bytes).map_err(D::Error::custom) } @@ -436,7 +436,7 @@ where { use de::Error; let encoded = String::deserialize(deserializer)?; - let bytes = base64::decode(&encoded).map_err(D::Error::custom)?; + let bytes = base64::decode(encoded).map_err(D::Error::custom)?; Secp256k1::from_sec1_bytes(&bytes).map_err(|_| D::Error::custom("invalid secp256k1 key")) } diff --git a/testgen/src/tester.rs b/testgen/src/tester.rs index 6bc3b58ab..1f9d73b98 100644 --- a/testgen/src/tester.rs +++ b/testgen/src/tester.rs @@ -462,7 +462,7 @@ impl Tester { } if let Ok(kind) = entry.file_type() { let path = format!("{}", entry.path().display()); - let rel_path = self.env().unwrap().rel_path(&path).unwrap(); + let rel_path = self.env().unwrap().rel_path(path).unwrap(); if kind.is_file() || kind.is_symlink() { if rel_path.ends_with(".json") { self.run_for_file(&rel_path); @@ -499,7 +499,7 @@ impl Tester { print(" Successful tests: "); for path in tests { print(&format!(" {}", path)); - if let Some(logs) = env.read_file(&(path + "/log")) { + if let Some(logs) = env.read_file(path + "/log") { print(&logs) } } @@ -510,7 +510,7 @@ impl Tester { print(" Failed tests: "); for (path, message, location) in tests { print(&format!(" {}, '{}', {}", path, message, location)); - if let Some(logs) = env.read_file(&(path + "/log")) { + if let Some(logs) = env.read_file(path + "/log") { print(&logs) } } From 08702c529e11cf5d8c82a92ce23b9edfafe922af Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 10 Jan 2023 16:23:45 +0200 Subject: [PATCH 30/77] tendermint: post-merge fix --- tendermint/src/validator.rs | 9 --------- 1 file changed, 9 deletions(-) diff --git a/tendermint/src/validator.rs b/tendermint/src/validator.rs index 48d3f1434..f8b99f5f9 100644 --- a/tendermint/src/validator.rs +++ b/tendermint/src/validator.rs @@ -175,15 +175,6 @@ pub struct SimpleValidator { /// Info -> SimpleValidator impl From<&Info> for SimpleValidator { fn from(info: &Info) -> SimpleValidator { - let sum = match &info.pub_key { - PublicKey::Ed25519(pk) => Some(tendermint_proto::crypto::public_key::Sum::Ed25519( - pk.as_ref().to_vec(), - )), - #[cfg(feature = "secp256k1")] - PublicKey::Secp256k1(pk) => Some(tendermint_proto::crypto::public_key::Sum::Secp256k1( - pk.to_bytes().to_vec(), - )), - }; SimpleValidator { pub_key: info.pub_key, voting_power: info.power, From 011dc7bb427f43e14b245d15d7939b2bbffe9411 Mon Sep 17 00:00:00 2001 From: Akosh Farkash Date: Thu, 12 Jan 2023 12:58:21 +0000 Subject: [PATCH 31/77] Add missing ConsensusRequest and ConsensusResponse mappings. --- tendermint/src/abci/request.rs | 4 ++++ tendermint/src/abci/response.rs | 4 ++++ tendermint/src/v0_34/abci/request.rs | 6 ++++++ tendermint/src/v0_34/abci/response.rs | 6 ++++++ tendermint/src/v0_37/abci/request.rs | 4 ++++ tendermint/src/v0_37/abci/response.rs | 4 ++++ 6 files changed, 28 insertions(+) diff --git a/tendermint/src/abci/request.rs b/tendermint/src/abci/request.rs index a582b2ec0..40f9bbdcf 100644 --- a/tendermint/src/abci/request.rs +++ b/tendermint/src/abci/request.rs @@ -56,6 +56,10 @@ pub use set_option::SetOption; pub enum ConsensusRequest { #[doc = include_str!("doc/request-initchain.md")] InitChain(InitChain), + #[doc = include_str!("doc/request-prepareproposal.md")] + PrepareProposal(PrepareProposal), + #[doc = include_str!("doc/request-processproposal.md")] + ProcessProposal(ProcessProposal), #[doc = include_str!("doc/request-beginblock.md")] BeginBlock(BeginBlock), #[doc = include_str!("doc/request-delivertx.md")] diff --git a/tendermint/src/abci/response.rs b/tendermint/src/abci/response.rs index 17ead4ae6..725de9f7d 100644 --- a/tendermint/src/abci/response.rs +++ b/tendermint/src/abci/response.rs @@ -61,6 +61,10 @@ pub use set_option::SetOption; pub enum ConsensusResponse { #[doc = include_str!("doc/response-initchain.md")] InitChain(InitChain), + #[doc = include_str!("doc/response-prepareproposal.md")] + PrepareProposal(PrepareProposal), + #[doc = include_str!("doc/response-processproposal.md")] + ProcessProposal(ProcessProposal), #[doc = include_str!("doc/response-beginblock.md")] BeginBlock(BeginBlock), #[doc = include_str!("doc/response-delivertx.md")] diff --git a/tendermint/src/v0_34/abci/request.rs b/tendermint/src/v0_34/abci/request.rs index cea3ba016..6199750b8 100644 --- a/tendermint/src/v0_34/abci/request.rs +++ b/tendermint/src/v0_34/abci/request.rs @@ -74,6 +74,12 @@ impl From for Request { fn from(req: ConsensusRequest) -> Self { match req { ConsensusRequest::InitChain(x) => Self::InitChain(x), + ConsensusRequest::PrepareProposal(_) => { + panic!("Cannot convert PrepareProposal into a v0.34 Request") + }, + ConsensusRequest::ProcessProposal(_) => { + panic!("Cannot convert ProcessProposal into a v0.34 Request") + }, ConsensusRequest::BeginBlock(x) => Self::BeginBlock(x), ConsensusRequest::DeliverTx(x) => Self::DeliverTx(x), ConsensusRequest::EndBlock(x) => Self::EndBlock(x), diff --git a/tendermint/src/v0_34/abci/response.rs b/tendermint/src/v0_34/abci/response.rs index 5efdf1466..3ab12b894 100644 --- a/tendermint/src/v0_34/abci/response.rs +++ b/tendermint/src/v0_34/abci/response.rs @@ -46,6 +46,12 @@ impl From for Response { fn from(req: ConsensusResponse) -> Self { match req { ConsensusResponse::InitChain(x) => Self::InitChain(x), + ConsensusResponse::PrepareProposal(_) => { + panic!("Cannot convert PrepareProposal into a v0.34 Response") + }, + ConsensusResponse::ProcessProposal(_) => { + panic!("Cannot convert ProcessProposal into a v0.34 Response") + }, ConsensusResponse::BeginBlock(x) => Self::BeginBlock(x), ConsensusResponse::DeliverTx(x) => Self::DeliverTx(x), ConsensusResponse::EndBlock(x) => Self::EndBlock(x), diff --git a/tendermint/src/v0_37/abci/request.rs b/tendermint/src/v0_37/abci/request.rs index faf52830c..fce4d19c8 100644 --- a/tendermint/src/v0_37/abci/request.rs +++ b/tendermint/src/v0_37/abci/request.rs @@ -77,6 +77,8 @@ impl From for Request { fn from(req: ConsensusRequest) -> Self { match req { ConsensusRequest::InitChain(x) => Self::InitChain(x), + ConsensusRequest::PrepareProposal(x) => Self::PrepareProposal(x), + ConsensusRequest::ProcessProposal(x) => Self::ProcessProposal(x), ConsensusRequest::BeginBlock(x) => Self::BeginBlock(x), ConsensusRequest::DeliverTx(x) => Self::DeliverTx(x), ConsensusRequest::EndBlock(x) => Self::EndBlock(x), @@ -90,6 +92,8 @@ impl TryFrom for ConsensusRequest { fn try_from(req: Request) -> Result { match req { Request::InitChain(x) => Ok(Self::InitChain(x)), + Request::PrepareProposal(x) => Ok(Self::PrepareProposal(x)), + Request::ProcessProposal(x) => Ok(Self::ProcessProposal(x)), Request::BeginBlock(x) => Ok(Self::BeginBlock(x)), Request::DeliverTx(x) => Ok(Self::DeliverTx(x)), Request::EndBlock(x) => Ok(Self::EndBlock(x)), diff --git a/tendermint/src/v0_37/abci/response.rs b/tendermint/src/v0_37/abci/response.rs index bfe7de822..831f2783c 100644 --- a/tendermint/src/v0_37/abci/response.rs +++ b/tendermint/src/v0_37/abci/response.rs @@ -49,6 +49,8 @@ impl From for Response { fn from(req: ConsensusResponse) -> Self { match req { ConsensusResponse::InitChain(x) => Self::InitChain(x), + ConsensusResponse::PrepareProposal(x) => Self::PrepareProposal(x), + ConsensusResponse::ProcessProposal(x) => Self::ProcessProposal(x), ConsensusResponse::BeginBlock(x) => Self::BeginBlock(x), ConsensusResponse::DeliverTx(x) => Self::DeliverTx(x), ConsensusResponse::EndBlock(x) => Self::EndBlock(x), @@ -62,6 +64,8 @@ impl TryFrom for ConsensusResponse { fn try_from(req: Response) -> Result { match req { Response::InitChain(x) => Ok(Self::InitChain(x)), + Response::PrepareProposal(x) => Ok(Self::PrepareProposal(x)), + Response::ProcessProposal(x) => Ok(Self::ProcessProposal(x)), Response::BeginBlock(x) => Ok(Self::BeginBlock(x)), Response::DeliverTx(x) => Ok(Self::DeliverTx(x)), Response::EndBlock(x) => Ok(Self::EndBlock(x)), From 1f782ea6d6787d7853d02032268f73d54b2b83da Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 16 Jan 2023 14:37:41 +0200 Subject: [PATCH 32/77] rpc: clean up change noise --- rpc/src/lib.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index 95bd9a0d2..3403f110d 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -34,12 +34,12 @@ mod prelude; #[cfg(any(feature = "http-client", feature = "websocket-client"))] mod client; -#[cfg(feature = "http-client")] -pub use client::{HttpClient, HttpClientUrl}; #[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use client::{ MockClient, MockRequestMatcher, MockRequestMethodMatcher, Subscription, SubscriptionClient, }; +#[cfg(feature = "http-client")] +pub use client::{HttpClient, HttpClientUrl}; #[cfg(feature = "websocket-client")] pub use client::{WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig}; From c2f06e3dca1dec34b07c0d3618edcae94439a795 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 16 Jan 2023 15:01:02 +0200 Subject: [PATCH 33/77] Changelog entries for #1193 --- .../1193-multi-version-tendermint.md | 7 +++++++ .../1193-multi-version-tendermint.md | 19 +++++++++++++++++++ 2 files changed, 26 insertions(+) create mode 100644 .changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md create mode 100644 .changelog/unreleased/enhancements/1193-multi-version-tendermint.md diff --git a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md new file mode 100644 index 000000000..7e8c8f758 --- /dev/null +++ b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md @@ -0,0 +1,7 @@ +- [`tendermint`] Version-specific definitions for ABCI `Request` and `Response` + enums under `v0_34::abci` and `v0_37::abci`, containing only the method variants + present in each of the respective protocol versions. + `Request` and `Response` defined under `v0_37` are re-exported under + the non-versioned `abci` module name, but the `SetOption` variant is not present + in these latest versions of the enums. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) diff --git a/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md b/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md new file mode 100644 index 000000000..42ea183e1 --- /dev/null +++ b/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md @@ -0,0 +1,19 @@ +- [`tendermint-proto`] Generate prost bindings for Tendermint 0.34 and 0.37 side by side. + The version-specific structs are placed under the `tendermint::v0_34` and + `tendermint::v0_37` module namespaces, respectively. The names under + `tendermint::v0_37` are also re-exported under `tendermint`. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) +- [`tendermint`] New and updated ABCI domain types for Tendermint Core v0.37 + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). +- [`tendermint`] Protobuf conversions provided for both `v0_34` and `v0_37` + versions of the generated [`tendermint-proto`] structs, where applicable. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). +- [`tendermint-rpc`] Provide separate `Client` traits for Tendermint Core 0.34 + and 0.37, placed under the `v0_34::client` and `v0_37::client` modules. + The latest version is re-exported as `crate::Client`. + The websocket and HTTP client implement both traits, it's up to the + application which one to import for use. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) +- [`tendermint-abci`] Port ABCI application support to 0.37 Tendermint Core API. + No legacy support for 0.34 is provided at the moment. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). From c2fa95a62e926001b2f810693201f16d07aa3d18 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 16 Jan 2023 15:15:11 +0200 Subject: [PATCH 34/77] Revert "rpc: clean up change noise" This reverts commit 1f782ea6d6787d7853d02032268f73d54b2b83da. rustfmt insists on this. --- rpc/src/lib.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index 3403f110d..95bd9a0d2 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -34,12 +34,12 @@ mod prelude; #[cfg(any(feature = "http-client", feature = "websocket-client"))] mod client; +#[cfg(feature = "http-client")] +pub use client::{HttpClient, HttpClientUrl}; #[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use client::{ MockClient, MockRequestMatcher, MockRequestMethodMatcher, Subscription, SubscriptionClient, }; -#[cfg(feature = "http-client")] -pub use client::{HttpClient, HttpClientUrl}; #[cfg(feature = "websocket-client")] pub use client::{WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig}; From 620aa99114d2495d827b292cb43ba69c07613857 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 18 Jan 2023 14:33:26 +0200 Subject: [PATCH 35/77] abci: change serialization to unsigned varint As the protocol used by tendermint-abci has been updated to 0.37, (with no compat mode for 0.34 at the moment), the encoding is changed to match. --- abci/src/codec.rs | 17 +++-------------- 1 file changed, 3 insertions(+), 14 deletions(-) diff --git a/abci/src/codec.rs b/abci/src/codec.rs index bd7796e1d..6542a066d 100644 --- a/abci/src/codec.rs +++ b/abci/src/codec.rs @@ -130,7 +130,7 @@ where message.encode(&mut buf).map_err(Error::encode)?; let buf = buf.freeze(); - encode_varint(buf.len() as u64, &mut dst); + prost::encoding::encode_varint(buf.len() as u64, &mut dst); dst.put(buf); Ok(()) } @@ -142,11 +142,11 @@ where { let src_len = src.len(); let mut tmp = src.clone().freeze(); - let encoded_len = match decode_varint(&mut tmp) { + let encoded_len = match prost::encoding::decode_varint(&mut tmp) { Ok(len) => len, // We've potentially only received a partial length delimiter Err(_) if src_len <= MAX_VARINT_LENGTH => return Ok(None), - Err(e) => return Err(e), + Err(e) => return Err(Error::decode(e)), }; let remaining = tmp.remaining() as u64; if remaining < encoded_len { @@ -164,14 +164,3 @@ where Ok(Some(res)) } } - -// encode_varint and decode_varint will be removed once -// https://github.com/tendermint/tendermint/issues/5783 lands in Tendermint. -pub fn encode_varint(val: u64, mut buf: &mut B) { - prost::encoding::encode_varint(val << 1, &mut buf); -} - -pub fn decode_varint(mut buf: &mut B) -> Result { - let len = prost::encoding::decode_varint(&mut buf).map_err(Error::decode)?; - Ok(len >> 1) -} From 483be773fc87921865f5cb863e229a64e42b84ae Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 18 Jan 2023 14:37:43 +0200 Subject: [PATCH 36/77] abci: changelog notice about varint encoding This is a breaking change. --- .../breaking-changes/1193-multi-version-tendermint.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md index 7e8c8f758..95639322d 100644 --- a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md +++ b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md @@ -5,3 +5,7 @@ the non-versioned `abci` module name, but the `SetOption` variant is not present in these latest versions of the enums. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) +- [`tendermint-abci`] Change the frame length encoding in the ABCI wire protocol + to unsigned varint, to correspond to the changes in Tendermint Core 0.37. + No compatibility with 0.34 is provided at the moment. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). From 0af8abaa381a27039360584218cc4e0fe9312037 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 30 Jan 2023 16:31:39 +0200 Subject: [PATCH 37/77] rpc: multi-version support through generics Introduce Dialect trait and data structures in modules dialect, v0_34::dialect, v0_37::dialect, to realize differences in serialization between RPC versions. Parameterize data structures that need to be differently serialized by generic parameters containing the differences. --- rpc/src/client/transport/http.rs | 35 ++-- rpc/src/client/transport/mock.rs | 15 +- rpc/src/client/transport/websocket.rs | 44 +++-- rpc/src/dialect.rs | 27 +++ rpc/src/dialect/begin_block.rs | 18 ++ rpc/src/dialect/check_tx.rs | 65 +++++++ rpc/src/dialect/deliver_tx.rs | 54 ++++++ rpc/src/dialect/end_block.rs | 30 ++++ rpc/src/endpoint/abci_info.rs | 6 +- rpc/src/endpoint/abci_query.rs | 5 +- rpc/src/endpoint/block.rs | 6 +- rpc/src/endpoint/block_by_hash.rs | 6 +- rpc/src/endpoint/block_results.rs | 22 +-- rpc/src/endpoint/block_search.rs | 6 +- rpc/src/endpoint/blockchain.rs | 5 +- rpc/src/endpoint/broadcast/tx_async.rs | 6 +- rpc/src/endpoint/broadcast/tx_commit.rs | 18 +- rpc/src/endpoint/broadcast/tx_sync.rs | 6 +- rpc/src/endpoint/commit.rs | 6 +- rpc/src/endpoint/consensus_params.rs | 6 +- rpc/src/endpoint/consensus_state.rs | 6 +- rpc/src/endpoint/evidence.rs | 6 +- rpc/src/endpoint/genesis.rs | 11 +- rpc/src/endpoint/header.rs | 6 +- rpc/src/endpoint/header_by_hash.rs | 6 +- rpc/src/endpoint/health.rs | 6 +- rpc/src/endpoint/net_info.rs | 5 +- rpc/src/endpoint/status.rs | 6 +- rpc/src/endpoint/subscribe.rs | 3 +- rpc/src/endpoint/tx.rs | 16 +- rpc/src/endpoint/tx_search.rs | 16 +- rpc/src/endpoint/unsubscribe.rs | 3 +- rpc/src/endpoint/validators.rs | 6 +- rpc/src/event.rs | 28 +-- rpc/src/lib.rs | 1 + rpc/src/request.rs | 46 ++++- rpc/src/v0_34.rs | 8 +- rpc/src/v0_34/client.rs | 16 +- rpc/src/v0_34/dialect.rs | 37 ++++ rpc/src/v0_37.rs | 8 +- rpc/src/v0_37/client.rs | 16 +- rpc/src/v0_37/dialect.rs | 28 +++ rpc/tests/gaia_fixtures.rs | 15 +- rpc/tests/kvstore_fixtures.rs | 47 +++-- .../simd_fixtures/incoming/tx_search.json | 166 ++++++++++++++++++ tendermint/src/abci/event.rs | 16 +- tendermint/src/abci/response/begin_block.rs | 5 +- tendermint/src/abci/response/check_tx.rs | 9 +- tendermint/src/abci/response/deliver_tx.rs | 8 +- tendermint/src/abci/response/end_block.rs | 8 +- 50 files changed, 736 insertions(+), 208 deletions(-) create mode 100644 rpc/src/dialect.rs create mode 100644 rpc/src/dialect/begin_block.rs create mode 100644 rpc/src/dialect/check_tx.rs create mode 100644 rpc/src/dialect/deliver_tx.rs create mode 100644 rpc/src/dialect/end_block.rs create mode 100644 rpc/src/v0_34/dialect.rs create mode 100644 rpc/src/v0_37/dialect.rs create mode 100644 rpc/tests/simd_fixtures/incoming/tx_search.json diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index 87cb4aed3..496333a03 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -87,7 +87,7 @@ impl HttpClient { impl v0_34::Client for HttpClient { async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, { self.inner.perform(request).await } @@ -97,7 +97,7 @@ impl v0_34::Client for HttpClient { impl v0_37::Client for HttpClient { async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, { self.inner.perform(request).await } @@ -178,7 +178,10 @@ mod sealed { use hyper_proxy::{Intercept, Proxy, ProxyConnector}; use hyper_rustls::HttpsConnector; - use crate::{client::transport::auth::authorize, prelude::*, Error, Response, SimpleRequest}; + use crate::prelude::*; + use crate::{ + client::transport::auth::authorize, dialect::Dialect, Error, Response, SimpleRequest, + }; /// A wrapper for a `hyper`-based client, generic over the connector type. #[derive(Debug, Clone)] @@ -197,9 +200,10 @@ mod sealed { where C: Connect + Clone + Send + Sync + 'static, { - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, + S: Dialect, { let request = self.build_request(request)?; let response = self.inner.request(request).await.map_err(Error::hyper)?; @@ -211,10 +215,11 @@ mod sealed { impl HyperClient { /// Build a request using the given Tendermint RPC request. - pub fn build_request( - &self, - request: R, - ) -> Result, Error> { + pub fn build_request(&self, request: R) -> Result, Error> + where + R: SimpleRequest, + S: Dialect, + { let request_body = request.into_json(); tracing::debug!("Outgoing request: {}", request_body); @@ -291,9 +296,10 @@ mod sealed { ))) } - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, + S: Dialect, { match self { HttpClient::Http(c) => c.perform(request).await, @@ -325,6 +331,7 @@ mod tests { use hyper::Body; use super::sealed::HyperClient; + use crate::dialect::DefaultDialect; use crate::endpoint::abci_info; fn authorization(req: &Request) -> Option<&str> { @@ -338,7 +345,8 @@ mod tests { let uri = Uri::from_str("http://example.com").unwrap(); let inner = hyper::Client::new(); let client = HyperClient::new(uri, inner); - let req = client.build_request(abci_info::Request).unwrap(); + let req = + HyperClient::build_request::<_, DefaultDialect>(&client, abci_info::Request).unwrap(); assert_eq!(authorization(&req), None); } @@ -348,7 +356,8 @@ mod tests { let uri = Uri::from_str("http://toto:tata@example.com").unwrap(); let inner = hyper::Client::new(); let client = HyperClient::new(uri, inner); - let req = client.build_request(abci_info::Request).unwrap(); + let req = + HyperClient::build_request::<_, DefaultDialect>(&client, abci_info::Request).unwrap(); assert_eq!(authorization(&req), Some("Basic dG90bzp0YXRh")); } diff --git a/rpc/src/client/transport/mock.rs b/rpc/src/client/transport/mock.rs index f9f3f6e64..7b613abdc 100644 --- a/rpc/src/client/transport/mock.rs +++ b/rpc/src/client/transport/mock.rs @@ -10,6 +10,7 @@ use crate::{ sync::{unbounded, ChannelRx, ChannelTx}, transport::router::SubscriptionRouter, }, + dialect::Dialect, event::Event, prelude::*, query::Query, @@ -63,7 +64,7 @@ pub struct MockClient { impl v0_34::Client for MockClient { async fn perform(&self, request: R) -> Result where - R: Request, + R: Request, { self.matcher .response_for(request) @@ -75,7 +76,7 @@ impl v0_34::Client for MockClient { impl v0_37::Client for MockClient { async fn perform(&self, request: R) -> Result where - R: Request, + R: Request, { self.matcher .response_for(request) @@ -209,9 +210,10 @@ impl MockClientDriver { /// [`MockClient`]: struct.MockClient.html pub trait MockRequestMatcher: Send + Sync { /// Provide the corresponding response for the given request (if any). - fn response_for(&self, request: R) -> Option> + fn response_for(&self, request: R) -> Option> where - R: Request; + R: Request, + S: Dialect; } /// Provides a simple [`MockRequestMatcher`] implementation that simply maps @@ -224,9 +226,10 @@ pub struct MockRequestMethodMatcher { } impl MockRequestMatcher for MockRequestMethodMatcher { - fn response_for(&self, request: R) -> Option> + fn response_for(&self, request: R) -> Option> where - R: Request, + R: Request, + S: Dialect, { self.mappings.get(&request.method()).map(|res| match res { Ok(json) => R::Response::from_string(json), diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 26fc349db..db5558b09 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -29,6 +29,7 @@ use crate::{ sync::{ChannelRx, ChannelTx}, transport::router::{PublishResult, SubscriptionRouter}, }, + dialect::Dialect, endpoint::{subscribe, unsubscribe}, error::Error, event::Event, @@ -38,6 +39,7 @@ use crate::{ response, Client, Id, Request, Response, Scheme, SimpleRequest, Subscription, SubscriptionClient, Url, }; +use crate::{v0_34, v0_37}; // WebSocket connection times out if we haven't heard anything at all from the // server in this long. @@ -175,10 +177,20 @@ impl WebSocketClient { } #[async_trait] -impl Client for WebSocketClient { - async fn perform(&self, request: R) -> Result<::Response, Error> +impl v0_34::Client for WebSocketClient { + async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, + { + self.inner.perform(request).await + } +} + +#[async_trait] +impl v0_37::Client for WebSocketClient { + async fn perform(&self, request: R) -> Result + where + R: SimpleRequest, { self.inner.perform(request).await } @@ -275,6 +287,7 @@ mod sealed { sync::{unbounded, ChannelTx}, transport::auth::authorize, }, + dialect::Dialect, prelude::*, query::Query, request::Wrapper, @@ -373,11 +386,12 @@ mod sealed { self.cmd_tx.send(cmd) } - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, + S: Dialect, { - let wrapper = Wrapper::new(request); + let wrapper = Wrapper::new_with_dialect(S::default(), request); let id = wrapper.id().to_string(); let wrapped_request = wrapper.into_json(); @@ -461,9 +475,10 @@ mod sealed { Ok((Self::Secure(client), driver)) } - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, + S: Dialect, { match self { WebSocketClient::Unsecure(c) => c.perform(request).await, @@ -647,9 +662,10 @@ impl WebSocketClientDriver { }) } - async fn send_request(&mut self, wrapper: Wrapper) -> Result<(), Error> + async fn send_request(&mut self, wrapper: Wrapper) -> Result<(), Error> where - R: Request, + R: Request, + S: Dialect, { self.send_msg(Message::Text( serde_json::to_string_pretty(&wrapper).unwrap(), @@ -657,7 +673,10 @@ impl WebSocketClientDriver { .await } - async fn subscribe(&mut self, cmd: SubscribeCommand) -> Result<(), Error> { + async fn subscribe(&mut self, cmd: SubscribeCommand) -> Result<(), Error> + where + S: Dialect, + { // If we already have an active subscription for the given query, // there's no need to initiate another one. Just add this subscription // to the router. @@ -669,8 +688,9 @@ impl WebSocketClientDriver { } // Otherwise, we need to initiate a subscription request. - let wrapper = Wrapper::new_with_id( + let wrapper = Wrapper::new_with_id_and_dialect( Id::Str(cmd.id.clone()), + S::default(), subscribe::Request::new(cmd.query.clone()), ); if let Err(e) = self.send_request(wrapper).await { diff --git a/rpc/src/dialect.rs b/rpc/src/dialect.rs new file mode 100644 index 000000000..38be62973 --- /dev/null +++ b/rpc/src/dialect.rs @@ -0,0 +1,27 @@ +//! Helper types to generalize differences in serialization between +//! Tendermint RPC protocol versions. + +mod begin_block; +mod check_tx; +mod deliver_tx; +mod end_block; + +pub use begin_block::BeginBlock; +pub use check_tx::CheckTx; +pub use deliver_tx::DeliverTx; +pub use end_block::EndBlock; + +use serde::{de::DeserializeOwned, Serialize}; + +pub trait Dialect: sealed::Sealed + Default { + type Event: Serialize + DeserializeOwned; +} + +pub type DefaultDialect = crate::v0_37::Dialect; + +mod sealed { + pub trait Sealed {} + + impl Sealed for crate::v0_34::Dialect {} + impl Sealed for crate::v0_37::Dialect {} +} diff --git a/rpc/src/dialect/begin_block.rs b/rpc/src/dialect/begin_block.rs new file mode 100644 index 000000000..81f716340 --- /dev/null +++ b/rpc/src/dialect/begin_block.rs @@ -0,0 +1,18 @@ +use serde::{Deserialize, Serialize}; + +use crate::prelude::*; + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +pub struct BeginBlock { + /// Events that occurred while beginning the block. + #[serde(default = "Default::default")] + pub events: Vec, +} + +impl Default for BeginBlock { + fn default() -> Self { + Self { + events: Default::default(), + } + } +} diff --git a/rpc/src/dialect/check_tx.rs b/rpc/src/dialect/check_tx.rs new file mode 100644 index 000000000..bddda2e90 --- /dev/null +++ b/rpc/src/dialect/check_tx.rs @@ -0,0 +1,65 @@ +use bytes::Bytes; +use serde::{Deserialize, Serialize}; + +use tendermint::abci::Code; + +use crate::prelude::*; +use crate::serializers; + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +#[serde(default)] +pub struct CheckTx { + /// The response code. + /// + /// Transactions where `code != 0` will be rejected; these transactions will + /// not be broadcast to other nodes or included in a proposal block. + /// Tendermint attributes no other value to the response code. + pub code: Code, + /// Result bytes, if any. + #[serde(with = "serializers::nullable")] + pub data: Bytes, + /// The output of the application's logger. + /// + /// **May be non-deterministic**. + pub log: String, + /// Additional information. + /// + /// **May be non-deterministic**. + pub info: String, + /// Amount of gas requested for the transaction. + #[serde(with = "serializers::from_str")] + pub gas_wanted: i64, + /// Amount of gas consumed by the transaction. + #[serde(with = "serializers::from_str")] + pub gas_used: i64, + /// Events that occurred while checking the transaction. + pub events: Vec, + /// The namespace for the `code`. + pub codespace: String, + /// The transaction's sender (e.g. the signer). + pub sender: String, + /// The transaction's priority (for mempool ordering). + #[serde(with = "serializers::from_str")] + pub priority: i64, + /// mempool_error is set by Tendermint. + /// ABCI applictions should not set mempool_error. + pub mempool_error: String, +} + +impl Default for CheckTx { + fn default() -> Self { + Self { + code: Default::default(), + data: Default::default(), + log: Default::default(), + info: Default::default(), + gas_wanted: Default::default(), + gas_used: Default::default(), + events: Default::default(), + codespace: Default::default(), + sender: Default::default(), + priority: Default::default(), + mempool_error: Default::default(), + } + } +} diff --git a/rpc/src/dialect/deliver_tx.rs b/rpc/src/dialect/deliver_tx.rs new file mode 100644 index 000000000..a618cd09c --- /dev/null +++ b/rpc/src/dialect/deliver_tx.rs @@ -0,0 +1,54 @@ +use bytes::Bytes; +use serde::{Deserialize, Serialize}; + +use tendermint::abci::Code; + +use crate::prelude::*; +use crate::serializers; + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +#[serde(default)] +pub struct DeliverTx { + /// The response code. + /// + /// This code should be `0` only if the transaction is fully valid. However, + /// invalid transactions included in a block will still be executed against + /// the application state. + pub code: Code, + /// Result bytes, if any. + #[serde(with = "serializers::nullable")] + pub data: Bytes, + /// The output of the application's logger. + /// + /// **May be non-deterministic**. + pub log: String, + /// Additional information. + /// + /// **May be non-deterministic**. + pub info: String, + /// Amount of gas requested for the transaction. + #[serde(with = "serializers::from_str")] + pub gas_wanted: i64, + /// Amount of gas consumed by the transaction. + #[serde(with = "serializers::from_str")] + pub gas_used: i64, + /// Events that occurred while executing the transaction. + pub events: Vec, + /// The namespace for the `code`. + pub codespace: String, +} + +impl Default for DeliverTx { + fn default() -> Self { + Self { + code: Default::default(), + data: Default::default(), + log: Default::default(), + info: Default::default(), + gas_wanted: Default::default(), + gas_used: Default::default(), + events: Default::default(), + codespace: Default::default(), + } + } +} diff --git a/rpc/src/dialect/end_block.rs b/rpc/src/dialect/end_block.rs new file mode 100644 index 000000000..50dbaa58c --- /dev/null +++ b/rpc/src/dialect/end_block.rs @@ -0,0 +1,30 @@ +use serde::{Deserialize, Serialize}; + +use tendermint::{consensus, validator}; + +use crate::prelude::*; +use crate::serializers; + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +pub struct EndBlock { + /// Changes to the validator set, if any. + /// + /// Setting the voting power to 0 removes a validator. + #[serde(with = "serializers::nullable")] + pub validator_updates: Vec, + /// Changes to consensus parameters (optional). + pub consensus_param_updates: Option, + /// Events that occurred while ending the block. + #[serde(default = "Default::default")] + pub events: Vec, +} + +impl Default for EndBlock { + fn default() -> Self { + Self { + validator_updates: Default::default(), + consensus_param_updates: Default::default(), + events: Default::default(), + } + } +} diff --git a/rpc/src/endpoint/abci_info.rs b/rpc/src/endpoint/abci_info.rs index 318207138..d272bafa8 100644 --- a/rpc/src/endpoint/abci_info.rs +++ b/rpc/src/endpoint/abci_info.rs @@ -2,11 +2,13 @@ use serde::{Deserialize, Serialize}; +use crate::dialect::Dialect; + /// Request ABCI information from a node #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -14,7 +16,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// ABCI information response #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/abci_query.rs b/rpc/src/endpoint/abci_query.rs index 7ed6cc464..85f061244 100644 --- a/rpc/src/endpoint/abci_query.rs +++ b/rpc/src/endpoint/abci_query.rs @@ -3,6 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{abci::Code, block, merkle::proof::ProofOps, serializers}; +use crate::dialect::Dialect; use crate::prelude::*; /// Query the ABCI application for information @@ -40,7 +41,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -48,7 +49,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// ABCI query response wrapper #[derive(Clone, Debug, PartialEq, Eq, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/block.rs b/rpc/src/endpoint/block.rs index a321d58a8..62c8074c7 100644 --- a/rpc/src/endpoint/block.rs +++ b/rpc/src/endpoint/block.rs @@ -3,6 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::block::{self, Block}; +use crate::dialect::Dialect; + /// Get information about a specific block #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] pub struct Request { @@ -21,7 +23,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -29,7 +31,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Block responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/block_by_hash.rs b/rpc/src/endpoint/block_by_hash.rs index 09100fce6..63e1f2fbd 100644 --- a/rpc/src/endpoint/block_by_hash.rs +++ b/rpc/src/endpoint/block_by_hash.rs @@ -6,6 +6,8 @@ use tendermint::{ Hash, }; +use crate::dialect::Dialect; + /// Get information about a specific block by its hash #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] pub struct Request { @@ -30,7 +32,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -38,7 +40,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Block responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/block_results.rs b/rpc/src/endpoint/block_results.rs index 75f5de739..1d37a7760 100644 --- a/rpc/src/endpoint/block_results.rs +++ b/rpc/src/endpoint/block_results.rs @@ -1,8 +1,10 @@ //! `/block_results` endpoint JSON-RPC wrapper +use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; -use tendermint::{abci, block, consensus, validator}; +use tendermint::{block, consensus, validator}; +use crate::dialect::{DeliverTx, Dialect}; use crate::prelude::*; use crate::serializers; @@ -24,30 +26,30 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; +impl crate::Request for Request { + type Response = Response; fn method(&self) -> crate::Method { crate::Method::BlockResults } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// ABCI result response. -#[derive(Clone, Debug, Deserialize, Serialize)] -pub struct Response { +#[derive(Clone, Debug, Serialize, Deserialize)] +pub struct Response { /// Block height pub height: block::Height, /// Txs results (might be explicit null) - pub txs_results: Option>, + pub txs_results: Option>>, /// Begin block events (might be explicit null) - pub begin_block_events: Option>, + pub begin_block_events: Option>, /// End block events (might be explicit null) - pub end_block_events: Option>, + pub end_block_events: Option>, /// Validator updates (might be explicit null) #[serde(deserialize_with = "serializers::nullable::deserialize")] @@ -57,4 +59,4 @@ pub struct Response { pub consensus_param_updates: Option, } -impl crate::Response for Response {} +impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} diff --git a/rpc/src/endpoint/block_search.rs b/rpc/src/endpoint/block_search.rs index dad8d8add..369f9133d 100644 --- a/rpc/src/endpoint/block_search.rs +++ b/rpc/src/endpoint/block_search.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; pub use super::{block, block_results}; -use crate::{prelude::*, serializers, Method, Order}; +use crate::{dialect::Dialect, prelude::*, serializers, Method, Order}; /// Request for searching for blocks by their BeginBlock and EndBlock events. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -28,7 +28,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> Method { @@ -36,7 +36,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} #[derive(Clone, Debug, Deserialize, Serialize)] pub struct Response { diff --git a/rpc/src/endpoint/blockchain.rs b/rpc/src/endpoint/blockchain.rs index 5fb8ecf24..bb9006fa1 100644 --- a/rpc/src/endpoint/blockchain.rs +++ b/rpc/src/endpoint/blockchain.rs @@ -5,6 +5,7 @@ use core::ops::Range; use serde::{Deserialize, Serialize}; use tendermint::block; +use crate::dialect::Dialect; use crate::prelude::*; /// Get information about a specific block @@ -35,7 +36,7 @@ impl From> for Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -43,7 +44,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Block responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/broadcast/tx_async.rs b/rpc/src/endpoint/broadcast/tx_async.rs index 278f2b7be..42fd86788 100644 --- a/rpc/src/endpoint/broadcast/tx_async.rs +++ b/rpc/src/endpoint/broadcast/tx_async.rs @@ -4,7 +4,7 @@ use bytes::Bytes; use serde::{Deserialize, Serialize}; use tendermint::{abci::Code, Hash}; -use crate::{prelude::*, serializers}; +use crate::{dialect::Dialect, prelude::*, serializers}; /// `/broadcast_tx_async`: broadcast a transaction and return immediately. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -21,7 +21,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -29,7 +29,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Response from either an async or sync transaction broadcast request. #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/broadcast/tx_commit.rs b/rpc/src/endpoint/broadcast/tx_commit.rs index 37a4b1448..c36720d60 100644 --- a/rpc/src/endpoint/broadcast/tx_commit.rs +++ b/rpc/src/endpoint/broadcast/tx_commit.rs @@ -1,9 +1,11 @@ //! `/broadcast_tx_commit`: only returns error if `mempool.CheckTx()` errs or //! if we timeout waiting for tx to commit. +use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; -use tendermint::{abci, block, Hash}; +use tendermint::{block, Hash}; +use crate::dialect::{CheckTx, DeliverTx, Dialect}; use crate::{prelude::*, serializers}; /// `/broadcast_tx_commit`: only returns error if `mempool.CheckTx()` errs or @@ -25,24 +27,24 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; +impl crate::Request for Request { + type Response = Response; fn method(&self) -> crate::Method { crate::Method::BroadcastTxCommit } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Response from `/broadcast_tx_commit`. #[derive(Clone, Debug, Deserialize, Serialize)] -pub struct Response { +pub struct Response { /// `CheckTx` result - pub check_tx: abci::response::CheckTx, + pub check_tx: CheckTx, /// `DeliverTx` result - pub deliver_tx: abci::response::DeliverTx, + pub deliver_tx: DeliverTx, /// Transaction pub hash: Hash, @@ -51,4 +53,4 @@ pub struct Response { pub height: block::Height, } -impl crate::Response for Response {} +impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} diff --git a/rpc/src/endpoint/broadcast/tx_sync.rs b/rpc/src/endpoint/broadcast/tx_sync.rs index ef6a709c1..e827c22af 100644 --- a/rpc/src/endpoint/broadcast/tx_sync.rs +++ b/rpc/src/endpoint/broadcast/tx_sync.rs @@ -4,7 +4,7 @@ use bytes::Bytes; use serde::{Deserialize, Serialize}; use tendermint::{abci::Code, Hash}; -use crate::{prelude::*, serializers}; +use crate::{dialect::Dialect, prelude::*, serializers}; /// `/broadcast_tx_sync`: returns with the response from `CheckTx`. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -21,7 +21,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -29,7 +29,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Response from either an async or sync transaction broadcast request. #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/commit.rs b/rpc/src/endpoint/commit.rs index f21e69cc6..bfdbb97ee 100644 --- a/rpc/src/endpoint/commit.rs +++ b/rpc/src/endpoint/commit.rs @@ -3,6 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, block::signed_header::SignedHeader}; +use crate::dialect::Dialect; + /// Get commit information about a specific block #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] pub struct Request { @@ -18,7 +20,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -26,7 +28,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Commit responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/consensus_params.rs b/rpc/src/endpoint/consensus_params.rs index bb45cff2a..3649137d8 100644 --- a/rpc/src/endpoint/consensus_params.rs +++ b/rpc/src/endpoint/consensus_params.rs @@ -3,6 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::block::Height; +use crate::dialect::Dialect; + /// Get the consensus parameters. /// /// If no height is supplied, the latest consensus parameters will be returned. @@ -20,7 +22,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -28,7 +30,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Consensus parameters response. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] diff --git a/rpc/src/endpoint/consensus_state.rs b/rpc/src/endpoint/consensus_state.rs index 42b426ab2..f96219a20 100644 --- a/rpc/src/endpoint/consensus_state.rs +++ b/rpc/src/endpoint/consensus_state.rs @@ -10,7 +10,7 @@ use tendermint::{ hash, vote, Hash, Time, }; -use crate::{prelude::*, Error, Method}; +use crate::{prelude::*, dialect::Dialect, Error, Method}; // From const NIL_VOTE_STR: &str = "nil-Vote"; @@ -25,7 +25,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> Method { @@ -33,7 +33,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// The current consensus state (UNSTABLE). /// diff --git a/rpc/src/endpoint/evidence.rs b/rpc/src/endpoint/evidence.rs index f5d4d4255..4a4649de9 100644 --- a/rpc/src/endpoint/evidence.rs +++ b/rpc/src/endpoint/evidence.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{evidence::Evidence, Hash}; -use crate::Method; +use crate::{dialect::Dialect, Method}; /// `/broadcast_evidence`: broadcast an evidence. #[derive(Clone, Debug, Deserialize, PartialEq, Eq, Serialize)] @@ -19,7 +19,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> Method { @@ -27,7 +27,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Response from either an evidence broadcast request. #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/genesis.rs b/rpc/src/endpoint/genesis.rs index 9893bfb36..c7cdbb8c7 100644 --- a/rpc/src/endpoint/genesis.rs +++ b/rpc/src/endpoint/genesis.rs @@ -5,6 +5,8 @@ use core::{fmt, marker::PhantomData}; use serde::{de::DeserializeOwned, Deserialize, Serialize}; use tendermint::Genesis; +use crate::dialect::Dialect; + /// Get the genesis state for the current chain #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request(#[serde(skip)] PhantomData); @@ -15,9 +17,10 @@ impl Default for Request { } } -impl crate::Request for Request +impl crate::Request for Request where AppState: fmt::Debug + Serialize + DeserializeOwned + Send, + S: Dialect, { type Response = Response; @@ -26,8 +29,10 @@ where } } -impl crate::SimpleRequest for Request where - AppState: fmt::Debug + Serialize + DeserializeOwned + Send +impl crate::SimpleRequest for Request +where + AppState: fmt::Debug + Serialize + DeserializeOwned + Send, + S: Dialect, { } diff --git a/rpc/src/endpoint/header.rs b/rpc/src/endpoint/header.rs index 373f9d346..a3d047c8f 100644 --- a/rpc/src/endpoint/header.rs +++ b/rpc/src/endpoint/header.rs @@ -3,6 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::block::{self, Header}; +use crate::v0_37; + /// Get information about a specific block #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] pub struct Request { @@ -21,7 +23,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -29,7 +31,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Header response #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/header_by_hash.rs b/rpc/src/endpoint/header_by_hash.rs index 0406942e4..c92c51131 100644 --- a/rpc/src/endpoint/header_by_hash.rs +++ b/rpc/src/endpoint/header_by_hash.rs @@ -3,6 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::{block::Header, Hash}; +use crate::v0_37; + /// Get information about a specific block by its hash #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] pub struct Request { @@ -27,7 +29,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -35,7 +37,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Header response #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/health.rs b/rpc/src/endpoint/health.rs index 677dee9e1..a72009f44 100644 --- a/rpc/src/endpoint/health.rs +++ b/rpc/src/endpoint/health.rs @@ -2,11 +2,13 @@ use serde::{Deserialize, Serialize}; +use crate::dialect::Dialect; + /// Perform a basic healthceck of the backend #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -14,7 +16,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Healthcheck responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/net_info.rs b/rpc/src/endpoint/net_info.rs index da2b56920..f89432e2e 100644 --- a/rpc/src/endpoint/net_info.rs +++ b/rpc/src/endpoint/net_info.rs @@ -9,13 +9,14 @@ use std::net::IpAddr; use serde::{Deserialize, Serialize}; use tendermint::{channel::Channel, node, serializers, Time}; +use crate::dialect::Dialect; use crate::prelude::*; /// Request network information from a node #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -23,7 +24,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Net info responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/status.rs b/rpc/src/endpoint/status.rs index 434b6185d..946b8d8c7 100644 --- a/rpc/src/endpoint/status.rs +++ b/rpc/src/endpoint/status.rs @@ -3,11 +3,13 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, node, validator, AppHash, Hash, Time}; +use crate::dialect::Dialect; + /// Node status request #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -15,7 +17,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Status responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/subscribe.rs b/rpc/src/endpoint/subscribe.rs index 2874bf8b7..12728b0c5 100644 --- a/rpc/src/endpoint/subscribe.rs +++ b/rpc/src/endpoint/subscribe.rs @@ -3,6 +3,7 @@ use serde::{Deserialize, Serialize}; use crate::prelude::*; +use crate::dialect::Dialect; /// Subscription request for events. /// @@ -23,7 +24,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { diff --git a/rpc/src/endpoint/tx.rs b/rpc/src/endpoint/tx.rs index fed4ae85b..f934685bd 100644 --- a/rpc/src/endpoint/tx.rs +++ b/rpc/src/endpoint/tx.rs @@ -1,8 +1,10 @@ //! `/tx` endpoint JSON-RPC wrapper +use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; -use tendermint::{abci, block, tx, Hash}; +use tendermint::{block, tx, Hash}; +use crate::dialect::{DeliverTx, Dialect}; use crate::{prelude::*, serializers, Method}; /// Request for finding a transaction by its hash. @@ -26,18 +28,18 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; +impl crate::Request for Request { + type Response = Response; fn method(&self) -> Method { Method::Tx } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} #[derive(Clone, Debug, Deserialize, Serialize)] -pub struct Response { +pub struct Response { /// The hash of the transaction. /// /// Deserialized from a hex-encoded string (there is a discrepancy between @@ -46,11 +48,11 @@ pub struct Response { pub hash: Hash, pub height: block::Height, pub index: u32, - pub tx_result: abci::response::DeliverTx, + pub tx_result: DeliverTx, #[serde(with = "serializers::bytes::base64string")] pub tx: Vec, #[serde(skip_serializing_if = "Option::is_none")] pub proof: Option, } -impl crate::Response for Response {} +impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} diff --git a/rpc/src/endpoint/tx_search.rs b/rpc/src/endpoint/tx_search.rs index b59ca2475..854b1b52e 100644 --- a/rpc/src/endpoint/tx_search.rs +++ b/rpc/src/endpoint/tx_search.rs @@ -1,9 +1,9 @@ //! `/tx_search` endpoint JSON-RPC wrapper -use serde::{Deserialize, Serialize}; +use serde::{de::DeserializeOwned, Deserialize, Serialize}; pub use super::tx; -use crate::{prelude::*, serializers, Method, Order}; +use crate::{dialect::Dialect, prelude::*, serializers, Method, Order}; /// Request for searching for transactions with their results. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -36,21 +36,21 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; +impl crate::Request for Request { + type Response = Response; fn method(&self) -> Method { Method::TxSearch } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} #[derive(Clone, Debug, Deserialize, Serialize)] -pub struct Response { - pub txs: Vec, +pub struct Response { + pub txs: Vec>, #[serde(with = "serializers::from_str")] pub total_count: u32, } -impl crate::Response for Response {} +impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} diff --git a/rpc/src/endpoint/unsubscribe.rs b/rpc/src/endpoint/unsubscribe.rs index b1c4596fc..546eb970c 100644 --- a/rpc/src/endpoint/unsubscribe.rs +++ b/rpc/src/endpoint/unsubscribe.rs @@ -2,6 +2,7 @@ use serde::{Deserialize, Serialize}; +use crate::dialect::Dialect; use crate::prelude::*; /// Request to unsubscribe from events relating to a given query. @@ -17,7 +18,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { diff --git a/rpc/src/endpoint/validators.rs b/rpc/src/endpoint/validators.rs index d71cf915d..423c8e7c3 100644 --- a/rpc/src/endpoint/validators.rs +++ b/rpc/src/endpoint/validators.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, validator}; -use crate::{prelude::*, serializers, PageNumber, PerPage}; +use crate::{dialect::Dialect, prelude::*, serializers, PageNumber, PerPage}; /// The default number of validators to return per page. pub const DEFAULT_VALIDATORS_PER_PAGE: u8 = 30; @@ -43,7 +43,7 @@ impl Request { } } -impl crate::Request for Request { +impl crate::Request for Request { type Response = Response; fn method(&self) -> crate::Method { @@ -51,7 +51,7 @@ impl crate::Request for Request { } } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request {} /// Validator responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/event.rs b/rpc/src/event.rs index 5ce997796..29057df9f 100644 --- a/rpc/src/event.rs +++ b/rpc/src/event.rs @@ -2,24 +2,26 @@ use alloc::collections::BTreeMap as HashMap; -use serde::{Deserialize, Serialize}; -use tendermint::{abci, Block}; +use serde::{de::DeserializeOwned, Deserialize, Serialize}; +use tendermint::Block; +use crate::dialect::{self, DefaultDialect, Dialect}; use crate::{prelude::*, query::EventType, response::Wrapper, serializers, Response}; /// An incoming event produced by a [`Subscription`]. /// /// [`Subscription`]: ../struct.Subscription.html #[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq)] -pub struct Event { +pub struct Event::Event> { /// The query that produced the event. pub query: String, /// The data associated with the event. - pub data: EventData, + pub data: EventData, /// Event type and attributes map. pub events: Option>>, } -impl Response for Event {} + +impl Response for Event where Ev: Serialize + DeserializeOwned {} /// A JSON-RPC-wrapped event. pub type WrappedEvent = Wrapper; @@ -41,37 +43,37 @@ impl Event { #[serde(tag = "type", content = "value")] // To be fixed in 0.24 #[allow(clippy::large_enum_variant)] -pub enum EventData { +pub enum EventData::Event> { #[serde(alias = "tendermint/event/NewBlock")] NewBlock { block: Option, - result_begin_block: Option, - result_end_block: Option, + result_begin_block: Option>, + result_end_block: Option>, }, #[serde(alias = "tendermint/event/Tx")] Tx { #[serde(rename = "TxResult")] - tx_result: TxInfo, + tx_result: TxInfo, }, GenericJsonEvent(serde_json::Value), } /// Transaction result info. #[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq)] -pub struct TxInfo { +pub struct TxInfo::Event> { #[serde(with = "serializers::from_str")] pub height: i64, pub index: Option, #[serde(with = "serializers::bytes::base64string")] pub tx: Vec, - pub result: TxResult, + pub result: TxResult, } /// Transaction result. #[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq)] -pub struct TxResult { +pub struct TxResult::Event> { pub log: Option, pub gas_wanted: Option, pub gas_used: Option, - pub events: Vec, + pub events: Vec, } diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index 95bd9a0d2..0251d9db4 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -43,6 +43,7 @@ pub use client::{ #[cfg(feature = "websocket-client")] pub use client::{WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig}; +mod dialect; pub mod endpoint; pub mod error; pub mod event; diff --git a/rpc/src/request.rs b/rpc/src/request.rs index ccafc45a3..6657d389a 100644 --- a/rpc/src/request.rs +++ b/rpc/src/request.rs @@ -5,10 +5,11 @@ use core::fmt::Debug; use serde::{de::DeserializeOwned, Deserialize, Serialize}; use super::{Id, Method, Version}; +use crate::dialect::{DefaultDialect, Dialect}; use crate::{prelude::*, Error}; /// JSON-RPC requests -pub trait Request: Debug + DeserializeOwned + Serialize + Sized + Send { +pub trait Request: DeserializeOwned + Serialize + Sized + Send { /// Response type for this command type Response: super::response::Response; @@ -17,12 +18,12 @@ pub trait Request: Debug + DeserializeOwned + Serialize + Sized + Send { /// Serialize this request as JSON fn into_json(self) -> String { - Wrapper::new(self).into_json() + Wrapper::new_with_dialect(S::default(), self).into_json() } /// Parse a JSON-RPC request from a JSON string. fn from_string(s: impl AsRef<[u8]>) -> Result { - let wrapper: Wrapper = serde_json::from_slice(s.as_ref()).map_err(Error::serde)?; + let wrapper: Wrapper = serde_json::from_slice(s.as_ref()).map_err(Error::serde)?; Ok(wrapper.params) } } @@ -35,11 +36,11 @@ pub trait Request: Debug + DeserializeOwned + Serialize + Sized + Send { /// simple, singular response. /// /// [`Subscription`]: struct.Subscription.html -pub trait SimpleRequest: Request {} +pub trait SimpleRequest: Request {} /// JSON-RPC request wrapper (i.e. message envelope) #[derive(Debug, Deserialize, Serialize)] -pub struct Wrapper { +pub struct Wrapper { /// JSON-RPC version jsonrpc: Version, @@ -51,11 +52,16 @@ pub struct Wrapper { /// Request parameters (i.e. request object) params: R, + + /// Dialect tag + #[serde(skip)] + #[allow(dead_code)] + dialect: S, } -impl Wrapper +impl Wrapper where - R: Request, + R: Request, { /// Create a new request wrapper from the given request. /// @@ -72,6 +78,32 @@ where id, method: request.method(), params: request, + dialect: Default::default(), + } + } +} + +impl Wrapper +where + R: Request, + S: Dialect, +{ + /// Create a new request wrapper from the given request. + /// + /// The ID of the request is set to a random [UUIDv4] value. + /// + /// [UUIDv4]: https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_4_(random) + pub fn new_with_dialect(dialect: S, request: R) -> Self { + Self::new_with_id_and_dialect(Id::uuid_v4(), dialect, request) + } + + pub(crate) fn new_with_id_and_dialect(id: Id, dialect: S, request: R) -> Self { + Self { + jsonrpc: Version::current(), + id, + method: request.method(), + params: request, + dialect, } } diff --git a/rpc/src/v0_34.rs b/rpc/src/v0_34.rs index 81ee4d6bc..d336a1328 100644 --- a/rpc/src/v0_34.rs +++ b/rpc/src/v0_34.rs @@ -1,5 +1,7 @@ -#![cfg(any(feature = "http-client", feature = "websocket-client"))] - +#[cfg(any(feature = "http-client", feature = "websocket-client"))] mod client; - +#[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use client::Client; + +pub mod dialect; +pub use dialect::Dialect; diff --git a/rpc/src/v0_34/client.rs b/rpc/src/v0_34/client.rs index 3d617b402..e942e35e3 100644 --- a/rpc/src/v0_34/client.rs +++ b/rpc/src/v0_34/client.rs @@ -7,6 +7,7 @@ use serde::{de::DeserializeOwned, Serialize}; use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; use tokio::time; +use super::dialect::{Dialect, Event}; use crate::{ endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, paging::Paging, @@ -68,7 +69,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for a block at a particular height. - async fn block_results(&self, height: H) -> Result + async fn block_results(&self, height: H) -> Result, Error> where H: Into + Send, { @@ -77,7 +78,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for the latest block. - async fn latest_block_results(&self) -> Result { + async fn latest_block_results(&self) -> Result, Error> { self.perform(block_results::Request::default()).await } @@ -126,7 +127,10 @@ pub trait Client { /// `/broadcast_tx_commit`: broadcast a transaction, returning the response /// from `DeliverTx`. - async fn broadcast_tx_commit(&self, tx: T) -> Result + async fn broadcast_tx_commit( + &self, + tx: T, + ) -> Result, Error> where T: Into> + Send, { @@ -248,7 +252,7 @@ pub trait Client { } /// `/tx`: find transaction by hash. - async fn tx(&self, hash: Hash, prove: bool) -> Result { + async fn tx(&self, hash: Hash, prove: bool) -> Result, Error> { self.perform(tx::Request::new(hash, prove)).await } @@ -260,7 +264,7 @@ pub trait Client { page: u32, per_page: u8, order: Order, - ) -> Result { + ) -> Result, Error> { self.perform(tx_search::Request::new(query, prove, page, per_page, order)) .await } @@ -290,5 +294,5 @@ pub trait Client { /// Perform a request against the RPC endpoint async fn perform(&self, request: R) -> Result where - R: SimpleRequest; + R: SimpleRequest; } diff --git a/rpc/src/v0_34/dialect.rs b/rpc/src/v0_34/dialect.rs new file mode 100644 index 000000000..ed47d936b --- /dev/null +++ b/rpc/src/v0_34/dialect.rs @@ -0,0 +1,37 @@ +use crate::prelude::*; +use crate::serializers::bytes::base64string; +use serde::{Deserialize, Serialize}; + +#[derive(Default)] +pub struct Dialect; + +impl crate::dialect::Dialect for Dialect { + type Event = Event; +} + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +pub struct Event { + #[serde(rename = "type")] + pub kind: String, + pub attributes: Vec, +} + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +pub struct EventAttribute { + /// The event key. + #[serde( + serialize_with = "base64string::serialize", + deserialize_with = "base64string::deserialize_to_string" + )] + pub key: String, + /// The event value. + #[serde( + serialize_with = "base64string::serialize", + deserialize_with = "base64string::deserialize_to_string" + )] + pub value: String, + /// Whether Tendermint's indexer should index this event. + /// + /// **This field is nondeterministic**. + pub index: bool, +} diff --git a/rpc/src/v0_37.rs b/rpc/src/v0_37.rs index 81ee4d6bc..d336a1328 100644 --- a/rpc/src/v0_37.rs +++ b/rpc/src/v0_37.rs @@ -1,5 +1,7 @@ -#![cfg(any(feature = "http-client", feature = "websocket-client"))] - +#[cfg(any(feature = "http-client", feature = "websocket-client"))] mod client; - +#[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use client::Client; + +pub mod dialect; +pub use dialect::Dialect; diff --git a/rpc/src/v0_37/client.rs b/rpc/src/v0_37/client.rs index 40daf5e67..b9e66d7e1 100644 --- a/rpc/src/v0_37/client.rs +++ b/rpc/src/v0_37/client.rs @@ -7,6 +7,7 @@ use serde::{de::DeserializeOwned, Serialize}; use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; use tokio::time; +use super::dialect::{Dialect, Event}; use crate::{ endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, paging::Paging, @@ -84,7 +85,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for a block at a particular height. - async fn block_results(&self, height: H) -> Result + async fn block_results(&self, height: H) -> Result, Error> where H: Into + Send, { @@ -93,7 +94,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for the latest block. - async fn latest_block_results(&self) -> Result { + async fn latest_block_results(&self) -> Result, Error> { self.perform(block_results::Request::default()).await } @@ -142,7 +143,10 @@ pub trait Client { /// `/broadcast_tx_commit`: broadcast a transaction, returning the response /// from `DeliverTx`. - async fn broadcast_tx_commit(&self, tx: T) -> Result + async fn broadcast_tx_commit( + &self, + tx: T, + ) -> Result, Error> where T: Into> + Send, { @@ -264,7 +268,7 @@ pub trait Client { } /// `/tx`: find transaction by hash. - async fn tx(&self, hash: Hash, prove: bool) -> Result { + async fn tx(&self, hash: Hash, prove: bool) -> Result, Error> { self.perform(tx::Request::new(hash, prove)).await } @@ -276,7 +280,7 @@ pub trait Client { page: u32, per_page: u8, order: Order, - ) -> Result { + ) -> Result, Error> { self.perform(tx_search::Request::new(query, prove, page, per_page, order)) .await } @@ -306,5 +310,5 @@ pub trait Client { /// Perform a request against the RPC endpoint async fn perform(&self, request: R) -> Result where - R: SimpleRequest; + R: SimpleRequest; } diff --git a/rpc/src/v0_37/dialect.rs b/rpc/src/v0_37/dialect.rs new file mode 100644 index 000000000..280e59df3 --- /dev/null +++ b/rpc/src/v0_37/dialect.rs @@ -0,0 +1,28 @@ +use crate::prelude::*; +use serde::{Deserialize, Serialize}; + +#[derive(Default)] +pub struct Dialect; + +impl crate::dialect::Dialect for Dialect { + type Event = Event; +} + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +pub struct Event { + #[serde(rename = "type")] + pub kind: String, + pub attributes: Vec, +} + +#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +pub struct EventAttribute { + /// The event key. + pub key: String, + /// The event value. + pub value: String, + /// Whether Tendermint's indexer should index this event. + /// + /// **This field is nondeterministic**. + pub index: bool, +} diff --git a/rpc/tests/gaia_fixtures.rs b/rpc/tests/gaia_fixtures.rs index 8bad4e7f2..e434cc073 100644 --- a/rpc/tests/gaia_fixtures.rs +++ b/rpc/tests/gaia_fixtures.rs @@ -1,6 +1,9 @@ use std::{fs, path::PathBuf}; +// TODO: generate fixtures and test with v0_37::dialect as well +use tendermint_rpc::v0_34::dialect::{Dialect as RpcDialect, Event as RpcEvent}; use tendermint_rpc::{endpoint, event::Event, Request, Response}; + use walkdir::WalkDir; fn find_fixtures(in_out_folder_name: &str) -> Vec { @@ -51,11 +54,11 @@ fn incoming_fixtures() { assert!(r.is_ok(), "{:?}", r); }, "block_results_at_height_10" => { - let r = endpoint::block_results::Response::from_string(content); + let r = endpoint::block_results::Response::::from_string(content); assert!(r.is_ok(), "block_results_at_height_10: {:?}", r); }, "block_results_at_height_4555980" => { - let r = endpoint::block_results::Response::from_string(content); + let r = endpoint::block_results::Response::::from_string(content); assert!(r.is_ok(), "block_results_at_height_4555980: {:?}", r); }, "blockchain_from_1_to_10" => { @@ -87,7 +90,7 @@ fn incoming_fixtures() { }, _ => { if file_name.starts_with("subscribe_newblock_") { - let r = Event::from_string(content); + let r = Event::::from_string(content); assert!(r.is_ok(), "failed to parse event {}: {:?}", file_name, r); } else { panic!("unhandled incoming fixture: {}", file_name); @@ -126,11 +129,13 @@ fn outgoing_fixtures() { assert!(endpoint::block::Request::from_string(content).is_ok()) }, "block_results_at_height_10" => { - let r = endpoint::block_results::Request::from_string(content); + let r = + >::from_string(content); assert!(r.is_ok(), "block_results_at_height_10: {:?}", r); }, "block_results_at_height_4555980" => { - let r = endpoint::block_results::Request::from_string(content); + let r = + >::from_string(content); assert!(r.is_ok(), "block_results_at_height_4555980: {:?}", r); }, "blockchain_from_1_to_10" => { diff --git a/rpc/tests/kvstore_fixtures.rs b/rpc/tests/kvstore_fixtures.rs index 587e83a8d..78d508ea0 100644 --- a/rpc/tests/kvstore_fixtures.rs +++ b/rpc/tests/kvstore_fixtures.rs @@ -298,6 +298,9 @@ fn outgoing_fixtures() { #[test] fn incoming_fixtures() { + // TODO: generate fixtures and test with v0_37::dialect as well + use tendermint_rpc::v0_34::dialect::Event as RpcEvent; + let empty_merkle_root_hash = Some( tendermint::Hash::from_hex_upper( tendermint::hash::Algorithm::Sha256, @@ -458,7 +461,8 @@ fn incoming_fixtures() { assert_eq!(result.block_id.part_set_header.total, 1); }, "block_results_at_height_10" => { - let result = endpoint::block_results::Response::from_string(content).unwrap(); + let result = + endpoint::block_results::Response::::from_string(content).unwrap(); assert!(result.begin_block_events.is_none()); assert!(result.consensus_param_updates.is_none()); assert!(result.end_block_events.is_none()); @@ -528,7 +532,8 @@ fn incoming_fixtures() { }, "broadcast_tx_commit" => { let result = - endpoint::broadcast::tx_commit::Response::from_string(content).unwrap(); + endpoint::broadcast::tx_commit::Response::::from_string(content) + .unwrap(); assert_eq!(result.check_tx.code, abci::Code::Ok); assert!(result.check_tx.codespace.is_empty()); assert!(result.check_tx.data.is_empty()); @@ -829,7 +834,8 @@ fn incoming_fixtures() { } }, "subscribe_newblock_0" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, @@ -884,7 +890,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'NewBlock'"); }, "subscribe_newblock_1" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, @@ -961,7 +968,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'NewBlock'"); }, "subscribe_newblock_2" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, @@ -1016,7 +1024,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'NewBlock'"); }, "subscribe_newblock_3" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, @@ -1071,7 +1080,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'NewBlock'"); }, "subscribe_newblock_4" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, @@ -1129,7 +1139,8 @@ fn incoming_fixtures() { assert!(endpoint::subscribe::Response::from_string(content).is_ok()); }, "subscribe_txs_0" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); let height; if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { height = tx_result.height; @@ -1161,7 +1172,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'Tx'"); }, "subscribe_txs_1" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); let height; if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { height = tx_result.height; @@ -1194,7 +1206,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'Tx'"); }, "subscribe_txs_2" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); let height; if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { height = tx_result.height; @@ -1226,7 +1239,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'Tx'"); }, "subscribe_txs_3" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); let height; if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { height = tx_result.height; @@ -1258,7 +1272,8 @@ fn incoming_fixtures() { assert_eq!(result.query, "tm.event = 'Tx'"); }, "subscribe_txs_4" => { - let result = tendermint_rpc::event::Event::from_string(content).unwrap(); + let result = + tendermint_rpc::event::Event::::from_string(content).unwrap(); let height; if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { height = tx_result.height; @@ -1350,7 +1365,7 @@ fn incoming_fixtures() { assert!(result.log.is_empty()); }, "tx" => { - let result = endpoint::tx::Response::from_string(content).unwrap(); + let result = endpoint::tx::Response::::from_string(content).unwrap(); assert_eq!( result.hash, Hash::from_bytes( @@ -1366,7 +1381,8 @@ fn incoming_fixtures() { assert_eq!(u64::from(result.height), 12u64); }, "tx_search_no_prove" => { - let result = endpoint::tx_search::Response::from_string(content).unwrap(); + let result = + endpoint::tx_search::Response::::from_string(content).unwrap(); assert_eq!(result.total_count as usize, result.txs.len()); // Test a few selected attributes of the results. for tx in result.txs { @@ -1382,7 +1398,8 @@ fn incoming_fixtures() { } }, "tx_search_with_prove" => { - let result = endpoint::tx_search::Response::from_string(content).unwrap(); + let result = + endpoint::tx_search::Response::::from_string(content).unwrap(); assert_eq!(result.total_count as usize, result.txs.len()); // Test a few selected attributes of the results. for tx in result.txs { diff --git a/rpc/tests/simd_fixtures/incoming/tx_search.json b/rpc/tests/simd_fixtures/incoming/tx_search.json new file mode 100644 index 000000000..0bbf8c6d5 --- /dev/null +++ b/rpc/tests/simd_fixtures/incoming/tx_search.json @@ -0,0 +1,166 @@ +{ + "jsonrpc": "2.0", + "id": "950dbe9e-8991-4680-b990-ac5cbe1cf9b5", + "result": { + "txs": [ + { + "hash": "ACDCA9995210D86AF9C73535047AAA3469E915C548194423279FE5F61E41E9F8", + "height": "925", + "index": 0, + "tx_result": { + "code": 0, + "data": "Ei0KKy9pYmMuY29yZS5jbGllbnQudjEuTXNnQ3JlYXRlQ2xpZW50UmVzcG9uc2U=", + "log": "[{\"msg_index\":0,\"events\":[{\"type\":\"create_client\",\"attributes\":[{\"key\":\"client_id\",\"value\":\"07-tendermint-17\"},{\"key\":\"client_type\",\"value\":\"07-tendermint\"},{\"key\":\"consensus_height\",\"value\":\"1-924\"}]},{\"type\":\"message\",\"attributes\":[{\"key\":\"action\",\"value\":\"/ibc.core.client.v1.MsgCreateClient\"},{\"key\":\"sender\",\"value\":\"cosmos175gsvrtdqe5j77566dfyf8f2pgle5v5u9xsda9\"},{\"key\":\"module\",\"value\":\"ibc_client\"}]}]}]", + "info": "", + "gas_wanted": "88080", + "gas_used": "79943", + "events": [ + { + "type": "coin_spent", + "attributes": [ + { + "key": "spender", + "value": "cosmos175gsvrtdqe5j77566dfyf8f2pgle5v5u9xsda9", + "index": true + }, + { + "key": "amount", + "value": "881stake", + "index": true + } + ] + }, + { + "type": "coin_received", + "attributes": [ + { + "key": "receiver", + "value": "cosmos17xpfvakm2amg962yls6f84z3kell8c5lserqta", + "index": true + }, + { + "key": "amount", + "value": "881stake", + "index": true + } + ] + }, + { + "type": "transfer", + "attributes": [ + { + "key": "recipient", + "value": "cosmos17xpfvakm2amg962yls6f84z3kell8c5lserqta", + "index": true + }, + { + "key": "sender", + "value": "cosmos175gsvrtdqe5j77566dfyf8f2pgle5v5u9xsda9", + "index": true + }, + { + "key": "amount", + "value": "881stake", + "index": true + } + ] + }, + { + "type": "message", + "attributes": [ + { + "key": "sender", + "value": "cosmos175gsvrtdqe5j77566dfyf8f2pgle5v5u9xsda9", + "index": true + } + ] + }, + { + "type": "tx", + "attributes": [ + { + "key": "fee", + "value": "881stake", + "index": true + }, + { + "key": "fee_payer", + "value": "cosmos175gsvrtdqe5j77566dfyf8f2pgle5v5u9xsda9", + "index": true + } + ] + }, + { + "type": "tx", + "attributes": [ + { + "key": "acc_seq", + "value": "cosmos175gsvrtdqe5j77566dfyf8f2pgle5v5u9xsda9/17", + "index": true + } + ] + }, + { + "type": "tx", + "attributes": [ + { + "key": "signature", + "value": "eaw7VwfoviJhMffnwxld3T4CR3o1SSZRaLvXldmZ9X5Ktzfegqb5kOKDZWjLPNh1szOiq7/umSm3kuRZNjZEeA==", + "index": true + } + ] + }, + { + "type": "message", + "attributes": [ + { + "key": "action", + "value": "/ibc.core.client.v1.MsgCreateClient", + "index": true + }, + { + "key": "sender", + "value": "cosmos175gsvrtdqe5j77566dfyf8f2pgle5v5u9xsda9", + "index": true + } + ] + }, + { + "type": "create_client", + "attributes": [ + { + "key": "client_id", + "value": "07-tendermint-17", + "index": true + }, + { + "key": "client_type", + "value": "07-tendermint", + "index": true + }, + { + "key": "consensus_height", + "value": "1-924", + "index": true + } + ] + }, + { + "type": "message", + "attributes": [ + { + "key": "module", + "value": "ibc_client", + "index": true + } + ] + } + ], + "codespace": "" + }, + "tx": "Cs8DCo0DCiMvaWJjLmNvcmUuY2xpZW50LnYxLk1zZ0NyZWF0ZUNsaWVudBLlAgqqAQorL2liYy5saWdodGNsaWVudHMudGVuZGVybWludC52MS5DbGllbnRTdGF0ZRJ7CgVpYmMtMRIECAEQAxoECIDqSSIECIDfbioCCCgyADoFCAEQnAdCGQoJCAEYASABKgEAEgwKAgABECEYBCAMMAFCGQoJCAEYASABKgEAEgwKAgABECAYASABMAFKB3VwZ3JhZGVKEHVwZ3JhZGVkSUJDU3RhdGVQAVgBEoYBCi4vaWJjLmxpZ2h0Y2xpZW50cy50ZW5kZXJtaW50LnYxLkNvbnNlbnN1c1N0YXRlElQKDAj2kMWeBhD4iszpARIiCiBZ4RxJoGp5+LiWhv9GmXmro0O9PsLAJae7p+ddjMlKshogtvCuWO8lJ8lFLlabtOVGzd/+1IblTmo12leDMLoFz/saLWNvc21vczE3NWdzdnJ0ZHFlNWo3NzU2NmRmeWY4ZjJwZ2xlNXY1dTl4c2RhORI9aGVybWVzIDEuMi4wKzdmM2M0ZDc4LWRpcnR5IChodHRwczovL2hlcm1lcy5pbmZvcm1hbC5zeXN0ZW1zKRJmClAKRgofL2Nvc21vcy5jcnlwdG8uc2VjcDI1NmsxLlB1YktleRIjCiED3b32P6jgs4E32s/TRZksqUTo3E7SuAcQOsAGQ5UYWjQSBAoCCAEYERISCgwKBXN0YWtlEgM4ODEQkLAFGkB5rDtXB+i+ImEx9+fDGV3dPgJHejVJJlFou9eV2Zn1fkq3N96CpvmQ4oNlaMs82HWzM6Krv+6ZKbeS5Fk2NkR4" + } + ], + "total_count": "1" + } +} \ No newline at end of file diff --git a/tendermint/src/abci/event.rs b/tendermint/src/abci/event.rs index f7c1aa7e2..099675110 100644 --- a/tendermint/src/abci/event.rs +++ b/tendermint/src/abci/event.rs @@ -1,7 +1,4 @@ -use serde::{Deserialize, Serialize}; - use crate::prelude::*; -use crate::serializers::bytes::base64string; /// An event that occurred while processing a request. /// @@ -13,13 +10,12 @@ use crate::serializers::bytes::base64string; /// be queried using these events. /// /// [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#events) -#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +#[derive(Clone, PartialEq, Eq, Debug)] pub struct Event { /// The kind of event. /// /// Tendermint calls this the `type`, but we use `kind` to avoid confusion /// with Rust types and follow Rust conventions. - #[serde(rename = "type")] pub kind: String, /// A list of [`EventAttribute`]s describing the event. pub attributes: Vec, @@ -63,19 +59,11 @@ impl Event { /// [`Event::new`] for details. /// /// [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#events) -#[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] +#[derive(Clone, PartialEq, Eq, Debug)] pub struct EventAttribute { /// The event key. - #[serde( - serialize_with = "base64string::serialize", - deserialize_with = "base64string::deserialize_to_string" - )] pub key: String, /// The event value. - #[serde( - serialize_with = "base64string::serialize", - deserialize_with = "base64string::deserialize_to_string" - )] pub value: String, /// Whether Tendermint's indexer should index this event. /// diff --git a/tendermint/src/abci/response/begin_block.rs b/tendermint/src/abci/response/begin_block.rs index 01ac0d202..8319a116a 100644 --- a/tendermint/src/abci/response/begin_block.rs +++ b/tendermint/src/abci/response/begin_block.rs @@ -1,13 +1,10 @@ -use serde::{Deserialize, Serialize}; - use super::super::Event; use crate::prelude::*; #[doc = include_str!("../doc/response-beginblock.md")] -#[derive(Clone, PartialEq, Eq, Debug, Default, Serialize, Deserialize)] +#[derive(Clone, PartialEq, Eq, Debug, Default)] pub struct BeginBlock { /// Events that occurred while beginning the block. - #[serde(default)] pub events: Vec, } diff --git a/tendermint/src/abci/response/check_tx.rs b/tendermint/src/abci/response/check_tx.rs index 355c1a330..ba9245ee8 100644 --- a/tendermint/src/abci/response/check_tx.rs +++ b/tendermint/src/abci/response/check_tx.rs @@ -1,13 +1,10 @@ use bytes::Bytes; -use serde::{Deserialize, Serialize}; use super::super::{Code, Event}; use crate::prelude::*; -use crate::serializers; #[doc = include_str!("../doc/response-checktx.md")] -#[derive(Clone, PartialEq, Eq, Debug, Default, Serialize, Deserialize)] -#[serde(default)] +#[derive(Clone, PartialEq, Eq, Debug, Default)] pub struct CheckTx { /// The response code. /// @@ -16,7 +13,6 @@ pub struct CheckTx { /// Tendermint attributes no other value to the response code. pub code: Code, /// Result bytes, if any. - #[serde(with = "serializers::nullable")] pub data: Bytes, /// The output of the application's logger. /// @@ -27,10 +23,8 @@ pub struct CheckTx { /// **May be non-deterministic**. pub info: String, /// Amount of gas requested for the transaction. - #[serde(with = "serializers::from_str")] pub gas_wanted: i64, /// Amount of gas consumed by the transaction. - #[serde(with = "serializers::from_str")] pub gas_used: i64, /// Events that occurred while checking the transaction. pub events: Vec, @@ -39,7 +33,6 @@ pub struct CheckTx { /// The transaction's sender (e.g. the signer). pub sender: String, /// The transaction's priority (for mempool ordering). - #[serde(with = "serializers::from_str")] pub priority: i64, /// mempool_error is set by Tendermint. /// ABCI applictions should not set mempool_error. diff --git a/tendermint/src/abci/response/deliver_tx.rs b/tendermint/src/abci/response/deliver_tx.rs index 8d269c6af..b8c6ff8f3 100644 --- a/tendermint/src/abci/response/deliver_tx.rs +++ b/tendermint/src/abci/response/deliver_tx.rs @@ -1,13 +1,10 @@ use bytes::Bytes; -use serde::{Deserialize, Serialize}; use super::super::{Code, Event}; use crate::prelude::*; -use crate::serializers; #[doc = include_str!("../doc/response-delivertx.md")] -#[derive(Clone, PartialEq, Eq, Debug, Default, Serialize, Deserialize)] -#[serde(default)] +#[derive(Clone, PartialEq, Eq, Debug, Default)] pub struct DeliverTx { /// The response code. /// @@ -16,7 +13,6 @@ pub struct DeliverTx { /// the application state. pub code: Code, /// Result bytes, if any. - #[serde(with = "serializers::nullable")] pub data: Bytes, /// The output of the application's logger. /// @@ -27,10 +23,8 @@ pub struct DeliverTx { /// **May be non-deterministic**. pub info: String, /// Amount of gas requested for the transaction. - #[serde(with = "serializers::from_str")] pub gas_wanted: i64, /// Amount of gas consumed by the transaction. - #[serde(with = "serializers::from_str")] pub gas_used: i64, /// Events that occurred while executing the transaction. pub events: Vec, diff --git a/tendermint/src/abci/response/end_block.rs b/tendermint/src/abci/response/end_block.rs index 9f5ad4ebb..ce2b9950f 100644 --- a/tendermint/src/abci/response/end_block.rs +++ b/tendermint/src/abci/response/end_block.rs @@ -1,20 +1,16 @@ -use serde::{Deserialize, Serialize}; - use super::super::Event; -use crate::{consensus, prelude::*, serializers, validator}; +use crate::{consensus, prelude::*, validator}; #[doc = include_str!("../doc/response-endblock.md")] -#[derive(Clone, PartialEq, Eq, Debug, Default, Serialize, Deserialize)] +#[derive(Clone, PartialEq, Eq, Debug, Default)] pub struct EndBlock { /// Changes to the validator set, if any. /// /// Setting the voting power to 0 removes a validator. - #[serde(with = "serializers::nullable")] pub validator_updates: Vec, /// Changes to consensus parameters (optional). pub consensus_param_updates: Option, /// Events that occurred while ending the block. - #[serde(default)] pub events: Vec, } From 91b984de870f79c008baa0b02a53cad1fb0c7ecb Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 31 Jan 2023 15:23:13 +0200 Subject: [PATCH 38/77] rpc: remove generic default from request::Wrapper --- rpc/src/client/transport/websocket.rs | 2 +- rpc/src/request.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 10aad5c0a..4b8cf8182 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -661,7 +661,7 @@ impl WebSocketClientDriver { }) } - async fn send_request(&mut self, wrapper: Wrapper) -> Result<(), Error> + async fn send_request(&mut self, wrapper: Wrapper) -> Result<(), Error> where R: Request, S: Dialect, diff --git a/rpc/src/request.rs b/rpc/src/request.rs index 6657d389a..78d315174 100644 --- a/rpc/src/request.rs +++ b/rpc/src/request.rs @@ -40,7 +40,7 @@ pub trait SimpleRequest: Request {} /// JSON-RPC request wrapper (i.e. message envelope) #[derive(Debug, Deserialize, Serialize)] -pub struct Wrapper { +pub struct Wrapper { /// JSON-RPC version jsonrpc: Version, From 6054e3eb5f8de00c77246b9b8fe1fffa4d9c6e13 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 1 Feb 2023 03:49:57 +0200 Subject: [PATCH 39/77] Implement both Client dialect traits for websocket --- rpc/src/client/transport/websocket.rs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 4b8cf8182..61ccc4abd 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -36,8 +36,7 @@ use crate::{ prelude::*, query::Query, request::Wrapper, - response, Client, Id, Request, Response, Scheme, SimpleRequest, Subscription, - SubscriptionClient, Url, + response, Id, Request, Response, Scheme, SimpleRequest, Subscription, SubscriptionClient, Url, }; use crate::{v0_34, v0_37}; From ab167850c1836b2345bce52e349f3c1f66809ae9 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 1 Feb 2023 03:54:24 +0200 Subject: [PATCH 40/77] Rework Event serialization with helper types DialectEvent and its sub-field structs take over the dialectal generics, while Event and its inner structs remain public types free from serialization concerns. --- rpc/src/client/transport/mock.rs | 89 ++++++++++--------- rpc/src/client/transport/router.rs | 5 +- rpc/src/dialect/begin_block.rs | 13 +++ rpc/src/dialect/end_block.rs | 15 +++- rpc/src/event.rs | 138 +++++++++++++++++++++++++---- rpc/src/request.rs | 4 +- rpc/src/v0_34/dialect.rs | 21 +++++ rpc/src/v0_37/dialect.rs | 21 +++++ 8 files changed, 244 insertions(+), 62 deletions(-) diff --git a/rpc/src/client/transport/mock.rs b/rpc/src/client/transport/mock.rs index 7b613abdc..1139e275c 100644 --- a/rpc/src/client/transport/mock.rs +++ b/rpc/src/client/transport/mock.rs @@ -269,13 +269,17 @@ mod test { .unwrap() } - async fn read_event(name: &str) -> Event { - Event::from_string(read_json_fixture(name).await).unwrap() - } - mod v0_34 { use super::*; - use crate::v0_34::Client; + use crate::event::DialectEvent; + use crate::v0_34::{dialect, Client}; + + async fn read_event(name: &str) -> Event { + let msg = + DialectEvent::::from_string(read_json_fixture(name).await).unwrap(); + msg.into() + } + #[tokio::test] async fn mock_client() { let abci_info_fixture = read_json_fixture("abci_info").await; @@ -296,11 +300,49 @@ mod test { client.close(); driver_hdl.await.unwrap().unwrap(); } + + #[tokio::test] + async fn mock_subscription_client() { + let (client, driver) = MockClient::new(MockRequestMethodMatcher::default()); + let driver_hdl = tokio::spawn(async move { driver.run().await }); + + let event1 = read_event("subscribe_newblock_0").await; + let event2 = read_event("subscribe_newblock_1").await; + let event3 = read_event("subscribe_newblock_2").await; + let events = vec![event1, event2, event3]; + + let subs1 = client.subscribe(EventType::NewBlock.into()).await.unwrap(); + let subs2 = client.subscribe(EventType::NewBlock.into()).await.unwrap(); + assert_ne!(subs1.id().to_string(), subs2.id().to_string()); + + // We can do this because the underlying channels can buffer the + // messages as we publish them. + let subs1_events = subs1.take(3); + let subs2_events = subs2.take(3); + for ev in &events { + client.publish(ev); + } + + // Here each subscription's channel is drained. + let subs1_events = subs1_events.collect::>>().await; + let subs2_events = subs2_events.collect::>>().await; + + assert_eq!(3, subs1_events.len()); + assert_eq!(3, subs2_events.len()); + + for i in 0..3 { + assert!(events[i].eq(subs1_events[i].as_ref().unwrap())); + } + + client.close(); + driver_hdl.await.unwrap().unwrap(); + } } mod v0_37 { use super::*; use crate::v0_37::Client; + #[tokio::test] async fn mock_client() { let abci_info_fixture = read_json_fixture("abci_info").await; @@ -321,42 +363,7 @@ mod test { client.close(); driver_hdl.await.unwrap().unwrap(); } - } - - #[tokio::test] - async fn mock_subscription_client() { - let (client, driver) = MockClient::new(MockRequestMethodMatcher::default()); - let driver_hdl = tokio::spawn(async move { driver.run().await }); - - let event1 = read_event("subscribe_newblock_0").await; - let event2 = read_event("subscribe_newblock_1").await; - let event3 = read_event("subscribe_newblock_2").await; - let events = vec![event1, event2, event3]; - - let subs1 = client.subscribe(EventType::NewBlock.into()).await.unwrap(); - let subs2 = client.subscribe(EventType::NewBlock.into()).await.unwrap(); - assert_ne!(subs1.id().to_string(), subs2.id().to_string()); - - // We can do this because the underlying channels can buffer the - // messages as we publish them. - let subs1_events = subs1.take(3); - let subs2_events = subs2.take(3); - for ev in &events { - client.publish(ev); - } - - // Here each subscription's channel is drained. - let subs1_events = subs1_events.collect::>>().await; - let subs2_events = subs2_events.collect::>>().await; - - assert_eq!(3, subs1_events.len()); - assert_eq!(3, subs2_events.len()); - - for i in 0..3 { - assert!(events[i].eq(subs1_events[i].as_ref().unwrap())); - } - client.close(); - driver_hdl.await.unwrap().unwrap(); + // TODO: add mock_subscription_client test for v0_37 } } diff --git a/rpc/src/client/transport/router.rs b/rpc/src/client/transport/router.rs index 906885a22..d58858caf 100644 --- a/rpc/src/client/transport/router.rs +++ b/rpc/src/client/transport/router.rs @@ -147,6 +147,8 @@ mod test { event::{Event, WrappedEvent}, utils::uuid_str, }; + // TODO: add fixtures for v0_37::dialect + use crate::v0_34::dialect::Event as RpcEvent; async fn read_json_fixture(name: &str) -> String { fs::read_to_string( @@ -157,10 +159,11 @@ mod test { } async fn read_event(name: &str) -> Event { - serde_json::from_str::(read_json_fixture(name).await.as_str()) + serde_json::from_str::>(read_json_fixture(name).await.as_str()) .unwrap() .into_result() .unwrap() + .into() } async fn must_recv(ch: &mut ChannelRx, timeout_ms: u64) -> T { diff --git a/rpc/src/dialect/begin_block.rs b/rpc/src/dialect/begin_block.rs index 81f716340..6e2a6c437 100644 --- a/rpc/src/dialect/begin_block.rs +++ b/rpc/src/dialect/begin_block.rs @@ -1,5 +1,7 @@ use serde::{Deserialize, Serialize}; +use tendermint::abci; + use crate::prelude::*; #[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] @@ -16,3 +18,14 @@ impl Default for BeginBlock { } } } + +impl From> for abci::response::BeginBlock +where + Ev: Into, +{ + fn from(msg: BeginBlock) -> Self { + Self { + events: msg.events.into_iter().map(Into::into).collect(), + } + } +} diff --git a/rpc/src/dialect/end_block.rs b/rpc/src/dialect/end_block.rs index 50dbaa58c..455d2f977 100644 --- a/rpc/src/dialect/end_block.rs +++ b/rpc/src/dialect/end_block.rs @@ -1,6 +1,6 @@ use serde::{Deserialize, Serialize}; -use tendermint::{consensus, validator}; +use tendermint::{abci, consensus, validator}; use crate::prelude::*; use crate::serializers; @@ -28,3 +28,16 @@ impl Default for EndBlock { } } } + +impl From> for abci::response::EndBlock +where + Ev: Into, +{ + fn from(msg: EndBlock) -> Self { + Self { + events: msg.events.into_iter().map(Into::into).collect(), + validator_updates: msg.validator_updates, + consensus_param_updates: msg.consensus_param_updates, + } + } +} diff --git a/rpc/src/event.rs b/rpc/src/event.rs index 29057df9f..a1481bfe4 100644 --- a/rpc/src/event.rs +++ b/rpc/src/event.rs @@ -3,28 +3,38 @@ use alloc::collections::BTreeMap as HashMap; use serde::{de::DeserializeOwned, Deserialize, Serialize}; -use tendermint::Block; +use tendermint::{abci, Block}; -use crate::dialect::{self, DefaultDialect, Dialect}; -use crate::{prelude::*, query::EventType, response::Wrapper, serializers, Response}; +use crate::{dialect, prelude::*, query::EventType, response::Wrapper, serializers, Response}; /// An incoming event produced by a [`Subscription`]. /// /// [`Subscription`]: ../struct.Subscription.html -#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq)] -pub struct Event::Event> { +#[derive(Debug, Clone, PartialEq, Eq)] +pub struct Event { /// The query that produced the event. pub query: String, /// The data associated with the event. - pub data: EventData, + pub data: EventData, /// Event type and attributes map. pub events: Option>>, } -impl Response for Event where Ev: Serialize + DeserializeOwned {} +// Serialization helper supporting differences in RPC versions. +#[derive(Serialize, Deserialize, Debug)] +pub(crate) struct DialectEvent { + /// The query that produced the event. + pub query: String, + /// The data associated with the event. + pub data: DialectEventData, + /// Event type and attributes map. + pub events: Option>>, +} + +impl Response for DialectEvent where Ev: Serialize + DeserializeOwned {} /// A JSON-RPC-wrapped event. -pub type WrappedEvent = Wrapper; +pub(crate) type WrappedEvent = Wrapper>; impl Event { /// Returns the type associated with this event, if we recognize it. @@ -39,11 +49,38 @@ impl Event { } } -#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq)] -#[serde(tag = "type", content = "value")] +impl From> for Event +where + Ev: Into, +{ + fn from(msg: DialectEvent) -> Self { + Event { + query: msg.query, + data: msg.data.into(), + events: msg.events, + } + } +} + +#[derive(Debug, Clone, PartialEq, Eq)] // To be fixed in 0.24 #[allow(clippy::large_enum_variant)] -pub enum EventData::Event> { +pub enum EventData { + NewBlock { + block: Option, + result_begin_block: Option, + result_end_block: Option, + }, + Tx { + tx_result: TxInfo, + }, + GenericJsonEvent(serde_json::Value), +} + +#[derive(Serialize, Deserialize, Debug)] +#[serde(tag = "type", content = "value")] +#[allow(clippy::large_enum_variant)] +pub(crate) enum DialectEventData { #[serde(alias = "tendermint/event/NewBlock")] NewBlock { block: Option, @@ -53,27 +90,94 @@ pub enum EventData::Event> { #[serde(alias = "tendermint/event/Tx")] Tx { #[serde(rename = "TxResult")] - tx_result: TxInfo, + tx_result: DialectTxInfo, }, GenericJsonEvent(serde_json::Value), } +impl From> for EventData +where + Ev: Into, +{ + fn from(msg: DialectEventData) -> Self { + match msg { + DialectEventData::NewBlock { + block, + result_begin_block, + result_end_block, + } => EventData::NewBlock { + block, + result_begin_block: result_begin_block.map(Into::into), + result_end_block: result_end_block.map(Into::into), + }, + DialectEventData::Tx { tx_result } => EventData::Tx { + tx_result: tx_result.into(), + }, + DialectEventData::GenericJsonEvent(v) => EventData::GenericJsonEvent(v), + } + } +} + /// Transaction result info. -#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq)] -pub struct TxInfo::Event> { +#[derive(Debug, Clone, PartialEq, Eq)] +pub struct TxInfo { + pub height: i64, + pub index: Option, + pub tx: Vec, + pub result: TxResult, +} + +#[derive(Serialize, Deserialize, Debug)] +pub(crate) struct DialectTxInfo { #[serde(with = "serializers::from_str")] pub height: i64, pub index: Option, #[serde(with = "serializers::bytes::base64string")] pub tx: Vec, - pub result: TxResult, + pub result: DialectTxResult, +} + +impl From> for TxInfo +where + Ev: Into, +{ + fn from(msg: DialectTxInfo) -> Self { + TxInfo { + height: msg.height, + index: msg.index, + tx: msg.tx, + result: msg.result.into(), + } + } } /// Transaction result. -#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq)] -pub struct TxResult::Event> { +#[derive(Debug, Clone, PartialEq, Eq)] +pub struct TxResult { + pub log: Option, + pub gas_wanted: Option, + pub gas_used: Option, + pub events: Vec, +} + +#[derive(Serialize, Deserialize, Debug)] +pub(crate) struct DialectTxResult { pub log: Option, pub gas_wanted: Option, pub gas_used: Option, pub events: Vec, } + +impl From> for TxResult +where + Ev: Into, +{ + fn from(msg: DialectTxResult) -> Self { + TxResult { + log: msg.log, + gas_wanted: msg.gas_wanted, + gas_used: msg.gas_used, + events: msg.events.into_iter().map(Into::into).collect(), + } + } +} diff --git a/rpc/src/request.rs b/rpc/src/request.rs index 78d315174..d59940930 100644 --- a/rpc/src/request.rs +++ b/rpc/src/request.rs @@ -9,7 +9,7 @@ use crate::dialect::{DefaultDialect, Dialect}; use crate::{prelude::*, Error}; /// JSON-RPC requests -pub trait Request: DeserializeOwned + Serialize + Sized + Send { +pub trait Request: DeserializeOwned + Serialize + Sized + Send { /// Response type for this command type Response: super::response::Response; @@ -36,7 +36,7 @@ pub trait Request: DeserializeOwned + Serialize + Sized + Send { /// simple, singular response. /// /// [`Subscription`]: struct.Subscription.html -pub trait SimpleRequest: Request {} +pub trait SimpleRequest: Request {} /// JSON-RPC request wrapper (i.e. message envelope) #[derive(Debug, Deserialize, Serialize)] diff --git a/rpc/src/v0_34/dialect.rs b/rpc/src/v0_34/dialect.rs index ed47d936b..2af6661d7 100644 --- a/rpc/src/v0_34/dialect.rs +++ b/rpc/src/v0_34/dialect.rs @@ -1,3 +1,5 @@ +use tendermint::abci; + use crate::prelude::*; use crate::serializers::bytes::base64string; use serde::{Deserialize, Serialize}; @@ -16,6 +18,15 @@ pub struct Event { pub attributes: Vec, } +impl From for abci::Event { + fn from(msg: Event) -> Self { + Self { + kind: msg.kind, + attributes: msg.attributes.into_iter().map(Into::into).collect(), + } + } +} + #[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] pub struct EventAttribute { /// The event key. @@ -35,3 +46,13 @@ pub struct EventAttribute { /// **This field is nondeterministic**. pub index: bool, } + +impl From for abci::EventAttribute { + fn from(msg: EventAttribute) -> Self { + Self { + key: msg.key, + value: msg.value, + index: msg.index, + } + } +} diff --git a/rpc/src/v0_37/dialect.rs b/rpc/src/v0_37/dialect.rs index 280e59df3..f052ede7f 100644 --- a/rpc/src/v0_37/dialect.rs +++ b/rpc/src/v0_37/dialect.rs @@ -1,3 +1,5 @@ +use tendermint::abci; + use crate::prelude::*; use serde::{Deserialize, Serialize}; @@ -15,6 +17,15 @@ pub struct Event { pub attributes: Vec, } +impl From for abci::Event { + fn from(msg: Event) -> Self { + Self { + kind: msg.kind, + attributes: msg.attributes.into_iter().map(Into::into).collect(), + } + } +} + #[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] pub struct EventAttribute { /// The event key. @@ -26,3 +37,13 @@ pub struct EventAttribute { /// **This field is nondeterministic**. pub index: bool, } + +impl From for abci::EventAttribute { + fn from(msg: EventAttribute) -> Self { + Self { + key: msg.key, + value: msg.value, + index: msg.index, + } + } +} From 03eda10fbe34c3dd7c3c05e5778f871903708dcc Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 1 Feb 2023 18:02:38 +0200 Subject: [PATCH 41/77] rpc: Refactor subscriptions to support dialects --- rpc/src/client/subscription.rs | 3 +- rpc/src/client/transport/websocket.rs | 157 ++++++++++++------------ rpc/src/dialect.rs | 6 +- rpc/src/endpoint/abci_info.rs | 9 +- rpc/src/endpoint/abci_query.rs | 10 +- rpc/src/endpoint/block.rs | 10 +- rpc/src/endpoint/block_by_hash.rs | 10 +- rpc/src/endpoint/block_results.rs | 9 +- rpc/src/endpoint/block_search.rs | 10 +- rpc/src/endpoint/blockchain.rs | 10 +- rpc/src/endpoint/broadcast/tx_async.rs | 10 +- rpc/src/endpoint/broadcast/tx_commit.rs | 10 +- rpc/src/endpoint/broadcast/tx_sync.rs | 10 +- rpc/src/endpoint/commit.rs | 10 +- rpc/src/endpoint/consensus_params.rs | 10 +- rpc/src/endpoint/consensus_state.rs | 10 +- rpc/src/endpoint/evidence.rs | 10 +- rpc/src/endpoint/genesis.rs | 15 ++- rpc/src/endpoint/header.rs | 9 +- rpc/src/endpoint/header_by_hash.rs | 9 +- rpc/src/endpoint/health.rs | 10 +- rpc/src/endpoint/net_info.rs | 10 +- rpc/src/endpoint/status.rs | 10 +- rpc/src/endpoint/subscribe.rs | 10 +- rpc/src/endpoint/tx.rs | 10 +- rpc/src/endpoint/tx_search.rs | 10 +- rpc/src/endpoint/unsubscribe.rs | 10 +- rpc/src/endpoint/validators.rs | 12 +- rpc/src/request.rs | 56 +++------ rpc/src/v0_34/dialect.rs | 2 +- rpc/src/v0_37/dialect.rs | 2 +- 31 files changed, 259 insertions(+), 220 deletions(-) diff --git a/rpc/src/client/subscription.rs b/rpc/src/client/subscription.rs index d530adf4a..105717e63 100644 --- a/rpc/src/client/subscription.rs +++ b/rpc/src/client/subscription.rs @@ -11,6 +11,7 @@ use pin_project::pin_project; use crate::{ client::sync::{ChannelRx, ChannelTx}, + dialect::DefaultDialect, event::Event, prelude::*, query::Query, @@ -20,7 +21,7 @@ use crate::{ /// A client that exclusively provides [`Event`] subscription capabilities, /// without any other RPC method support. #[async_trait] -pub trait SubscriptionClient { +pub trait SubscriptionClient { /// `/subscribe`: subscribe to receive events produced by the given query. async fn subscribe(&self, query: Query) -> Result; diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 61ccc4abd..bd9711435 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -3,6 +3,7 @@ use alloc::{borrow::Cow, collections::BTreeMap as HashMap}; use core::{ convert::{TryFrom, TryInto}, + marker::PhantomData, ops::Add, str::FromStr, }; @@ -32,7 +33,7 @@ use crate::{ dialect::Dialect, endpoint::{subscribe, unsubscribe}, error::Error, - event::Event, + event::{DialectEvent, Event}, prelude::*, query::Query, request::Wrapper, @@ -136,16 +137,16 @@ pub use async_tungstenite::tungstenite::protocol::WebSocketConfig; /// /// [tendermint-websocket-ping]: https://github.com/tendermint/tendermint/blob/309e29c245a01825fc9630103311fd04de99fa5e/rpc/jsonrpc/server/ws_handler.go#L28 #[derive(Debug, Clone)] -pub struct WebSocketClient { - inner: sealed::WebSocketClient, +pub struct WebSocketClient { + inner: sealed::WebSocketClient, } -impl WebSocketClient { +impl WebSocketClient { /// Construct a new WebSocket-based client connecting to the given /// Tendermint node's RPC endpoint. /// /// Supports both `ws://` and `wss://` protocols. - pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> + pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, { @@ -159,16 +160,17 @@ impl WebSocketClient { pub async fn new_with_config( url: U, config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> + ) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, { let url = url.try_into()?; + let dialect = S::default(); let (inner, driver) = if url.0.is_secure() { - sealed::WebSocketClient::new_secure(url.0, config).await? + sealed::WebSocketClient::new_secure(url.0, config, dialect).await? } else { - sealed::WebSocketClient::new_unsecure(url.0, config).await? + sealed::WebSocketClient::new_unsecure(url.0, config, dialect).await? }; Ok((Self { inner }, driver)) @@ -176,7 +178,7 @@ impl WebSocketClient { } #[async_trait] -impl v0_34::Client for WebSocketClient { +impl v0_34::Client for WebSocketClient { async fn perform(&self, request: R) -> Result where R: SimpleRequest, @@ -186,7 +188,7 @@ impl v0_34::Client for WebSocketClient { } #[async_trait] -impl v0_37::Client for WebSocketClient { +impl v0_37::Client for WebSocketClient { async fn perform(&self, request: R) -> Result where R: SimpleRequest, @@ -196,7 +198,7 @@ impl v0_37::Client for WebSocketClient { } #[async_trait] -impl SubscriptionClient for WebSocketClient { +impl SubscriptionClient for WebSocketClient { async fn subscribe(&self, query: Query) -> Result { self.inner.subscribe(query).await } @@ -310,12 +312,12 @@ mod sealed { /// /// [`async-tungstenite`]: https://crates.io/crates/async-tungstenite #[derive(Debug, Clone)] - pub struct AsyncTungsteniteClient { + pub struct AsyncTungsteniteClient { cmd_tx: ChannelTx, - _client_type: core::marker::PhantomData, + _phantom: core::marker::PhantomData<(C, S)>, } - impl AsyncTungsteniteClient { + impl AsyncTungsteniteClient { /// Construct a WebSocket client. Immediately attempts to open a WebSocket /// connection to the node with the given address. /// @@ -327,7 +329,7 @@ mod sealed { pub async fn new( url: Url, config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { + ) -> Result<(Self, WebSocketClientDriver), Error> { debug!("Connecting to unsecure WebSocket endpoint: {}", url); let (stream, _response) = connect_async_with_config(url, config) @@ -338,14 +340,14 @@ mod sealed { let driver = WebSocketClientDriver::new(stream, cmd_rx); let client = Self { cmd_tx, - _client_type: Default::default(), + _phantom: Default::default(), }; Ok((client, driver)) } } - impl AsyncTungsteniteClient { + impl AsyncTungsteniteClient { /// Construct a WebSocket client. Immediately attempts to open a WebSocket /// connection to the node with the given address, but over a secure /// connection. @@ -358,7 +360,7 @@ mod sealed { pub async fn new( url: Url, config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { + ) -> Result<(Self, WebSocketClientDriver), Error> { debug!("Connecting to secure WebSocket endpoint: {}", url); // Not supplying a connector means async_tungstenite will create the @@ -372,24 +374,30 @@ mod sealed { let driver = WebSocketClientDriver::new(stream, cmd_rx); let client = Self { cmd_tx, - _client_type: Default::default(), + _phantom: Default::default(), }; Ok((client, driver)) } } - impl AsyncTungsteniteClient { + impl AsyncTungsteniteClient { fn send_cmd(&self, cmd: DriverCommand) -> Result<(), Error> { self.cmd_tx.send(cmd) } - pub async fn perform(&self, request: R) -> Result + /// Signals to the driver that it must terminate. + pub fn close(self) -> Result<(), Error> { + self.send_cmd(DriverCommand::Terminate) + } + } + + impl AsyncTungsteniteClient { + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, - S: Dialect, { - let wrapper = Wrapper::new_with_dialect(S::default(), request); + let wrapper = Wrapper::new(request); let id = wrapper.id().to_string(); let wrapped_request = wrapper.into_json(); @@ -441,42 +449,47 @@ mod sealed { })??; Ok(()) } - - /// Signals to the driver that it must terminate. - pub fn close(self) -> Result<(), Error> { - self.send_cmd(DriverCommand::Terminate) - } } /// Allows us to erase the type signatures associated with the different /// WebSocket client variants. #[derive(Debug, Clone)] - pub enum WebSocketClient { - Unsecure(AsyncTungsteniteClient), - Secure(AsyncTungsteniteClient), + pub enum WebSocketClient { + Unsecure(AsyncTungsteniteClient), + Secure(AsyncTungsteniteClient), } - impl WebSocketClient { + impl WebSocketClient { pub async fn new_unsecure( url: Url, config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { - let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; + dialect: S, + ) -> Result<(Self, WebSocketClientDriver), Error> { + let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; Ok((Self::Unsecure(client), driver)) } pub async fn new_secure( url: Url, config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { - let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; + dialect: S, + ) -> Result<(Self, WebSocketClientDriver), Error> { + let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; Ok((Self::Secure(client), driver)) } - pub async fn perform(&self, request: R) -> Result + pub fn close(self) -> Result<(), Error> { + match self { + WebSocketClient::Unsecure(c) => c.close(), + WebSocketClient::Secure(c) => c.close(), + } + } + } + + impl WebSocketClient { + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, - S: Dialect, { match self { WebSocketClient::Unsecure(c) => c.perform(request).await, @@ -497,13 +510,6 @@ mod sealed { WebSocketClient::Secure(c) => c.unsubscribe(query).await, } } - - pub fn close(self) -> Result<(), Error> { - match self { - WebSocketClient::Unsecure(c) => c.close(), - WebSocketClient::Secure(c) => c.close(), - } - } } use async_tungstenite::tungstenite; @@ -593,7 +599,7 @@ impl Response for GenericJsonResponse {} /// /// This is the primary component responsible for transport-level interaction /// with the remote WebSocket endpoint. -pub struct WebSocketClientDriver { +pub struct WebSocketClientDriver { // The underlying WebSocket network connection. stream: WebSocketStream, // Facilitates routing of events to their respective subscriptions. @@ -603,18 +609,41 @@ pub struct WebSocketClientDriver { // Commands we've received but have not yet completed, indexed by their ID. // A Terminate command is executed immediately. pending_commands: HashMap, + _dialect: PhantomData, } -impl WebSocketClientDriver { +impl WebSocketClientDriver { fn new(stream: WebSocketStream, cmd_rx: ChannelRx) -> Self { Self { stream, router: SubscriptionRouter::default(), cmd_rx, pending_commands: HashMap::new(), + _dialect: Default::default(), } } + async fn send_msg(&mut self, msg: Message) -> Result<(), Error> { + self.stream.send(msg).await.map_err(|e| { + Error::web_socket("failed to write to WebSocket connection".to_string(), e) + }) + } + + async fn simple_request(&mut self, cmd: SimpleRequestCommand) -> Result<(), Error> { + if let Err(e) = self + .send_msg(Message::Text(cmd.wrapped_request.clone())) + .await + { + cmd.response_tx.send(Err(e.clone()))?; + return Err(e); + } + self.pending_commands + .insert(cmd.id.clone(), DriverCommand::SimpleRequest(cmd)); + Ok(()) + } +} + +impl WebSocketClientDriver { /// Executes the WebSocket driver, which manages the underlying WebSocket /// transport. pub async fn run(mut self) -> Result<(), Error> { @@ -654,16 +683,9 @@ impl WebSocketClientDriver { } } - async fn send_msg(&mut self, msg: Message) -> Result<(), Error> { - self.stream.send(msg).await.map_err(|e| { - Error::web_socket("failed to write to WebSocket connection".to_string(), e) - }) - } - - async fn send_request(&mut self, wrapper: Wrapper) -> Result<(), Error> + async fn send_request(&mut self, wrapper: Wrapper) -> Result<(), Error> where R: Request, - S: Dialect, { self.send_msg(Message::Text( serde_json::to_string_pretty(&wrapper).unwrap(), @@ -671,10 +693,7 @@ impl WebSocketClientDriver { .await } - async fn subscribe(&mut self, cmd: SubscribeCommand) -> Result<(), Error> - where - S: Dialect, - { + async fn subscribe(&mut self, cmd: SubscribeCommand) -> Result<(), Error> { // If we already have an active subscription for the given query, // there's no need to initiate another one. Just add this subscription // to the router. @@ -686,9 +705,8 @@ impl WebSocketClientDriver { } // Otherwise, we need to initiate a subscription request. - let wrapper = Wrapper::new_with_id_and_dialect( + let wrapper = Wrapper::new_with_id( Id::Str(cmd.id.clone()), - S::default(), subscribe::Request::new(cmd.query.clone()), ); if let Err(e) = self.send_request(wrapper).await { @@ -724,19 +742,6 @@ impl WebSocketClientDriver { Ok(()) } - async fn simple_request(&mut self, cmd: SimpleRequestCommand) -> Result<(), Error> { - if let Err(e) = self - .send_msg(Message::Text(cmd.wrapped_request.clone())) - .await - { - cmd.response_tx.send(Err(e.clone()))?; - return Err(e); - } - self.pending_commands - .insert(cmd.id.clone(), DriverCommand::SimpleRequest(cmd)); - Ok(()) - } - async fn handle_incoming_msg(&mut self, msg: Message) -> Result<(), Error> { match msg { Message::Text(s) => self.handle_text_msg(s).await, @@ -746,8 +751,8 @@ impl WebSocketClientDriver { } async fn handle_text_msg(&mut self, msg: String) -> Result<(), Error> { - if let Ok(ev) = Event::from_string(&msg) { - self.publish_event(ev).await; + if let Ok(ev) = DialectEvent::::from_string(&msg) { + self.publish_event(ev.into()).await; return Ok(()); } diff --git a/rpc/src/dialect.rs b/rpc/src/dialect.rs index 38be62973..04bb85ff8 100644 --- a/rpc/src/dialect.rs +++ b/rpc/src/dialect.rs @@ -13,8 +13,10 @@ pub use end_block::EndBlock; use serde::{de::DeserializeOwned, Serialize}; -pub trait Dialect: sealed::Sealed + Default { - type Event: Serialize + DeserializeOwned; +use tendermint::abci; + +pub trait Dialect: sealed::Sealed + Default + Clone + Send + Sync { + type Event: Into + Serialize + DeserializeOwned; } pub type DefaultDialect = crate::v0_37::Dialect; diff --git a/rpc/src/endpoint/abci_info.rs b/rpc/src/endpoint/abci_info.rs index d272bafa8..6d887a80a 100644 --- a/rpc/src/endpoint/abci_info.rs +++ b/rpc/src/endpoint/abci_info.rs @@ -3,19 +3,22 @@ use serde::{Deserialize, Serialize}; use crate::dialect::Dialect; +use crate::request::RequestMessage; /// Request ABCI information from a node #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::AbciInfo } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// ABCI information response diff --git a/rpc/src/endpoint/abci_query.rs b/rpc/src/endpoint/abci_query.rs index 85f061244..6e330ead4 100644 --- a/rpc/src/endpoint/abci_query.rs +++ b/rpc/src/endpoint/abci_query.rs @@ -3,8 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::{abci::Code, block, merkle::proof::ProofOps, serializers}; -use crate::dialect::Dialect; use crate::prelude::*; +use crate::{dialect::Dialect, request::RequestMessage}; /// Query the ABCI application for information #[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] @@ -41,14 +41,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::AbciQuery } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// ABCI query response wrapper diff --git a/rpc/src/endpoint/block.rs b/rpc/src/endpoint/block.rs index 62c8074c7..11ef07a64 100644 --- a/rpc/src/endpoint/block.rs +++ b/rpc/src/endpoint/block.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::block::{self, Block}; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Get information about a specific block #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] @@ -23,14 +23,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Block } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Block responses diff --git a/rpc/src/endpoint/block_by_hash.rs b/rpc/src/endpoint/block_by_hash.rs index 63e1f2fbd..980dfff80 100644 --- a/rpc/src/endpoint/block_by_hash.rs +++ b/rpc/src/endpoint/block_by_hash.rs @@ -6,7 +6,7 @@ use tendermint::{ Hash, }; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Get information about a specific block by its hash #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] @@ -32,14 +32,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::BlockByHash } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Block responses diff --git a/rpc/src/endpoint/block_results.rs b/rpc/src/endpoint/block_results.rs index 1d37a7760..83f65141c 100644 --- a/rpc/src/endpoint/block_results.rs +++ b/rpc/src/endpoint/block_results.rs @@ -6,6 +6,7 @@ use tendermint::{block, consensus, validator}; use crate::dialect::{DeliverTx, Dialect}; use crate::prelude::*; +use crate::request::RequestMessage; use crate::serializers; /// Get ABCI results at a given height. @@ -26,14 +27,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::BlockResults } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// ABCI result response. diff --git a/rpc/src/endpoint/block_search.rs b/rpc/src/endpoint/block_search.rs index 369f9133d..5054de171 100644 --- a/rpc/src/endpoint/block_search.rs +++ b/rpc/src/endpoint/block_search.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; pub use super::{block, block_results}; -use crate::{dialect::Dialect, prelude::*, serializers, Method, Order}; +use crate::{dialect::Dialect, prelude::*, request::RequestMessage, serializers, Method, Order}; /// Request for searching for blocks by their BeginBlock and EndBlock events. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -28,14 +28,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> Method { Method::BlockSearch } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/blockchain.rs b/rpc/src/endpoint/blockchain.rs index bb9006fa1..f605b2a9f 100644 --- a/rpc/src/endpoint/blockchain.rs +++ b/rpc/src/endpoint/blockchain.rs @@ -5,8 +5,8 @@ use core::ops::Range; use serde::{Deserialize, Serialize}; use tendermint::block; -use crate::dialect::Dialect; use crate::prelude::*; +use crate::{dialect::Dialect, request::RequestMessage}; /// Get information about a specific block #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -36,14 +36,16 @@ impl From> for Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Blockchain } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Block responses diff --git a/rpc/src/endpoint/broadcast/tx_async.rs b/rpc/src/endpoint/broadcast/tx_async.rs index 42fd86788..3a1863b56 100644 --- a/rpc/src/endpoint/broadcast/tx_async.rs +++ b/rpc/src/endpoint/broadcast/tx_async.rs @@ -4,7 +4,7 @@ use bytes::Bytes; use serde::{Deserialize, Serialize}; use tendermint::{abci::Code, Hash}; -use crate::{dialect::Dialect, prelude::*, serializers}; +use crate::{dialect::Dialect, prelude::*, request::RequestMessage, serializers}; /// `/broadcast_tx_async`: broadcast a transaction and return immediately. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -21,14 +21,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::BroadcastTxAsync } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Response from either an async or sync transaction broadcast request. diff --git a/rpc/src/endpoint/broadcast/tx_commit.rs b/rpc/src/endpoint/broadcast/tx_commit.rs index c36720d60..0d65aa655 100644 --- a/rpc/src/endpoint/broadcast/tx_commit.rs +++ b/rpc/src/endpoint/broadcast/tx_commit.rs @@ -6,7 +6,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, Hash}; use crate::dialect::{CheckTx, DeliverTx, Dialect}; -use crate::{prelude::*, serializers}; +use crate::{prelude::*, request::RequestMessage, serializers}; /// `/broadcast_tx_commit`: only returns error if `mempool.CheckTx()` errs or /// if we timeout waiting for tx to commit. @@ -27,14 +27,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::BroadcastTxCommit } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Response from `/broadcast_tx_commit`. diff --git a/rpc/src/endpoint/broadcast/tx_sync.rs b/rpc/src/endpoint/broadcast/tx_sync.rs index e827c22af..70c8c8858 100644 --- a/rpc/src/endpoint/broadcast/tx_sync.rs +++ b/rpc/src/endpoint/broadcast/tx_sync.rs @@ -4,7 +4,7 @@ use bytes::Bytes; use serde::{Deserialize, Serialize}; use tendermint::{abci::Code, Hash}; -use crate::{dialect::Dialect, prelude::*, serializers}; +use crate::{dialect::Dialect, prelude::*, request::RequestMessage, serializers}; /// `/broadcast_tx_sync`: returns with the response from `CheckTx`. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -21,14 +21,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::BroadcastTxSync } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Response from either an async or sync transaction broadcast request. diff --git a/rpc/src/endpoint/commit.rs b/rpc/src/endpoint/commit.rs index bfdbb97ee..f5222c887 100644 --- a/rpc/src/endpoint/commit.rs +++ b/rpc/src/endpoint/commit.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, block::signed_header::SignedHeader}; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Get commit information about a specific block #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] @@ -20,14 +20,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Commit } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Commit responses diff --git a/rpc/src/endpoint/consensus_params.rs b/rpc/src/endpoint/consensus_params.rs index 3649137d8..b586362a4 100644 --- a/rpc/src/endpoint/consensus_params.rs +++ b/rpc/src/endpoint/consensus_params.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::block::Height; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Get the consensus parameters. /// @@ -22,14 +22,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::ConsensusParams } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Consensus parameters response. diff --git a/rpc/src/endpoint/consensus_state.rs b/rpc/src/endpoint/consensus_state.rs index f6852e628..11e3cd70e 100644 --- a/rpc/src/endpoint/consensus_state.rs +++ b/rpc/src/endpoint/consensus_state.rs @@ -10,7 +10,7 @@ use tendermint::{ hash, vote, Hash, Time, }; -use crate::{prelude::*, dialect::Dialect, Error, Method}; +use crate::{dialect::Dialect, prelude::*, request::RequestMessage, Error, Method}; // From const NIL_VOTE_STR: &str = "nil-Vote"; @@ -25,14 +25,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> Method { Method::ConsensusState } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// The current consensus state (UNSTABLE). diff --git a/rpc/src/endpoint/evidence.rs b/rpc/src/endpoint/evidence.rs index 4a4649de9..5ce38e26c 100644 --- a/rpc/src/endpoint/evidence.rs +++ b/rpc/src/endpoint/evidence.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{evidence::Evidence, Hash}; -use crate::{dialect::Dialect, Method}; +use crate::{dialect::Dialect, request::RequestMessage, Method}; /// `/broadcast_evidence`: broadcast an evidence. #[derive(Clone, Debug, Deserialize, PartialEq, Eq, Serialize)] @@ -19,14 +19,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> Method { Method::BroadcastEvidence } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Response from either an evidence broadcast request. diff --git a/rpc/src/endpoint/genesis.rs b/rpc/src/endpoint/genesis.rs index c7cdbb8c7..e2c193656 100644 --- a/rpc/src/endpoint/genesis.rs +++ b/rpc/src/endpoint/genesis.rs @@ -5,7 +5,7 @@ use core::{fmt, marker::PhantomData}; use serde::{de::DeserializeOwned, Deserialize, Serialize}; use tendermint::Genesis; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Get the genesis state for the current chain #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -17,16 +17,21 @@ impl Default for Request { } } +impl RequestMessage for Request +where + AppState: Serialize + DeserializeOwned, +{ + fn method(&self) -> crate::Method { + crate::Method::Genesis + } +} + impl crate::Request for Request where AppState: fmt::Debug + Serialize + DeserializeOwned + Send, S: Dialect, { type Response = Response; - - fn method(&self) -> crate::Method { - crate::Method::Genesis - } } impl crate::SimpleRequest for Request diff --git a/rpc/src/endpoint/header.rs b/rpc/src/endpoint/header.rs index a3d047c8f..bc020128d 100644 --- a/rpc/src/endpoint/header.rs +++ b/rpc/src/endpoint/header.rs @@ -3,6 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::block::{self, Header}; +use crate::request::RequestMessage; use crate::v0_37; /// Get information about a specific block @@ -23,14 +24,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Header } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Header response diff --git a/rpc/src/endpoint/header_by_hash.rs b/rpc/src/endpoint/header_by_hash.rs index c92c51131..9a90c327f 100644 --- a/rpc/src/endpoint/header_by_hash.rs +++ b/rpc/src/endpoint/header_by_hash.rs @@ -3,6 +3,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{block::Header, Hash}; +use crate::request::RequestMessage; use crate::v0_37; /// Get information about a specific block by its hash @@ -29,14 +30,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::HeaderByHash } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Header response diff --git a/rpc/src/endpoint/health.rs b/rpc/src/endpoint/health.rs index a72009f44..042574036 100644 --- a/rpc/src/endpoint/health.rs +++ b/rpc/src/endpoint/health.rs @@ -2,20 +2,22 @@ use serde::{Deserialize, Serialize}; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Perform a basic healthceck of the backend #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Health } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Healthcheck responses diff --git a/rpc/src/endpoint/net_info.rs b/rpc/src/endpoint/net_info.rs index f89432e2e..42a770ff0 100644 --- a/rpc/src/endpoint/net_info.rs +++ b/rpc/src/endpoint/net_info.rs @@ -9,21 +9,23 @@ use std::net::IpAddr; use serde::{Deserialize, Serialize}; use tendermint::{channel::Channel, node, serializers, Time}; -use crate::dialect::Dialect; use crate::prelude::*; +use crate::{dialect::Dialect, request::RequestMessage}; /// Request network information from a node #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::NetInfo } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Net info responses diff --git a/rpc/src/endpoint/status.rs b/rpc/src/endpoint/status.rs index 946b8d8c7..66eca8e99 100644 --- a/rpc/src/endpoint/status.rs +++ b/rpc/src/endpoint/status.rs @@ -3,20 +3,22 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, node, validator, AppHash, Hash, Time}; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Node status request #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] pub struct Request; -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Status } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Status responses diff --git a/rpc/src/endpoint/subscribe.rs b/rpc/src/endpoint/subscribe.rs index 12728b0c5..df99dc6d7 100644 --- a/rpc/src/endpoint/subscribe.rs +++ b/rpc/src/endpoint/subscribe.rs @@ -3,7 +3,7 @@ use serde::{Deserialize, Serialize}; use crate::prelude::*; -use crate::dialect::Dialect; +use crate::{dialect::Dialect, request::RequestMessage}; /// Subscription request for events. /// @@ -24,14 +24,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Subscribe } } +impl crate::Request for Request { + type Response = Response; +} + /// Status responses #[derive(Clone, Debug, Deserialize, Serialize)] pub struct Response {} diff --git a/rpc/src/endpoint/tx.rs b/rpc/src/endpoint/tx.rs index f934685bd..0dce25c78 100644 --- a/rpc/src/endpoint/tx.rs +++ b/rpc/src/endpoint/tx.rs @@ -5,7 +5,7 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, tx, Hash}; use crate::dialect::{DeliverTx, Dialect}; -use crate::{prelude::*, serializers, Method}; +use crate::{prelude::*, request::RequestMessage, serializers, Method}; /// Request for finding a transaction by its hash. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -28,14 +28,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> Method { Method::Tx } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/tx_search.rs b/rpc/src/endpoint/tx_search.rs index 854b1b52e..a5556a579 100644 --- a/rpc/src/endpoint/tx_search.rs +++ b/rpc/src/endpoint/tx_search.rs @@ -3,7 +3,7 @@ use serde::{de::DeserializeOwned, Deserialize, Serialize}; pub use super::tx; -use crate::{dialect::Dialect, prelude::*, serializers, Method, Order}; +use crate::{dialect::Dialect, prelude::*, request::RequestMessage, serializers, Method, Order}; /// Request for searching for transactions with their results. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -36,14 +36,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> Method { Method::TxSearch } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/unsubscribe.rs b/rpc/src/endpoint/unsubscribe.rs index 546eb970c..37faf94d1 100644 --- a/rpc/src/endpoint/unsubscribe.rs +++ b/rpc/src/endpoint/unsubscribe.rs @@ -2,8 +2,8 @@ use serde::{Deserialize, Serialize}; -use crate::dialect::Dialect; use crate::prelude::*; +use crate::{dialect::Dialect, request::RequestMessage}; /// Request to unsubscribe from events relating to a given query. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] @@ -18,14 +18,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Unsubscribe } } +impl crate::Request for Request { + type Response = Response; +} + /// Status responses #[derive(Clone, Debug, Deserialize, Serialize)] pub struct Response {} diff --git a/rpc/src/endpoint/validators.rs b/rpc/src/endpoint/validators.rs index 423c8e7c3..363e80638 100644 --- a/rpc/src/endpoint/validators.rs +++ b/rpc/src/endpoint/validators.rs @@ -3,7 +3,9 @@ use serde::{Deserialize, Serialize}; use tendermint::{block, validator}; -use crate::{dialect::Dialect, prelude::*, serializers, PageNumber, PerPage}; +use crate::{ + dialect::Dialect, prelude::*, request::RequestMessage, serializers, PageNumber, PerPage, +}; /// The default number of validators to return per page. pub const DEFAULT_VALIDATORS_PER_PAGE: u8 = 30; @@ -43,14 +45,16 @@ impl Request { } } -impl crate::Request for Request { - type Response = Response; - +impl RequestMessage for Request { fn method(&self) -> crate::Method { crate::Method::Validators } } +impl crate::Request for Request { + type Response = Response; +} + impl crate::SimpleRequest for Request {} /// Validator responses diff --git a/rpc/src/request.rs b/rpc/src/request.rs index d59940930..fe9e70757 100644 --- a/rpc/src/request.rs +++ b/rpc/src/request.rs @@ -5,29 +5,32 @@ use core::fmt::Debug; use serde::{de::DeserializeOwned, Deserialize, Serialize}; use super::{Id, Method, Version}; -use crate::dialect::{DefaultDialect, Dialect}; +use crate::dialect::Dialect; use crate::{prelude::*, Error}; -/// JSON-RPC requests -pub trait Request: DeserializeOwned + Serialize + Sized + Send { - /// Response type for this command - type Response: super::response::Response; - +/// Serialization for JSON-RPC requests +pub trait RequestMessage: DeserializeOwned + Serialize + Sized { /// Request method fn method(&self) -> Method; /// Serialize this request as JSON fn into_json(self) -> String { - Wrapper::new_with_dialect(S::default(), self).into_json() + Wrapper::new(self).into_json() } /// Parse a JSON-RPC request from a JSON string. fn from_string(s: impl AsRef<[u8]>) -> Result { - let wrapper: Wrapper = serde_json::from_slice(s.as_ref()).map_err(Error::serde)?; + let wrapper: Wrapper = serde_json::from_slice(s.as_ref()).map_err(Error::serde)?; Ok(wrapper.params) } } +/// JSON-RPC requests +pub trait Request: RequestMessage + Send { + /// Response type for this command + type Response: super::response::Response; +} + /// Simple JSON-RPC requests which correlate with a single response from the /// remote endpoint. /// @@ -40,7 +43,7 @@ pub trait SimpleRequest: Request {} /// JSON-RPC request wrapper (i.e. message envelope) #[derive(Debug, Deserialize, Serialize)] -pub struct Wrapper { +pub struct Wrapper { /// JSON-RPC version jsonrpc: Version, @@ -52,16 +55,11 @@ pub struct Wrapper { /// Request parameters (i.e. request object) params: R, - - /// Dialect tag - #[serde(skip)] - #[allow(dead_code)] - dialect: S, } -impl Wrapper +impl Wrapper where - R: Request, + R: RequestMessage, { /// Create a new request wrapper from the given request. /// @@ -78,32 +76,6 @@ where id, method: request.method(), params: request, - dialect: Default::default(), - } - } -} - -impl Wrapper -where - R: Request, - S: Dialect, -{ - /// Create a new request wrapper from the given request. - /// - /// The ID of the request is set to a random [UUIDv4] value. - /// - /// [UUIDv4]: https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_4_(random) - pub fn new_with_dialect(dialect: S, request: R) -> Self { - Self::new_with_id_and_dialect(Id::uuid_v4(), dialect, request) - } - - pub(crate) fn new_with_id_and_dialect(id: Id, dialect: S, request: R) -> Self { - Self { - jsonrpc: Version::current(), - id, - method: request.method(), - params: request, - dialect, } } diff --git a/rpc/src/v0_34/dialect.rs b/rpc/src/v0_34/dialect.rs index 2af6661d7..fba1e433e 100644 --- a/rpc/src/v0_34/dialect.rs +++ b/rpc/src/v0_34/dialect.rs @@ -4,7 +4,7 @@ use crate::prelude::*; use crate::serializers::bytes::base64string; use serde::{Deserialize, Serialize}; -#[derive(Default)] +#[derive(Default, Clone)] pub struct Dialect; impl crate::dialect::Dialect for Dialect { diff --git a/rpc/src/v0_37/dialect.rs b/rpc/src/v0_37/dialect.rs index f052ede7f..2bd90615f 100644 --- a/rpc/src/v0_37/dialect.rs +++ b/rpc/src/v0_37/dialect.rs @@ -3,7 +3,7 @@ use tendermint::abci; use crate::prelude::*; use serde::{Deserialize, Serialize}; -#[derive(Default)] +#[derive(Default, Clone)] pub struct Dialect; impl crate::dialect::Dialect for Dialect { From 6beba5fca88eb00fc903035e088d75eba1be2671 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 1 Feb 2023 20:21:06 +0200 Subject: [PATCH 42/77] rpc: fix the fixture tests Have to make DialectEvent and friends public for these "integration" tests. --- rpc/src/event.rs | 9 ++++---- rpc/tests/gaia_fixtures.rs | 12 +++++------ rpc/tests/kvstore_fixtures.rs | 40 +++++++++++++++++------------------ 3 files changed, 30 insertions(+), 31 deletions(-) diff --git a/rpc/src/event.rs b/rpc/src/event.rs index a1481bfe4..e3085a0b2 100644 --- a/rpc/src/event.rs +++ b/rpc/src/event.rs @@ -22,7 +22,7 @@ pub struct Event { // Serialization helper supporting differences in RPC versions. #[derive(Serialize, Deserialize, Debug)] -pub(crate) struct DialectEvent { +pub struct DialectEvent { /// The query that produced the event. pub query: String, /// The data associated with the event. @@ -34,6 +34,7 @@ pub(crate) struct DialectEvent { impl Response for DialectEvent where Ev: Serialize + DeserializeOwned {} /// A JSON-RPC-wrapped event. +#[allow(dead_code)] pub(crate) type WrappedEvent = Wrapper>; impl Event { @@ -80,7 +81,7 @@ pub enum EventData { #[derive(Serialize, Deserialize, Debug)] #[serde(tag = "type", content = "value")] #[allow(clippy::large_enum_variant)] -pub(crate) enum DialectEventData { +pub enum DialectEventData { #[serde(alias = "tendermint/event/NewBlock")] NewBlock { block: Option, @@ -128,7 +129,7 @@ pub struct TxInfo { } #[derive(Serialize, Deserialize, Debug)] -pub(crate) struct DialectTxInfo { +pub struct DialectTxInfo { #[serde(with = "serializers::from_str")] pub height: i64, pub index: Option, @@ -161,7 +162,7 @@ pub struct TxResult { } #[derive(Serialize, Deserialize, Debug)] -pub(crate) struct DialectTxResult { +pub struct DialectTxResult { pub log: Option, pub gas_wanted: Option, pub gas_used: Option, diff --git a/rpc/tests/gaia_fixtures.rs b/rpc/tests/gaia_fixtures.rs index 548eb58a1..80c8d0921 100644 --- a/rpc/tests/gaia_fixtures.rs +++ b/rpc/tests/gaia_fixtures.rs @@ -1,8 +1,8 @@ use std::{fs, path::PathBuf}; // TODO: generate fixtures and test with v0_37::dialect as well -use tendermint_rpc::v0_34::dialect::{Dialect as RpcDialect, Event as RpcEvent}; -use tendermint_rpc::{endpoint, event::Event, Request, Response}; +use tendermint_rpc::v0_34::dialect::Event as RpcEvent; +use tendermint_rpc::{endpoint, event::DialectEvent, request::RequestMessage, Response}; use walkdir::WalkDir; @@ -90,7 +90,7 @@ fn incoming_fixtures() { }, _ => { if file_name.starts_with("subscribe_newblock_") { - let r = Event::::from_string(content); + let r = DialectEvent::::from_string(content); assert!(r.is_ok(), "failed to parse event {file_name}: {r:?}"); } else { panic!("unhandled incoming fixture: {file_name}"); @@ -129,13 +129,11 @@ fn outgoing_fixtures() { assert!(endpoint::block::Request::from_string(content).is_ok()) }, "block_results_at_height_10" => { - let r = - >::from_string(content); + let r = endpoint::block_results::Request::from_string(content); assert!(r.is_ok(), "block_results_at_height_10: {r:?}"); }, "block_results_at_height_4555980" => { - let r = - >::from_string(content); + let r = endpoint::block_results::Request::from_string(content); assert!(r.is_ok(), "block_results_at_height_4555980: {r:?}"); }, "blockchain_from_1_to_10" => { diff --git a/rpc/tests/kvstore_fixtures.rs b/rpc/tests/kvstore_fixtures.rs index c6aa27a37..84e9e17db 100644 --- a/rpc/tests/kvstore_fixtures.rs +++ b/rpc/tests/kvstore_fixtures.rs @@ -835,12 +835,12 @@ fn incoming_fixtures() { }, "subscribe_newblock_0" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, result_end_block, - } = result.data + } = result.data.into() { let b = block.unwrap(); assert!(b.data.get(0).is_none()); @@ -891,12 +891,12 @@ fn incoming_fixtures() { }, "subscribe_newblock_1" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, result_end_block, - } = result.data + } = result.data.into() { let b = block.unwrap(); assert!(b.data.get(0).is_none()); @@ -969,12 +969,12 @@ fn incoming_fixtures() { }, "subscribe_newblock_2" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, result_end_block, - } = result.data + } = result.data.into() { let b = block.unwrap(); assert!(b.data.get(0).is_none()); @@ -1025,12 +1025,12 @@ fn incoming_fixtures() { }, "subscribe_newblock_3" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, result_end_block, - } = result.data + } = result.data.into() { let b = block.unwrap(); assert!(b.data.get(0).is_none()); @@ -1081,12 +1081,12 @@ fn incoming_fixtures() { }, "subscribe_newblock_4" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); if let tendermint_rpc::event::EventData::NewBlock { block, result_begin_block, result_end_block, - } = result.data + } = result.data.into() { let b = block.unwrap(); assert!(b.data.get(0).is_none()); @@ -1140,9 +1140,9 @@ fn incoming_fixtures() { }, "subscribe_txs_0" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { height = tx_result.height; assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); @@ -1173,9 +1173,9 @@ fn incoming_fixtures() { }, "subscribe_txs_1" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { height = tx_result.height; assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); @@ -1207,9 +1207,9 @@ fn incoming_fixtures() { }, "subscribe_txs_2" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { height = tx_result.height; assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); @@ -1240,9 +1240,9 @@ fn incoming_fixtures() { }, "subscribe_txs_3" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { height = tx_result.height; assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); @@ -1273,9 +1273,9 @@ fn incoming_fixtures() { }, "subscribe_txs_4" => { let result = - tendermint_rpc::event::Event::::from_string(content).unwrap(); + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data { + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { height = tx_result.height; assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); From d708fd0134835c92c99ebc5cd56c91267a51df52 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 1 Feb 2023 21:09:38 +0200 Subject: [PATCH 43/77] rpc: fix websocket tests --- rpc/src/client/bin/main.rs | 9 +++- rpc/src/client/transport/websocket.rs | 63 +++++++++++++++++++++----- rpc/src/dialect/begin_block.rs | 11 +++++ rpc/src/dialect/end_block.rs | 13 ++++++ rpc/src/event.rs | 64 +++++++++++++++++++++++++++ rpc/src/lib.rs | 2 +- rpc/src/v0_34/dialect.rs | 19 ++++++++ rpc/src/v0_37/dialect.rs | 19 ++++++++ 8 files changed, 187 insertions(+), 13 deletions(-) diff --git a/rpc/src/client/bin/main.rs b/rpc/src/client/bin/main.rs index 46816f25a..506d70fb0 100644 --- a/rpc/src/client/bin/main.rs +++ b/rpc/src/client/bin/main.rs @@ -6,8 +6,11 @@ use futures::StreamExt; use structopt::StructOpt; use tendermint::Hash; use tendermint_rpc::{ - query::Query, Client, Error, HttpClient, Order, Paging, Scheme, Subscription, - SubscriptionClient, Url, WebSocketClient, + dialect::{DefaultDialect, Dialect}, + event::DialectEvent, + query::Query, + Client, Error, HttpClient, Order, Paging, Scheme, Subscription, SubscriptionClient, Url, + WebSocketClient, }; use tokio::time::Duration; use tracing::{error, info, level_filters::LevelFilter, warn}; @@ -467,6 +470,7 @@ async fn recv_events_with_timeout( } }; let event = result?; + let event: DialectEvent<::Event> = event.into(); println!("{}", serde_json::to_string_pretty(&event).map_err(Error::serde)?); event_count += 1; if let Some(me) = max_events { @@ -488,6 +492,7 @@ async fn recv_events(mut subs: Subscription, max_events: Option) -> Result< let mut event_count = 0u64; while let Some(result) = subs.next().await { let event = result?; + let event: DialectEvent<::Event> = event.into(); println!( "{}", serde_json::to_string_pretty(&event).map_err(Error::serde)? diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index bd9711435..fd21db12a 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -30,7 +30,7 @@ use crate::{ sync::{ChannelRx, ChannelTx}, transport::router::{PublishResult, SubscriptionRouter}, }, - dialect::Dialect, + dialect::{DefaultDialect, Dialect}, endpoint::{subscribe, unsubscribe}, error::Error, event::{DialectEvent, Event}, @@ -141,12 +141,13 @@ pub struct WebSocketClient { inner: sealed::WebSocketClient, } -impl WebSocketClient { +impl WebSocketClient { /// Construct a new WebSocket-based client connecting to the given /// Tendermint node's RPC endpoint. + /// The RPC protocol version is the one supported by this crate by default. /// /// Supports both `ws://` and `wss://` protocols. - pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> + pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, { @@ -155,22 +156,61 @@ impl WebSocketClient { /// Construct a new WebSocket-based client connecting to the given /// Tendermint node's RPC endpoint. + /// The RPC protocol version is the one supported by this crate by default. /// /// Supports both `ws://` and `wss://` protocols. pub async fn new_with_config( url: U, config: Option, + ) -> Result<(Self, WebSocketClientDriver), Error> + where + U: TryInto, + { + let url = url.try_into()?; + + let (inner, driver) = if url.0.is_secure() { + sealed::WebSocketClient::new_secure(url.0, config).await? + } else { + sealed::WebSocketClient::new_unsecure(url.0, config).await? + }; + + Ok((Self { inner }, driver)) + } +} + +impl WebSocketClient { + /// Construct a new WebSocket-based client connecting to the given + /// Tendermint node's RPC endpoint. + /// + /// Supports both `ws://` and `wss://` protocols. + pub async fn new_with_dialect( + url: U, + dialect: S, + ) -> Result<(Self, WebSocketClientDriver), Error> + where + U: TryInto, + { + Self::new_with_config_and_dialect(url, None, dialect).await + } + + /// Construct a new WebSocket-based client connecting to the given + /// Tendermint node's RPC endpoint. + /// + /// Supports both `ws://` and `wss://` protocols. + pub async fn new_with_config_and_dialect( + url: U, + config: Option, + _dialect: S, ) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, { let url = url.try_into()?; - let dialect = S::default(); let (inner, driver) = if url.0.is_secure() { - sealed::WebSocketClient::new_secure(url.0, config, dialect).await? + sealed::WebSocketClient::new_secure(url.0, config).await? } else { - sealed::WebSocketClient::new_unsecure(url.0, config, dialect).await? + sealed::WebSocketClient::new_unsecure(url.0, config).await? }; Ok((Self { inner }, driver)) @@ -463,7 +503,6 @@ mod sealed { pub async fn new_unsecure( url: Url, config: Option, - dialect: S, ) -> Result<(Self, WebSocketClientDriver), Error> { let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; Ok((Self::Unsecure(client), driver)) @@ -472,7 +511,6 @@ mod sealed { pub async fn new_secure( url: Url, config: Option, - dialect: S, ) -> Result<(Self, WebSocketClientDriver), Error> { let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; Ok((Self::Secure(client), driver)) @@ -889,6 +927,8 @@ mod test { use super::*; use crate::{client::sync::unbounded, query::EventType, request, Id, Method}; + // TODO: test with v0_37::dialect as well + use crate::v0_34::dialect::{Dialect, Event as RpcEvent}; // Interface to a driver that manages all incoming WebSocket connections. struct TestServer { @@ -1069,6 +1109,7 @@ mod test { Some(id) => id.clone(), None => return, }; + let ev: DialectEvent = ev.into(); self.send(Id::Str(subs_id), ev).await; } @@ -1177,7 +1218,9 @@ mod test { } async fn read_event(name: &str) -> Event { - Event::from_string(read_json_fixture(name).await).unwrap() + DialectEvent::::from_string(read_json_fixture(name).await) + .unwrap() + .into() } #[tokio::test] @@ -1190,7 +1233,7 @@ mod test { println!("Starting WebSocket server..."); let mut server = TestServer::new("127.0.0.1:0").await; println!("Creating client RPC WebSocket connection..."); - let (client, driver) = WebSocketClient::new(server.node_addr.clone()) + let (client, driver) = WebSocketClient::new_with_dialect(server.node_addr.clone(), Dialect) .await .unwrap(); let driver_handle = tokio::spawn(async move { driver.run().await }); diff --git a/rpc/src/dialect/begin_block.rs b/rpc/src/dialect/begin_block.rs index 6e2a6c437..2cb36bf6a 100644 --- a/rpc/src/dialect/begin_block.rs +++ b/rpc/src/dialect/begin_block.rs @@ -29,3 +29,14 @@ where } } } + +impl From for BeginBlock +where + abci::Event: Into, +{ + fn from(msg: abci::response::BeginBlock) -> Self { + Self { + events: msg.events.into_iter().map(Into::into).collect(), + } + } +} diff --git a/rpc/src/dialect/end_block.rs b/rpc/src/dialect/end_block.rs index 455d2f977..98c2d6eea 100644 --- a/rpc/src/dialect/end_block.rs +++ b/rpc/src/dialect/end_block.rs @@ -41,3 +41,16 @@ where } } } + +impl From for EndBlock +where + abci::Event: Into, +{ + fn from(msg: abci::response::EndBlock) -> Self { + Self { + events: msg.events.into_iter().map(Into::into).collect(), + validator_updates: msg.validator_updates, + consensus_param_updates: msg.consensus_param_updates, + } + } +} diff --git a/rpc/src/event.rs b/rpc/src/event.rs index e3085a0b2..6133c8845 100644 --- a/rpc/src/event.rs +++ b/rpc/src/event.rs @@ -63,6 +63,19 @@ where } } +impl From for DialectEvent +where + abci::Event: Into, +{ + fn from(msg: Event) -> Self { + DialectEvent { + query: msg.query, + data: msg.data.into(), + events: msg.events, + } + } +} + #[derive(Debug, Clone, PartialEq, Eq)] // To be fixed in 0.24 #[allow(clippy::large_enum_variant)] @@ -119,6 +132,29 @@ where } } +impl From for DialectEventData +where + abci::Event: Into, +{ + fn from(msg: EventData) -> Self { + match msg { + EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } => DialectEventData::NewBlock { + block, + result_begin_block: result_begin_block.map(Into::into), + result_end_block: result_end_block.map(Into::into), + }, + EventData::Tx { tx_result } => DialectEventData::Tx { + tx_result: tx_result.into(), + }, + EventData::GenericJsonEvent(v) => DialectEventData::GenericJsonEvent(v), + } + } +} + /// Transaction result info. #[derive(Debug, Clone, PartialEq, Eq)] pub struct TxInfo { @@ -152,6 +188,20 @@ where } } +impl From for DialectTxInfo +where + abci::Event: Into, +{ + fn from(msg: TxInfo) -> Self { + DialectTxInfo { + height: msg.height, + index: msg.index, + tx: msg.tx, + result: msg.result.into(), + } + } +} + /// Transaction result. #[derive(Debug, Clone, PartialEq, Eq)] pub struct TxResult { @@ -182,3 +232,17 @@ where } } } + +impl From for DialectTxResult +where + abci::Event: Into, +{ + fn from(msg: TxResult) -> Self { + DialectTxResult { + log: msg.log, + gas_wanted: msg.gas_wanted, + gas_used: msg.gas_used, + events: msg.events.into_iter().map(Into::into).collect(), + } + } +} diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index 0251d9db4..dddd53264 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -43,7 +43,7 @@ pub use client::{ #[cfg(feature = "websocket-client")] pub use client::{WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig}; -mod dialect; +pub mod dialect; pub mod endpoint; pub mod error; pub mod event; diff --git a/rpc/src/v0_34/dialect.rs b/rpc/src/v0_34/dialect.rs index fba1e433e..6e972b1d7 100644 --- a/rpc/src/v0_34/dialect.rs +++ b/rpc/src/v0_34/dialect.rs @@ -27,6 +27,15 @@ impl From for abci::Event { } } +impl From for Event { + fn from(msg: abci::Event) -> Self { + Self { + kind: msg.kind, + attributes: msg.attributes.into_iter().map(Into::into).collect(), + } + } +} + #[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] pub struct EventAttribute { /// The event key. @@ -56,3 +65,13 @@ impl From for abci::EventAttribute { } } } + +impl From for EventAttribute { + fn from(msg: abci::EventAttribute) -> Self { + Self { + key: msg.key, + value: msg.value, + index: msg.index, + } + } +} diff --git a/rpc/src/v0_37/dialect.rs b/rpc/src/v0_37/dialect.rs index 2bd90615f..28cc49947 100644 --- a/rpc/src/v0_37/dialect.rs +++ b/rpc/src/v0_37/dialect.rs @@ -26,6 +26,15 @@ impl From for abci::Event { } } +impl From for Event { + fn from(msg: abci::Event) -> Self { + Self { + kind: msg.kind, + attributes: msg.attributes.into_iter().map(Into::into).collect(), + } + } +} + #[derive(Clone, PartialEq, Eq, Debug, Serialize, Deserialize)] pub struct EventAttribute { /// The event key. @@ -47,3 +56,13 @@ impl From for abci::EventAttribute { } } } + +impl From for EventAttribute { + fn from(msg: abci::EventAttribute) -> Self { + Self { + key: msg.key, + value: msg.value, + index: msg.index, + } + } +} From 580b36717797cf1e54f680e7d0e52e6bf59265cc Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 2 Feb 2023 14:02:11 +0200 Subject: [PATCH 44/77] tendermint: Fix test_sign_bytes_compatibility Badly merged code broke the test. --- tendermint/src/vote/sign_vote.rs | 27 ++++++++++----------------- 1 file changed, 10 insertions(+), 17 deletions(-) diff --git a/tendermint/src/vote/sign_vote.rs b/tendermint/src/vote/sign_vote.rs index 8e243dd43..e4707150c 100644 --- a/tendermint/src/vote/sign_vote.rs +++ b/tendermint/src/vote/sign_vote.rs @@ -281,6 +281,16 @@ mod tests { #[test] fn test_sign_bytes_compatibility() { + let cv = CanonicalVote::new(Vote::default(), ChainId::try_from("A").unwrap()); + let mut got = vec![]; + // SignBytes are encoded using MarshalBinary and not MarshalBinaryBare + Protobuf::::encode_length_delimited(&cv, &mut got).unwrap(); + let want = vec![ + 0x10, 0x8, 0x1, 0x11, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2a, 0x0, 0x32, 0x1, + 0x41, + ]; // Todo: Get these bytes from Go. During protobuf upgrade we didn't get to generate them. + assert_eq!(got, want); + // with proper (fixed size) height and round (Precommit): { let vt_precommit = Vote { @@ -292,23 +302,6 @@ mod tests { println!("{vt_precommit:?}"); let cv_precommit = CanonicalVote::new(vt_precommit, ChainId::try_from("A").unwrap()); let got = Protobuf::::encode_vec(&cv_precommit).unwrap(); - let want = vec![ - 0x10, 0x8, 0x1, 0x11, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2a, 0x0, 0x32, 0x1, - 0x41, - ]; // Todo: Get these bytes from Go. During protobuf upgrade we didn't get to generate them. - assert_eq!(got, want); - } - // with proper (fixed size) height and round (Precommit): - { - let vt_precommit = Vote { - height: Height::from(1_u32), - round: Round::from(1_u16), - vote_type: Type::Precommit, - ..Default::default() - }; - println!("{:?}", vt_precommit); - let cv_precommit = CanonicalVote::new(vt_precommit, ChainId::try_from("A").unwrap()); - let got = Protobuf::::encode_vec(&cv_precommit).unwrap(); let want = vec![ 0x8, // (field_number << 3) | wire_type 0x2, // PrecommitType From 0305ba8a2bf31d47e370779a4434d5055e479f3f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 2 Feb 2023 20:37:16 +0200 Subject: [PATCH 45/77] Versioned type aliases for WebSocketClient Also for WebSocketClientDriver. The specializations for v0_37 are also re-exported under crate root, providing some backward compatibility. --- rpc/src/lib.rs | 4 +++- rpc/src/v0_34.rs | 6 ++++++ rpc/src/v0_37.rs | 6 ++++++ 3 files changed, 15 insertions(+), 1 deletion(-) diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index dddd53264..db56680d7 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -41,7 +41,7 @@ pub use client::{ MockClient, MockRequestMatcher, MockRequestMethodMatcher, Subscription, SubscriptionClient, }; #[cfg(feature = "websocket-client")] -pub use client::{WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig}; +pub use client::{WebSocketClientUrl, WebSocketConfig}; pub mod dialect; pub mod endpoint; @@ -65,6 +65,8 @@ pub mod v0_37; #[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use v0_37::Client; +#[cfg(feature = "websocket-client")] +pub use v0_37::{WebSocketClient, WebSocketClientDriver}; pub use error::Error; pub use id::Id; diff --git a/rpc/src/v0_34.rs b/rpc/src/v0_34.rs index d336a1328..bab85f704 100644 --- a/rpc/src/v0_34.rs +++ b/rpc/src/v0_34.rs @@ -5,3 +5,9 @@ pub use client::Client; pub mod dialect; pub use dialect::Dialect; + +#[cfg(feature = "websocket-client")] +pub type WebSocketClient = crate::client::WebSocketClient; + +#[cfg(feature = "websocket-client")] +pub type WebSocketClientDriver = crate::client::WebSocketClientDriver; diff --git a/rpc/src/v0_37.rs b/rpc/src/v0_37.rs index d336a1328..bab85f704 100644 --- a/rpc/src/v0_37.rs +++ b/rpc/src/v0_37.rs @@ -5,3 +5,9 @@ pub use client::Client; pub mod dialect; pub use dialect::Dialect; + +#[cfg(feature = "websocket-client")] +pub type WebSocketClient = crate::client::WebSocketClient; + +#[cfg(feature = "websocket-client")] +pub type WebSocketClientDriver = crate::client::WebSocketClientDriver; From 75c212f8b1fe429066e37f6b05fa8125602cdbf3 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 2 Feb 2023 20:37:31 +0200 Subject: [PATCH 46/77] Fix tools build --- tools/kvstore-test/tests/tendermint.rs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/tools/kvstore-test/tests/tendermint.rs b/tools/kvstore-test/tests/tendermint.rs index 8a78ec458..4a13a27e0 100644 --- a/tools/kvstore-test/tests/tendermint.rs +++ b/tools/kvstore-test/tests/tendermint.rs @@ -30,7 +30,6 @@ mod rpc { merkle::simple_hash_from_byte_vectors, }; use tendermint_rpc::{ - endpoint::tx::Response as ResultTx, event::{Event, EventData, TxInfo}, query::{EventType, Query}, Client, HttpClient, Id, Order, SubscriptionClient, WebSocketClient, WebSocketClientDriver, @@ -462,7 +461,7 @@ mod rpc { .txs .iter() .filter(|tx| tx.height.value() == (tx_info.height as u64)) - .collect::>(); + .collect::>(); assert_eq!(1, txs.len()); assert_eq!(tx_info.tx, txs[0].tx); From 546170ee89e080ecc3811764ca1d7be2914e3b53 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 2 Feb 2023 20:42:11 +0200 Subject: [PATCH 47/77] Remove dialect parameter for SubscriptionClient The trait does not need it and the Subscription public API is erased. Only WebSocketClient needs the dialect parameter. --- rpc/src/client/subscription.rs | 3 +-- rpc/src/client/transport/websocket.rs | 2 +- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/rpc/src/client/subscription.rs b/rpc/src/client/subscription.rs index 105717e63..d530adf4a 100644 --- a/rpc/src/client/subscription.rs +++ b/rpc/src/client/subscription.rs @@ -11,7 +11,6 @@ use pin_project::pin_project; use crate::{ client::sync::{ChannelRx, ChannelTx}, - dialect::DefaultDialect, event::Event, prelude::*, query::Query, @@ -21,7 +20,7 @@ use crate::{ /// A client that exclusively provides [`Event`] subscription capabilities, /// without any other RPC method support. #[async_trait] -pub trait SubscriptionClient { +pub trait SubscriptionClient { /// `/subscribe`: subscribe to receive events produced by the given query. async fn subscribe(&self, query: Query) -> Result; diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index fd21db12a..3686e46b8 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -238,7 +238,7 @@ impl v0_37::Client for WebSocketClient { } #[async_trait] -impl SubscriptionClient for WebSocketClient { +impl SubscriptionClient for WebSocketClient { async fn subscribe(&self, query: Query) -> Result { self.inner.subscribe(query).await } From 52197f0b41f65b4dbfbb9f2b753de7f2281dc12a Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Fri, 3 Feb 2023 13:45:45 +0200 Subject: [PATCH 48/77] Derive PartialEq, Eq on ProdCommitValidator Also add test code that ensures ProdVerifier supports the common derived traits. --- light-client-verifier/src/operations/commit_validator.rs | 2 +- light-client-verifier/src/verifier.rs | 6 ++++++ 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/light-client-verifier/src/operations/commit_validator.rs b/light-client-verifier/src/operations/commit_validator.rs index 315cd60d6..24908b74f 100644 --- a/light-client-verifier/src/operations/commit_validator.rs +++ b/light-client-verifier/src/operations/commit_validator.rs @@ -65,7 +65,7 @@ pub trait CommitValidator: Send + Sync { } /// Production-ready implementation of a commit validator. -#[derive(Copy, Clone, Default, Debug)] +#[derive(Copy, Clone, Default, Debug, PartialEq, Eq)] pub struct ProdCommitValidator; impl CommitValidator for ProdCommitValidator {} diff --git a/light-client-verifier/src/verifier.rs b/light-client-verifier/src/verifier.rs index 6bddabe7f..748821060 100644 --- a/light-client-verifier/src/verifier.rs +++ b/light-client-verifier/src/verifier.rs @@ -285,6 +285,12 @@ mod tests { Verdict, Verifier, }; + #[cfg(feature = "rust-crypto")] + #[derive(Clone, Debug, PartialEq, Eq)] + struct ProdVerifierSupportsCommonDerivedTraits { + verifier: ProdVerifier, + } + #[test] fn test_verification_failure_on_chain_id_mismatch() { let now = Time::now(); From 1610120938b4894cd5f1f67dd7f3decd0d7a94a3 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 6 Feb 2023 18:05:58 +0200 Subject: [PATCH 49/77] tendermint: restore Serialize impl on Event Also on ABCI domain types containing Event instances. This is needed for CLI. --- tendermint/src/abci/event.rs | 6 ++++-- tendermint/src/abci/response/check_tx.rs | 3 ++- tendermint/src/abci/response/deliver_tx.rs | 3 ++- 3 files changed, 8 insertions(+), 4 deletions(-) diff --git a/tendermint/src/abci/event.rs b/tendermint/src/abci/event.rs index 099675110..04c4baa65 100644 --- a/tendermint/src/abci/event.rs +++ b/tendermint/src/abci/event.rs @@ -1,3 +1,5 @@ +use serde::Serialize; + use crate::prelude::*; /// An event that occurred while processing a request. @@ -10,7 +12,7 @@ use crate::prelude::*; /// be queried using these events. /// /// [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#events) -#[derive(Clone, PartialEq, Eq, Debug)] +#[derive(Clone, PartialEq, Eq, Debug, Serialize)] pub struct Event { /// The kind of event. /// @@ -59,7 +61,7 @@ impl Event { /// [`Event::new`] for details. /// /// [ABCI documentation](https://docs.tendermint.com/master/spec/abci/abci.html#events) -#[derive(Clone, PartialEq, Eq, Debug)] +#[derive(Clone, PartialEq, Eq, Debug, Serialize)] pub struct EventAttribute { /// The event key. pub key: String, diff --git a/tendermint/src/abci/response/check_tx.rs b/tendermint/src/abci/response/check_tx.rs index ba9245ee8..5d41109da 100644 --- a/tendermint/src/abci/response/check_tx.rs +++ b/tendermint/src/abci/response/check_tx.rs @@ -1,10 +1,11 @@ use bytes::Bytes; +use serde::Serialize; use super::super::{Code, Event}; use crate::prelude::*; #[doc = include_str!("../doc/response-checktx.md")] -#[derive(Clone, PartialEq, Eq, Debug, Default)] +#[derive(Clone, PartialEq, Eq, Debug, Default, Serialize)] pub struct CheckTx { /// The response code. /// diff --git a/tendermint/src/abci/response/deliver_tx.rs b/tendermint/src/abci/response/deliver_tx.rs index b8c6ff8f3..f98f77624 100644 --- a/tendermint/src/abci/response/deliver_tx.rs +++ b/tendermint/src/abci/response/deliver_tx.rs @@ -1,10 +1,11 @@ use bytes::Bytes; +use serde::Serialize; use super::super::{Code, Event}; use crate::prelude::*; #[doc = include_str!("../doc/response-delivertx.md")] -#[derive(Clone, PartialEq, Eq, Debug, Default)] +#[derive(Clone, PartialEq, Eq, Debug, Default, Serialize)] pub struct DeliverTx { /// The response code. /// From 2d864bbbd2563760e184cf30190daddf4190b56f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 6 Feb 2023 18:11:49 +0200 Subject: [PATCH 50/77] rpc: de-genericized result types Add associated type Output to SimpleRequest to designate the output type produced from the response. Implement so that the output type is a generics-free Response, while the Result type for the Request trait is a DialectResponse where it needs to be. --- rpc/src/client/transport/http.rs | 10 ++-- rpc/src/client/transport/mock.rs | 11 +++-- rpc/src/client/transport/websocket.rs | 10 ++-- rpc/src/dialect/begin_block.rs | 4 +- rpc/src/dialect/check_tx.rs | 23 ++++++++- rpc/src/dialect/deliver_tx.rs | 20 +++++++- rpc/src/dialect/end_block.rs | 8 ++-- rpc/src/endpoint/abci_info.rs | 4 +- rpc/src/endpoint/abci_query.rs | 4 +- rpc/src/endpoint/block.rs | 4 +- rpc/src/endpoint/block_by_hash.rs | 4 +- rpc/src/endpoint/block_results.rs | 62 +++++++++++++++++++++---- rpc/src/endpoint/block_search.rs | 4 +- rpc/src/endpoint/blockchain.rs | 4 +- rpc/src/endpoint/broadcast/tx_async.rs | 4 +- rpc/src/endpoint/broadcast/tx_commit.rs | 51 ++++++++++++++++---- rpc/src/endpoint/broadcast/tx_sync.rs | 4 +- rpc/src/endpoint/commit.rs | 4 +- rpc/src/endpoint/consensus_params.rs | 4 +- rpc/src/endpoint/consensus_state.rs | 4 +- rpc/src/endpoint/evidence.rs | 4 +- rpc/src/endpoint/genesis.rs | 1 + rpc/src/endpoint/header.rs | 4 +- rpc/src/endpoint/header_by_hash.rs | 4 +- rpc/src/endpoint/health.rs | 4 +- rpc/src/endpoint/net_info.rs | 4 +- rpc/src/endpoint/status.rs | 4 +- rpc/src/endpoint/tx.rs | 46 +++++++++++++++--- rpc/src/endpoint/tx_search.rs | 35 +++++++++++--- rpc/src/endpoint/validators.rs | 4 +- rpc/src/request.rs | 5 +- rpc/src/v0_34/client.rs | 17 +++---- rpc/src/v0_37/client.rs | 17 +++---- rpc/tests/gaia_fixtures.rs | 4 +- rpc/tests/kvstore_fixtures.rs | 32 +++++++++---- 35 files changed, 326 insertions(+), 102 deletions(-) diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index 65c409846..32149186e 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -85,7 +85,7 @@ impl HttpClient { #[async_trait] impl v0_34::Client for HttpClient { - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where R: SimpleRequest, { @@ -95,7 +95,7 @@ impl v0_34::Client for HttpClient { #[async_trait] impl v0_37::Client for HttpClient { - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where R: SimpleRequest, { @@ -200,7 +200,7 @@ mod sealed { where C: Connect + Clone + Send + Sync + 'static, { - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, S: Dialect, @@ -209,7 +209,7 @@ mod sealed { let response = self.inner.request(request).await.map_err(Error::hyper)?; let response_body = response_to_string(response).await?; tracing::debug!("Incoming response: {}", response_body); - R::Response::from_string(&response_body) + R::Response::from_string(&response_body).map(Into::into) } } @@ -296,7 +296,7 @@ mod sealed { ))) } - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, S: Dialect, diff --git a/rpc/src/client/transport/mock.rs b/rpc/src/client/transport/mock.rs index 1139e275c..69eb3e728 100644 --- a/rpc/src/client/transport/mock.rs +++ b/rpc/src/client/transport/mock.rs @@ -14,6 +14,7 @@ use crate::{ event::Event, prelude::*, query::Query, + request::SimpleRequest, utils::uuid_str, Error, Method, Request, Response, Subscription, SubscriptionClient, }; @@ -62,25 +63,27 @@ pub struct MockClient { #[async_trait] impl v0_34::Client for MockClient { - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where - R: Request, + R: SimpleRequest, { self.matcher .response_for(request) .ok_or_else(Error::mismatch_response)? + .map(Into::into) } } #[async_trait] impl v0_37::Client for MockClient { - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where - R: Request, + R: SimpleRequest, { self.matcher .response_for(request) .ok_or_else(Error::mismatch_response)? + .map(Into::into) } } diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 3686e46b8..9ee418fd6 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -219,7 +219,7 @@ impl WebSocketClient { #[async_trait] impl v0_34::Client for WebSocketClient { - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where R: SimpleRequest, { @@ -229,7 +229,7 @@ impl v0_34::Client for WebSocketClient { #[async_trait] impl v0_37::Client for WebSocketClient { - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where R: SimpleRequest, { @@ -433,7 +433,7 @@ mod sealed { } impl AsyncTungsteniteClient { - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, { @@ -457,7 +457,7 @@ mod sealed { tracing::debug!("Incoming response: {}", response); - R::Response::from_string(response) + R::Response::from_string(response).map(Into::into) } pub async fn subscribe(&self, query: Query) -> Result { @@ -525,7 +525,7 @@ mod sealed { } impl WebSocketClient { - pub async fn perform(&self, request: R) -> Result + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, { diff --git a/rpc/src/dialect/begin_block.rs b/rpc/src/dialect/begin_block.rs index 2cb36bf6a..fdb5a2a28 100644 --- a/rpc/src/dialect/begin_block.rs +++ b/rpc/src/dialect/begin_block.rs @@ -34,9 +34,9 @@ impl From for BeginBlock where abci::Event: Into, { - fn from(msg: abci::response::BeginBlock) -> Self { + fn from(value: abci::response::BeginBlock) -> Self { Self { - events: msg.events.into_iter().map(Into::into).collect(), + events: value.events.into_iter().map(Into::into).collect(), } } } diff --git a/rpc/src/dialect/check_tx.rs b/rpc/src/dialect/check_tx.rs index bddda2e90..47b8d17c9 100644 --- a/rpc/src/dialect/check_tx.rs +++ b/rpc/src/dialect/check_tx.rs @@ -1,7 +1,7 @@ use bytes::Bytes; use serde::{Deserialize, Serialize}; -use tendermint::abci::Code; +use tendermint::abci::{self, Code}; use crate::prelude::*; use crate::serializers; @@ -63,3 +63,24 @@ impl Default for CheckTx { } } } + +impl From> for abci::response::CheckTx +where + Ev: Into, +{ + fn from(msg: CheckTx) -> Self { + Self { + code: msg.code, + data: msg.data, + log: msg.log, + info: msg.info, + gas_wanted: msg.gas_wanted, + gas_used: msg.gas_used, + events: msg.events.into_iter().map(Into::into).collect(), + codespace: msg.codespace, + sender: msg.sender, + priority: msg.priority, + mempool_error: msg.mempool_error, + } + } +} diff --git a/rpc/src/dialect/deliver_tx.rs b/rpc/src/dialect/deliver_tx.rs index a618cd09c..ccb0452ec 100644 --- a/rpc/src/dialect/deliver_tx.rs +++ b/rpc/src/dialect/deliver_tx.rs @@ -1,7 +1,7 @@ use bytes::Bytes; use serde::{Deserialize, Serialize}; -use tendermint::abci::Code; +use tendermint::abci::{self, Code}; use crate::prelude::*; use crate::serializers; @@ -52,3 +52,21 @@ impl Default for DeliverTx { } } } + +impl From> for abci::response::DeliverTx +where + Ev: Into, +{ + fn from(msg: DeliverTx) -> Self { + Self { + code: msg.code, + data: msg.data, + log: msg.log, + info: msg.info, + gas_wanted: msg.gas_wanted, + gas_used: msg.gas_used, + events: msg.events.into_iter().map(Into::into).collect(), + codespace: msg.codespace, + } + } +} diff --git a/rpc/src/dialect/end_block.rs b/rpc/src/dialect/end_block.rs index 98c2d6eea..89f556a1e 100644 --- a/rpc/src/dialect/end_block.rs +++ b/rpc/src/dialect/end_block.rs @@ -46,11 +46,11 @@ impl From for EndBlock where abci::Event: Into, { - fn from(msg: abci::response::EndBlock) -> Self { + fn from(value: abci::response::EndBlock) -> Self { Self { - events: msg.events.into_iter().map(Into::into).collect(), - validator_updates: msg.validator_updates, - consensus_param_updates: msg.consensus_param_updates, + events: value.events.into_iter().map(Into::into).collect(), + validator_updates: value.validator_updates, + consensus_param_updates: value.consensus_param_updates, } } } diff --git a/rpc/src/endpoint/abci_info.rs b/rpc/src/endpoint/abci_info.rs index 6d887a80a..1d174aa18 100644 --- a/rpc/src/endpoint/abci_info.rs +++ b/rpc/src/endpoint/abci_info.rs @@ -19,7 +19,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// ABCI information response #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/abci_query.rs b/rpc/src/endpoint/abci_query.rs index 6e330ead4..4a025cf23 100644 --- a/rpc/src/endpoint/abci_query.rs +++ b/rpc/src/endpoint/abci_query.rs @@ -51,7 +51,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// ABCI query response wrapper #[derive(Clone, Debug, PartialEq, Eq, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/block.rs b/rpc/src/endpoint/block.rs index 11ef07a64..558f7dc0e 100644 --- a/rpc/src/endpoint/block.rs +++ b/rpc/src/endpoint/block.rs @@ -33,7 +33,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Block responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/block_by_hash.rs b/rpc/src/endpoint/block_by_hash.rs index 980dfff80..84a16e212 100644 --- a/rpc/src/endpoint/block_by_hash.rs +++ b/rpc/src/endpoint/block_by_hash.rs @@ -42,7 +42,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Block responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/block_results.rs b/rpc/src/endpoint/block_results.rs index 83f65141c..ee28cb03b 100644 --- a/rpc/src/endpoint/block_results.rs +++ b/rpc/src/endpoint/block_results.rs @@ -2,9 +2,9 @@ use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; -use tendermint::{block, consensus, validator}; +use tendermint::{abci, block, consensus, validator}; -use crate::dialect::{DeliverTx, Dialect}; +use crate::dialect::{self, Dialect}; use crate::prelude::*; use crate::request::RequestMessage; use crate::serializers; @@ -34,19 +34,43 @@ impl RequestMessage for Request { } impl crate::Request for Request { - type Response = Response; + type Response = DialectResponse; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// ABCI result response. -#[derive(Clone, Debug, Serialize, Deserialize)] -pub struct Response { +#[derive(Clone, Debug, Serialize)] +pub struct Response { /// Block height pub height: block::Height, /// Txs results (might be explicit null) - pub txs_results: Option>>, + pub txs_results: Option>, + + /// Begin block events (might be explicit null) + pub begin_block_events: Option>, + + /// End block events (might be explicit null) + pub end_block_events: Option>, + + /// Validator updates (might be explicit null) + pub validator_updates: Vec, + + /// New consensus params (might be explicit null) + pub consensus_param_updates: Option, +} + +/// RPC dialect helper for serialization of the response. +#[derive(Debug, Serialize, Deserialize)] +pub struct DialectResponse { + /// Block height + pub height: block::Height, + + /// Txs results (might be explicit null) + pub txs_results: Option>>, /// Begin block events (might be explicit null) pub begin_block_events: Option>, @@ -62,4 +86,26 @@ pub struct Response { pub consensus_param_updates: Option, } -impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} +impl crate::Response for DialectResponse where Ev: Serialize + DeserializeOwned {} + +impl From> for Response +where + Ev: Into, +{ + fn from(msg: DialectResponse) -> Self { + Response { + height: msg.height, + txs_results: msg + .txs_results + .map(|v| v.into_iter().map(Into::into).collect()), + begin_block_events: msg + .begin_block_events + .map(|v| v.into_iter().map(Into::into).collect()), + end_block_events: msg + .end_block_events + .map(|v| v.into_iter().map(Into::into).collect()), + validator_updates: msg.validator_updates, + consensus_param_updates: msg.consensus_param_updates, + } + } +} diff --git a/rpc/src/endpoint/block_search.rs b/rpc/src/endpoint/block_search.rs index 5054de171..2cfc92f0f 100644 --- a/rpc/src/endpoint/block_search.rs +++ b/rpc/src/endpoint/block_search.rs @@ -38,7 +38,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} #[derive(Clone, Debug, Deserialize, Serialize)] pub struct Response { diff --git a/rpc/src/endpoint/blockchain.rs b/rpc/src/endpoint/blockchain.rs index f605b2a9f..76883ab15 100644 --- a/rpc/src/endpoint/blockchain.rs +++ b/rpc/src/endpoint/blockchain.rs @@ -46,7 +46,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Block responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/broadcast/tx_async.rs b/rpc/src/endpoint/broadcast/tx_async.rs index 3a1863b56..3880d3e24 100644 --- a/rpc/src/endpoint/broadcast/tx_async.rs +++ b/rpc/src/endpoint/broadcast/tx_async.rs @@ -31,7 +31,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Response from either an async or sync transaction broadcast request. #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/broadcast/tx_commit.rs b/rpc/src/endpoint/broadcast/tx_commit.rs index 0d65aa655..195f04295 100644 --- a/rpc/src/endpoint/broadcast/tx_commit.rs +++ b/rpc/src/endpoint/broadcast/tx_commit.rs @@ -3,9 +3,10 @@ use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; -use tendermint::{block, Hash}; -use crate::dialect::{CheckTx, DeliverTx, Dialect}; +use tendermint::{abci, block, Hash}; + +use crate::dialect::{self, Dialect}; use crate::{prelude::*, request::RequestMessage, serializers}; /// `/broadcast_tx_commit`: only returns error if `mempool.CheckTx()` errs or @@ -34,19 +35,37 @@ impl RequestMessage for Request { } impl crate::Request for Request { - type Response = Response; + type Response = DialectResponse; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Response from `/broadcast_tx_commit`. -#[derive(Clone, Debug, Deserialize, Serialize)] -pub struct Response { +#[derive(Clone, Debug, Serialize)] +pub struct Response { + /// `CheckTx` result + pub check_tx: abci::response::CheckTx, + + /// `DeliverTx` result + pub deliver_tx: abci::response::DeliverTx, + + /// Transaction + pub hash: Hash, + + /// Height + pub height: block::Height, +} + +/// RPC dialect helper for serialization of the response. +#[derive(Debug, Deserialize, Serialize)] +pub struct DialectResponse { /// `CheckTx` result - pub check_tx: CheckTx, + pub check_tx: dialect::CheckTx, /// `DeliverTx` result - pub deliver_tx: DeliverTx, + pub deliver_tx: dialect::DeliverTx, /// Transaction pub hash: Hash, @@ -55,4 +74,18 @@ pub struct Response { pub height: block::Height, } -impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} +impl crate::Response for DialectResponse where Ev: Serialize + DeserializeOwned {} + +impl From> for Response +where + Ev: Into, +{ + fn from(msg: DialectResponse) -> Self { + Self { + check_tx: msg.check_tx.into(), + deliver_tx: msg.deliver_tx.into(), + hash: msg.hash, + height: msg.height, + } + } +} diff --git a/rpc/src/endpoint/broadcast/tx_sync.rs b/rpc/src/endpoint/broadcast/tx_sync.rs index 70c8c8858..8bd0a6295 100644 --- a/rpc/src/endpoint/broadcast/tx_sync.rs +++ b/rpc/src/endpoint/broadcast/tx_sync.rs @@ -31,7 +31,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Response from either an async or sync transaction broadcast request. #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/commit.rs b/rpc/src/endpoint/commit.rs index f5222c887..b65635fd2 100644 --- a/rpc/src/endpoint/commit.rs +++ b/rpc/src/endpoint/commit.rs @@ -30,7 +30,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Commit responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/consensus_params.rs b/rpc/src/endpoint/consensus_params.rs index b586362a4..5f20b2b80 100644 --- a/rpc/src/endpoint/consensus_params.rs +++ b/rpc/src/endpoint/consensus_params.rs @@ -32,7 +32,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Consensus parameters response. #[derive(Clone, Debug, Deserialize, Eq, PartialEq, Serialize)] diff --git a/rpc/src/endpoint/consensus_state.rs b/rpc/src/endpoint/consensus_state.rs index 11e3cd70e..0186e69a0 100644 --- a/rpc/src/endpoint/consensus_state.rs +++ b/rpc/src/endpoint/consensus_state.rs @@ -35,7 +35,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// The current consensus state (UNSTABLE). /// diff --git a/rpc/src/endpoint/evidence.rs b/rpc/src/endpoint/evidence.rs index 5ce38e26c..d45977174 100644 --- a/rpc/src/endpoint/evidence.rs +++ b/rpc/src/endpoint/evidence.rs @@ -29,7 +29,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Response from either an evidence broadcast request. #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/genesis.rs b/rpc/src/endpoint/genesis.rs index e2c193656..698fb3ddd 100644 --- a/rpc/src/endpoint/genesis.rs +++ b/rpc/src/endpoint/genesis.rs @@ -39,6 +39,7 @@ where AppState: fmt::Debug + Serialize + DeserializeOwned + Send, S: Dialect, { + type Output = Response; } /// Block responses diff --git a/rpc/src/endpoint/header.rs b/rpc/src/endpoint/header.rs index bc020128d..5de321b3e 100644 --- a/rpc/src/endpoint/header.rs +++ b/rpc/src/endpoint/header.rs @@ -34,7 +34,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Header response #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/header_by_hash.rs b/rpc/src/endpoint/header_by_hash.rs index 9a90c327f..597b2348d 100644 --- a/rpc/src/endpoint/header_by_hash.rs +++ b/rpc/src/endpoint/header_by_hash.rs @@ -40,7 +40,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Header response #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/health.rs b/rpc/src/endpoint/health.rs index 042574036..7699cf0d0 100644 --- a/rpc/src/endpoint/health.rs +++ b/rpc/src/endpoint/health.rs @@ -18,7 +18,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Healthcheck responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/net_info.rs b/rpc/src/endpoint/net_info.rs index 42a770ff0..f7f4fe6ca 100644 --- a/rpc/src/endpoint/net_info.rs +++ b/rpc/src/endpoint/net_info.rs @@ -26,7 +26,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Net info responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/status.rs b/rpc/src/endpoint/status.rs index 66eca8e99..2850eec13 100644 --- a/rpc/src/endpoint/status.rs +++ b/rpc/src/endpoint/status.rs @@ -19,7 +19,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Status responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/endpoint/tx.rs b/rpc/src/endpoint/tx.rs index 0dce25c78..dcf6fad9d 100644 --- a/rpc/src/endpoint/tx.rs +++ b/rpc/src/endpoint/tx.rs @@ -2,7 +2,7 @@ use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; -use tendermint::{block, tx, Hash}; +use tendermint::{abci, block, tx, Hash}; use crate::dialect::{DeliverTx, Dialect}; use crate::{prelude::*, request::RequestMessage, serializers, Method}; @@ -35,13 +35,31 @@ impl RequestMessage for Request { } impl crate::Request for Request { - type Response = Response; + type Response = DialectResponse; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} + +#[derive(Clone, Debug, Serialize)] +pub struct Response { + /// The hash of the transaction. + /// + /// Deserialized from a hex-encoded string (there is a discrepancy between + /// the format used for the request and the format used for the response in + /// the Tendermint RPC). + pub hash: Hash, + pub height: block::Height, + pub index: u32, + pub tx_result: abci::response::DeliverTx, + pub tx: Vec, + pub proof: Option, +} -#[derive(Clone, Debug, Deserialize, Serialize)] -pub struct Response { +/// RPC dialect helper for serialization of the response. +#[derive(Debug, Deserialize, Serialize)] +pub struct DialectResponse { /// The hash of the transaction. /// /// Deserialized from a hex-encoded string (there is a discrepancy between @@ -57,4 +75,20 @@ pub struct Response { pub proof: Option, } -impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} +impl crate::Response for DialectResponse where Ev: Serialize + DeserializeOwned {} + +impl From> for Response +where + Ev: Into, +{ + fn from(msg: DialectResponse) -> Self { + Self { + hash: msg.hash, + height: msg.height, + index: msg.index, + tx_result: msg.tx_result.into(), + tx: msg.tx, + proof: msg.proof, + } + } +} diff --git a/rpc/src/endpoint/tx_search.rs b/rpc/src/endpoint/tx_search.rs index a5556a579..278a66c79 100644 --- a/rpc/src/endpoint/tx_search.rs +++ b/rpc/src/endpoint/tx_search.rs @@ -2,6 +2,8 @@ use serde::{de::DeserializeOwned, Deserialize, Serialize}; +use tendermint::abci; + pub use super::tx; use crate::{dialect::Dialect, prelude::*, request::RequestMessage, serializers, Method, Order}; @@ -43,16 +45,37 @@ impl RequestMessage for Request { } impl crate::Request for Request { - type Response = Response; + type Response = DialectResponse; +} + +impl crate::SimpleRequest for Request { + type Output = Response; } -impl crate::SimpleRequest for Request {} +#[derive(Clone, Debug, Serialize)] +pub struct Response { + pub txs: Vec, + pub total_count: u32, +} -#[derive(Clone, Debug, Deserialize, Serialize)] -pub struct Response { - pub txs: Vec>, +/// RPC dialect helper for serialization of the response. +#[derive(Debug, Deserialize, Serialize)] +pub struct DialectResponse { + pub txs: Vec>, #[serde(with = "serializers::from_str")] pub total_count: u32, } -impl crate::Response for Response where Ev: Serialize + DeserializeOwned {} +impl crate::Response for DialectResponse where Ev: Serialize + DeserializeOwned {} + +impl From> for Response +where + Ev: Into, +{ + fn from(msg: DialectResponse) -> Self { + Self { + txs: msg.txs.into_iter().map(Into::into).collect(), + total_count: msg.total_count, + } + } +} diff --git a/rpc/src/endpoint/validators.rs b/rpc/src/endpoint/validators.rs index 363e80638..c4bded01d 100644 --- a/rpc/src/endpoint/validators.rs +++ b/rpc/src/endpoint/validators.rs @@ -55,7 +55,9 @@ impl crate::Request for Request { type Response = Response; } -impl crate::SimpleRequest for Request {} +impl crate::SimpleRequest for Request { + type Output = Response; +} /// Validator responses #[derive(Clone, Debug, Deserialize, Serialize)] diff --git a/rpc/src/request.rs b/rpc/src/request.rs index fe9e70757..90160ea35 100644 --- a/rpc/src/request.rs +++ b/rpc/src/request.rs @@ -39,7 +39,10 @@ pub trait Request: RequestMessage + Send { /// simple, singular response. /// /// [`Subscription`]: struct.Subscription.html -pub trait SimpleRequest: Request {} +pub trait SimpleRequest: Request { + /// The output data, converted from Response. + type Output: From; +} /// JSON-RPC request wrapper (i.e. message envelope) #[derive(Debug, Deserialize, Serialize)] diff --git a/rpc/src/v0_34/client.rs b/rpc/src/v0_34/client.rs index e942e35e3..3b7c23f8f 100644 --- a/rpc/src/v0_34/client.rs +++ b/rpc/src/v0_34/client.rs @@ -7,7 +7,7 @@ use serde::{de::DeserializeOwned, Serialize}; use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; use tokio::time; -use super::dialect::{Dialect, Event}; +use super::dialect::Dialect; use crate::{ endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, paging::Paging, @@ -69,7 +69,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for a block at a particular height. - async fn block_results(&self, height: H) -> Result, Error> + async fn block_results(&self, height: H) -> Result where H: Into + Send, { @@ -78,7 +78,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for the latest block. - async fn latest_block_results(&self) -> Result, Error> { + async fn latest_block_results(&self) -> Result { self.perform(block_results::Request::default()).await } @@ -127,10 +127,7 @@ pub trait Client { /// `/broadcast_tx_commit`: broadcast a transaction, returning the response /// from `DeliverTx`. - async fn broadcast_tx_commit( - &self, - tx: T, - ) -> Result, Error> + async fn broadcast_tx_commit(&self, tx: T) -> Result where T: Into> + Send, { @@ -252,7 +249,7 @@ pub trait Client { } /// `/tx`: find transaction by hash. - async fn tx(&self, hash: Hash, prove: bool) -> Result, Error> { + async fn tx(&self, hash: Hash, prove: bool) -> Result { self.perform(tx::Request::new(hash, prove)).await } @@ -264,7 +261,7 @@ pub trait Client { page: u32, per_page: u8, order: Order, - ) -> Result, Error> { + ) -> Result { self.perform(tx_search::Request::new(query, prove, page, per_page, order)) .await } @@ -292,7 +289,7 @@ pub trait Client { } /// Perform a request against the RPC endpoint - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where R: SimpleRequest; } diff --git a/rpc/src/v0_37/client.rs b/rpc/src/v0_37/client.rs index b9e66d7e1..072b1ace0 100644 --- a/rpc/src/v0_37/client.rs +++ b/rpc/src/v0_37/client.rs @@ -7,7 +7,7 @@ use serde::{de::DeserializeOwned, Serialize}; use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; use tokio::time; -use super::dialect::{Dialect, Event}; +use super::dialect::Dialect; use crate::{ endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, paging::Paging, @@ -85,7 +85,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for a block at a particular height. - async fn block_results(&self, height: H) -> Result, Error> + async fn block_results(&self, height: H) -> Result where H: Into + Send, { @@ -94,7 +94,7 @@ pub trait Client { } /// `/block_results`: get ABCI results for the latest block. - async fn latest_block_results(&self) -> Result, Error> { + async fn latest_block_results(&self) -> Result { self.perform(block_results::Request::default()).await } @@ -143,10 +143,7 @@ pub trait Client { /// `/broadcast_tx_commit`: broadcast a transaction, returning the response /// from `DeliverTx`. - async fn broadcast_tx_commit( - &self, - tx: T, - ) -> Result, Error> + async fn broadcast_tx_commit(&self, tx: T) -> Result where T: Into> + Send, { @@ -268,7 +265,7 @@ pub trait Client { } /// `/tx`: find transaction by hash. - async fn tx(&self, hash: Hash, prove: bool) -> Result, Error> { + async fn tx(&self, hash: Hash, prove: bool) -> Result { self.perform(tx::Request::new(hash, prove)).await } @@ -280,7 +277,7 @@ pub trait Client { page: u32, per_page: u8, order: Order, - ) -> Result, Error> { + ) -> Result { self.perform(tx_search::Request::new(query, prove, page, per_page, order)) .await } @@ -308,7 +305,7 @@ pub trait Client { } /// Perform a request against the RPC endpoint - async fn perform(&self, request: R) -> Result + async fn perform(&self, request: R) -> Result where R: SimpleRequest; } diff --git a/rpc/tests/gaia_fixtures.rs b/rpc/tests/gaia_fixtures.rs index 80c8d0921..ffc4f9d30 100644 --- a/rpc/tests/gaia_fixtures.rs +++ b/rpc/tests/gaia_fixtures.rs @@ -54,11 +54,11 @@ fn incoming_fixtures() { assert!(r.is_ok(), "{r:?}"); }, "block_results_at_height_10" => { - let r = endpoint::block_results::Response::::from_string(content); + let r = endpoint::block_results::DialectResponse::::from_string(content); assert!(r.is_ok(), "block_results_at_height_10: {r:?}"); }, "block_results_at_height_4555980" => { - let r = endpoint::block_results::Response::::from_string(content); + let r = endpoint::block_results::DialectResponse::::from_string(content); assert!(r.is_ok(), "block_results_at_height_4555980: {r:?}"); }, "blockchain_from_1_to_10" => { diff --git a/rpc/tests/kvstore_fixtures.rs b/rpc/tests/kvstore_fixtures.rs index 84e9e17db..44c05a3a2 100644 --- a/rpc/tests/kvstore_fixtures.rs +++ b/rpc/tests/kvstore_fixtures.rs @@ -461,8 +461,10 @@ fn incoming_fixtures() { assert_eq!(result.block_id.part_set_header.total, 1); }, "block_results_at_height_10" => { - let result = - endpoint::block_results::Response::::from_string(content).unwrap(); + let result: endpoint::block_results::Response = + endpoint::block_results::DialectResponse::::from_string(content) + .unwrap() + .into(); assert!(result.begin_block_events.is_none()); assert!(result.consensus_param_updates.is_none()); assert!(result.end_block_events.is_none()); @@ -531,9 +533,12 @@ fn incoming_fixtures() { assert!(result.log.is_empty()); }, "broadcast_tx_commit" => { - let result = - endpoint::broadcast::tx_commit::Response::::from_string(content) - .unwrap(); + let result: endpoint::broadcast::tx_commit::Response = + endpoint::broadcast::tx_commit::DialectResponse::::from_string( + content, + ) + .unwrap() + .into(); assert_eq!(result.check_tx.code, abci::Code::Ok); assert!(result.check_tx.codespace.is_empty()); assert!(result.check_tx.data.is_empty()); @@ -1365,7 +1370,10 @@ fn incoming_fixtures() { assert!(result.log.is_empty()); }, "tx" => { - let result = endpoint::tx::Response::::from_string(content).unwrap(); + let result: endpoint::tx::Response = + endpoint::tx::DialectResponse::::from_string(content) + .unwrap() + .into(); assert_eq!( result.hash, Hash::from_bytes( @@ -1381,8 +1389,10 @@ fn incoming_fixtures() { assert_eq!(u64::from(result.height), 12u64); }, "tx_search_no_prove" => { - let result = - endpoint::tx_search::Response::::from_string(content).unwrap(); + let result: endpoint::tx_search::Response = + endpoint::tx_search::DialectResponse::::from_string(content) + .unwrap() + .into(); assert_eq!(result.total_count as usize, result.txs.len()); // Test a few selected attributes of the results. for tx in result.txs { @@ -1398,8 +1408,10 @@ fn incoming_fixtures() { } }, "tx_search_with_prove" => { - let result = - endpoint::tx_search::Response::::from_string(content).unwrap(); + let result: endpoint::tx_search::Response = + endpoint::tx_search::DialectResponse::::from_string(content) + .unwrap() + .into(); assert_eq!(result.total_count as usize, result.txs.len()); // Test a few selected attributes of the results. for tx in result.txs { From 504bbe77572a7da7b4ac0aa24736d63e5e2e833e Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 13 Feb 2023 17:20:04 +0200 Subject: [PATCH 51/77] rpc: make the client module public The purpose is to expose the generic WebSocketClient and WebSocketClientDriver types, though not under the crate root that's reserved for the type aliases specialized for the latest protocol version. --- rpc/src/lib.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index db56680d7..a9008af49 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -33,7 +33,7 @@ extern crate std; mod prelude; #[cfg(any(feature = "http-client", feature = "websocket-client"))] -mod client; +pub mod client; #[cfg(feature = "http-client")] pub use client::{HttpClient, HttpClientUrl}; #[cfg(any(feature = "http-client", feature = "websocket-client"))] From e81f7bf23d63ffbcd242381d1ce5e35da3515ff1 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 14 Feb 2023 21:38:31 +0200 Subject: [PATCH 52/77] Remove WebSocketClient::*_with_dialect It's enough to just offer generic new and new_with_config constructors, so that version-specific type aliases have them. --- rpc/src/client/transport/websocket.rs | 47 +++------------------------ 1 file changed, 4 insertions(+), 43 deletions(-) diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 9ee418fd6..97becce4d 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -30,7 +30,7 @@ use crate::{ sync::{ChannelRx, ChannelTx}, transport::router::{PublishResult, SubscriptionRouter}, }, - dialect::{DefaultDialect, Dialect}, + dialect::Dialect, endpoint::{subscribe, unsubscribe}, error::Error, event::{DialectEvent, Event}, @@ -141,13 +141,13 @@ pub struct WebSocketClient { inner: sealed::WebSocketClient, } -impl WebSocketClient { +impl WebSocketClient { /// Construct a new WebSocket-based client connecting to the given /// Tendermint node's RPC endpoint. /// The RPC protocol version is the one supported by this crate by default. /// /// Supports both `ws://` and `wss://` protocols. - pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> + pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, { @@ -162,45 +162,6 @@ impl WebSocketClient { pub async fn new_with_config( url: U, config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> - where - U: TryInto, - { - let url = url.try_into()?; - - let (inner, driver) = if url.0.is_secure() { - sealed::WebSocketClient::new_secure(url.0, config).await? - } else { - sealed::WebSocketClient::new_unsecure(url.0, config).await? - }; - - Ok((Self { inner }, driver)) - } -} - -impl WebSocketClient { - /// Construct a new WebSocket-based client connecting to the given - /// Tendermint node's RPC endpoint. - /// - /// Supports both `ws://` and `wss://` protocols. - pub async fn new_with_dialect( - url: U, - dialect: S, - ) -> Result<(Self, WebSocketClientDriver), Error> - where - U: TryInto, - { - Self::new_with_config_and_dialect(url, None, dialect).await - } - - /// Construct a new WebSocket-based client connecting to the given - /// Tendermint node's RPC endpoint. - /// - /// Supports both `ws://` and `wss://` protocols. - pub async fn new_with_config_and_dialect( - url: U, - config: Option, - _dialect: S, ) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, @@ -1233,7 +1194,7 @@ mod test { println!("Starting WebSocket server..."); let mut server = TestServer::new("127.0.0.1:0").await; println!("Creating client RPC WebSocket connection..."); - let (client, driver) = WebSocketClient::new_with_dialect(server.node_addr.clone(), Dialect) + let (client, driver) = WebSocketClient::::new(server.node_addr.clone()) .await .unwrap(); let driver_handle = tokio::spawn(async move { driver.run().await }); From 064534bd9e6ef38fbce90e9e6bbed35fb5007fd5 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Fri, 17 Feb 2023 00:45:24 +0200 Subject: [PATCH 53/77] rpc: rename DefaultDialect to LatestDialect --- rpc/src/client/bin/main.rs | 6 +++--- rpc/src/client/transport/http.rs | 6 +++--- rpc/src/dialect.rs | 2 +- 3 files changed, 7 insertions(+), 7 deletions(-) diff --git a/rpc/src/client/bin/main.rs b/rpc/src/client/bin/main.rs index 506d70fb0..b2a2e810c 100644 --- a/rpc/src/client/bin/main.rs +++ b/rpc/src/client/bin/main.rs @@ -6,7 +6,7 @@ use futures::StreamExt; use structopt::StructOpt; use tendermint::Hash; use tendermint_rpc::{ - dialect::{DefaultDialect, Dialect}, + dialect::{Dialect, LatestDialect}, event::DialectEvent, query::Query, Client, Error, HttpClient, Order, Paging, Scheme, Subscription, SubscriptionClient, Url, @@ -470,7 +470,7 @@ async fn recv_events_with_timeout( } }; let event = result?; - let event: DialectEvent<::Event> = event.into(); + let event: DialectEvent<::Event> = event.into(); println!("{}", serde_json::to_string_pretty(&event).map_err(Error::serde)?); event_count += 1; if let Some(me) = max_events { @@ -492,7 +492,7 @@ async fn recv_events(mut subs: Subscription, max_events: Option) -> Result< let mut event_count = 0u64; while let Some(result) = subs.next().await { let event = result?; - let event: DialectEvent<::Event> = event.into(); + let event: DialectEvent<::Event> = event.into(); println!( "{}", serde_json::to_string_pretty(&event).map_err(Error::serde)? diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index 32149186e..1aea2542e 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -331,7 +331,7 @@ mod tests { use hyper::Body; use super::sealed::HyperClient; - use crate::dialect::DefaultDialect; + use crate::dialect::LatestDialect; use crate::endpoint::abci_info; fn authorization(req: &Request) -> Option<&str> { @@ -346,7 +346,7 @@ mod tests { let inner = hyper::Client::new(); let client = HyperClient::new(uri, inner); let req = - HyperClient::build_request::<_, DefaultDialect>(&client, abci_info::Request).unwrap(); + HyperClient::build_request::<_, LatestDialect>(&client, abci_info::Request).unwrap(); assert_eq!(authorization(&req), None); } @@ -357,7 +357,7 @@ mod tests { let inner = hyper::Client::new(); let client = HyperClient::new(uri, inner); let req = - HyperClient::build_request::<_, DefaultDialect>(&client, abci_info::Request).unwrap(); + HyperClient::build_request::<_, LatestDialect>(&client, abci_info::Request).unwrap(); assert_eq!(authorization(&req), Some("Basic dG90bzp0YXRh")); } diff --git a/rpc/src/dialect.rs b/rpc/src/dialect.rs index 04bb85ff8..04f4895cb 100644 --- a/rpc/src/dialect.rs +++ b/rpc/src/dialect.rs @@ -19,7 +19,7 @@ pub trait Dialect: sealed::Sealed + Default + Clone + Send + Sync { type Event: Into + Serialize + DeserializeOwned; } -pub type DefaultDialect = crate::v0_37::Dialect; +pub type LatestDialect = crate::v0_37::Dialect; mod sealed { pub trait Sealed {} From fca0f1a91fbd65520df1a3a250f4c05277351d43 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Sat, 18 Feb 2023 00:21:28 +0200 Subject: [PATCH 54/77] rpc: dynamic compat mode for HttpClient Instead of using statically selected, but mostly identical Client traits to specify the protocol version, add the dynamic compatibility mode parameter with enum type CompatMode, and implement v0.34 RPC compatibility mode with its different JSON serialization if the parameter specifies so. --- rpc/src/client.rs | 4 +- rpc/src/client/compat.rs | 16 +++ rpc/src/client/transport/http.rs | 151 +++++++++++++++++++++++++++-- rpc/src/endpoint/header.rs | 8 ++ rpc/src/endpoint/header_by_hash.rs | 8 ++ 5 files changed, 177 insertions(+), 10 deletions(-) create mode 100644 rpc/src/client/compat.rs diff --git a/rpc/src/client.rs b/rpc/src/client.rs index e3c2eb63f..0a6c7371f 100644 --- a/rpc/src/client.rs +++ b/rpc/src/client.rs @@ -1,5 +1,7 @@ //! Tendermint RPC client. +mod compat; +pub use compat::CompatMode; mod subscription; pub use subscription::{Subscription, SubscriptionClient}; pub mod sync; @@ -7,7 +9,7 @@ pub mod sync; mod transport; #[cfg(feature = "http-client")] -pub use transport::http::{HttpClient, HttpClientUrl}; +pub use transport::http::{HttpClient, HttpClientUrl, HttpConfig}; pub use transport::mock::{MockClient, MockRequestMatcher, MockRequestMethodMatcher}; #[cfg(feature = "websocket-client")] pub use transport::websocket::{ diff --git a/rpc/src/client/compat.rs b/rpc/src/client/compat.rs new file mode 100644 index 000000000..e61ce62f4 --- /dev/null +++ b/rpc/src/client/compat.rs @@ -0,0 +1,16 @@ +//! Support for dynamic compatibility with older protocol versions. + +/// Protocol compatibility mode for a Tendermint RPC client. +#[derive(Copy, Clone, Debug, PartialEq, Eq)] +pub enum CompatMode { + /// Use the latest version of the protocol (v0.37 in this release). + Latest, + /// Use v0.34 version of the protocol. + V0_34, +} + +impl Default for CompatMode { + fn default() -> Self { + CompatMode::Latest + } +} diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index 1aea2542e..a419c111e 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -6,9 +6,12 @@ use core::{ }; use async_trait::async_trait; + +use tendermint::{block::Height, Hash}; use tendermint_config::net; -use crate::{prelude::*, Error, Scheme, SimpleRequest, Url}; +use crate::prelude::*; +use crate::{client::CompatMode, endpoint, query::Query, Error, Order, Scheme, SimpleRequest, Url}; use crate::{v0_34, v0_37}; /// A JSON-RPC/HTTP Tendermint RPC client (implements [`crate::Client`]). @@ -40,6 +43,14 @@ use crate::{v0_34, v0_37}; #[derive(Debug, Clone)] pub struct HttpClient { inner: sealed::HttpClient, + compat: CompatMode, +} + +#[derive(Debug, Clone, Default)] +pub struct HttpConfig { + /// Compatibility mode for Tendermint RPC protocol. + pub compat: CompatMode, + pub proxy_url: Option, } impl HttpClient { @@ -56,6 +67,7 @@ impl HttpClient { } else { sealed::HttpClient::new_http(url.try_into()?) }, + compat: Default::default(), }) } @@ -71,15 +83,53 @@ impl HttpClient { U: TryInto, P: TryInto, { - let url = url.try_into()?; - let proxy_url = proxy_url.try_into()?; - Ok(Self { - inner: if proxy_url.0.is_secure() { - sealed::HttpClient::new_https_proxy(url.try_into()?, proxy_url.try_into()?)? - } else { - sealed::HttpClient::new_http_proxy(url.try_into()?, proxy_url.try_into()?)? + Self::new_with_config( + url, + HttpConfig { + proxy_url: Some(proxy_url.try_into()?), + ..Default::default() }, - }) + ) + } + + /// Construct a new Tendermint RPC HTTP/S client connecting to the given + /// URL with specified configuration options. + /// + /// If the `proxy_url` member of the [`HttpConfig`] parameter is not `None` + /// and the RPC endpoint is secured (HTTPS), the proxy will automatically + /// attempt to connect using the [HTTP CONNECT] method. + /// + /// [HTTP CONNECT]: https://en.wikipedia.org/wiki/HTTP_tunnel + pub fn new_with_config(url: U, config: HttpConfig) -> Result + where + U: TryInto, + { + let url = url.try_into()?; + match config.proxy_url { + None => Ok(Self { + inner: if url.0.is_secure() { + sealed::HttpClient::new_https(url.try_into()?) + } else { + sealed::HttpClient::new_http(url.try_into()?) + }, + compat: config.compat, + }), + Some(proxy_url) => Ok(Self { + inner: if proxy_url.0.is_secure() { + sealed::HttpClient::new_https_proxy(url.try_into()?, proxy_url.try_into()?)? + } else { + sealed::HttpClient::new_http_proxy(url.try_into()?, proxy_url.try_into()?)? + }, + compat: config.compat, + }), + } + } + + async fn perform_v0_34(&self, request: R) -> Result + where + R: SimpleRequest, + { + self.inner.perform(request).await } } @@ -93,6 +143,16 @@ impl v0_34::Client for HttpClient { } } +macro_rules! perform_with_compat { + ($self:expr, $request:expr) => {{ + let request = $request; + match $self.compat { + CompatMode::Latest => $self.perform(request).await, + CompatMode::V0_34 => $self.perform_v0_34(request).await, + } + }}; +} + #[async_trait] impl v0_37::Client for HttpClient { async fn perform(&self, request: R) -> Result @@ -101,6 +161,79 @@ impl v0_37::Client for HttpClient { { self.inner.perform(request).await } + + async fn block_results(&self, height: H) -> Result + where + H: Into + Send, + { + perform_with_compat!(self, endpoint::block_results::Request::new(height.into())) + } + + async fn header(&self, height: H) -> Result + where + H: Into + Send, + { + let height = height.into(); + match self.compat { + CompatMode::Latest => self.perform(endpoint::header::Request::new(height)).await, + CompatMode::V0_34 => { + // Back-fill with a request to /block endpoint and + // taking just the header from the response. + let resp = self + .perform_v0_34(endpoint::block::Request::new(height)) + .await?; + Ok(resp.into()) + }, + } + } + + async fn header_by_hash( + &self, + hash: Hash, + ) -> Result { + match self.compat { + CompatMode::Latest => { + self.perform(endpoint::header_by_hash::Request::new(hash)) + .await + }, + CompatMode::V0_34 => { + // Back-fill with a request to /block_by_hash endpoint and + // taking just the header from the response. + let resp = self + .perform_v0_34(endpoint::block_by_hash::Request::new(hash)) + .await?; + Ok(resp.into()) + }, + } + } + + async fn tx(&self, hash: Hash, prove: bool) -> Result { + perform_with_compat!(self, endpoint::tx::Request::new(hash, prove)) + } + + async fn tx_search( + &self, + query: Query, + prove: bool, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + perform_with_compat!( + self, + endpoint::tx_search::Request::new(query, prove, page, per_page, order) + ) + } + + async fn broadcast_tx_commit( + &self, + tx: T, + ) -> Result + where + T: Into> + Send, + { + perform_with_compat!(self, endpoint::broadcast::tx_commit::Request::new(tx)) + } } /// A URL limited to use with HTTP clients. diff --git a/rpc/src/endpoint/header.rs b/rpc/src/endpoint/header.rs index 5de321b3e..36e816258 100644 --- a/rpc/src/endpoint/header.rs +++ b/rpc/src/endpoint/header.rs @@ -46,3 +46,11 @@ pub struct Response { } impl crate::Response for Response {} + +impl From for Response { + fn from(block_resp: super::block::Response) -> Self { + Response { + header: block_resp.block.header, + } + } +} diff --git a/rpc/src/endpoint/header_by_hash.rs b/rpc/src/endpoint/header_by_hash.rs index 597b2348d..d4b646ef6 100644 --- a/rpc/src/endpoint/header_by_hash.rs +++ b/rpc/src/endpoint/header_by_hash.rs @@ -52,3 +52,11 @@ pub struct Response { } impl crate::Response for Response {} + +impl From for Response { + fn from(block_resp: super::block_by_hash::Response) -> Self { + Response { + header: block_resp.block.map(|b| b.header), + } + } +} From 31cf889b5c3531c9c9a6d6de9632fb03932978cf Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 20 Feb 2023 14:11:48 +0200 Subject: [PATCH 55/77] rpc: eliminate dialect Client traits Get back to the single Client trait, with the clients supporting protocol dialects through the compatibility mode selected at runtime. Add CompatMode support to WebSocketClient and make the web socket client types back non-generic. --- rpc/src/client.rs | 310 +++++++++++++++++ rpc/src/client/transport.rs | 10 + rpc/src/client/transport/http.rs | 31 +- rpc/src/client/transport/mock.rs | 25 +- rpc/src/client/transport/router.rs | 4 +- rpc/src/client/transport/websocket.rs | 220 +++++++++---- rpc/src/dialect.rs | 9 +- .../{v0_34/dialect.rs => dialect/v0_34.rs} | 0 .../{v0_37/dialect.rs => dialect/v0_37.rs} | 0 rpc/src/endpoint/header.rs | 2 +- rpc/src/endpoint/header_by_hash.rs | 2 +- rpc/src/lib.rs | 17 +- rpc/src/request.rs | 6 +- rpc/src/v0_34.rs | 13 - rpc/src/v0_34/client.rs | 295 ----------------- rpc/src/v0_37.rs | 13 - rpc/src/v0_37/client.rs | 311 ------------------ rpc/tests/gaia_fixtures.rs | 2 +- rpc/tests/kvstore_fixtures.rs | 2 +- 19 files changed, 506 insertions(+), 766 deletions(-) rename rpc/src/{v0_34/dialect.rs => dialect/v0_34.rs} (100%) rename rpc/src/{v0_37/dialect.rs => dialect/v0_37.rs} (100%) delete mode 100644 rpc/src/v0_34.rs delete mode 100644 rpc/src/v0_34/client.rs delete mode 100644 rpc/src/v0_37.rs delete mode 100644 rpc/src/v0_37/client.rs diff --git a/rpc/src/client.rs b/rpc/src/client.rs index 0a6c7371f..c4081ddd0 100644 --- a/rpc/src/client.rs +++ b/rpc/src/client.rs @@ -15,3 +15,313 @@ pub use transport::mock::{MockClient, MockRequestMatcher, MockRequestMethodMatch pub use transport::websocket::{ WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig, }; + +use core::{fmt, time::Duration}; + +use async_trait::async_trait; +use serde::{de::DeserializeOwned, Serialize}; +use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; +use tokio::time; + +use crate::{ + dialect::v0_37::Dialect, + endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, + paging::Paging, + prelude::*, + query::Query, + Error, Order, SimpleRequest, +}; + +/// Provides lightweight access to the Tendermint RPC. It gives access to all +/// endpoints with the exception of the event subscription-related ones. +/// +/// To access event subscription capabilities, use a client that implements the +/// [`SubscriptionClient`] trait. +/// +/// [`SubscriptionClient`]: trait.SubscriptionClient.html +#[async_trait] +pub trait Client { + /// `/abci_info`: get information about the ABCI application. + async fn abci_info(&self) -> Result { + Ok(self.perform(abci_info::Request).await?.response) + } + + /// `/abci_query`: query the ABCI application + async fn abci_query( + &self, + path: Option, + data: V, + height: Option, + prove: bool, + ) -> Result + where + V: Into> + Send, + { + Ok(self + .perform(abci_query::Request::new(path, data, height, prove)) + .await? + .response) + } + + /// `/block`: get block at a given height. + async fn block(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(block::Request::new(height.into())).await + } + + /// `/block_by_hash`: get block by hash. + async fn block_by_hash( + &self, + hash: tendermint::Hash, + ) -> Result { + self.perform(block_by_hash::Request::new(hash)).await + } + + /// `/block`: get the latest block. + async fn latest_block(&self) -> Result { + self.perform(block::Request::default()).await + } + + /// `/header`: get block header at a given height. + async fn header(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(header::Request::new(height.into())).await + } + + /// `/header_by_hash`: get block by hash. + async fn header_by_hash( + &self, + hash: tendermint::Hash, + ) -> Result { + self.perform(header_by_hash::Request::new(hash)).await + } + + /// `/block_results`: get ABCI results for a block at a particular height. + async fn block_results(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(block_results::Request::new(height.into())) + .await + } + + /// `/block_results`: get ABCI results for the latest block. + async fn latest_block_results(&self) -> Result { + self.perform(block_results::Request::default()).await + } + + /// `/block_search`: search for blocks by BeginBlock and EndBlock events. + async fn block_search( + &self, + query: Query, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + self.perform(block_search::Request::new(query, page, per_page, order)) + .await + } + + /// `/blockchain`: get block headers for `min` <= `height` <= `max`. + /// + /// Block headers are returned in descending order (highest first). + /// + /// Returns at most 20 items. + async fn blockchain(&self, min: H, max: H) -> Result + where + H: Into + Send, + { + // TODO(tarcieri): return errors for invalid params before making request? + self.perform(blockchain::Request::new(min.into(), max.into())) + .await + } + + /// `/broadcast_tx_async`: broadcast a transaction, returning immediately. + async fn broadcast_tx_async(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_async::Request::new(tx)).await + } + + /// `/broadcast_tx_sync`: broadcast a transaction, returning the response + /// from `CheckTx`. + async fn broadcast_tx_sync(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_sync::Request::new(tx)).await + } + + /// `/broadcast_tx_commit`: broadcast a transaction, returning the response + /// from `DeliverTx`. + async fn broadcast_tx_commit(&self, tx: T) -> Result + where + T: Into> + Send, + { + self.perform(broadcast::tx_commit::Request::new(tx)).await + } + + /// `/commit`: get block commit at a given height. + async fn commit(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(commit::Request::new(height.into())).await + } + + /// `/consensus_params`: get current consensus parameters at the specified + /// height. + async fn consensus_params(&self, height: H) -> Result + where + H: Into + Send, + { + self.perform(consensus_params::Request::new(Some(height.into()))) + .await + } + + /// `/consensus_state`: get current consensus state + async fn consensus_state(&self) -> Result { + self.perform(consensus_state::Request::new()).await + } + + // TODO(thane): Simplify once validators endpoint removes pagination. + /// `/validators`: get validators a given height. + async fn validators(&self, height: H, paging: Paging) -> Result + where + H: Into + Send, + { + let height = height.into(); + match paging { + Paging::Default => { + self.perform(validators::Request::new(Some(height), None, None)) + .await + }, + Paging::Specific { + page_number, + per_page, + } => { + self.perform(validators::Request::new( + Some(height), + Some(page_number), + Some(per_page), + )) + .await + }, + Paging::All => { + let mut page_num = 1_usize; + let mut validators = Vec::new(); + let per_page = DEFAULT_VALIDATORS_PER_PAGE.into(); + loop { + let response = self + .perform(validators::Request::new( + Some(height), + Some(page_num.into()), + Some(per_page), + )) + .await?; + validators.extend(response.validators); + if validators.len() as i32 == response.total { + return Ok(validators::Response::new( + response.block_height, + validators, + response.total, + )); + } + page_num += 1; + } + }, + } + } + + /// `/consensus_params`: get the latest consensus parameters. + async fn latest_consensus_params(&self) -> Result { + self.perform(consensus_params::Request::new(None)).await + } + + /// `/commit`: get the latest block commit + async fn latest_commit(&self) -> Result { + self.perform(commit::Request::default()).await + } + + /// `/health`: get node health. + /// + /// Returns empty result (200 OK) on success, no response in case of an error. + async fn health(&self) -> Result<(), Error> { + self.perform(health::Request).await?; + Ok(()) + } + + /// `/genesis`: get genesis file. + async fn genesis(&self) -> Result, Error> + where + AppState: fmt::Debug + Serialize + DeserializeOwned + Send, + { + Ok(self.perform(genesis::Request::default()).await?.genesis) + } + + /// `/net_info`: obtain information about P2P and other network connections. + async fn net_info(&self) -> Result { + self.perform(net_info::Request).await + } + + /// `/status`: get Tendermint status including node info, pubkey, latest + /// block hash, app hash, block height and time. + async fn status(&self) -> Result { + self.perform(status::Request).await + } + + /// `/broadcast_evidence`: broadcast an evidence. + async fn broadcast_evidence(&self, e: Evidence) -> Result { + self.perform(evidence::Request::new(e)).await + } + + /// `/tx`: find transaction by hash. + async fn tx(&self, hash: Hash, prove: bool) -> Result { + self.perform(tx::Request::new(hash, prove)).await + } + + /// `/tx_search`: search for transactions with their results. + async fn tx_search( + &self, + query: Query, + prove: bool, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + self.perform(tx_search::Request::new(query, prove, page, per_page, order)) + .await + } + + /// Poll the `/health` endpoint until it returns a successful result or + /// the given `timeout` has elapsed. + async fn wait_until_healthy(&self, timeout: T) -> Result<(), Error> + where + T: Into + Send, + { + let timeout = timeout.into(); + let poll_interval = Duration::from_millis(200); + let mut attempts_remaining = timeout.as_millis() / poll_interval.as_millis(); + + while self.health().await.is_err() { + if attempts_remaining == 0 { + return Err(Error::timeout(timeout)); + } + + attempts_remaining -= 1; + time::sleep(poll_interval).await; + } + + Ok(()) + } + + /// Perform a request against the RPC endpoint + async fn perform(&self, request: R) -> Result + where + R: SimpleRequest; +} diff --git a/rpc/src/client/transport.rs b/rpc/src/client/transport.rs index a9ba2242e..c0f9f0c5c 100644 --- a/rpc/src/client/transport.rs +++ b/rpc/src/client/transport.rs @@ -4,6 +4,16 @@ mod auth; pub mod mock; mod router; +macro_rules! perform_with_compat { + ($self:expr, $request:expr) => {{ + let request = $request; + match $self.compat { + CompatMode::Latest => $self.perform(request).await, + CompatMode::V0_34 => $self.perform_v0_34(request).await, + } + }}; +} + #[cfg(feature = "http-client")] pub mod http; #[cfg(feature = "websocket-client")] diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index a419c111e..9b4496064 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -10,9 +10,14 @@ use async_trait::async_trait; use tendermint::{block::Height, Hash}; use tendermint_config::net; +use crate::dialect::{v0_34, v0_37}; use crate::prelude::*; -use crate::{client::CompatMode, endpoint, query::Query, Error, Order, Scheme, SimpleRequest, Url}; -use crate::{v0_34, v0_37}; +use crate::{ + client::{Client, CompatMode}, + endpoint, + query::Query, + Error, Order, Scheme, SimpleRequest, Url, +}; /// A JSON-RPC/HTTP Tendermint RPC client (implements [`crate::Client`]). /// @@ -134,27 +139,7 @@ impl HttpClient { } #[async_trait] -impl v0_34::Client for HttpClient { - async fn perform(&self, request: R) -> Result - where - R: SimpleRequest, - { - self.inner.perform(request).await - } -} - -macro_rules! perform_with_compat { - ($self:expr, $request:expr) => {{ - let request = $request; - match $self.compat { - CompatMode::Latest => $self.perform(request).await, - CompatMode::V0_34 => $self.perform_v0_34(request).await, - } - }}; -} - -#[async_trait] -impl v0_37::Client for HttpClient { +impl Client for HttpClient { async fn perform(&self, request: R) -> Result where R: SimpleRequest, diff --git a/rpc/src/client/transport/mock.rs b/rpc/src/client/transport/mock.rs index 69eb3e728..52edebd2f 100644 --- a/rpc/src/client/transport/mock.rs +++ b/rpc/src/client/transport/mock.rs @@ -4,13 +4,14 @@ use alloc::collections::BTreeMap as HashMap; use async_trait::async_trait; +use crate::dialect::{v0_37, Dialect}; use crate::{ client::{ subscription::SubscriptionTx, sync::{unbounded, ChannelRx, ChannelTx}, transport::router::SubscriptionRouter, + Client, }, - dialect::Dialect, event::Event, prelude::*, query::Query, @@ -18,7 +19,6 @@ use crate::{ utils::uuid_str, Error, Method, Request, Response, Subscription, SubscriptionClient, }; -use crate::{v0_34, v0_37}; /// A mock client implementation for use in testing. /// @@ -62,20 +62,7 @@ pub struct MockClient { } #[async_trait] -impl v0_34::Client for MockClient { - async fn perform(&self, request: R) -> Result - where - R: SimpleRequest, - { - self.matcher - .response_for(request) - .ok_or_else(Error::mismatch_response)? - .map(Into::into) - } -} - -#[async_trait] -impl v0_37::Client for MockClient { +impl Client for MockClient { async fn perform(&self, request: R) -> Result where R: SimpleRequest, @@ -274,12 +261,11 @@ mod test { mod v0_34 { use super::*; + use crate::dialect::v0_34::Event as RpcEvent; use crate::event::DialectEvent; - use crate::v0_34::{dialect, Client}; async fn read_event(name: &str) -> Event { - let msg = - DialectEvent::::from_string(read_json_fixture(name).await).unwrap(); + let msg = DialectEvent::::from_string(read_json_fixture(name).await).unwrap(); msg.into() } @@ -344,7 +330,6 @@ mod test { mod v0_37 { use super::*; - use crate::v0_37::Client; #[tokio::test] async fn mock_client() { diff --git a/rpc/src/client/transport/router.rs b/rpc/src/client/transport/router.rs index d58858caf..40542c61b 100644 --- a/rpc/src/client/transport/router.rs +++ b/rpc/src/client/transport/router.rs @@ -147,8 +147,8 @@ mod test { event::{Event, WrappedEvent}, utils::uuid_str, }; - // TODO: add fixtures for v0_37::dialect - use crate::v0_34::dialect::Event as RpcEvent; + // TODO: add fixtures for dialect::v0_37 + use crate::dialect::v0_34::Event as RpcEvent; async fn read_json_fixture(name: &str) -> String { fs::read_to_string( diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 97becce4d..a153a29ef 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -3,7 +3,6 @@ use alloc::{borrow::Cow, collections::BTreeMap as HashMap}; use core::{ convert::{TryFrom, TryInto}, - marker::PhantomData, ops::Add, str::FromStr, }; @@ -19,27 +18,30 @@ use async_tungstenite::{ }; use futures::{SinkExt, StreamExt}; use serde::{Deserialize, Serialize}; -use tendermint_config::net; use tokio::time::{Duration, Instant}; use tracing::{debug, error}; +use tendermint::{block::Height, Hash}; +use tendermint_config::net; + use super::router::{SubscriptionId, SubscriptionIdRef}; +use crate::dialect::{v0_34, v0_37}; use crate::{ client::{ subscription::SubscriptionTx, sync::{ChannelRx, ChannelTx}, transport::router::{PublishResult, SubscriptionRouter}, + Client, CompatMode, }, - dialect::Dialect, - endpoint::{subscribe, unsubscribe}, + endpoint::{self, subscribe, unsubscribe}, error::Error, event::{DialectEvent, Event}, prelude::*, query::Query, request::Wrapper, - response, Id, Request, Response, Scheme, SimpleRequest, Subscription, SubscriptionClient, Url, + response, Id, Order, Request, Response, Scheme, SimpleRequest, Subscription, + SubscriptionClient, Url, }; -use crate::{v0_34, v0_37}; // WebSocket connection times out if we haven't heard anything at all from the // server in this long. @@ -54,8 +56,13 @@ const RECV_TIMEOUT: Duration = Duration::from_secs(RECV_TIMEOUT_SECONDS); // Taken from https://github.com/tendermint/tendermint/blob/309e29c245a01825fc9630103311fd04de99fa5e/rpc/jsonrpc/server/ws_handler.go#L28 const PING_INTERVAL: Duration = Duration::from_secs((RECV_TIMEOUT_SECONDS * 9) / 10); -/// Low-level WebSocket configuration -pub use async_tungstenite::tungstenite::protocol::WebSocketConfig; +#[derive(Default)] +/// WebSocket client configuration +pub struct WebSocketConfig { + compat: CompatMode, + /// Low-level protocol configuration + transport: Option, +} /// Tendermint RPC client that provides access to all RPC functionality /// (including [`Event`] subscription) over a WebSocket connection. @@ -137,36 +144,36 @@ pub use async_tungstenite::tungstenite::protocol::WebSocketConfig; /// /// [tendermint-websocket-ping]: https://github.com/tendermint/tendermint/blob/309e29c245a01825fc9630103311fd04de99fa5e/rpc/jsonrpc/server/ws_handler.go#L28 #[derive(Debug, Clone)] -pub struct WebSocketClient { - inner: sealed::WebSocketClient, +pub struct WebSocketClient { + inner: sealed::WebSocketClient, + compat: CompatMode, } -impl WebSocketClient { +impl WebSocketClient { /// Construct a new WebSocket-based client connecting to the given /// Tendermint node's RPC endpoint. - /// The RPC protocol version is the one supported by this crate by default. /// /// Supports both `ws://` and `wss://` protocols. - pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> + pub async fn new(url: U) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, { - Self::new_with_config(url, None).await + Self::new_with_config(url, Default::default()).await } /// Construct a new WebSocket-based client connecting to the given /// Tendermint node's RPC endpoint. - /// The RPC protocol version is the one supported by this crate by default. /// /// Supports both `ws://` and `wss://` protocols. pub async fn new_with_config( url: U, - config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> + config: WebSocketConfig, + ) -> Result<(Self, WebSocketClientDriver), Error> where U: TryInto, { let url = url.try_into()?; + let compat = config.compat; let (inner, driver) = if url.0.is_secure() { sealed::WebSocketClient::new_secure(url.0, config).await? @@ -174,13 +181,10 @@ impl WebSocketClient { sealed::WebSocketClient::new_unsecure(url.0, config).await? }; - Ok((Self { inner }, driver)) + Ok((Self { inner, compat }, driver)) } -} -#[async_trait] -impl v0_34::Client for WebSocketClient { - async fn perform(&self, request: R) -> Result + async fn perform_v0_34(&self, request: R) -> Result where R: SimpleRequest, { @@ -189,17 +193,90 @@ impl v0_34::Client for WebSocketClient { } #[async_trait] -impl v0_37::Client for WebSocketClient { +impl Client for WebSocketClient { async fn perform(&self, request: R) -> Result where R: SimpleRequest, { self.inner.perform(request).await } + + async fn block_results(&self, height: H) -> Result + where + H: Into + Send, + { + perform_with_compat!(self, endpoint::block_results::Request::new(height.into())) + } + + async fn header(&self, height: H) -> Result + where + H: Into + Send, + { + let height = height.into(); + match self.compat { + CompatMode::Latest => self.perform(endpoint::header::Request::new(height)).await, + CompatMode::V0_34 => { + // Back-fill with a request to /block endpoint and + // taking just the header from the response. + let resp = self + .perform_v0_34(endpoint::block::Request::new(height)) + .await?; + Ok(resp.into()) + }, + } + } + + async fn header_by_hash( + &self, + hash: Hash, + ) -> Result { + match self.compat { + CompatMode::Latest => { + self.perform(endpoint::header_by_hash::Request::new(hash)) + .await + }, + CompatMode::V0_34 => { + // Back-fill with a request to /block_by_hash endpoint and + // taking just the header from the response. + let resp = self + .perform_v0_34(endpoint::block_by_hash::Request::new(hash)) + .await?; + Ok(resp.into()) + }, + } + } + + async fn tx(&self, hash: Hash, prove: bool) -> Result { + perform_with_compat!(self, endpoint::tx::Request::new(hash, prove)) + } + + async fn tx_search( + &self, + query: Query, + prove: bool, + page: u32, + per_page: u8, + order: Order, + ) -> Result { + perform_with_compat!( + self, + endpoint::tx_search::Request::new(query, prove, page, per_page, order) + ) + } + + async fn broadcast_tx_commit( + &self, + tx: T, + ) -> Result + where + T: Into> + Send, + { + perform_with_compat!(self, endpoint::broadcast::tx_commit::Request::new(tx)) + } } #[async_trait] -impl SubscriptionClient for WebSocketClient { +impl SubscriptionClient for WebSocketClient { async fn subscribe(&self, query: Query) -> Result { self.inner.subscribe(query).await } @@ -275,13 +352,13 @@ impl From for Url { mod sealed { use async_tungstenite::{ tokio::{connect_async_with_config, connect_async_with_tls_connector_and_config}, - tungstenite::{client::IntoClientRequest, protocol::WebSocketConfig}, + tungstenite::client::IntoClientRequest, }; use tracing::debug; use super::{ DriverCommand, SimpleRequestCommand, SubscribeCommand, UnsubscribeCommand, - WebSocketClientDriver, + WebSocketClientDriver, WebSocketConfig, }; use crate::{ client::{ @@ -313,12 +390,12 @@ mod sealed { /// /// [`async-tungstenite`]: https://crates.io/crates/async-tungstenite #[derive(Debug, Clone)] - pub struct AsyncTungsteniteClient { + pub struct AsyncTungsteniteClient { cmd_tx: ChannelTx, - _phantom: core::marker::PhantomData<(C, S)>, + _client_type: core::marker::PhantomData, } - impl AsyncTungsteniteClient { + impl AsyncTungsteniteClient { /// Construct a WebSocket client. Immediately attempts to open a WebSocket /// connection to the node with the given address. /// @@ -329,26 +406,26 @@ mod sealed { /// doesn't block the client. pub async fn new( url: Url, - config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { + config: WebSocketConfig, + ) -> Result<(Self, WebSocketClientDriver), Error> { debug!("Connecting to unsecure WebSocket endpoint: {}", url); - let (stream, _response) = connect_async_with_config(url, config) + let (stream, _response) = connect_async_with_config(url, config.transport) .await .map_err(Error::tungstenite)?; let (cmd_tx, cmd_rx) = unbounded(); - let driver = WebSocketClientDriver::new(stream, cmd_rx); + let driver = WebSocketClientDriver::new(stream, cmd_rx, config.compat); let client = Self { cmd_tx, - _phantom: Default::default(), + _client_type: Default::default(), }; Ok((client, driver)) } } - impl AsyncTungsteniteClient { + impl AsyncTungsteniteClient { /// Construct a WebSocket client. Immediately attempts to open a WebSocket /// connection to the node with the given address, but over a secure /// connection. @@ -360,29 +437,29 @@ mod sealed { /// doesn't block the client. pub async fn new( url: Url, - config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { + config: WebSocketConfig, + ) -> Result<(Self, WebSocketClientDriver), Error> { debug!("Connecting to secure WebSocket endpoint: {}", url); // Not supplying a connector means async_tungstenite will create the // connector for us. let (stream, _response) = - connect_async_with_tls_connector_and_config(url, None, config) + connect_async_with_tls_connector_and_config(url, None, config.transport) .await .map_err(Error::tungstenite)?; let (cmd_tx, cmd_rx) = unbounded(); - let driver = WebSocketClientDriver::new(stream, cmd_rx); + let driver = WebSocketClientDriver::new(stream, cmd_rx, config.compat); let client = Self { cmd_tx, - _phantom: Default::default(), + _client_type: Default::default(), }; Ok((client, driver)) } } - impl AsyncTungsteniteClient { + impl AsyncTungsteniteClient { fn send_cmd(&self, cmd: DriverCommand) -> Result<(), Error> { self.cmd_tx.send(cmd) } @@ -393,10 +470,11 @@ mod sealed { } } - impl AsyncTungsteniteClient { - pub async fn perform(&self, request: R) -> Result + impl AsyncTungsteniteClient { + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, + S: Dialect, { let wrapper = Wrapper::new(request); let id = wrapper.id().to_string(); @@ -455,25 +533,25 @@ mod sealed { /// Allows us to erase the type signatures associated with the different /// WebSocket client variants. #[derive(Debug, Clone)] - pub enum WebSocketClient { - Unsecure(AsyncTungsteniteClient), - Secure(AsyncTungsteniteClient), + pub enum WebSocketClient { + Unsecure(AsyncTungsteniteClient), + Secure(AsyncTungsteniteClient), } - impl WebSocketClient { + impl WebSocketClient { pub async fn new_unsecure( url: Url, - config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { - let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; + config: WebSocketConfig, + ) -> Result<(Self, WebSocketClientDriver), Error> { + let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; Ok((Self::Unsecure(client), driver)) } pub async fn new_secure( url: Url, - config: Option, - ) -> Result<(Self, WebSocketClientDriver), Error> { - let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; + config: WebSocketConfig, + ) -> Result<(Self, WebSocketClientDriver), Error> { + let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; Ok((Self::Secure(client), driver)) } @@ -485,10 +563,11 @@ mod sealed { } } - impl WebSocketClient { - pub async fn perform(&self, request: R) -> Result + impl WebSocketClient { + pub async fn perform(&self, request: R) -> Result where R: SimpleRequest, + S: Dialect, { match self { WebSocketClient::Unsecure(c) => c.perform(request).await, @@ -598,7 +677,7 @@ impl Response for GenericJsonResponse {} /// /// This is the primary component responsible for transport-level interaction /// with the remote WebSocket endpoint. -pub struct WebSocketClientDriver { +pub struct WebSocketClientDriver { // The underlying WebSocket network connection. stream: WebSocketStream, // Facilitates routing of events to their respective subscriptions. @@ -608,17 +687,22 @@ pub struct WebSocketClientDriver { // Commands we've received but have not yet completed, indexed by their ID. // A Terminate command is executed immediately. pending_commands: HashMap, - _dialect: PhantomData, + // The compatibility mode directing how to parse subscription events. + compat: CompatMode, } -impl WebSocketClientDriver { - fn new(stream: WebSocketStream, cmd_rx: ChannelRx) -> Self { +impl WebSocketClientDriver { + fn new( + stream: WebSocketStream, + cmd_rx: ChannelRx, + compat: CompatMode, + ) -> Self { Self { stream, router: SubscriptionRouter::default(), cmd_rx, pending_commands: HashMap::new(), - _dialect: Default::default(), + compat, } } @@ -640,9 +724,7 @@ impl WebSocketClientDriver { .insert(cmd.id.clone(), DriverCommand::SimpleRequest(cmd)); Ok(()) } -} -impl WebSocketClientDriver { /// Executes the WebSocket driver, which manages the underlying WebSocket /// transport. pub async fn run(mut self) -> Result<(), Error> { @@ -684,7 +766,7 @@ impl WebSocketClientDriver { async fn send_request(&mut self, wrapper: Wrapper) -> Result<(), Error> where - R: Request, + R: Request, { self.send_msg(Message::Text( serde_json::to_string_pretty(&wrapper).unwrap(), @@ -750,8 +832,12 @@ impl WebSocketClientDriver { } async fn handle_text_msg(&mut self, msg: String) -> Result<(), Error> { - if let Ok(ev) = DialectEvent::::from_string(&msg) { - self.publish_event(ev.into()).await; + let parse_res = match self.compat { + CompatMode::Latest => DialectEvent::::from_string(&msg).map(Into::into), + CompatMode::V0_34 => DialectEvent::::from_string(&msg).map(Into::into), + }; + if let Ok(ev) = parse_res { + self.publish_event(ev).await; return Ok(()); } @@ -889,7 +975,7 @@ mod test { use super::*; use crate::{client::sync::unbounded, query::EventType, request, Id, Method}; // TODO: test with v0_37::dialect as well - use crate::v0_34::dialect::{Dialect, Event as RpcEvent}; + use crate::dialect::v0_34::Event as RpcEvent; // Interface to a driver that manages all incoming WebSocket connections. struct TestServer { @@ -1194,7 +1280,7 @@ mod test { println!("Starting WebSocket server..."); let mut server = TestServer::new("127.0.0.1:0").await; println!("Creating client RPC WebSocket connection..."); - let (client, driver) = WebSocketClient::::new(server.node_addr.clone()) + let (client, driver) = WebSocketClient::new(server.node_addr.clone()) .await .unwrap(); let driver_handle = tokio::spawn(async move { driver.run().await }); diff --git a/rpc/src/dialect.rs b/rpc/src/dialect.rs index 04f4895cb..ddcb94748 100644 --- a/rpc/src/dialect.rs +++ b/rpc/src/dialect.rs @@ -1,6 +1,9 @@ //! Helper types to generalize differences in serialization between //! Tendermint RPC protocol versions. +pub mod v0_34; +pub mod v0_37; + mod begin_block; mod check_tx; mod deliver_tx; @@ -19,11 +22,11 @@ pub trait Dialect: sealed::Sealed + Default + Clone + Send + Sync { type Event: Into + Serialize + DeserializeOwned; } -pub type LatestDialect = crate::v0_37::Dialect; +pub type LatestDialect = v0_37::Dialect; mod sealed { pub trait Sealed {} - impl Sealed for crate::v0_34::Dialect {} - impl Sealed for crate::v0_37::Dialect {} + impl Sealed for super::v0_34::Dialect {} + impl Sealed for super::v0_37::Dialect {} } diff --git a/rpc/src/v0_34/dialect.rs b/rpc/src/dialect/v0_34.rs similarity index 100% rename from rpc/src/v0_34/dialect.rs rename to rpc/src/dialect/v0_34.rs diff --git a/rpc/src/v0_37/dialect.rs b/rpc/src/dialect/v0_37.rs similarity index 100% rename from rpc/src/v0_37/dialect.rs rename to rpc/src/dialect/v0_37.rs diff --git a/rpc/src/endpoint/header.rs b/rpc/src/endpoint/header.rs index 36e816258..ad1506205 100644 --- a/rpc/src/endpoint/header.rs +++ b/rpc/src/endpoint/header.rs @@ -3,8 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::block::{self, Header}; +use crate::dialect::v0_37; use crate::request::RequestMessage; -use crate::v0_37; /// Get information about a specific block #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] diff --git a/rpc/src/endpoint/header_by_hash.rs b/rpc/src/endpoint/header_by_hash.rs index d4b646ef6..e887944e2 100644 --- a/rpc/src/endpoint/header_by_hash.rs +++ b/rpc/src/endpoint/header_by_hash.rs @@ -3,8 +3,8 @@ use serde::{Deserialize, Serialize}; use tendermint::{block::Header, Hash}; +use crate::dialect::v0_37; use crate::request::RequestMessage; -use crate::v0_37; /// Get information about a specific block by its hash #[derive(Clone, Debug, Default, Deserialize, Eq, PartialEq, Serialize)] diff --git a/rpc/src/lib.rs b/rpc/src/lib.rs index a9008af49..9fba54790 100644 --- a/rpc/src/lib.rs +++ b/rpc/src/lib.rs @@ -34,14 +34,15 @@ mod prelude; #[cfg(any(feature = "http-client", feature = "websocket-client"))] pub mod client; -#[cfg(feature = "http-client")] -pub use client::{HttpClient, HttpClientUrl}; #[cfg(any(feature = "http-client", feature = "websocket-client"))] pub use client::{ - MockClient, MockRequestMatcher, MockRequestMethodMatcher, Subscription, SubscriptionClient, + Client, MockClient, MockRequestMatcher, MockRequestMethodMatcher, Subscription, + SubscriptionClient, }; +#[cfg(feature = "http-client")] +pub use client::{HttpClient, HttpClientUrl}; #[cfg(feature = "websocket-client")] -pub use client::{WebSocketClientUrl, WebSocketConfig}; +pub use client::{WebSocketClient, WebSocketClientDriver, WebSocketClientUrl, WebSocketConfig}; pub mod dialect; pub mod endpoint; @@ -60,14 +61,6 @@ pub mod serializers; mod utils; mod version; -pub mod v0_34; -pub mod v0_37; - -#[cfg(any(feature = "http-client", feature = "websocket-client"))] -pub use v0_37::Client; -#[cfg(feature = "websocket-client")] -pub use v0_37::{WebSocketClient, WebSocketClientDriver}; - pub use error::Error; pub use id::Id; pub use method::Method; diff --git a/rpc/src/request.rs b/rpc/src/request.rs index 90160ea35..684746479 100644 --- a/rpc/src/request.rs +++ b/rpc/src/request.rs @@ -5,7 +5,7 @@ use core::fmt::Debug; use serde::{de::DeserializeOwned, Deserialize, Serialize}; use super::{Id, Method, Version}; -use crate::dialect::Dialect; +use crate::dialect::{Dialect, LatestDialect}; use crate::{prelude::*, Error}; /// Serialization for JSON-RPC requests @@ -26,7 +26,7 @@ pub trait RequestMessage: DeserializeOwned + Serialize + Sized { } /// JSON-RPC requests -pub trait Request: RequestMessage + Send { +pub trait Request: RequestMessage + Send { /// Response type for this command type Response: super::response::Response; } @@ -39,7 +39,7 @@ pub trait Request: RequestMessage + Send { /// simple, singular response. /// /// [`Subscription`]: struct.Subscription.html -pub trait SimpleRequest: Request { +pub trait SimpleRequest: Request { /// The output data, converted from Response. type Output: From; } diff --git a/rpc/src/v0_34.rs b/rpc/src/v0_34.rs deleted file mode 100644 index bab85f704..000000000 --- a/rpc/src/v0_34.rs +++ /dev/null @@ -1,13 +0,0 @@ -#[cfg(any(feature = "http-client", feature = "websocket-client"))] -mod client; -#[cfg(any(feature = "http-client", feature = "websocket-client"))] -pub use client::Client; - -pub mod dialect; -pub use dialect::Dialect; - -#[cfg(feature = "websocket-client")] -pub type WebSocketClient = crate::client::WebSocketClient; - -#[cfg(feature = "websocket-client")] -pub type WebSocketClientDriver = crate::client::WebSocketClientDriver; diff --git a/rpc/src/v0_34/client.rs b/rpc/src/v0_34/client.rs deleted file mode 100644 index 3b7c23f8f..000000000 --- a/rpc/src/v0_34/client.rs +++ /dev/null @@ -1,295 +0,0 @@ -//! The v0.34 RPC client interface. - -use core::{fmt, time::Duration}; - -use async_trait::async_trait; -use serde::{de::DeserializeOwned, Serialize}; -use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; -use tokio::time; - -use super::dialect::Dialect; -use crate::{ - endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, - paging::Paging, - prelude::*, - query::Query, - Error, Order, SimpleRequest, -}; - -/// Provides lightweight access to the Tendermint RPC. It gives access to all -/// endpoints with the exception of the event subscription-related ones. -/// -/// To access event subscription capabilities, use a client that implements the -/// [`SubscriptionClient`] trait. -/// -/// [`SubscriptionClient`]: trait.SubscriptionClient.html -#[async_trait] -pub trait Client { - /// `/abci_info`: get information about the ABCI application. - async fn abci_info(&self) -> Result { - Ok(self.perform(abci_info::Request).await?.response) - } - - /// `/abci_query`: query the ABCI application - async fn abci_query( - &self, - path: Option, - data: V, - height: Option, - prove: bool, - ) -> Result - where - V: Into> + Send, - { - Ok(self - .perform(abci_query::Request::new(path, data, height, prove)) - .await? - .response) - } - - /// `/block`: get block at a given height. - async fn block(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(block::Request::new(height.into())).await - } - - /// `/block_by_hash`: get block by hash. - async fn block_by_hash( - &self, - hash: tendermint::Hash, - ) -> Result { - self.perform(block_by_hash::Request::new(hash)).await - } - - /// `/block`: get the latest block. - async fn latest_block(&self) -> Result { - self.perform(block::Request::default()).await - } - - /// `/block_results`: get ABCI results for a block at a particular height. - async fn block_results(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(block_results::Request::new(height.into())) - .await - } - - /// `/block_results`: get ABCI results for the latest block. - async fn latest_block_results(&self) -> Result { - self.perform(block_results::Request::default()).await - } - - /// `/block_search`: search for blocks by BeginBlock and EndBlock events. - async fn block_search( - &self, - query: Query, - page: u32, - per_page: u8, - order: Order, - ) -> Result { - self.perform(block_search::Request::new(query, page, per_page, order)) - .await - } - - /// `/blockchain`: get block headers for `min` <= `height` <= `max`. - /// - /// Block headers are returned in descending order (highest first). - /// - /// Returns at most 20 items. - async fn blockchain(&self, min: H, max: H) -> Result - where - H: Into + Send, - { - // TODO(tarcieri): return errors for invalid params before making request? - self.perform(blockchain::Request::new(min.into(), max.into())) - .await - } - - /// `/broadcast_tx_async`: broadcast a transaction, returning immediately. - async fn broadcast_tx_async(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_async::Request::new(tx)).await - } - - /// `/broadcast_tx_sync`: broadcast a transaction, returning the response - /// from `CheckTx`. - async fn broadcast_tx_sync(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_sync::Request::new(tx)).await - } - - /// `/broadcast_tx_commit`: broadcast a transaction, returning the response - /// from `DeliverTx`. - async fn broadcast_tx_commit(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_commit::Request::new(tx)).await - } - - /// `/commit`: get block commit at a given height. - async fn commit(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(commit::Request::new(height.into())).await - } - - /// `/consensus_params`: get current consensus parameters at the specified - /// height. - async fn consensus_params(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(consensus_params::Request::new(Some(height.into()))) - .await - } - - /// `/consensus_state`: get current consensus state - async fn consensus_state(&self) -> Result { - self.perform(consensus_state::Request::new()).await - } - - // TODO(thane): Simplify once validators endpoint removes pagination. - /// `/validators`: get validators a given height. - async fn validators(&self, height: H, paging: Paging) -> Result - where - H: Into + Send, - { - let height = height.into(); - match paging { - Paging::Default => { - self.perform(validators::Request::new(Some(height), None, None)) - .await - }, - Paging::Specific { - page_number, - per_page, - } => { - self.perform(validators::Request::new( - Some(height), - Some(page_number), - Some(per_page), - )) - .await - }, - Paging::All => { - let mut page_num = 1_usize; - let mut validators = Vec::new(); - let per_page = DEFAULT_VALIDATORS_PER_PAGE.into(); - loop { - let response = self - .perform(validators::Request::new( - Some(height), - Some(page_num.into()), - Some(per_page), - )) - .await?; - validators.extend(response.validators); - if validators.len() as i32 == response.total { - return Ok(validators::Response::new( - response.block_height, - validators, - response.total, - )); - } - page_num += 1; - } - }, - } - } - - /// `/consensus_params`: get the latest consensus parameters. - async fn latest_consensus_params(&self) -> Result { - self.perform(consensus_params::Request::new(None)).await - } - - /// `/commit`: get the latest block commit - async fn latest_commit(&self) -> Result { - self.perform(commit::Request::default()).await - } - - /// `/health`: get node health. - /// - /// Returns empty result (200 OK) on success, no response in case of an error. - async fn health(&self) -> Result<(), Error> { - self.perform(health::Request).await?; - Ok(()) - } - - /// `/genesis`: get genesis file. - async fn genesis(&self) -> Result, Error> - where - AppState: fmt::Debug + Serialize + DeserializeOwned + Send, - { - Ok(self.perform(genesis::Request::default()).await?.genesis) - } - - /// `/net_info`: obtain information about P2P and other network connections. - async fn net_info(&self) -> Result { - self.perform(net_info::Request).await - } - - /// `/status`: get Tendermint status including node info, pubkey, latest - /// block hash, app hash, block height and time. - async fn status(&self) -> Result { - self.perform(status::Request).await - } - - /// `/broadcast_evidence`: broadcast an evidence. - async fn broadcast_evidence(&self, e: Evidence) -> Result { - self.perform(evidence::Request::new(e)).await - } - - /// `/tx`: find transaction by hash. - async fn tx(&self, hash: Hash, prove: bool) -> Result { - self.perform(tx::Request::new(hash, prove)).await - } - - /// `/tx_search`: search for transactions with their results. - async fn tx_search( - &self, - query: Query, - prove: bool, - page: u32, - per_page: u8, - order: Order, - ) -> Result { - self.perform(tx_search::Request::new(query, prove, page, per_page, order)) - .await - } - - /// Poll the `/health` endpoint until it returns a successful result or - /// the given `timeout` has elapsed. - async fn wait_until_healthy(&self, timeout: T) -> Result<(), Error> - where - T: Into + Send, - { - let timeout = timeout.into(); - let poll_interval = Duration::from_millis(200); - let mut attempts_remaining = timeout.as_millis() / poll_interval.as_millis(); - - while self.health().await.is_err() { - if attempts_remaining == 0 { - return Err(Error::timeout(timeout)); - } - - attempts_remaining -= 1; - time::sleep(poll_interval).await; - } - - Ok(()) - } - - /// Perform a request against the RPC endpoint - async fn perform(&self, request: R) -> Result - where - R: SimpleRequest; -} diff --git a/rpc/src/v0_37.rs b/rpc/src/v0_37.rs deleted file mode 100644 index bab85f704..000000000 --- a/rpc/src/v0_37.rs +++ /dev/null @@ -1,13 +0,0 @@ -#[cfg(any(feature = "http-client", feature = "websocket-client"))] -mod client; -#[cfg(any(feature = "http-client", feature = "websocket-client"))] -pub use client::Client; - -pub mod dialect; -pub use dialect::Dialect; - -#[cfg(feature = "websocket-client")] -pub type WebSocketClient = crate::client::WebSocketClient; - -#[cfg(feature = "websocket-client")] -pub type WebSocketClientDriver = crate::client::WebSocketClientDriver; diff --git a/rpc/src/v0_37/client.rs b/rpc/src/v0_37/client.rs deleted file mode 100644 index 072b1ace0..000000000 --- a/rpc/src/v0_37/client.rs +++ /dev/null @@ -1,311 +0,0 @@ -//! The v0.37 RPC client interface. - -use core::{fmt, time::Duration}; - -use async_trait::async_trait; -use serde::{de::DeserializeOwned, Serialize}; -use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; -use tokio::time; - -use super::dialect::Dialect; -use crate::{ - endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, - paging::Paging, - prelude::*, - query::Query, - Error, Order, SimpleRequest, -}; - -/// Provides lightweight access to the Tendermint RPC. It gives access to all -/// endpoints with the exception of the event subscription-related ones. -/// -/// To access event subscription capabilities, use a client that implements the -/// [`SubscriptionClient`] trait. -/// -/// [`SubscriptionClient`]: trait.SubscriptionClient.html -#[async_trait] -pub trait Client { - /// `/abci_info`: get information about the ABCI application. - async fn abci_info(&self) -> Result { - Ok(self.perform(abci_info::Request).await?.response) - } - - /// `/abci_query`: query the ABCI application - async fn abci_query( - &self, - path: Option, - data: V, - height: Option, - prove: bool, - ) -> Result - where - V: Into> + Send, - { - Ok(self - .perform(abci_query::Request::new(path, data, height, prove)) - .await? - .response) - } - - /// `/block`: get block at a given height. - async fn block(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(block::Request::new(height.into())).await - } - - /// `/block_by_hash`: get block by hash. - async fn block_by_hash( - &self, - hash: tendermint::Hash, - ) -> Result { - self.perform(block_by_hash::Request::new(hash)).await - } - - /// `/block`: get the latest block. - async fn latest_block(&self) -> Result { - self.perform(block::Request::default()).await - } - - /// `/header`: get block header at a given height. - async fn header(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(header::Request::new(height.into())).await - } - - /// `/header_by_hash`: get block by hash. - async fn header_by_hash( - &self, - hash: tendermint::Hash, - ) -> Result { - self.perform(header_by_hash::Request::new(hash)).await - } - - /// `/block_results`: get ABCI results for a block at a particular height. - async fn block_results(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(block_results::Request::new(height.into())) - .await - } - - /// `/block_results`: get ABCI results for the latest block. - async fn latest_block_results(&self) -> Result { - self.perform(block_results::Request::default()).await - } - - /// `/block_search`: search for blocks by BeginBlock and EndBlock events. - async fn block_search( - &self, - query: Query, - page: u32, - per_page: u8, - order: Order, - ) -> Result { - self.perform(block_search::Request::new(query, page, per_page, order)) - .await - } - - /// `/blockchain`: get block headers for `min` <= `height` <= `max`. - /// - /// Block headers are returned in descending order (highest first). - /// - /// Returns at most 20 items. - async fn blockchain(&self, min: H, max: H) -> Result - where - H: Into + Send, - { - // TODO(tarcieri): return errors for invalid params before making request? - self.perform(blockchain::Request::new(min.into(), max.into())) - .await - } - - /// `/broadcast_tx_async`: broadcast a transaction, returning immediately. - async fn broadcast_tx_async(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_async::Request::new(tx)).await - } - - /// `/broadcast_tx_sync`: broadcast a transaction, returning the response - /// from `CheckTx`. - async fn broadcast_tx_sync(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_sync::Request::new(tx)).await - } - - /// `/broadcast_tx_commit`: broadcast a transaction, returning the response - /// from `DeliverTx`. - async fn broadcast_tx_commit(&self, tx: T) -> Result - where - T: Into> + Send, - { - self.perform(broadcast::tx_commit::Request::new(tx)).await - } - - /// `/commit`: get block commit at a given height. - async fn commit(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(commit::Request::new(height.into())).await - } - - /// `/consensus_params`: get current consensus parameters at the specified - /// height. - async fn consensus_params(&self, height: H) -> Result - where - H: Into + Send, - { - self.perform(consensus_params::Request::new(Some(height.into()))) - .await - } - - /// `/consensus_state`: get current consensus state - async fn consensus_state(&self) -> Result { - self.perform(consensus_state::Request::new()).await - } - - // TODO(thane): Simplify once validators endpoint removes pagination. - /// `/validators`: get validators a given height. - async fn validators(&self, height: H, paging: Paging) -> Result - where - H: Into + Send, - { - let height = height.into(); - match paging { - Paging::Default => { - self.perform(validators::Request::new(Some(height), None, None)) - .await - }, - Paging::Specific { - page_number, - per_page, - } => { - self.perform(validators::Request::new( - Some(height), - Some(page_number), - Some(per_page), - )) - .await - }, - Paging::All => { - let mut page_num = 1_usize; - let mut validators = Vec::new(); - let per_page = DEFAULT_VALIDATORS_PER_PAGE.into(); - loop { - let response = self - .perform(validators::Request::new( - Some(height), - Some(page_num.into()), - Some(per_page), - )) - .await?; - validators.extend(response.validators); - if validators.len() as i32 == response.total { - return Ok(validators::Response::new( - response.block_height, - validators, - response.total, - )); - } - page_num += 1; - } - }, - } - } - - /// `/consensus_params`: get the latest consensus parameters. - async fn latest_consensus_params(&self) -> Result { - self.perform(consensus_params::Request::new(None)).await - } - - /// `/commit`: get the latest block commit - async fn latest_commit(&self) -> Result { - self.perform(commit::Request::default()).await - } - - /// `/health`: get node health. - /// - /// Returns empty result (200 OK) on success, no response in case of an error. - async fn health(&self) -> Result<(), Error> { - self.perform(health::Request).await?; - Ok(()) - } - - /// `/genesis`: get genesis file. - async fn genesis(&self) -> Result, Error> - where - AppState: fmt::Debug + Serialize + DeserializeOwned + Send, - { - Ok(self.perform(genesis::Request::default()).await?.genesis) - } - - /// `/net_info`: obtain information about P2P and other network connections. - async fn net_info(&self) -> Result { - self.perform(net_info::Request).await - } - - /// `/status`: get Tendermint status including node info, pubkey, latest - /// block hash, app hash, block height and time. - async fn status(&self) -> Result { - self.perform(status::Request).await - } - - /// `/broadcast_evidence`: broadcast an evidence. - async fn broadcast_evidence(&self, e: Evidence) -> Result { - self.perform(evidence::Request::new(e)).await - } - - /// `/tx`: find transaction by hash. - async fn tx(&self, hash: Hash, prove: bool) -> Result { - self.perform(tx::Request::new(hash, prove)).await - } - - /// `/tx_search`: search for transactions with their results. - async fn tx_search( - &self, - query: Query, - prove: bool, - page: u32, - per_page: u8, - order: Order, - ) -> Result { - self.perform(tx_search::Request::new(query, prove, page, per_page, order)) - .await - } - - /// Poll the `/health` endpoint until it returns a successful result or - /// the given `timeout` has elapsed. - async fn wait_until_healthy(&self, timeout: T) -> Result<(), Error> - where - T: Into + Send, - { - let timeout = timeout.into(); - let poll_interval = Duration::from_millis(200); - let mut attempts_remaining = timeout.as_millis() / poll_interval.as_millis(); - - while self.health().await.is_err() { - if attempts_remaining == 0 { - return Err(Error::timeout(timeout)); - } - - attempts_remaining -= 1; - time::sleep(poll_interval).await; - } - - Ok(()) - } - - /// Perform a request against the RPC endpoint - async fn perform(&self, request: R) -> Result - where - R: SimpleRequest; -} diff --git a/rpc/tests/gaia_fixtures.rs b/rpc/tests/gaia_fixtures.rs index ffc4f9d30..c6aa90c13 100644 --- a/rpc/tests/gaia_fixtures.rs +++ b/rpc/tests/gaia_fixtures.rs @@ -1,7 +1,7 @@ use std::{fs, path::PathBuf}; // TODO: generate fixtures and test with v0_37::dialect as well -use tendermint_rpc::v0_34::dialect::Event as RpcEvent; +use tendermint_rpc::dialect::v0_34::Event as RpcEvent; use tendermint_rpc::{endpoint, event::DialectEvent, request::RequestMessage, Response}; use walkdir::WalkDir; diff --git a/rpc/tests/kvstore_fixtures.rs b/rpc/tests/kvstore_fixtures.rs index 44c05a3a2..a62322c8b 100644 --- a/rpc/tests/kvstore_fixtures.rs +++ b/rpc/tests/kvstore_fixtures.rs @@ -299,7 +299,7 @@ fn outgoing_fixtures() { #[test] fn incoming_fixtures() { // TODO: generate fixtures and test with v0_37::dialect as well - use tendermint_rpc::v0_34::dialect::Event as RpcEvent; + use tendermint_rpc::dialect::v0_34::Event as RpcEvent; let empty_merkle_root_hash = Some( tendermint::Hash::from_hex_upper( From 1c1432ed324b6db58f82faa24b2114f3041f9a3b Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 20 Feb 2023 16:40:12 +0200 Subject: [PATCH 56/77] rpc: Add client::compat::discover A utility function to discover the compatibility mode using a pre-instantiated RPC client. This has a bit of a chicken-and-egg problem, but it should work in practice as long as it's the first operation done for the client. HttpClient gets a set_compat_mode method to update the mode on the fly. No such thing is provided for WebSocketClient, though, because the compat mode is set into the subscription driver and cannot be updated. --- rpc/Cargo.toml | 3 +++ rpc/src/client.rs | 2 +- rpc/src/client/compat.rs | 29 +++++++++++++++++++++++++++++ rpc/src/client/transport/http.rs | 9 +++++++++ rpc/src/error.rs | 15 +++++++++++++++ tendermint/src/version.rs | 6 ++++++ 6 files changed, 63 insertions(+), 1 deletion(-) diff --git a/rpc/Cargo.toml b/rpc/Cargo.toml index 432ac36fc..03c472927 100644 --- a/rpc/Cargo.toml +++ b/rpc/Cargo.toml @@ -43,6 +43,7 @@ http-client = [ "hyper", "hyper-proxy", "hyper-rustls", + "semver", "tokio/fs", "tokio/macros", "tracing" @@ -53,6 +54,7 @@ websocket-client = [ "async-tungstenite", "futures", "http", + "semver", "tokio/rt-multi-thread", "tokio/fs", "tokio/macros", @@ -88,6 +90,7 @@ http = { version = "0.2", optional = true, default-features = false } hyper = { version = "0.14", optional = true, default-features = false, features = ["client", "http1", "http2"] } hyper-proxy = { version = "0.9.1", optional = true, default-features = false, features = ["rustls"] } hyper-rustls = { version = "0.22.1", optional = true, default-features = false, features = ["rustls-native-certs", "webpki-roots", "tokio-runtime"] } +semver = { version = "1.0", optional = true, default-features = false } structopt = { version = "0.3", optional = true, default-features = false } tokio = { version = "1.0", optional = true, default-features = false, features = ["rt-multi-thread"] } tracing = { version = "0.1", optional = true, default-features = false } diff --git a/rpc/src/client.rs b/rpc/src/client.rs index c4081ddd0..b75911e97 100644 --- a/rpc/src/client.rs +++ b/rpc/src/client.rs @@ -1,6 +1,6 @@ //! Tendermint RPC client. -mod compat; +pub mod compat; pub use compat::CompatMode; mod subscription; pub use subscription::{Subscription, SubscriptionClient}; diff --git a/rpc/src/client/compat.rs b/rpc/src/client/compat.rs index e61ce62f4..e37971cf8 100644 --- a/rpc/src/client/compat.rs +++ b/rpc/src/client/compat.rs @@ -1,5 +1,9 @@ //! Support for dynamic compatibility with older protocol versions. +use super::Client; +use crate::prelude::*; +use crate::Error; + /// Protocol compatibility mode for a Tendermint RPC client. #[derive(Copy, Clone, Debug, PartialEq, Eq)] pub enum CompatMode { @@ -14,3 +18,28 @@ impl Default for CompatMode { CompatMode::Latest } } + +/// Queries the `/status` RPC endpoint to discover which compatibility mode +/// to use for the node that this client connects to. +/// +/// Note that this is not fail-proof: the version is reported for a particular +/// client connection, so any other connections to the same URL might not +/// be handled by the same server. In the future, the RPC protocol should +/// follow versioning practices designed to avoid ambiguities with +/// message formats. +pub async fn discover(client: &C) -> Result +where + C: Client + Send + Sync, +{ + let status = client.status().await?; + let raw_version: String = status.node_info.version.into(); + let tm_version = semver::Version::parse(&raw_version) + .map_err(|_| Error::invalid_tendermint_version(raw_version))?; + match (tm_version.major, tm_version.minor) { + (0, 34) => Ok(CompatMode::V0_34), + (0, 37) => Ok(CompatMode::Latest), + _ => Err(Error::unsupported_tendermint_version( + tm_version.to_string(), + )), + } +} diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index 9b4496064..13df4299c 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -130,6 +130,15 @@ impl HttpClient { } } + /// Set compatibility mode on the instantiated client. + /// + /// As the HTTP client is stateless and does not support subscriptions, + /// the protocol version it uses can be changed at will, for example, + /// as a result of version discovery over the `/status` endpoint. + pub fn set_compat_mode(&mut self, compat: CompatMode) { + self.compat = compat; + } + async fn perform_v0_34(&self, request: R) -> Result where R: SimpleRequest, diff --git a/rpc/src/error.rs b/rpc/src/error.rs index 3c9ff4435..c1119708b 100644 --- a/rpc/src/error.rs +++ b/rpc/src/error.rs @@ -203,6 +203,21 @@ define_error! { e.version, e.supported) }, + InvalidTendermintVersion + { + version: String, + } + | e | { + format_args!("invalid Tendermint version reported by the node: {}", e.version) + }, + + UnsupportedTendermintVersion + { + version: String, + } + | e | { + format_args!("unsupported Tendermint version reported by the node: {}", e.version) + }, } } diff --git a/tendermint/src/version.rs b/tendermint/src/version.rs index f814edf6c..364f5f6a9 100644 --- a/tendermint/src/version.rs +++ b/tendermint/src/version.rs @@ -13,3 +13,9 @@ impl Display for Version { write!(f, "{}", self.0) } } + +impl From for String { + fn from(value: Version) -> Self { + value.0 + } +} From b587e6e86717593bb0e4aa0a17cf775d801b152f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 20 Feb 2023 16:55:17 +0200 Subject: [PATCH 57/77] rpc: unit test for CompatMode version parsing --- rpc/src/client/compat.rs | 48 ++++++++++++++++++++++++++++++++-------- 1 file changed, 39 insertions(+), 9 deletions(-) diff --git a/rpc/src/client/compat.rs b/rpc/src/client/compat.rs index e37971cf8..d641e7562 100644 --- a/rpc/src/client/compat.rs +++ b/rpc/src/client/compat.rs @@ -19,6 +19,18 @@ impl Default for CompatMode { } } +impl CompatMode { + fn from_tendermint_version(raw_version: String) -> Result { + let version = semver::Version::parse(&raw_version) + .map_err(|_| Error::invalid_tendermint_version(raw_version))?; + match (version.major, version.minor) { + (0, 34) => Ok(CompatMode::V0_34), + (0, 37) => Ok(CompatMode::Latest), + _ => Err(Error::unsupported_tendermint_version(version.to_string())), + } + } +} + /// Queries the `/status` RPC endpoint to discover which compatibility mode /// to use for the node that this client connects to. /// @@ -32,14 +44,32 @@ where C: Client + Send + Sync, { let status = client.status().await?; - let raw_version: String = status.node_info.version.into(); - let tm_version = semver::Version::parse(&raw_version) - .map_err(|_| Error::invalid_tendermint_version(raw_version))?; - match (tm_version.major, tm_version.minor) { - (0, 34) => Ok(CompatMode::V0_34), - (0, 37) => Ok(CompatMode::Latest), - _ => Err(Error::unsupported_tendermint_version( - tm_version.to_string(), - )), + CompatMode::from_tendermint_version(status.node_info.version.into()) +} + +#[cfg(test)] +mod tests { + use super::CompatMode; + + #[test] + fn test_parse_version_for_compat_mode() { + assert_eq!( + CompatMode::from_tendermint_version("0.34.16".into()).unwrap(), + CompatMode::V0_34 + ); + assert_eq!( + CompatMode::from_tendermint_version("0.37.0-pre1".into()).unwrap(), + CompatMode::Latest + ); + assert_eq!( + CompatMode::from_tendermint_version("0.37.0".into()).unwrap(), + CompatMode::Latest + ); + let res = CompatMode::from_tendermint_version("0.38.0".into()); + assert!(res.is_err()); + let res = CompatMode::from_tendermint_version("1.0.0".into()); + assert!(res.is_err()); + let res = CompatMode::from_tendermint_version("poobah".into()); + assert!(res.is_err()); } } From 7691ba07ac373e0530d83d7ad01795b14f358e0f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 20 Feb 2023 18:15:50 +0200 Subject: [PATCH 58/77] rpc: make WebSocketConfig struct more usable Make the fileds public, derive Debug. --- rpc/src/client/transport/websocket.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index a153a29ef..880fb2412 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -56,12 +56,12 @@ const RECV_TIMEOUT: Duration = Duration::from_secs(RECV_TIMEOUT_SECONDS); // Taken from https://github.com/tendermint/tendermint/blob/309e29c245a01825fc9630103311fd04de99fa5e/rpc/jsonrpc/server/ws_handler.go#L28 const PING_INTERVAL: Duration = Duration::from_secs((RECV_TIMEOUT_SECONDS * 9) / 10); -#[derive(Default)] +#[derive(Default, Debug)] /// WebSocket client configuration pub struct WebSocketConfig { - compat: CompatMode, + pub compat: CompatMode, /// Low-level protocol configuration - transport: Option, + pub transport: Option, } /// Tendermint RPC client that provides access to all RPC functionality From 3866d0e1275454dc8204f4fc23022193d53ae7f9 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 20 Feb 2023 19:17:51 +0200 Subject: [PATCH 59/77] rpc: expose CompatMode::from_version Erase client::compat::discover. If the client has other reasons to call `/status`, they can derive CompatMode from the version field in the response. --- rpc/src/client/compat.rs | 54 ++++++++++++++++++++++------------------ 1 file changed, 30 insertions(+), 24 deletions(-) diff --git a/rpc/src/client/compat.rs b/rpc/src/client/compat.rs index d641e7562..c8209031d 100644 --- a/rpc/src/client/compat.rs +++ b/rpc/src/client/compat.rs @@ -1,6 +1,7 @@ //! Support for dynamic compatibility with older protocol versions. -use super::Client; +use tendermint::Version; + use crate::prelude::*; use crate::Error; @@ -20,7 +21,21 @@ impl Default for CompatMode { } impl CompatMode { - fn from_tendermint_version(raw_version: String) -> Result { + /// Parse the Tendermint version string to determine + /// the compatibility mode. + /// + /// The version can be obtained by querying the `/status` endpoint. + /// The request and response format of this endpoint is currently the same + /// for all supported RPC dialects, so such a request can be performed + /// before the required compatibility mode is settled upon. + /// + /// Note that this is not fail-proof: the version is reported for a particular + /// client connection, so any other connections to the same URL might not + /// be handled by the same server. In the future, the RPC protocol should + /// follow versioning practices designed to avoid ambiguities with + /// message formats. + pub fn from_version(tendermint_version: Version) -> Result { + let raw_version: String = tendermint_version.into(); let version = semver::Version::parse(&raw_version) .map_err(|_| Error::invalid_tendermint_version(raw_version))?; match (version.major, version.minor) { @@ -31,45 +46,36 @@ impl CompatMode { } } -/// Queries the `/status` RPC endpoint to discover which compatibility mode -/// to use for the node that this client connects to. -/// -/// Note that this is not fail-proof: the version is reported for a particular -/// client connection, so any other connections to the same URL might not -/// be handled by the same server. In the future, the RPC protocol should -/// follow versioning practices designed to avoid ambiguities with -/// message formats. -pub async fn discover(client: &C) -> Result -where - C: Client + Send + Sync, -{ - let status = client.status().await?; - CompatMode::from_tendermint_version(status.node_info.version.into()) -} - #[cfg(test)] mod tests { use super::CompatMode; + use crate::prelude::*; + use tendermint::Version; + + fn parse_version(s: &str) -> Version { + let json = format!("\"{s}\""); + serde_json::from_str(&json).unwrap() + } #[test] fn test_parse_version_for_compat_mode() { assert_eq!( - CompatMode::from_tendermint_version("0.34.16".into()).unwrap(), + CompatMode::from_version(parse_version("0.34.16")).unwrap(), CompatMode::V0_34 ); assert_eq!( - CompatMode::from_tendermint_version("0.37.0-pre1".into()).unwrap(), + CompatMode::from_version(parse_version("0.37.0-pre1")).unwrap(), CompatMode::Latest ); assert_eq!( - CompatMode::from_tendermint_version("0.37.0".into()).unwrap(), + CompatMode::from_version(parse_version("0.37.0")).unwrap(), CompatMode::Latest ); - let res = CompatMode::from_tendermint_version("0.38.0".into()); + let res = CompatMode::from_version(parse_version("0.38.0")); assert!(res.is_err()); - let res = CompatMode::from_tendermint_version("1.0.0".into()); + let res = CompatMode::from_version(parse_version("1.0.0")); assert!(res.is_err()); - let res = CompatMode::from_tendermint_version("poobah".into()); + let res = CompatMode::from_version(parse_version("poobah")); assert!(res.is_err()); } } From 62f6e5deada3c50f8e3200120174449c7467bdde Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 20 Feb 2023 19:44:07 +0200 Subject: [PATCH 60/77] rpc: make mod client::compat private CompatMode is the only thing exposed, and it's re-exported at client. --- rpc/src/client.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rpc/src/client.rs b/rpc/src/client.rs index b75911e97..c4081ddd0 100644 --- a/rpc/src/client.rs +++ b/rpc/src/client.rs @@ -1,6 +1,6 @@ //! Tendermint RPC client. -pub mod compat; +mod compat; pub use compat::CompatMode; mod subscription; pub use subscription::{Subscription, SubscriptionClient}; From 4c55808092c6ebaf39f6290716980b5e28545896 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 20 Feb 2023 20:58:51 +0200 Subject: [PATCH 61/77] rpc: account for "v" prefixing Tendermint version --- rpc/src/client/compat.rs | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/rpc/src/client/compat.rs b/rpc/src/client/compat.rs index c8209031d..778b20832 100644 --- a/rpc/src/client/compat.rs +++ b/rpc/src/client/compat.rs @@ -36,7 +36,7 @@ impl CompatMode { /// message formats. pub fn from_version(tendermint_version: Version) -> Result { let raw_version: String = tendermint_version.into(); - let version = semver::Version::parse(&raw_version) + let version = semver::Version::parse(raw_version.trim_start_matches('v')) .map_err(|_| Error::invalid_tendermint_version(raw_version))?; match (version.major, version.minor) { (0, 34) => Ok(CompatMode::V0_34), @@ -60,20 +60,20 @@ mod tests { #[test] fn test_parse_version_for_compat_mode() { assert_eq!( - CompatMode::from_version(parse_version("0.34.16")).unwrap(), + CompatMode::from_version(parse_version("v0.34.16")).unwrap(), CompatMode::V0_34 ); assert_eq!( - CompatMode::from_version(parse_version("0.37.0-pre1")).unwrap(), + CompatMode::from_version(parse_version("v0.37.0-pre1")).unwrap(), CompatMode::Latest ); assert_eq!( - CompatMode::from_version(parse_version("0.37.0")).unwrap(), + CompatMode::from_version(parse_version("v0.37.0")).unwrap(), CompatMode::Latest ); - let res = CompatMode::from_version(parse_version("0.38.0")); + let res = CompatMode::from_version(parse_version("v0.38.0")); assert!(res.is_err()); - let res = CompatMode::from_version(parse_version("1.0.0")); + let res = CompatMode::from_version(parse_version("v1.0.0")); assert!(res.is_err()); let res = CompatMode::from_version(parse_version("poobah")); assert!(res.is_err()); From b526b2ab06aa1a874bd082c811d3960621781eae Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 21 Feb 2023 11:50:04 +0200 Subject: [PATCH 62/77] rpc: fix websocket tests The coverage of fixture-based tests is still exclusive to the v0_34 dialect. --- rpc/src/client/transport/websocket.rs | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 880fb2412..e9cde6ef8 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -974,7 +974,7 @@ mod test { use super::*; use crate::{client::sync::unbounded, query::EventType, request, Id, Method}; - // TODO: test with v0_37::dialect as well + // TODO: test with dialect::v0_37 as well use crate::dialect::v0_34::Event as RpcEvent; // Interface to a driver that manages all incoming WebSocket connections. @@ -1280,9 +1280,15 @@ mod test { println!("Starting WebSocket server..."); let mut server = TestServer::new("127.0.0.1:0").await; println!("Creating client RPC WebSocket connection..."); - let (client, driver) = WebSocketClient::new(server.node_addr.clone()) - .await - .unwrap(); + let (client, driver) = WebSocketClient::new_with_config( + server.node_addr.clone(), + WebSocketConfig { + compat: CompatMode::V0_34, + ..Default::default() + }, + ) + .await + .unwrap(); let driver_handle = tokio::spawn(async move { driver.run().await }); println!("Initiating subscription for new blocks..."); From c6c5aa6a89c7183d16d3bfab2b9cc1077603d4a8 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Thu, 23 Feb 2023 14:33:23 +0200 Subject: [PATCH 63/77] rpc: debug received events in WebSocketTransport --- rpc/src/client/transport/websocket.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index e9cde6ef8..8c3665c7b 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -837,6 +837,7 @@ impl WebSocketClientDriver { CompatMode::V0_34 => DialectEvent::::from_string(&msg).map(Into::into), }; if let Ok(ev) = parse_res { + debug!("JSON-RPC event: {}", msg); self.publish_event(ev).await; return Ok(()); } From f0d9e6a2ecf71e9d3b3b8a3cbb07159384ffe47e Mon Sep 17 00:00:00 2001 From: Romain Ruetschi Date: Thu, 23 Feb 2023 17:27:16 +0100 Subject: [PATCH 64/77] Quick fix for running `rpc-probe` against a Comet 0.37 node --- tools/rpc-probe/Makefile.toml | 5 +++-- tools/rpc-probe/src/kvstore.rs | 6 +++++- tools/rpc-probe/src/plan.rs | 2 ++ 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/tools/rpc-probe/Makefile.toml b/tools/rpc-probe/Makefile.toml index 1c71a74c3..bb4d28c19 100644 --- a/tools/rpc-probe/Makefile.toml +++ b/tools/rpc-probe/Makefile.toml @@ -1,8 +1,9 @@ [env] CONTAINER_NAME = "kvstore-rpc-probe" -DOCKER_IMAGE = "informaldev/tendermint:0.34.21" +DOCKER_IMAGE = "cometbft/cometbft:v0.37.x" HOST_RPC_PORT = 26657 CARGO_MAKE_WAIT_MILLISECONDS = 3500 +OUTPUT_DIR = "fixtures" [tasks.default] clear = true @@ -10,7 +11,7 @@ dependencies = [ "docker-up", "wait", "run", "docker-down" ] [tasks.run] command = "cargo" -args = ["run", "kvstore"] +args = ["run", "--", "--verbose", "--output", "${OUTPUT_DIR}", "kvstore"] [tasks.docker-down] dependencies = [ "docker-stop", "docker-rm" ] diff --git a/tools/rpc-probe/src/kvstore.rs b/tools/rpc-probe/src/kvstore.rs index f6186cc51..4fac5be26 100644 --- a/tools/rpc-probe/src/kvstore.rs +++ b/tools/rpc-probe/src/kvstore.rs @@ -26,8 +26,12 @@ pub fn quick_probe_plan(output_path: &Path, request_wait: Duration) -> Result 1", 1, 100, "asc").with_name("block_search"), blockchain(1, 10).with_name("blockchain_from_1_to_10"), commit(10).with_name("commit_at_height_10"), diff --git a/tools/rpc-probe/src/plan.rs b/tools/rpc-probe/src/plan.rs index 982ef9a09..6212cc680 100644 --- a/tools/rpc-probe/src/plan.rs +++ b/tools/rpc-probe/src/plan.rs @@ -369,6 +369,8 @@ async fn execute_request( request: Request, ) -> Result<()> { let request_json = request.as_json(); + debug!("Sending outgoing request: {}", request_json); + write_json(&config.out_path, name, &request_json).await?; let response_json = match client.request(&request_json).await { Ok(r) => { From 4f8f1226045438d4d92404e1afb8d61aa127f7a4 Mon Sep 17 00:00:00 2001 From: Romain Ruetschi Date: Thu, 23 Feb 2023 17:30:44 +0100 Subject: [PATCH 65/77] Fix doc for overriding env variable in rpc-probe README --- tools/rpc-probe/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/rpc-probe/README.md b/tools/rpc-probe/README.md index 2cd62b654..f7679452e 100644 --- a/tools/rpc-probe/README.md +++ b/tools/rpc-probe/README.md @@ -37,7 +37,7 @@ This will: To run a specific version of Tendermint, simply: ```bash -DOCKER_IMAGE="informaldev/tendermint:v0.34.0" cargo make +cargo make --env DOCKER_IMAGE="informaldev/tendermint:v0.34.0" ``` ## Usage (without Docker) From ab8b54e045140e9af2344ca7d25ddca0ea8230d9 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Fri, 24 Feb 2023 18:48:25 +0200 Subject: [PATCH 66/77] rpc: added kvstore test fixtures for 0.37 Obtained with rpc-probe against a Docker image cometbft/cometbft:v0.37.x (ID 4ab97039d4c42dd67e62ecfe72307e1552f9b9c0e48ec15958197d637f1fdde9). The fixtures for 0.34 have been moved alongside. --- rpc/tests/kvstore_fixtures.rs | 1406 +--- rpc/tests/kvstore_fixtures/v0_34.rs | 1412 ++++ .../{ => v0_34}/incoming/abci_info.json | 0 .../abci_query_with_existing_key.json | 0 .../abci_query_with_non_existent_key.json | 0 .../incoming/block_at_height_0.json | 0 .../incoming/block_at_height_1.json | 0 .../incoming/block_at_height_10.json | 0 .../{ => v0_34}/incoming/block_by_hash.json | 0 .../incoming/block_results_at_height_10.json | 0 .../{ => v0_34}/incoming/block_search.json | 0 .../incoming/block_search_evidence.json | 0 .../incoming/blockchain_from_1_to_10.json | 0 .../incoming/broadcast_tx_async.json | 0 .../incoming/broadcast_tx_commit.json | 0 .../incoming/broadcast_tx_sync.json | 0 .../incoming/commit_at_height_10.json | 0 .../incoming/consensus_params.json | 0 .../{ => v0_34}/incoming/consensus_state.json | 0 .../{ => v0_34}/incoming/genesis.json | 0 .../{ => v0_34}/incoming/net_info.json | 0 .../{ => v0_34}/incoming/status.json | 0 .../incoming/subscribe_malformed.json | 0 .../incoming/subscribe_newblock.json | 0 .../incoming/subscribe_newblock_0.json | 0 .../incoming/subscribe_newblock_1.json | 0 .../incoming/subscribe_newblock_2.json | 0 .../incoming/subscribe_newblock_3.json | 0 .../incoming/subscribe_newblock_4.json | 0 .../{ => v0_34}/incoming/subscribe_txs.json | 0 .../{ => v0_34}/incoming/subscribe_txs_0.json | 0 .../{ => v0_34}/incoming/subscribe_txs_1.json | 0 .../{ => v0_34}/incoming/subscribe_txs_2.json | 0 .../{ => v0_34}/incoming/subscribe_txs_3.json | 0 .../{ => v0_34}/incoming/subscribe_txs_4.json | 0 .../subscribe_txs_broadcast_tx_0.json | 0 .../subscribe_txs_broadcast_tx_1.json | 0 .../subscribe_txs_broadcast_tx_2.json | 0 .../subscribe_txs_broadcast_tx_3.json | 0 .../subscribe_txs_broadcast_tx_4.json | 0 .../subscribe_txs_broadcast_tx_5.json | 0 .../{ => v0_34}/incoming/tx.json | 0 .../incoming/tx_search_no_prove.json | 0 .../incoming/tx_search_with_prove.json | 0 .../{ => v0_34}/outgoing/abci_info.json | 0 .../abci_query_with_existing_key.json | 0 .../abci_query_with_non_existent_key.json | 0 .../outgoing/block_at_height_0.json | 0 .../outgoing/block_at_height_1.json | 0 .../outgoing/block_at_height_10.json | 0 .../{ => v0_34}/outgoing/block_by_hash.json | 0 .../outgoing/block_results_at_height_10.json | 0 .../{ => v0_34}/outgoing/block_search.json | 0 .../outgoing/blockchain_from_1_to_10.json | 0 .../outgoing/broadcast_tx_async.json | 0 .../outgoing/broadcast_tx_commit.json | 0 .../outgoing/broadcast_tx_sync.json | 0 .../outgoing/commit_at_height_10.json | 0 .../outgoing/consensus_params.json | 0 .../{ => v0_34}/outgoing/consensus_state.json | 0 .../{ => v0_34}/outgoing/genesis.json | 0 .../{ => v0_34}/outgoing/net_info.json | 0 .../{ => v0_34}/outgoing/status.json | 0 .../outgoing/subscribe_malformed.json | 0 .../outgoing/subscribe_newblock.json | 0 .../{ => v0_34}/outgoing/subscribe_txs.json | 0 .../subscribe_txs_broadcast_tx_0.json | 0 .../subscribe_txs_broadcast_tx_1.json | 0 .../subscribe_txs_broadcast_tx_2.json | 0 .../subscribe_txs_broadcast_tx_3.json | 0 .../subscribe_txs_broadcast_tx_4.json | 0 .../subscribe_txs_broadcast_tx_5.json | 0 .../{ => v0_34}/outgoing/tx.json | 0 .../outgoing/tx_search_no_prove.json | 0 .../outgoing/tx_search_with_prove.json | 0 rpc/tests/kvstore_fixtures/v0_37.rs | 1396 ++++ .../v0_37/incoming/abci_info.json | 13 + .../abci_query_with_existing_key.json | 17 + .../abci_query_with_non_existent_key.json | 17 + .../v0_37/incoming/block_at_height_0.json | 9 + .../v0_37/incoming/block_at_height_1.json | 58 + .../v0_37/incoming/block_at_height_10.json | 65 + .../v0_37/incoming/block_by_hash.json | 14 + .../incoming/block_results_at_height_10.json | 12 + .../v0_37/incoming/block_search.json | 6109 +++++++++++++++++ .../incoming/blockchain_from_1_to_10.json | 369 + .../v0_37/incoming/broadcast_tx_async.json | 11 + .../v0_37/incoming/broadcast_tx_commit.json | 82 + .../v0_37/incoming/broadcast_tx_sync.json | 11 + .../v0_37/incoming/commit_at_height_10.json | 53 + .../v0_37/incoming/consensus_params.json | 26 + .../v0_37/incoming/consensus_state.json | 30 + .../v0_37/incoming/genesis.json | 42 + .../v0_37/incoming/net_info.json | 12 + .../v0_37/incoming/status.json | 42 + .../v0_37/incoming/subscribe_malformed.json | 9 + .../v0_37/incoming/subscribe_newblock.json | 1 + .../v0_37/incoming/subscribe_newblock_0.json | 73 + .../v0_37/incoming/subscribe_newblock_1.json | 73 + .../v0_37/incoming/subscribe_newblock_2.json | 73 + .../v0_37/incoming/subscribe_newblock_3.json | 73 + .../v0_37/incoming/subscribe_newblock_4.json | 73 + .../v0_37/incoming/subscribe_txs.json | 5 + .../v0_37/incoming/subscribe_txs_0.json | 97 + .../v0_37/incoming/subscribe_txs_1.json | 97 + .../v0_37/incoming/subscribe_txs_2.json | 97 + .../v0_37/incoming/subscribe_txs_3.json | 97 + .../v0_37/incoming/subscribe_txs_4.json | 97 + .../subscribe_txs_broadcast_tx_0.json | 11 + .../subscribe_txs_broadcast_tx_1.json | 11 + .../subscribe_txs_broadcast_tx_2.json | 11 + .../subscribe_txs_broadcast_tx_3.json | 11 + .../subscribe_txs_broadcast_tx_4.json | 11 + .../subscribe_txs_broadcast_tx_5.json | 11 + .../v0_37/incoming/tx_search_no_prove.json | 612 ++ .../v0_37/incoming/tx_search_with_prove.json | 702 ++ .../v0_37/outgoing/abci_info.json | 6 + .../abci_query_with_existing_key.json | 8 + .../abci_query_with_non_existent_key.json | 8 + .../v0_37/outgoing/block_at_height_0.json | 8 + .../v0_37/outgoing/block_at_height_1.json | 8 + .../v0_37/outgoing/block_at_height_10.json | 8 + .../v0_37/outgoing/block_by_hash.json | 8 + .../outgoing/block_results_at_height_10.json | 8 + .../v0_37/outgoing/block_search.json | 11 + .../outgoing/blockchain_from_1_to_10.json | 9 + .../v0_37/outgoing/broadcast_tx_async.json | 8 + .../v0_37/outgoing/broadcast_tx_commit.json | 8 + .../v0_37/outgoing/broadcast_tx_sync.json | 8 + .../v0_37/outgoing/commit_at_height_10.json | 8 + .../v0_37/outgoing/consensus_params.json | 8 + .../v0_37/outgoing/consensus_state.json | 6 + .../v0_37/outgoing/genesis.json | 6 + .../v0_37/outgoing/net_info.json | 6 + .../v0_37/outgoing/status.json | 6 + .../v0_37/outgoing/subscribe_malformed.json | 8 + .../v0_37/outgoing/subscribe_newblock.json | 8 + .../v0_37/outgoing/subscribe_txs.json | 8 + .../subscribe_txs_broadcast_tx_0.json | 8 + .../subscribe_txs_broadcast_tx_1.json | 8 + .../subscribe_txs_broadcast_tx_2.json | 8 + .../subscribe_txs_broadcast_tx_3.json | 8 + .../subscribe_txs_broadcast_tx_4.json | 8 + .../subscribe_txs_broadcast_tx_5.json | 8 + .../v0_37/outgoing/tx_search_no_prove.json | 12 + .../v0_37/outgoing/tx_search_with_prove.json | 12 + 146 files changed, 12296 insertions(+), 1397 deletions(-) create mode 100644 rpc/tests/kvstore_fixtures/v0_34.rs rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/abci_info.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/abci_query_with_existing_key.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/abci_query_with_non_existent_key.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/block_at_height_0.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/block_at_height_1.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/block_at_height_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/block_by_hash.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/block_results_at_height_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/block_search.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/block_search_evidence.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/blockchain_from_1_to_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/broadcast_tx_async.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/broadcast_tx_commit.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/broadcast_tx_sync.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/commit_at_height_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/consensus_params.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/consensus_state.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/genesis.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/net_info.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/status.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_malformed.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_newblock.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_newblock_0.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_newblock_1.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_newblock_2.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_newblock_3.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_newblock_4.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_0.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_1.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_2.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_3.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_4.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_broadcast_tx_0.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_broadcast_tx_1.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_broadcast_tx_2.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_broadcast_tx_3.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_broadcast_tx_4.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/subscribe_txs_broadcast_tx_5.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/tx.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/tx_search_no_prove.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/incoming/tx_search_with_prove.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/abci_info.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/abci_query_with_existing_key.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/abci_query_with_non_existent_key.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/block_at_height_0.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/block_at_height_1.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/block_at_height_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/block_by_hash.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/block_results_at_height_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/block_search.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/blockchain_from_1_to_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/broadcast_tx_async.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/broadcast_tx_commit.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/broadcast_tx_sync.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/commit_at_height_10.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/consensus_params.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/consensus_state.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/genesis.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/net_info.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/status.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_malformed.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_newblock.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_txs.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_txs_broadcast_tx_0.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_txs_broadcast_tx_1.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_txs_broadcast_tx_2.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_txs_broadcast_tx_3.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_txs_broadcast_tx_4.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/subscribe_txs_broadcast_tx_5.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/tx.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/tx_search_no_prove.json (100%) rename rpc/tests/kvstore_fixtures/{ => v0_34}/outgoing/tx_search_with_prove.json (100%) create mode 100644 rpc/tests/kvstore_fixtures/v0_37.rs create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/status.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json create mode 100644 rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json diff --git a/rpc/tests/kvstore_fixtures.rs b/rpc/tests/kvstore_fixtures.rs index a62322c8b..087f3a053 100644 --- a/rpc/tests/kvstore_fixtures.rs +++ b/rpc/tests/kvstore_fixtures.rs @@ -23,11 +23,19 @@ use walkdir::WalkDir; const CHAIN_ID: &str = "dockerchain"; -fn find_fixtures(in_out_folder_name: &str) -> Vec { +// Test modules in the kvstore_fixtures subdirectory +mod kvstore_fixtures { + use super::*; + mod v0_34; + mod v0_37; +} + +fn find_fixtures(ver_folder_name: &str, in_out_folder_name: &str) -> Vec { WalkDir::new( PathBuf::from(env!("CARGO_MANIFEST_DIR")) .join("tests") .join("kvstore_fixtures") + .join(ver_folder_name) .join(in_out_folder_name), ) .into_iter() @@ -41,1402 +49,6 @@ fn find_fixtures(in_out_folder_name: &str) -> Vec { .collect::>() } -#[test] -fn outgoing_fixtures() { - for json_file in find_fixtures("outgoing") { - let file_name = json_file - .file_name() - .unwrap() - .to_str() - .unwrap() - .strip_suffix(".json") - .unwrap(); - let content = fs::read_to_string(&json_file).unwrap(); - match file_name { - "abci_info" => assert!(serde_json::from_str::< - RequestWrapper, - >(&content) - .is_ok()), - "abci_query_with_existing_key" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert!(wrapped.params().path.is_none()); - assert_eq!(wrapped.params().data, hex::decode("747830").unwrap()); - assert!(wrapped.params().height.is_none()); - assert!(!wrapped.params().prove); - }, - "abci_query_with_non_existent_key" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert!(wrapped.params().path.is_none()); - assert_eq!( - wrapped.params().data, - hex::decode("6e6f6e5f6578697374656e745f6b6579").unwrap() - ); - assert!(wrapped.params().height.is_none()); - assert!(!wrapped.params().prove); - }, - "block_at_height_0" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().height.unwrap().value(), 0); - }, - "block_at_height_1" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().height.unwrap().value(), 1); - }, - "block_at_height_10" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().height.unwrap().value(), 10); - }, - "block_by_hash" => { - // First, get the hash at height 1. - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!( - wrapped.params().hash.unwrap().to_string(), - "00112233445566778899AABBCCDDEEFF00112233445566778899AABBCCDDEEFF" - ); - }, - "block_results_at_height_10" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!(wrapped.params().height.unwrap().value(), 10); - }, - "block_search" => { - let wrapped = - serde_json::from_str::>( - &content, - ) - .unwrap(); - assert_eq!(wrapped.params().query, "block.height > 1"); - assert_eq!(wrapped.params().page, 1); - assert_eq!(wrapped.params().per_page, 100); - assert_eq!(wrapped.params().order_by, Order::Ascending); - }, - "blockchain_from_1_to_10" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().min_height.value(), 1); - assert_eq!(wrapped.params().max_height.value(), 10); - }, - "broadcast_tx_async" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!( - wrapped.params().tx, - base64::decode("YXN5bmMta2V5PXZhbHVl").unwrap() - ); - }, - "broadcast_tx_commit" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!( - wrapped.params().tx, - base64::decode("Y29tbWl0LWtleT12YWx1ZQ==").unwrap() - ); - }, - "broadcast_tx_sync" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!( - wrapped.params().tx, - base64::decode("c3luYy1rZXk9dmFsdWU=").unwrap() - ); - }, - "commit_at_height_10" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().height.unwrap().value(), 10); - }, - "consensus_params" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - let height = wrapped.params().height.unwrap(); - assert_eq!(u64::from(height), 10u64); - }, - "consensus_state" => assert!(serde_json::from_str::< - RequestWrapper, - >(&content) - .is_ok()), - "genesis" => assert!(serde_json::from_str::< - RequestWrapper>, - >(&content) - .is_ok()), - "net_info" => assert!(serde_json::from_str::< - RequestWrapper, - >(&content) - .is_ok()), - "status" => assert!( - serde_json::from_str::>(&content).is_ok() - ), - "subscribe_malformed" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().query, "malformed query"); - }, - "subscribe_newblock" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().query, "tm.event = 'NewBlock'"); - }, - "subscribe_txs" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().query, "tm.event = 'Tx'"); - }, - "subscribe_txs_broadcast_tx_0" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!(wrapped.params().tx, base64::decode("dHgwPXZhbHVl").unwrap()); - }, - "subscribe_txs_broadcast_tx_1" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!(wrapped.params().tx, base64::decode("dHgxPXZhbHVl").unwrap()); - }, - "subscribe_txs_broadcast_tx_2" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!(wrapped.params().tx, base64::decode("dHgyPXZhbHVl").unwrap()); - }, - "subscribe_txs_broadcast_tx_3" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!(wrapped.params().tx, base64::decode("dHgzPXZhbHVl").unwrap()); - }, - "subscribe_txs_broadcast_tx_4" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!(wrapped.params().tx, base64::decode("dHg0PXZhbHVl").unwrap()); - }, - "subscribe_txs_broadcast_tx_5" => { - let wrapped = serde_json::from_str::< - RequestWrapper, - >(&content) - .unwrap(); - assert_eq!(wrapped.params().tx, base64::decode("dHg1PXZhbHVl").unwrap()); - }, - "tx" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!( - wrapped.params().hash, - Hash::from_bytes( - Algorithm::Sha256, - &[ - 214, 63, 156, 35, 121, 30, 97, 4, 16, 181, 118, 216, 194, 123, 181, - 174, 172, 147, 204, 26, 88, 82, 36, 40, 167, 179, 42, 18, 118, 8, 88, - 96 - ] - ) - .unwrap() - ); - assert!(!wrapped.params().prove); - }, - "tx_search_no_prove" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().query, "tx.height > 1"); - assert!(!wrapped.params().prove); - assert_eq!(wrapped.params().page, 1); - assert_eq!(wrapped.params().per_page, 10); - assert_eq!(wrapped.params().order_by, Order::Ascending); - }, - "tx_search_with_prove" => { - let wrapped = - serde_json::from_str::>(&content) - .unwrap(); - assert_eq!(wrapped.params().query, "tx.height > 1"); - assert!(wrapped.params().prove); - assert_eq!(wrapped.params().page, 1); - assert_eq!(wrapped.params().per_page, 10); - assert_eq!(wrapped.params().order_by, Order::Ascending); - }, - _ => { - panic!("cannot parse file name: {file_name}"); - }, - } - } -} - -#[test] -fn incoming_fixtures() { - // TODO: generate fixtures and test with v0_37::dialect as well - use tendermint_rpc::dialect::v0_34::Event as RpcEvent; - - let empty_merkle_root_hash = Some( - tendermint::Hash::from_hex_upper( - tendermint::hash::Algorithm::Sha256, - "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - ) - .unwrap(), - ); - let informal_epoch = - tendermint::Time::parse_from_rfc3339("2020-01-01T00:00:00.000000000Z").unwrap(); - - for json_file in find_fixtures("incoming") { - let file_name = json_file - .file_name() - .unwrap() - .to_str() - .unwrap() - .strip_suffix(".json") - .unwrap(); - let content = fs::read_to_string(&json_file).unwrap(); - match file_name { - "abci_info" => { - let result = endpoint::abci_info::Response::from_string(content).unwrap(); - assert_eq!(result.response.app_version, 1); - assert_eq!(result.response.data, "{\"size\":0}"); - assert_eq!( - result.response.last_block_app_hash.as_bytes(), - b"AAAAAAAAAAA=" - ); - assert_eq!(result.response.version, "0.17.0"); - }, - "abci_query_with_existing_key" => { - let result = endpoint::abci_query::Response::from_string(content).unwrap(); - assert_eq!(result.response.code.value(), 0); - assert!(result.response.codespace.is_empty()); - assert_eq!(result.response.index, 0); - assert!(result.response.info.is_empty()); - assert_eq!(result.response.key, base64::decode("dHgw").unwrap()); - assert_eq!(result.response.log, "exists"); - assert!(result.response.proof.is_none()); - assert_eq!(result.response.value, base64::decode("dmFsdWU=").unwrap()); - }, - "abci_query_with_non_existent_key" => { - let result = endpoint::abci_query::Response::from_string(content).unwrap(); - assert_eq!(result.response.code.value(), 0); - assert!(result.response.codespace.is_empty()); - assert_eq!(result.response.index, 0); - assert!(result.response.info.is_empty()); - assert_eq!( - result.response.key, - base64::decode("bm9uX2V4aXN0ZW50X2tleQ==").unwrap() - ); - assert_eq!(result.response.log, "does not exist"); - assert!(result.response.proof.is_none()); - assert!(result.response.value.is_empty()); - }, - "block_at_height_0" => { - let res = endpoint::block::Response::from_string(&content); - - match res { - Err(Error(ErrorDetail::Response(e), _)) => { - let response = e.source; - assert_eq!(response.code(), Code::InternalError); - assert_eq!(response.message(), "Internal error"); - assert_eq!( - response.data(), - Some("height must be greater than 0, but got 0") - ); - }, - _ => panic!("expected Response error"), - } - }, - "block_at_height_1" => { - let result = endpoint::block::Response::from_string(content).unwrap(); - assert!(result.block.data.get(0).is_none()); - assert!(result.block.evidence.iter().next().is_none()); - assert!(result.block.header.app_hash.as_bytes().is_empty()); - assert_eq!(result.block.header.chain_id.as_str(), CHAIN_ID); - assert!(!result.block.header.consensus_hash.is_empty()); - assert_eq!(result.block.header.data_hash, empty_merkle_root_hash); - assert_eq!(result.block.header.evidence_hash, empty_merkle_root_hash); - assert_eq!(result.block.header.height.value(), 1); - assert!(result.block.header.last_block_id.is_none()); - assert_eq!(result.block.header.last_commit_hash, empty_merkle_root_hash); - assert_eq!( - result.block.header.last_results_hash, - empty_merkle_root_hash - ); - assert!(!result.block.header.next_validators_hash.is_empty()); - assert_ne!( - result.block.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - result - .block - .header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!result.block.header.validators_hash.is_empty()); - assert_eq!( - result.block.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - assert!(result.block.last_commit.is_none()); - assert!(!result.block_id.hash.is_empty()); - assert!(!result.block_id.part_set_header.hash.is_empty()); - assert_eq!(result.block_id.part_set_header.total, 1); - }, - "block_at_height_10" => { - let result = endpoint::block::Response::from_string(content).unwrap(); - assert!(result.block.data.get(0).is_none()); - assert!(result.block.evidence.iter().next().is_none()); - assert_eq!(result.block.header.app_hash.as_bytes(), &[0u8; 8]); - assert_eq!(result.block.header.chain_id.as_str(), CHAIN_ID); - assert!(!result.block.header.consensus_hash.is_empty()); - assert_eq!(result.block.header.data_hash, empty_merkle_root_hash); - assert_eq!(result.block.header.evidence_hash, empty_merkle_root_hash); - assert_eq!(result.block.header.height.value(), 10); - assert!(result.block.header.last_block_id.is_some()); - assert!(result.block.header.last_commit_hash.is_some()); - assert!(result.block.header.last_results_hash.is_some()); - assert!(!result.block.header.next_validators_hash.is_empty()); - assert_ne!( - result.block.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - result - .block - .header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!result.block.header.validators_hash.is_empty()); - assert_eq!( - result.block.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - let last_commit = result.block.last_commit.unwrap(); - assert!(!last_commit.block_id.hash.is_empty()); - assert!(!last_commit.block_id.part_set_header.hash.is_empty()); - assert_eq!(last_commit.block_id.part_set_header.total, 1); - assert_eq!(last_commit.height.value(), 9); - assert_eq!(last_commit.round.value(), 0); - assert_eq!(last_commit.signatures.len(), 1); - assert!(last_commit.signatures[0].is_commit()); - assert!(last_commit.signatures[0].validator_address().is_some()); - // It's weird but there is no implementation to get the signature out of CommitSig. - assert!(!result.block_id.hash.is_empty()); - assert!(!result.block_id.part_set_header.hash.is_empty()); - assert_eq!(result.block_id.part_set_header.total, 1); - }, - "block_results_at_height_10" => { - let result: endpoint::block_results::Response = - endpoint::block_results::DialectResponse::::from_string(content) - .unwrap() - .into(); - assert!(result.begin_block_events.is_none()); - assert!(result.consensus_param_updates.is_none()); - assert!(result.end_block_events.is_none()); - assert_eq!(result.height.value(), 10); - assert!(result.txs_results.is_none()); - assert!(result.validator_updates.is_empty()); - }, - "block_by_hash" => { - let result = endpoint::block::Response::from_string(content).unwrap(); - assert_eq!( - result.block_id.hash.to_string(), - "BCF3DB412E80A396D10BF5B5E6D3E63D3B06DEB25AA958BCB8CE18D023838042" - ); - }, - "block_search" => { - let result = endpoint::block_search::Response::from_string(content).unwrap(); - assert_eq!(result.total_count as usize, result.blocks.len()); - for response in result.blocks { - assert!(response.block.header.height.value() > 1); - } - }, - "block_search_evidence" => { - let result = endpoint::block_search::Response::from_string(content).unwrap(); - assert_eq!(result.total_count as usize, result.blocks.len()); - - // Test a few selected attributes of the results. - for block in result.blocks { - let evidence = block.block.evidence.iter().next().unwrap(); - - use tendermint::vote; - - fn check_vote(vote: &Vote) { - assert_eq!(vote.vote_type, vote::Type::Precommit); - assert_eq!(vote.height.value(), 8009); - assert_eq!(vote.round.value(), 0); - assert_eq!( - vote.validator_address, - "9319035301DA526CC78DCF174A47A74F81401291".parse().unwrap(), - ); - assert_eq!(vote.validator_index.value(), 8); - } - - if let Evidence::DuplicateVote(dup) = evidence { - assert_eq!(dup.total_voting_power.value(), 121); - assert_eq!(dup.validator_power.value(), 1); - assert_eq!( - dup.timestamp, - "2022-09-12T19:49:49.984608464Z".parse().unwrap() - ); - - check_vote(&dup.vote_a); - check_vote(&dup.vote_b); - } else { - panic!("not a duplicate vote: {evidence:?}"); - } - } - }, - "broadcast_tx_async" => { - let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "broadcast_tx_commit" => { - let result: endpoint::broadcast::tx_commit::Response = - endpoint::broadcast::tx_commit::DialectResponse::::from_string( - content, - ) - .unwrap() - .into(); - assert_eq!(result.check_tx.code, abci::Code::Ok); - assert!(result.check_tx.codespace.is_empty()); - assert!(result.check_tx.data.is_empty()); - assert!(result.check_tx.events.is_empty()); - assert_eq!(result.check_tx.gas_used, 0); - // Todo: https://github.com/informalsystems/tendermint-rs/issues/761 - // assert_eq!(result.check_tx.gas_wanted.value(), 1); - assert!(result.check_tx.info.to_string().is_empty()); - assert!(result.check_tx.log.is_empty()); - assert_eq!(result.deliver_tx.code, abci::Code::Ok); - assert!(result.deliver_tx.codespace.is_empty()); - assert!(result.deliver_tx.data.is_empty()); - assert_eq!(result.deliver_tx.events.len(), 1); - assert_eq!(result.deliver_tx.events[0].attributes.len(), 4); - assert_eq!(result.deliver_tx.events[0].attributes[0].key, "creator"); - assert_eq!( - result.deliver_tx.events[0].attributes[0].value, - "Cosmoshi Netowoko" - ); - assert_eq!(result.deliver_tx.events[0].attributes[1].key, "key"); - assert_eq!( - result.deliver_tx.events[0].attributes[1].value, - "commit-key" - ); - assert_eq!(result.deliver_tx.events[0].attributes[2].key, "index_key"); - assert_eq!( - result.deliver_tx.events[0].attributes[2].value, - "index is working" - ); - assert_eq!(result.deliver_tx.events[0].attributes[3].key, "noindex_key"); - assert_eq!( - result.deliver_tx.events[0].attributes[3].value, - "index is working" - ); - assert_eq!(result.deliver_tx.events[0].kind, "app"); - assert_eq!(result.deliver_tx.gas_used, 0); - assert_eq!(result.deliver_tx.gas_wanted, 0); - assert!(result.deliver_tx.info.to_string().is_empty()); - assert!(result.deliver_tx.log.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - }, - "broadcast_tx_sync" => { - let result = endpoint::broadcast::tx_sync::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "commit_at_height_10" => { - let result = endpoint::commit::Response::from_string(content).unwrap(); - assert!(!result.signed_header.commit.block_id.hash.is_empty()); - assert_eq!(result.signed_header.commit.height.value(), 10); - assert_eq!(result.signed_header.commit.round.value(), 0); - assert_eq!(result.signed_header.commit.signatures.len(), 1); - assert!(result.signed_header.commit.signatures[0].is_commit()); - assert!(result.signed_header.commit.signatures[0] - .validator_address() - .is_some()); - assert_eq!(result.signed_header.header.app_hash.as_bytes(), [0u8; 8]); - assert_eq!(result.signed_header.header.chain_id.as_str(), CHAIN_ID); - assert!(!result.signed_header.header.consensus_hash.is_empty()); - assert_eq!( - result.signed_header.header.data_hash, - empty_merkle_root_hash - ); - assert_eq!( - result.signed_header.header.evidence_hash, - empty_merkle_root_hash - ); - assert_eq!(result.signed_header.header.height.value(), 10); - assert!(result.signed_header.header.last_block_id.is_some()); - assert!(result.signed_header.header.last_commit_hash.is_some()); - assert!(result.signed_header.header.last_results_hash.is_some()); - assert!(!result.signed_header.header.next_validators_hash.is_empty()); - assert_ne!( - result.signed_header.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - result - .signed_header - .header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!result.signed_header.header.validators_hash.is_empty()); - assert_eq!( - result.signed_header.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - }, - "consensus_params" => { - let result = endpoint::consensus_params::Response::from_string(content).unwrap(); - assert_eq!(u64::from(result.block_height), 10_u64); - assert_eq!(result.consensus_params.block.max_bytes, 22020096_u64); - assert_eq!(result.consensus_params.block.max_gas, -1_i64); - assert_eq!(result.consensus_params.block.time_iota_ms, 500_i64); - assert_eq!( - result.consensus_params.evidence.max_age_duration, - Duration(core::time::Duration::from_nanos(172800000000000_u64)) - ); - assert_eq!( - result.consensus_params.evidence.max_age_num_blocks, - 100000_u64 - ); - assert_eq!(result.consensus_params.evidence.max_bytes, 1048576_i64); - assert_eq!( - result.consensus_params.validator.pub_key_types, - vec![public_key::Algorithm::Ed25519] - ); - }, - "consensus_state" => { - assert!(endpoint::consensus_state::Response::from_string(content).is_ok()); - }, - "genesis" => { - let result = - endpoint::genesis::Response::>::from_string(content) - .unwrap(); - assert!(result.genesis.app_hash.as_bytes().is_empty()); - assert_eq!(result.genesis.chain_id.as_str(), CHAIN_ID); - assert_eq!(result.genesis.consensus_params.block.max_bytes, 22020096); - assert_eq!(result.genesis.consensus_params.block.max_gas, -1); - assert_eq!( - result - .genesis - .consensus_params - .evidence - .max_age_duration - .0 - .as_nanos(), - 172800000000000 - ); - assert_eq!( - result.genesis.consensus_params.evidence.max_age_num_blocks, - 100000 - ); - assert_eq!(result.genesis.consensus_params.evidence.max_bytes, 1048576); - assert_eq!( - result - .genesis - .consensus_params - .validator - .pub_key_types - .len(), - 1 - ); - assert_eq!( - result.genesis.consensus_params.validator.pub_key_types[0], - tendermint::public_key::Algorithm::Ed25519 - ); - assert!(result.genesis.consensus_params.version.is_none()); - assert!( - result - .genesis - .genesis_time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert_eq!(result.genesis.validators.len(), 1); - assert_ne!( - result.genesis.validators[0].address.as_bytes(), - [0; tendermint::account::LENGTH] - ); - assert_eq!(result.genesis.validators[0].power(), 10); - assert!(result.genesis.validators[0].pub_key.ed25519().is_some()); - assert_eq!(result.genesis.validators[0].proposer_priority.value(), 0); - assert_eq!(result.genesis.consensus_params.block.time_iota_ms, 500); - }, - "net_info" => { - let result = endpoint::net_info::Response::from_string(content).unwrap(); - assert_eq!(result.listeners.len(), 1); - assert_eq!(result.listeners[0].to_string(), "Listener(@)"); - assert!(result.listening); - assert_eq!(result.n_peers, 0); - assert!(result.peers.is_empty()); - }, - "status" => { - let result = endpoint::status::Response::from_string(content).unwrap(); - assert_eq!( - Address::from_listen_address(&result.node_info.listen_addr).unwrap(), - Address::from_str("tcp://0.0.0.0:26656").unwrap() - ); - assert_eq!(result.node_info.moniker.to_string(), "dockernode"); - assert_eq!(result.node_info.network.to_string(), CHAIN_ID); - assert_eq!( - result.node_info.other.rpc_address, - format!("{}", Address::from_str("tcp://0.0.0.0:26657").unwrap()) - ); - assert_eq!( - result.node_info.other.tx_index, - tendermint::node::info::TxIndexStatus::On - ); - assert_eq!( - result.node_info.protocol_version, - tendermint::node::info::ProtocolVersionInfo { - p2p: 8, - block: 11, - app: 1 - } - ); - assert_eq!(result.node_info.version.to_string(), "0.34.21"); - assert!(!result.sync_info.catching_up); - assert_eq!( - result.sync_info.latest_app_hash.as_bytes(), - [6, 0, 0, 0, 0, 0, 0, 0] - ); - assert!(!result.sync_info.latest_block_hash.is_empty()); - assert!( - result - .sync_info - .latest_block_time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(result.validator_info.pub_key.ed25519().is_some()); - assert_eq!(result.validator_info.power.value(), 10); - }, - "blockchain_from_1_to_10" => { - let result = endpoint::blockchain::Response::from_string(content).unwrap(); - assert_eq!(result.block_metas.len(), 10); - for block_meta in result.block_metas { - assert!(!block_meta.block_id.hash.is_empty()); - assert!(!block_meta.block_id.part_set_header.hash.is_empty()); - assert_eq!(block_meta.block_id.part_set_header.total, 1); - assert!(block_meta.block_size > 0); - if block_meta.header.height.value() == 1 { - assert!(block_meta.header.app_hash.as_bytes().is_empty()); - assert_eq!(block_meta.header.data_hash, empty_merkle_root_hash); - assert_eq!(block_meta.header.evidence_hash, empty_merkle_root_hash); - assert!(block_meta.header.last_block_id.is_none()); - assert_eq!(block_meta.header.last_commit_hash, empty_merkle_root_hash); - assert_eq!(block_meta.header.last_results_hash, empty_merkle_root_hash); - } else { - assert!(!block_meta.header.app_hash.as_bytes().is_empty()); - assert!(block_meta.header.data_hash.is_some()); - assert!(block_meta.header.evidence_hash.is_some()); - assert!(block_meta.header.last_block_id.is_some()); - assert!(block_meta.header.last_commit_hash.is_some()); - assert!(block_meta.header.last_results_hash.is_some()); - } - assert_eq!(block_meta.header.chain_id.as_str(), CHAIN_ID); - assert!(!block_meta.header.consensus_hash.is_empty()); - assert!(!block_meta.header.next_validators_hash.is_empty()); - assert_ne!( - block_meta.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - block_meta - .header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!block_meta.header.validators_hash.is_empty()); - assert_eq!( - block_meta.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - assert_eq!(block_meta.num_txs, 0); - } - }, - "subscribe_malformed" => { - let result = endpoint::subscribe::Response::from_string(content); - - match result { - Err(Error(ErrorDetail::Response(e), _)) => { - let response = e.source; - - assert_eq!(response.code(), Code::InternalError); - assert_eq!(response.message(), "Internal error"); - assert_eq!(response.data().unwrap(),"failed to parse query: \nparse error near PegText (line 1 symbol 2 - line 1 symbol 11):\n\"malformed\"\n"); - }, - _ => panic!("expected Response error"), - } - }, - "subscribe_newblock" => { - let result = endpoint::subscribe::Response::from_string(content); - - match result { - Err(Error(ErrorDetail::Serde(_), _)) => {}, - _ => panic!("expected Serde parse error, instead got {result:?}"), - } - }, - "subscribe_newblock_0" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - if let tendermint_rpc::event::EventData::NewBlock { - block, - result_begin_block, - result_end_block, - } = result.data.into() - { - let b = block.unwrap(); - assert!(b.data.get(0).is_none()); - assert!(b.evidence.iter().next().is_none()); - assert!(!b.header.app_hash.as_bytes().is_empty()); - assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); - assert!(!b.header.consensus_hash.is_empty()); - assert_eq!(b.header.data_hash, empty_merkle_root_hash); - assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); - assert!(b.header.last_block_id.is_some()); - assert!(b.header.last_commit_hash.is_some()); - assert!(b.header.last_results_hash.is_some()); - assert!(!b.header.next_validators_hash.is_empty()); - assert_ne!( - b.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - b.header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!b.header.validators_hash.is_empty()); - assert_eq!( - b.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - let last_commit = b.last_commit.unwrap(); - assert!(!last_commit.block_id.hash.is_empty()); - assert!(!last_commit.block_id.part_set_header.hash.is_empty()); - assert_eq!(last_commit.block_id.part_set_header.total, 1); - assert_eq!(last_commit.round.value(), 0); - assert_eq!(last_commit.signatures.len(), 1); - assert!(last_commit.signatures[0].is_commit()); - assert!(last_commit.signatures[0].validator_address().is_some()); - assert!(result_begin_block.unwrap().events.is_empty()); - let reb = result_end_block.unwrap(); - assert!(reb.validator_updates.is_empty()); - assert!(reb.consensus_param_updates.is_none()); - assert!(reb.events.is_empty()); - } else { - panic!("not a newblock"); - } - assert_eq!(result.query, "tm.event = 'NewBlock'"); - }, - "subscribe_newblock_1" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - if let tendermint_rpc::event::EventData::NewBlock { - block, - result_begin_block, - result_end_block, - } = result.data.into() - { - let b = block.unwrap(); - assert!(b.data.get(0).is_none()); - assert!(b.evidence.iter().next().is_none()); - assert!(!b.header.app_hash.as_bytes().is_empty()); - assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); - assert!(!b.header.consensus_hash.is_empty()); - assert_eq!(b.header.data_hash, empty_merkle_root_hash); - assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); - assert!(b.header.last_block_id.is_some()); - assert!(b.header.last_commit_hash.is_some()); - assert!(b.header.last_results_hash.is_some()); - assert!(!b.header.next_validators_hash.is_empty()); - assert_ne!( - b.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - b.header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!b.header.validators_hash.is_empty()); - assert_eq!( - b.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - let last_commit = b.last_commit.unwrap(); - assert!(!last_commit.block_id.hash.is_empty()); - assert!(!last_commit.block_id.part_set_header.hash.is_empty()); - assert_eq!(last_commit.block_id.part_set_header.total, 1); - assert_eq!(last_commit.round.value(), 0); - assert_eq!(last_commit.signatures.len(), 1); - assert!(last_commit.signatures[0].is_commit()); - assert!(last_commit.signatures[0].validator_address().is_some()); - let rbb = result_begin_block.unwrap(); - assert_eq!(rbb.events.len(), 2); - assert_eq!(rbb.events[0].kind, "transfer"); - assert_eq!(rbb.events[0].attributes.len(), 2); - assert_eq!(rbb.events[0].attributes[0].key, "recipient"); - assert_eq!( - rbb.events[0].attributes[0].value, - "cosmos17xpfvakm2amg962yls6f84z3kell8c5lserqta" - ); - assert!(rbb.events[0].attributes[0].index); - assert_eq!(rbb.events[0].attributes[1].key, "sender"); - assert_eq!( - rbb.events[0].attributes[1].value, - "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" - ); - assert!(!rbb.events[0].attributes[1].index); - assert_eq!(rbb.events[1].kind, "message"); - assert_eq!(rbb.events[1].attributes.len(), 1); - assert_eq!(rbb.events[1].attributes[0].key, "sender"); - assert_eq!( - rbb.events[1].attributes[0].value, - "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" - ); - let reb = result_end_block.unwrap(); - assert!(reb.validator_updates.is_empty()); - assert!(reb.consensus_param_updates.is_none()); - assert!(reb.events.is_empty()); - } else { - panic!("not a newblock"); - } - assert_eq!(result.query, "tm.event = 'NewBlock'"); - }, - "subscribe_newblock_2" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - if let tendermint_rpc::event::EventData::NewBlock { - block, - result_begin_block, - result_end_block, - } = result.data.into() - { - let b = block.unwrap(); - assert!(b.data.get(0).is_none()); - assert!(b.evidence.iter().next().is_none()); - assert!(!b.header.app_hash.as_bytes().is_empty()); - assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); - assert!(!b.header.consensus_hash.is_empty()); - assert_eq!(b.header.data_hash, empty_merkle_root_hash); - assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); - assert!(b.header.last_block_id.is_some()); - assert!(b.header.last_commit_hash.is_some()); - assert!(b.header.last_results_hash.is_some()); - assert!(!b.header.next_validators_hash.is_empty()); - assert_ne!( - b.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - b.header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!b.header.validators_hash.is_empty()); - assert_eq!( - b.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - let last_commit = b.last_commit.unwrap(); - assert!(!last_commit.block_id.hash.is_empty()); - assert!(!last_commit.block_id.part_set_header.hash.is_empty()); - assert_eq!(last_commit.block_id.part_set_header.total, 1); - assert_eq!(last_commit.round.value(), 0); - assert_eq!(last_commit.signatures.len(), 1); - assert!(last_commit.signatures[0].is_commit()); - assert!(last_commit.signatures[0].validator_address().is_some()); - assert!(result_begin_block.unwrap().events.is_empty()); - let reb = result_end_block.unwrap(); - assert!(reb.validator_updates.is_empty()); - assert!(reb.consensus_param_updates.is_none()); - assert!(reb.events.is_empty()); - } else { - panic!("not a newblock"); - } - assert_eq!(result.query, "tm.event = 'NewBlock'"); - }, - "subscribe_newblock_3" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - if let tendermint_rpc::event::EventData::NewBlock { - block, - result_begin_block, - result_end_block, - } = result.data.into() - { - let b = block.unwrap(); - assert!(b.data.get(0).is_none()); - assert!(b.evidence.iter().next().is_none()); - assert!(!b.header.app_hash.as_bytes().is_empty()); - assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); - assert!(!b.header.consensus_hash.is_empty()); - assert_eq!(b.header.data_hash, empty_merkle_root_hash); - assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); - assert!(b.header.last_block_id.is_some()); - assert!(b.header.last_commit_hash.is_some()); - assert!(b.header.last_results_hash.is_some()); - assert!(!b.header.next_validators_hash.is_empty()); - assert_ne!( - b.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - b.header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!b.header.validators_hash.is_empty()); - assert_eq!( - b.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - let last_commit = b.last_commit.unwrap(); - assert!(!last_commit.block_id.hash.is_empty()); - assert!(!last_commit.block_id.part_set_header.hash.is_empty()); - assert_eq!(last_commit.block_id.part_set_header.total, 1); - assert_eq!(last_commit.round.value(), 0); - assert_eq!(last_commit.signatures.len(), 1); - assert!(last_commit.signatures[0].is_commit()); - assert!(last_commit.signatures[0].validator_address().is_some()); - assert!(result_begin_block.unwrap().events.is_empty()); - let reb = result_end_block.unwrap(); - assert!(reb.validator_updates.is_empty()); - assert!(reb.consensus_param_updates.is_none()); - assert!(reb.events.is_empty()); - } else { - panic!("not a newblock"); - } - assert_eq!(result.query, "tm.event = 'NewBlock'"); - }, - "subscribe_newblock_4" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - if let tendermint_rpc::event::EventData::NewBlock { - block, - result_begin_block, - result_end_block, - } = result.data.into() - { - let b = block.unwrap(); - assert!(b.data.get(0).is_none()); - assert!(b.evidence.iter().next().is_none()); - assert!(!b.header.app_hash.as_bytes().is_empty()); - assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); - assert!(!b.header.consensus_hash.is_empty()); - assert_eq!(b.header.data_hash, empty_merkle_root_hash); - assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); - assert!(b.header.last_block_id.is_some()); - assert!(b.header.last_commit_hash.is_some()); - assert!(b.header.last_results_hash.is_some()); - assert!(!b.header.next_validators_hash.is_empty()); - assert_ne!( - b.header.proposer_address.as_bytes(), - [0u8; tendermint::account::LENGTH] - ); - assert!( - b.header - .time - .duration_since(informal_epoch) - .unwrap() - .as_secs() - > 0 - ); - assert!(!b.header.validators_hash.is_empty()); - assert_eq!( - b.header.version, - tendermint::block::header::Version { block: 11, app: 1 } - ); - let last_commit = b.last_commit.unwrap(); - assert!(!last_commit.block_id.hash.is_empty()); - assert!(!last_commit.block_id.part_set_header.hash.is_empty()); - assert_eq!(last_commit.block_id.part_set_header.total, 1); - assert_eq!(last_commit.round.value(), 0); - assert_eq!(last_commit.signatures.len(), 1); - assert!(last_commit.signatures[0].is_commit()); - assert!(last_commit.signatures[0].validator_address().is_some()); - assert!(result_begin_block.unwrap().events.is_empty()); - let reb = result_end_block.unwrap(); - assert!(reb.validator_updates.is_empty()); - assert!(reb.consensus_param_updates.is_none()); - assert!(reb.events.is_empty()); - } else { - panic!("not a newblock"); - } - assert_eq!(result.query, "tm.event = 'NewBlock'"); - }, - "subscribe_txs" => { - assert!(endpoint::subscribe::Response::from_string(content).is_ok()); - }, - "subscribe_txs_0" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { - height = tx_result.height; - assert!(tx_result.result.log.is_none()); - assert!(tx_result.result.gas_wanted.is_none()); - assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); - assert_eq!(tx_result.result.events[0].kind, "app"); - for attr in &tx_result.result.events[0].attributes { - match attr.key.as_str() { - "creator" => { - assert_eq!(attr.value, "Cosmoshi Netowoko") - }, - "key" => assert_eq!(attr.value, "tx0"), - "index_key" => { - assert_eq!(attr.value, "index is working") - }, - "noindex_key" => { - assert_eq!(attr.value, "index is working") - }, - _ => panic!("unknown attribute found {}", attr.key), - } - } - assert_eq!(tx_result.tx, base64::decode("dHgwPXZhbHVl").unwrap()); - } else { - panic!("not a tx"); - } - check_event_attrs(&result.events.unwrap(), "tx0", height); - assert_eq!(result.query, "tm.event = 'Tx'"); - }, - "subscribe_txs_1" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { - height = tx_result.height; - assert!(tx_result.result.log.is_none()); - assert!(tx_result.result.gas_wanted.is_none()); - assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); - assert_eq!(tx_result.result.events[0].kind, "app"); - for attr in &tx_result.result.events[0].attributes { - match attr.key.as_str() { - "creator" => { - assert_eq!(attr.value, "Cosmoshi Netowoko") - }, - "key" => assert_eq!(attr.value, "tx1"), - "index_key" => { - assert_eq!(attr.value, "index is working") - }, - "noindex_key" => { - assert_eq!(attr.value, "index is working") - }, - _ => panic!("unknown attribute found {}", attr.key), - } - } - assert_eq!(tx_result.tx, base64::decode("dHgxPXZhbHVl").unwrap()); - } else { - panic!("not a tx"); - } - - check_event_attrs(&result.events.unwrap(), "tx1", height); - assert_eq!(result.query, "tm.event = 'Tx'"); - }, - "subscribe_txs_2" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { - height = tx_result.height; - assert!(tx_result.result.log.is_none()); - assert!(tx_result.result.gas_wanted.is_none()); - assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); - assert_eq!(tx_result.result.events[0].kind, "app"); - for attr in &tx_result.result.events[0].attributes { - match attr.key.as_str() { - "creator" => { - assert_eq!(attr.value, "Cosmoshi Netowoko") - }, - "key" => assert_eq!(attr.value, "tx2"), - "index_key" => { - assert_eq!(attr.value, "index is working") - }, - "noindex_key" => { - assert_eq!(attr.value, "index is working") - }, - _ => panic!("unknown attribute found {}", attr.key), - } - } - assert_eq!(tx_result.tx, base64::decode("dHgyPXZhbHVl").unwrap()); - } else { - panic!("not a tx"); - } - check_event_attrs(&result.events.unwrap(), "tx2", height); - assert_eq!(result.query, "tm.event = 'Tx'"); - }, - "subscribe_txs_3" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { - height = tx_result.height; - assert!(tx_result.result.log.is_none()); - assert!(tx_result.result.gas_wanted.is_none()); - assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); - assert_eq!(tx_result.result.events[0].kind, "app"); - for attr in &tx_result.result.events[0].attributes { - match attr.key.as_str() { - "creator" => { - assert_eq!(attr.value, "Cosmoshi Netowoko") - }, - "key" => assert_eq!(attr.value, "tx3"), - "index_key" => { - assert_eq!(attr.value, "index is working") - }, - "noindex_key" => { - assert_eq!(attr.value, "index is working") - }, - _ => panic!("unknown attribute found {}", attr.key), - } - } - assert_eq!(tx_result.tx, base64::decode("dHgzPXZhbHVl").unwrap()); - } else { - panic!("not a tx"); - } - check_event_attrs(&result.events.unwrap(), "tx3", height); - assert_eq!(result.query, "tm.event = 'Tx'"); - }, - "subscribe_txs_4" => { - let result = - tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); - let height; - if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { - height = tx_result.height; - assert!(tx_result.result.log.is_none()); - assert!(tx_result.result.gas_wanted.is_none()); - assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); - assert_eq!(tx_result.result.events[0].kind, "app"); - for attr in &tx_result.result.events[0].attributes { - match attr.key.as_str() { - "creator" => { - assert_eq!(attr.value, "Cosmoshi Netowoko") - }, - "key" => assert_eq!(attr.value, "tx4"), - "index_key" => { - assert_eq!(attr.value, "index is working") - }, - "noindex_key" => { - assert_eq!(attr.value, "index is working") - }, - _ => panic!("unknown attribute found {}", attr.key), - } - } - assert_eq!(tx_result.tx, base64::decode("dHg0PXZhbHVl").unwrap()); - } else { - panic!("not a tx"); - } - check_event_attrs(&result.events.unwrap(), "tx4", height); - assert_eq!(result.query, "tm.event = 'Tx'"); - }, - "subscribe_txs_broadcast_tx_0" => { - let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "subscribe_txs_broadcast_tx_1" => { - let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "subscribe_txs_broadcast_tx_2" => { - let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "subscribe_txs_broadcast_tx_3" => { - let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "subscribe_txs_broadcast_tx_4" => { - let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "subscribe_txs_broadcast_tx_5" => { - let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); - assert_eq!(result.code, abci::Code::Ok); - assert!(result.data.is_empty()); - assert_ne!( - result.hash, - Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() - ); - assert!(result.log.is_empty()); - }, - "tx" => { - let result: endpoint::tx::Response = - endpoint::tx::DialectResponse::::from_string(content) - .unwrap() - .into(); - assert_eq!( - result.hash, - Hash::from_bytes( - Algorithm::Sha256, - &[ - 214, 63, 156, 35, 121, 30, 97, 4, 16, 181, 118, 216, 194, 123, 181, - 174, 172, 147, 204, 26, 88, 82, 36, 40, 167, 179, 42, 18, 118, 8, 88, - 96 - ] - ) - .unwrap() - ); - assert_eq!(u64::from(result.height), 12u64); - }, - "tx_search_no_prove" => { - let result: endpoint::tx_search::Response = - endpoint::tx_search::DialectResponse::::from_string(content) - .unwrap() - .into(); - assert_eq!(result.total_count as usize, result.txs.len()); - // Test a few selected attributes of the results. - for tx in result.txs { - assert_ne!(tx.hash.as_bytes(), [0; 32]); - assert_eq!(tx.tx_result.code, abci::Code::Ok); - assert_eq!(tx.tx_result.events.len(), 1); - assert_eq!(tx.tx_result.events[0].kind, "app"); - assert_eq!(tx.tx_result.gas_used, 0); - assert_eq!(tx.tx_result.gas_wanted, 0); - assert!(tx.tx_result.info.to_string().is_empty()); - assert!(tx.tx_result.log.is_empty()); - assert!(tx.proof.is_none()); - } - }, - "tx_search_with_prove" => { - let result: endpoint::tx_search::Response = - endpoint::tx_search::DialectResponse::::from_string(content) - .unwrap() - .into(); - assert_eq!(result.total_count as usize, result.txs.len()); - // Test a few selected attributes of the results. - for tx in result.txs { - assert_ne!(tx.hash.as_bytes(), [0; 32]); - assert_eq!(tx.tx_result.code, abci::Code::Ok); - assert_eq!(tx.tx_result.events.len(), 1); - assert_eq!(tx.tx_result.events[0].kind, "app"); - assert_eq!(tx.tx_result.gas_used, 0); - assert_eq!(tx.tx_result.gas_wanted, 0); - assert!(tx.tx_result.info.to_string().is_empty()); - assert!(tx.tx_result.log.is_empty()); - let proof = tx.proof.unwrap(); - assert_eq!(proof.data, tx.tx); - assert_eq!(proof.proof.total, 1); - assert_eq!(proof.proof.index, 0); - assert_ne!(proof.root_hash.as_bytes(), [0; 32]); - } - }, - _ => { - panic!("cannot parse file name: {file_name}"); - }, - } - } -} - fn check_event_attrs(events: &HashMap>, app_key: &str, height: i64) { for (k, v) in events { assert_eq!(v.len(), 1); diff --git a/rpc/tests/kvstore_fixtures/v0_34.rs b/rpc/tests/kvstore_fixtures/v0_34.rs new file mode 100644 index 000000000..8b8d528ab --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_34.rs @@ -0,0 +1,1412 @@ +use super::*; + +#[test] +fn outgoing_fixtures() { + for json_file in find_fixtures("v0_34", "outgoing") { + let file_name = json_file + .file_name() + .unwrap() + .to_str() + .unwrap() + .strip_suffix(".json") + .unwrap(); + let content = fs::read_to_string(&json_file).unwrap(); + match file_name { + "abci_info" => assert!(serde_json::from_str::< + RequestWrapper, + >(&content) + .is_ok()), + "abci_query_with_existing_key" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert!(wrapped.params().path.is_none()); + assert_eq!(wrapped.params().data, hex::decode("747830").unwrap()); + assert!(wrapped.params().height.is_none()); + assert!(!wrapped.params().prove); + }, + "abci_query_with_non_existent_key" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert!(wrapped.params().path.is_none()); + assert_eq!( + wrapped.params().data, + hex::decode("6e6f6e5f6578697374656e745f6b6579").unwrap() + ); + assert!(wrapped.params().height.is_none()); + assert!(!wrapped.params().prove); + }, + "block_at_height_0" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 0); + }, + "block_at_height_1" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 1); + }, + "block_at_height_10" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 10); + }, + "block_by_hash" => { + // First, get the hash at height 1. + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().hash.unwrap().to_string(), + "00112233445566778899AABBCCDDEEFF00112233445566778899AABBCCDDEEFF" + ); + }, + "block_results_at_height_10" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 10); + }, + "block_search" => { + let wrapped = + serde_json::from_str::>( + &content, + ) + .unwrap(); + assert_eq!(wrapped.params().query, "block.height > 1"); + assert_eq!(wrapped.params().page, 1); + assert_eq!(wrapped.params().per_page, 100); + assert_eq!(wrapped.params().order_by, Order::Ascending); + }, + "blockchain_from_1_to_10" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().min_height.value(), 1); + assert_eq!(wrapped.params().max_height.value(), 10); + }, + "broadcast_tx_async" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().tx, + base64::decode("YXN5bmMta2V5PXZhbHVl").unwrap() + ); + }, + "broadcast_tx_commit" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().tx, + base64::decode("Y29tbWl0LWtleT12YWx1ZQ==").unwrap() + ); + }, + "broadcast_tx_sync" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().tx, + base64::decode("c3luYy1rZXk9dmFsdWU=").unwrap() + ); + }, + "commit_at_height_10" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 10); + }, + "consensus_params" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + let height = wrapped.params().height.unwrap(); + assert_eq!(u64::from(height), 10u64); + }, + "consensus_state" => assert!(serde_json::from_str::< + RequestWrapper, + >(&content) + .is_ok()), + "genesis" => assert!(serde_json::from_str::< + RequestWrapper>, + >(&content) + .is_ok()), + "net_info" => assert!(serde_json::from_str::< + RequestWrapper, + >(&content) + .is_ok()), + "status" => assert!( + serde_json::from_str::>(&content).is_ok() + ), + "subscribe_malformed" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "malformed query"); + }, + "subscribe_newblock" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tm.event = 'NewBlock'"); + }, + "subscribe_txs" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tm.event = 'Tx'"); + }, + "subscribe_txs_broadcast_tx_0" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgwPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_1" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgxPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_2" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgyPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_3" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgzPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_4" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHg0PXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_5" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHg1PXZhbHVl").unwrap()); + }, + "tx" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!( + wrapped.params().hash, + Hash::from_bytes( + Algorithm::Sha256, + &[ + 214, 63, 156, 35, 121, 30, 97, 4, 16, 181, 118, 216, 194, 123, 181, + 174, 172, 147, 204, 26, 88, 82, 36, 40, 167, 179, 42, 18, 118, 8, 88, + 96 + ] + ) + .unwrap() + ); + assert!(!wrapped.params().prove); + }, + "tx_search_no_prove" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tx.height > 1"); + assert!(!wrapped.params().prove); + assert_eq!(wrapped.params().page, 1); + assert_eq!(wrapped.params().per_page, 10); + assert_eq!(wrapped.params().order_by, Order::Ascending); + }, + "tx_search_with_prove" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tx.height > 1"); + assert!(wrapped.params().prove); + assert_eq!(wrapped.params().page, 1); + assert_eq!(wrapped.params().per_page, 10); + assert_eq!(wrapped.params().order_by, Order::Ascending); + }, + _ => { + panic!("cannot parse file name: {file_name}"); + }, + } + } +} + +#[test] +fn incoming_fixtures() { + use tendermint_rpc::dialect::v0_34::Event as RpcEvent; + + let empty_merkle_root_hash = Some( + tendermint::Hash::from_hex_upper( + tendermint::hash::Algorithm::Sha256, + "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + ) + .unwrap(), + ); + let informal_epoch = + tendermint::Time::parse_from_rfc3339("2020-01-01T00:00:00.000000000Z").unwrap(); + + for json_file in find_fixtures("v0_34", "incoming") { + let file_name = json_file + .file_name() + .unwrap() + .to_str() + .unwrap() + .strip_suffix(".json") + .unwrap(); + let content = fs::read_to_string(&json_file).unwrap(); + match file_name { + "abci_info" => { + let result = endpoint::abci_info::Response::from_string(content).unwrap(); + assert_eq!(result.response.app_version, 1); + assert_eq!(result.response.data, "{\"size\":0}"); + assert_eq!( + result.response.last_block_app_hash.as_bytes(), + b"AAAAAAAAAAA=" + ); + assert_eq!(result.response.version, "0.17.0"); + }, + "abci_query_with_existing_key" => { + let result = endpoint::abci_query::Response::from_string(content).unwrap(); + assert_eq!(result.response.code.value(), 0); + assert!(result.response.codespace.is_empty()); + assert_eq!(result.response.index, 0); + assert!(result.response.info.is_empty()); + assert_eq!(result.response.key, base64::decode("dHgw").unwrap()); + assert_eq!(result.response.log, "exists"); + assert!(result.response.proof.is_none()); + assert_eq!(result.response.value, base64::decode("dmFsdWU=").unwrap()); + }, + "abci_query_with_non_existent_key" => { + let result = endpoint::abci_query::Response::from_string(content).unwrap(); + assert_eq!(result.response.code.value(), 0); + assert!(result.response.codespace.is_empty()); + assert_eq!(result.response.index, 0); + assert!(result.response.info.is_empty()); + assert_eq!( + result.response.key, + base64::decode("bm9uX2V4aXN0ZW50X2tleQ==").unwrap() + ); + assert_eq!(result.response.log, "does not exist"); + assert!(result.response.proof.is_none()); + assert!(result.response.value.is_empty()); + }, + "block_at_height_0" => { + let res = endpoint::block::Response::from_string(&content); + + match res { + Err(Error(ErrorDetail::Response(e), _)) => { + let response = e.source; + assert_eq!(response.code(), Code::InternalError); + assert_eq!(response.message(), "Internal error"); + assert_eq!( + response.data(), + Some("height must be greater than 0, but got 0") + ); + }, + _ => panic!("expected Response error"), + } + }, + "block_at_height_1" => { + let result = endpoint::block::Response::from_string(content).unwrap(); + assert!(result.block.data.get(0).is_none()); + assert!(result.block.evidence.iter().next().is_none()); + assert!(result.block.header.app_hash.as_bytes().is_empty()); + assert_eq!(result.block.header.chain_id.as_str(), CHAIN_ID); + assert!(!result.block.header.consensus_hash.is_empty()); + assert_eq!(result.block.header.data_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.evidence_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.height.value(), 1); + assert!(result.block.header.last_block_id.is_none()); + assert_eq!(result.block.header.last_commit_hash, empty_merkle_root_hash); + assert_eq!( + result.block.header.last_results_hash, + empty_merkle_root_hash + ); + assert!(!result.block.header.next_validators_hash.is_empty()); + assert_ne!( + result.block.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + result + .block + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!result.block.header.validators_hash.is_empty()); + assert_eq!( + result.block.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + assert!(result.block.last_commit.is_none()); + assert!(!result.block_id.hash.is_empty()); + assert!(!result.block_id.part_set_header.hash.is_empty()); + assert_eq!(result.block_id.part_set_header.total, 1); + }, + "block_at_height_10" => { + let result = endpoint::block::Response::from_string(content).unwrap(); + assert!(result.block.data.get(0).is_none()); + assert!(result.block.evidence.iter().next().is_none()); + assert_eq!(result.block.header.app_hash.as_bytes(), &[0u8; 8]); + assert_eq!(result.block.header.chain_id.as_str(), CHAIN_ID); + assert!(!result.block.header.consensus_hash.is_empty()); + assert_eq!(result.block.header.data_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.evidence_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.height.value(), 10); + assert!(result.block.header.last_block_id.is_some()); + assert!(result.block.header.last_commit_hash.is_some()); + assert!(result.block.header.last_results_hash.is_some()); + assert!(!result.block.header.next_validators_hash.is_empty()); + assert_ne!( + result.block.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + result + .block + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!result.block.header.validators_hash.is_empty()); + assert_eq!( + result.block.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = result.block.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.height.value(), 9); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + // It's weird but there is no implementation to get the signature out of CommitSig. + assert!(!result.block_id.hash.is_empty()); + assert!(!result.block_id.part_set_header.hash.is_empty()); + assert_eq!(result.block_id.part_set_header.total, 1); + }, + "block_results_at_height_10" => { + let result: endpoint::block_results::Response = + endpoint::block_results::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert!(result.begin_block_events.is_none()); + assert!(result.consensus_param_updates.is_none()); + assert!(result.end_block_events.is_none()); + assert_eq!(result.height.value(), 10); + assert!(result.txs_results.is_none()); + assert!(result.validator_updates.is_empty()); + }, + "block_by_hash" => { + let result = endpoint::block_by_hash::Response::from_string(content).unwrap(); + assert_eq!( + result.block_id.hash.to_string(), + "BCF3DB412E80A396D10BF5B5E6D3E63D3B06DEB25AA958BCB8CE18D023838042" + ); + }, + "block_search" => { + let result = endpoint::block_search::Response::from_string(content).unwrap(); + assert_eq!(result.total_count as usize, result.blocks.len()); + for response in result.blocks { + assert!(response.block.header.height.value() > 1); + } + }, + "block_search_evidence" => { + let result = endpoint::block_search::Response::from_string(content).unwrap(); + assert_eq!(result.total_count as usize, result.blocks.len()); + + // Test a few selected attributes of the results. + for block in result.blocks { + let evidence = block.block.evidence.iter().next().unwrap(); + + use tendermint::vote; + + fn check_vote(vote: &Vote) { + assert_eq!(vote.vote_type, vote::Type::Precommit); + assert_eq!(vote.height.value(), 8009); + assert_eq!(vote.round.value(), 0); + assert_eq!( + vote.validator_address, + "9319035301DA526CC78DCF174A47A74F81401291".parse().unwrap(), + ); + assert_eq!(vote.validator_index.value(), 8); + } + + if let Evidence::DuplicateVote(dup) = evidence { + assert_eq!(dup.total_voting_power.value(), 121); + assert_eq!(dup.validator_power.value(), 1); + assert_eq!( + dup.timestamp, + "2022-09-12T19:49:49.984608464Z".parse().unwrap() + ); + + check_vote(&dup.vote_a); + check_vote(&dup.vote_b); + } else { + panic!("not a duplicate vote: {evidence:?}"); + } + } + }, + "broadcast_tx_async" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "broadcast_tx_commit" => { + let result: endpoint::broadcast::tx_commit::Response = + endpoint::broadcast::tx_commit::DialectResponse::::from_string( + content, + ) + .unwrap() + .into(); + assert_eq!(result.check_tx.code, abci::Code::Ok); + assert!(result.check_tx.codespace.is_empty()); + assert!(result.check_tx.data.is_empty()); + assert!(result.check_tx.events.is_empty()); + assert_eq!(result.check_tx.gas_used, 0); + // Todo: https://github.com/informalsystems/tendermint-rs/issues/761 + // assert_eq!(result.check_tx.gas_wanted.value(), 1); + assert!(result.check_tx.info.to_string().is_empty()); + assert!(result.check_tx.log.is_empty()); + assert_eq!(result.deliver_tx.code, abci::Code::Ok); + assert!(result.deliver_tx.codespace.is_empty()); + assert!(result.deliver_tx.data.is_empty()); + assert_eq!(result.deliver_tx.events.len(), 1); + assert_eq!(result.deliver_tx.events[0].attributes.len(), 4); + assert_eq!(result.deliver_tx.events[0].attributes[0].key, "creator"); + assert_eq!( + result.deliver_tx.events[0].attributes[0].value, + "Cosmoshi Netowoko" + ); + assert_eq!(result.deliver_tx.events[0].attributes[1].key, "key"); + assert_eq!( + result.deliver_tx.events[0].attributes[1].value, + "commit-key" + ); + assert_eq!(result.deliver_tx.events[0].attributes[2].key, "index_key"); + assert_eq!( + result.deliver_tx.events[0].attributes[2].value, + "index is working" + ); + assert_eq!(result.deliver_tx.events[0].attributes[3].key, "noindex_key"); + assert_eq!( + result.deliver_tx.events[0].attributes[3].value, + "index is working" + ); + assert_eq!(result.deliver_tx.events[0].kind, "app"); + assert_eq!(result.deliver_tx.gas_used, 0); + assert_eq!(result.deliver_tx.gas_wanted, 0); + assert!(result.deliver_tx.info.to_string().is_empty()); + assert!(result.deliver_tx.log.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + }, + "broadcast_tx_sync" => { + let result = endpoint::broadcast::tx_sync::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "commit_at_height_10" => { + let result = endpoint::commit::Response::from_string(content).unwrap(); + assert!(!result.signed_header.commit.block_id.hash.is_empty()); + assert_eq!(result.signed_header.commit.height.value(), 10); + assert_eq!(result.signed_header.commit.round.value(), 0); + assert_eq!(result.signed_header.commit.signatures.len(), 1); + assert!(result.signed_header.commit.signatures[0].is_commit()); + assert!(result.signed_header.commit.signatures[0] + .validator_address() + .is_some()); + assert_eq!(result.signed_header.header.app_hash.as_bytes(), [0u8; 8]); + assert_eq!(result.signed_header.header.chain_id.as_str(), CHAIN_ID); + assert!(!result.signed_header.header.consensus_hash.is_empty()); + assert_eq!( + result.signed_header.header.data_hash, + empty_merkle_root_hash + ); + assert_eq!( + result.signed_header.header.evidence_hash, + empty_merkle_root_hash + ); + assert_eq!(result.signed_header.header.height.value(), 10); + assert!(result.signed_header.header.last_block_id.is_some()); + assert!(result.signed_header.header.last_commit_hash.is_some()); + assert!(result.signed_header.header.last_results_hash.is_some()); + assert!(!result.signed_header.header.next_validators_hash.is_empty()); + assert_ne!( + result.signed_header.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + result + .signed_header + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!result.signed_header.header.validators_hash.is_empty()); + assert_eq!( + result.signed_header.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + }, + "consensus_params" => { + let result = endpoint::consensus_params::Response::from_string(content).unwrap(); + assert_eq!(u64::from(result.block_height), 10_u64); + assert_eq!(result.consensus_params.block.max_bytes, 22020096_u64); + assert_eq!(result.consensus_params.block.max_gas, -1_i64); + assert_eq!(result.consensus_params.block.time_iota_ms, 500_i64); + assert_eq!( + result.consensus_params.evidence.max_age_duration, + Duration(core::time::Duration::from_nanos(172800000000000_u64)) + ); + assert_eq!( + result.consensus_params.evidence.max_age_num_blocks, + 100000_u64 + ); + assert_eq!(result.consensus_params.evidence.max_bytes, 1048576_i64); + assert_eq!( + result.consensus_params.validator.pub_key_types, + vec![public_key::Algorithm::Ed25519] + ); + }, + "consensus_state" => { + assert!(endpoint::consensus_state::Response::from_string(content).is_ok()); + }, + "genesis" => { + let result = + endpoint::genesis::Response::>::from_string(content) + .unwrap(); + assert!(result.genesis.app_hash.as_bytes().is_empty()); + assert_eq!(result.genesis.chain_id.as_str(), CHAIN_ID); + assert_eq!(result.genesis.consensus_params.block.max_bytes, 22020096); + assert_eq!(result.genesis.consensus_params.block.max_gas, -1); + assert_eq!( + result + .genesis + .consensus_params + .evidence + .max_age_duration + .0 + .as_nanos(), + 172800000000000 + ); + assert_eq!( + result.genesis.consensus_params.evidence.max_age_num_blocks, + 100000 + ); + assert_eq!(result.genesis.consensus_params.evidence.max_bytes, 1048576); + assert_eq!( + result + .genesis + .consensus_params + .validator + .pub_key_types + .len(), + 1 + ); + assert_eq!( + result.genesis.consensus_params.validator.pub_key_types[0], + tendermint::public_key::Algorithm::Ed25519 + ); + assert!(result.genesis.consensus_params.version.is_none()); + assert!( + result + .genesis + .genesis_time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert_eq!(result.genesis.validators.len(), 1); + assert_ne!( + result.genesis.validators[0].address.as_bytes(), + [0; tendermint::account::LENGTH] + ); + assert_eq!(result.genesis.validators[0].power(), 10); + assert!(result.genesis.validators[0].pub_key.ed25519().is_some()); + assert_eq!(result.genesis.validators[0].proposer_priority.value(), 0); + assert_eq!(result.genesis.consensus_params.block.time_iota_ms, 500); + }, + "net_info" => { + let result = endpoint::net_info::Response::from_string(content).unwrap(); + assert_eq!(result.listeners.len(), 1); + assert_eq!(result.listeners[0].to_string(), "Listener(@)"); + assert!(result.listening); + assert_eq!(result.n_peers, 0); + assert!(result.peers.is_empty()); + }, + "status" => { + let result = endpoint::status::Response::from_string(content).unwrap(); + assert_eq!( + Address::from_listen_address(&result.node_info.listen_addr).unwrap(), + Address::from_str("tcp://0.0.0.0:26656").unwrap() + ); + assert_eq!(result.node_info.moniker.to_string(), "dockernode"); + assert_eq!(result.node_info.network.to_string(), CHAIN_ID); + assert_eq!( + result.node_info.other.rpc_address, + format!("{}", Address::from_str("tcp://0.0.0.0:26657").unwrap()) + ); + assert_eq!( + result.node_info.other.tx_index, + tendermint::node::info::TxIndexStatus::On + ); + assert_eq!( + result.node_info.protocol_version, + tendermint::node::info::ProtocolVersionInfo { + p2p: 8, + block: 11, + app: 1 + } + ); + assert_eq!(result.node_info.version.to_string(), "0.34.21"); + assert!(!result.sync_info.catching_up); + assert_eq!( + result.sync_info.latest_app_hash.as_bytes(), + [6, 0, 0, 0, 0, 0, 0, 0] + ); + assert!(!result.sync_info.latest_block_hash.is_empty()); + assert!( + result + .sync_info + .latest_block_time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(result.validator_info.pub_key.ed25519().is_some()); + assert_eq!(result.validator_info.power.value(), 10); + }, + "blockchain_from_1_to_10" => { + let result = endpoint::blockchain::Response::from_string(content).unwrap(); + assert_eq!(result.block_metas.len(), 10); + for block_meta in result.block_metas { + assert!(!block_meta.block_id.hash.is_empty()); + assert!(!block_meta.block_id.part_set_header.hash.is_empty()); + assert_eq!(block_meta.block_id.part_set_header.total, 1); + assert!(block_meta.block_size > 0); + if block_meta.header.height.value() == 1 { + assert!(block_meta.header.app_hash.as_bytes().is_empty()); + assert_eq!(block_meta.header.data_hash, empty_merkle_root_hash); + assert_eq!(block_meta.header.evidence_hash, empty_merkle_root_hash); + assert!(block_meta.header.last_block_id.is_none()); + assert_eq!(block_meta.header.last_commit_hash, empty_merkle_root_hash); + assert_eq!(block_meta.header.last_results_hash, empty_merkle_root_hash); + } else { + assert!(!block_meta.header.app_hash.as_bytes().is_empty()); + assert!(block_meta.header.data_hash.is_some()); + assert!(block_meta.header.evidence_hash.is_some()); + assert!(block_meta.header.last_block_id.is_some()); + assert!(block_meta.header.last_commit_hash.is_some()); + assert!(block_meta.header.last_results_hash.is_some()); + } + assert_eq!(block_meta.header.chain_id.as_str(), CHAIN_ID); + assert!(!block_meta.header.consensus_hash.is_empty()); + assert!(!block_meta.header.next_validators_hash.is_empty()); + assert_ne!( + block_meta.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + block_meta + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!block_meta.header.validators_hash.is_empty()); + assert_eq!( + block_meta.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + assert_eq!(block_meta.num_txs, 0); + } + }, + "subscribe_malformed" => { + let result = endpoint::subscribe::Response::from_string(content); + + match result { + Err(Error(ErrorDetail::Response(e), _)) => { + let response = e.source; + + assert_eq!(response.code(), Code::InternalError); + assert_eq!(response.message(), "Internal error"); + assert_eq!(response.data().unwrap(),"failed to parse query: \nparse error near PegText (line 1 symbol 2 - line 1 symbol 11):\n\"malformed\"\n"); + }, + _ => panic!("expected Response error"), + } + }, + "subscribe_newblock" => { + let result = endpoint::subscribe::Response::from_string(content); + + match result { + Err(Error(ErrorDetail::Serde(_), _)) => {}, + _ => panic!("expected Serde parse error, instead got {result:?}"), + } + }, + "subscribe_newblock_0" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_1" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + let rbb = result_begin_block.unwrap(); + assert_eq!(rbb.events.len(), 2); + assert_eq!(rbb.events[0].kind, "transfer"); + assert_eq!(rbb.events[0].attributes.len(), 2); + assert_eq!(rbb.events[0].attributes[0].key, "recipient"); + assert_eq!( + rbb.events[0].attributes[0].value, + "cosmos17xpfvakm2amg962yls6f84z3kell8c5lserqta" + ); + assert!(rbb.events[0].attributes[0].index); + assert_eq!(rbb.events[0].attributes[1].key, "sender"); + assert_eq!( + rbb.events[0].attributes[1].value, + "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" + ); + assert!(!rbb.events[0].attributes[1].index); + assert_eq!(rbb.events[1].kind, "message"); + assert_eq!(rbb.events[1].attributes.len(), 1); + assert_eq!(rbb.events[1].attributes[0].key, "sender"); + assert_eq!( + rbb.events[1].attributes[0].value, + "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" + ); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_2" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_3" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_4" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_txs" => { + assert!(endpoint::subscribe::Response::from_string(content).is_ok()); + }, + "subscribe_txs_0" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx0"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgwPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx0", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_1" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx1"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgxPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + + check_event_attrs(&result.events.unwrap(), "tx1", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_2" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx2"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgyPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx2", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_3" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx3"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgzPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx3", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_4" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx4"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHg0PXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx4", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_broadcast_tx_0" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_1" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_2" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_3" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_4" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_5" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "tx" => { + let result: endpoint::tx::Response = + endpoint::tx::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert_eq!( + result.hash, + Hash::from_bytes( + Algorithm::Sha256, + &[ + 214, 63, 156, 35, 121, 30, 97, 4, 16, 181, 118, 216, 194, 123, 181, + 174, 172, 147, 204, 26, 88, 82, 36, 40, 167, 179, 42, 18, 118, 8, 88, + 96 + ] + ) + .unwrap() + ); + assert_eq!(u64::from(result.height), 12u64); + }, + "tx_search_no_prove" => { + let result: endpoint::tx_search::Response = + endpoint::tx_search::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert_eq!(result.total_count as usize, result.txs.len()); + // Test a few selected attributes of the results. + for tx in result.txs { + assert_ne!(tx.hash.as_bytes(), [0; 32]); + assert_eq!(tx.tx_result.code, abci::Code::Ok); + assert_eq!(tx.tx_result.events.len(), 1); + assert_eq!(tx.tx_result.events[0].kind, "app"); + assert_eq!(tx.tx_result.gas_used, 0); + assert_eq!(tx.tx_result.gas_wanted, 0); + assert!(tx.tx_result.info.to_string().is_empty()); + assert!(tx.tx_result.log.is_empty()); + assert!(tx.proof.is_none()); + } + }, + "tx_search_with_prove" => { + let result: endpoint::tx_search::Response = + endpoint::tx_search::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert_eq!(result.total_count as usize, result.txs.len()); + // Test a few selected attributes of the results. + for tx in result.txs { + assert_ne!(tx.hash.as_bytes(), [0; 32]); + assert_eq!(tx.tx_result.code, abci::Code::Ok); + assert_eq!(tx.tx_result.events.len(), 1); + assert_eq!(tx.tx_result.events[0].kind, "app"); + assert_eq!(tx.tx_result.gas_used, 0); + assert_eq!(tx.tx_result.gas_wanted, 0); + assert!(tx.tx_result.info.to_string().is_empty()); + assert!(tx.tx_result.log.is_empty()); + let proof = tx.proof.unwrap(); + assert_eq!(proof.data, tx.tx); + assert_eq!(proof.proof.total, 1); + assert_eq!(proof.proof.index, 0); + assert_ne!(proof.root_hash.as_bytes(), [0; 32]); + } + }, + _ => { + panic!("cannot parse file name: {file_name}"); + }, + } + } +} + +fn check_event_attrs(events: &HashMap>, app_key: &str, height: i64) { + for (k, v) in events { + assert_eq!(v.len(), 1); + match k.as_str() { + "app.creator" => assert_eq!(v[0], "Cosmoshi Netowoko"), + "app.index_key" => assert_eq!(v[0], "index is working"), + "app.key" => assert_eq!(v[0], app_key), + "app.noindex_key" => assert_eq!(v[0], "index is working"), + "tm.event" => assert_eq!(v[0], "Tx"), + "tx.hash" => assert_eq!(v[0].len(), 64), + "tx.height" => assert_eq!(v[0], height.to_string()), + _ => panic!("unknown event found {k}"), + } + } +} diff --git a/rpc/tests/kvstore_fixtures/incoming/abci_info.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/abci_info.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/abci_info.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/abci_info.json diff --git a/rpc/tests/kvstore_fixtures/incoming/abci_query_with_existing_key.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/abci_query_with_existing_key.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/abci_query_with_existing_key.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/abci_query_with_existing_key.json diff --git a/rpc/tests/kvstore_fixtures/incoming/abci_query_with_non_existent_key.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/abci_query_with_non_existent_key.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/abci_query_with_non_existent_key.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/abci_query_with_non_existent_key.json diff --git a/rpc/tests/kvstore_fixtures/incoming/block_at_height_0.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/block_at_height_0.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/block_at_height_0.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/block_at_height_0.json diff --git a/rpc/tests/kvstore_fixtures/incoming/block_at_height_1.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/block_at_height_1.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/block_at_height_1.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/block_at_height_1.json diff --git a/rpc/tests/kvstore_fixtures/incoming/block_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/block_at_height_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/block_at_height_10.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/block_at_height_10.json diff --git a/rpc/tests/kvstore_fixtures/incoming/block_by_hash.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/block_by_hash.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/block_by_hash.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/block_by_hash.json diff --git a/rpc/tests/kvstore_fixtures/incoming/block_results_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/block_results_at_height_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/block_results_at_height_10.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/block_results_at_height_10.json diff --git a/rpc/tests/kvstore_fixtures/incoming/block_search.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/block_search.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/block_search.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/block_search.json diff --git a/rpc/tests/kvstore_fixtures/incoming/block_search_evidence.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/block_search_evidence.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/block_search_evidence.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/block_search_evidence.json diff --git a/rpc/tests/kvstore_fixtures/incoming/blockchain_from_1_to_10.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/blockchain_from_1_to_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/blockchain_from_1_to_10.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/blockchain_from_1_to_10.json diff --git a/rpc/tests/kvstore_fixtures/incoming/broadcast_tx_async.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/broadcast_tx_async.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/broadcast_tx_async.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/broadcast_tx_async.json diff --git a/rpc/tests/kvstore_fixtures/incoming/broadcast_tx_commit.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/broadcast_tx_commit.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/broadcast_tx_commit.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/broadcast_tx_commit.json diff --git a/rpc/tests/kvstore_fixtures/incoming/broadcast_tx_sync.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/broadcast_tx_sync.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/broadcast_tx_sync.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/broadcast_tx_sync.json diff --git a/rpc/tests/kvstore_fixtures/incoming/commit_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/commit_at_height_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/commit_at_height_10.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/commit_at_height_10.json diff --git a/rpc/tests/kvstore_fixtures/incoming/consensus_params.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/consensus_params.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/consensus_params.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/consensus_params.json diff --git a/rpc/tests/kvstore_fixtures/incoming/consensus_state.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/consensus_state.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/consensus_state.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/consensus_state.json diff --git a/rpc/tests/kvstore_fixtures/incoming/genesis.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/genesis.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/genesis.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/genesis.json diff --git a/rpc/tests/kvstore_fixtures/incoming/net_info.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/net_info.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/net_info.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/net_info.json diff --git a/rpc/tests/kvstore_fixtures/incoming/status.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/status.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/status.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/status.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_malformed.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_malformed.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_malformed.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_malformed.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_newblock.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_newblock.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_0.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_0.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_0.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_0.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_1.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_1.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_1.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_1.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_2.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_2.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_2.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_2.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_3.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_3.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_3.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_3.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_4.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_4.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_newblock_4.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_newblock_4.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_0.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_0.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_0.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_0.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_1.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_1.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_1.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_1.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_2.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_2.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_2.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_2.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_3.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_3.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_3.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_3.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_4.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_4.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_4.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_4.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_0.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_0.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_0.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_0.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_1.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_1.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_1.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_1.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_2.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_2.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_2.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_2.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_3.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_3.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_3.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_3.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_4.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_4.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_4.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_4.json diff --git a/rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_5.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_5.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/subscribe_txs_broadcast_tx_5.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/subscribe_txs_broadcast_tx_5.json diff --git a/rpc/tests/kvstore_fixtures/incoming/tx.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/tx.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/tx.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/tx.json diff --git a/rpc/tests/kvstore_fixtures/incoming/tx_search_no_prove.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/tx_search_no_prove.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/tx_search_no_prove.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/tx_search_no_prove.json diff --git a/rpc/tests/kvstore_fixtures/incoming/tx_search_with_prove.json b/rpc/tests/kvstore_fixtures/v0_34/incoming/tx_search_with_prove.json similarity index 100% rename from rpc/tests/kvstore_fixtures/incoming/tx_search_with_prove.json rename to rpc/tests/kvstore_fixtures/v0_34/incoming/tx_search_with_prove.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/abci_info.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/abci_info.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/abci_info.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/abci_info.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/abci_query_with_existing_key.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/abci_query_with_existing_key.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/abci_query_with_existing_key.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/abci_query_with_existing_key.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/abci_query_with_non_existent_key.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/abci_query_with_non_existent_key.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/abci_query_with_non_existent_key.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/abci_query_with_non_existent_key.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/block_at_height_0.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/block_at_height_0.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/block_at_height_0.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/block_at_height_0.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/block_at_height_1.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/block_at_height_1.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/block_at_height_1.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/block_at_height_1.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/block_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/block_at_height_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/block_at_height_10.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/block_at_height_10.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/block_by_hash.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/block_by_hash.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/block_by_hash.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/block_by_hash.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/block_results_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/block_results_at_height_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/block_results_at_height_10.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/block_results_at_height_10.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/block_search.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/block_search.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/block_search.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/block_search.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/blockchain_from_1_to_10.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/blockchain_from_1_to_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/blockchain_from_1_to_10.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/blockchain_from_1_to_10.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/broadcast_tx_async.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/broadcast_tx_async.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/broadcast_tx_async.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/broadcast_tx_async.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/broadcast_tx_commit.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/broadcast_tx_commit.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/broadcast_tx_commit.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/broadcast_tx_commit.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/broadcast_tx_sync.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/broadcast_tx_sync.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/broadcast_tx_sync.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/broadcast_tx_sync.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/commit_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/commit_at_height_10.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/commit_at_height_10.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/commit_at_height_10.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/consensus_params.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/consensus_params.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/consensus_params.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/consensus_params.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/consensus_state.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/consensus_state.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/consensus_state.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/consensus_state.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/genesis.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/genesis.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/genesis.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/genesis.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/net_info.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/net_info.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/net_info.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/net_info.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/status.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/status.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/status.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/status.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_malformed.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_malformed.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_malformed.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_malformed.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_newblock.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_newblock.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_newblock.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_newblock.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_txs.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_txs.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_0.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_0.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_0.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_0.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_1.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_1.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_1.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_1.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_2.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_2.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_2.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_2.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_3.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_3.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_3.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_3.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_4.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_4.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_4.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_4.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_5.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_5.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/subscribe_txs_broadcast_tx_5.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/subscribe_txs_broadcast_tx_5.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/tx.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/tx.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/tx.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/tx.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/tx_search_no_prove.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/tx_search_no_prove.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/tx_search_no_prove.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/tx_search_no_prove.json diff --git a/rpc/tests/kvstore_fixtures/outgoing/tx_search_with_prove.json b/rpc/tests/kvstore_fixtures/v0_34/outgoing/tx_search_with_prove.json similarity index 100% rename from rpc/tests/kvstore_fixtures/outgoing/tx_search_with_prove.json rename to rpc/tests/kvstore_fixtures/v0_34/outgoing/tx_search_with_prove.json diff --git a/rpc/tests/kvstore_fixtures/v0_37.rs b/rpc/tests/kvstore_fixtures/v0_37.rs new file mode 100644 index 000000000..448d48d95 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37.rs @@ -0,0 +1,1396 @@ +use super::*; + +#[test] +fn outgoing_fixtures() { + for json_file in find_fixtures("v0_37", "outgoing") { + let file_name = json_file + .file_name() + .unwrap() + .to_str() + .unwrap() + .strip_suffix(".json") + .unwrap(); + let content = fs::read_to_string(&json_file).unwrap(); + match file_name { + "abci_info" => assert!(serde_json::from_str::< + RequestWrapper, + >(&content) + .is_ok()), + "abci_query_with_existing_key" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert!(wrapped.params().path.is_none()); + assert_eq!(wrapped.params().data, hex::decode("747830").unwrap()); + assert!(wrapped.params().height.is_none()); + assert!(!wrapped.params().prove); + }, + "abci_query_with_non_existent_key" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert!(wrapped.params().path.is_none()); + assert_eq!( + wrapped.params().data, + hex::decode("6e6f6e5f6578697374656e745f6b6579").unwrap() + ); + assert!(wrapped.params().height.is_none()); + assert!(!wrapped.params().prove); + }, + "block_at_height_0" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 0); + }, + "block_at_height_1" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 1); + }, + "block_at_height_10" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 10); + }, + "block_by_hash" => { + // First, get the hash at height 1. + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().hash.unwrap().to_string(), + "00112233445566778899AABBCCDDEEFF00112233445566778899AABBCCDDEEFF" + ); + }, + "block_results_at_height_10" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 10); + }, + "block_search" => { + let wrapped = + serde_json::from_str::>( + &content, + ) + .unwrap(); + assert_eq!(wrapped.params().query, "block.height > 1"); + assert_eq!(wrapped.params().page, 1); + assert_eq!(wrapped.params().per_page, 100); + assert_eq!(wrapped.params().order_by, Order::Ascending); + }, + "blockchain_from_1_to_10" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().min_height.value(), 1); + assert_eq!(wrapped.params().max_height.value(), 10); + }, + "broadcast_tx_async" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().tx, + base64::decode("YXN5bmMta2V5PXZhbHVl").unwrap() + ); + }, + "broadcast_tx_commit" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().tx, + base64::decode("Y29tbWl0LWtleT12YWx1ZQ==").unwrap() + ); + }, + "broadcast_tx_sync" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!( + wrapped.params().tx, + base64::decode("c3luYy1rZXk9dmFsdWU=").unwrap() + ); + }, + "commit_at_height_10" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().height.unwrap().value(), 10); + }, + "consensus_params" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + let height = wrapped.params().height.unwrap(); + assert_eq!(u64::from(height), 10u64); + }, + "consensus_state" => assert!(serde_json::from_str::< + RequestWrapper, + >(&content) + .is_ok()), + "genesis" => assert!(serde_json::from_str::< + RequestWrapper>, + >(&content) + .is_ok()), + "net_info" => assert!(serde_json::from_str::< + RequestWrapper, + >(&content) + .is_ok()), + "status" => assert!( + serde_json::from_str::>(&content).is_ok() + ), + "subscribe_malformed" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "malformed query"); + }, + "subscribe_newblock" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tm.event = 'NewBlock'"); + }, + "subscribe_txs" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tm.event = 'Tx'"); + }, + "subscribe_txs_broadcast_tx_0" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgwPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_1" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgxPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_2" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgyPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_3" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHgzPXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_4" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHg0PXZhbHVl").unwrap()); + }, + "subscribe_txs_broadcast_tx_5" => { + let wrapped = serde_json::from_str::< + RequestWrapper, + >(&content) + .unwrap(); + assert_eq!(wrapped.params().tx, base64::decode("dHg1PXZhbHVl").unwrap()); + }, + "tx" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!( + wrapped.params().hash, + Hash::from_bytes( + Algorithm::Sha256, + &[ + 214, 63, 156, 35, 121, 30, 97, 4, 16, 181, 118, 216, 194, 123, 181, + 174, 172, 147, 204, 26, 88, 82, 36, 40, 167, 179, 42, 18, 118, 8, 88, + 96 + ] + ) + .unwrap() + ); + assert!(!wrapped.params().prove); + }, + "tx_search_no_prove" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tx.height > 1"); + assert!(!wrapped.params().prove); + assert_eq!(wrapped.params().page, 1); + assert_eq!(wrapped.params().per_page, 10); + assert_eq!(wrapped.params().order_by, Order::Ascending); + }, + "tx_search_with_prove" => { + let wrapped = + serde_json::from_str::>(&content) + .unwrap(); + assert_eq!(wrapped.params().query, "tx.height > 1"); + assert!(wrapped.params().prove); + assert_eq!(wrapped.params().page, 1); + assert_eq!(wrapped.params().per_page, 10); + assert_eq!(wrapped.params().order_by, Order::Ascending); + }, + _ => { + panic!("cannot parse file name: {file_name}"); + }, + } + } +} + +#[test] +fn incoming_fixtures() { + use tendermint_rpc::dialect::v0_37::Event as RpcEvent; + + let empty_merkle_root_hash = Some( + tendermint::Hash::from_hex_upper( + tendermint::hash::Algorithm::Sha256, + "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + ) + .unwrap(), + ); + let informal_epoch = + tendermint::Time::parse_from_rfc3339("2020-01-01T00:00:00.000000000Z").unwrap(); + + for json_file in find_fixtures("v0_37", "incoming") { + let file_name = json_file + .file_name() + .unwrap() + .to_str() + .unwrap() + .strip_suffix(".json") + .unwrap(); + let content = fs::read_to_string(&json_file).unwrap(); + match file_name { + "abci_info" => { + let result = endpoint::abci_info::Response::from_string(content).unwrap(); + assert_eq!(result.response.app_version, 1); + assert_eq!(result.response.data, "{\"size\":0}"); + assert_eq!( + result.response.last_block_app_hash.as_bytes(), + b"AAAAAAAAAAA=" + ); + assert_eq!(result.response.version, "1.0.0"); + }, + "abci_query_with_existing_key" => { + let result = endpoint::abci_query::Response::from_string(content).unwrap(); + assert_eq!(result.response.code.value(), 0); + assert!(result.response.codespace.is_empty()); + assert_eq!(result.response.index, 0); + assert!(result.response.info.is_empty()); + assert_eq!(result.response.key, base64::decode("dHgw").unwrap()); + assert_eq!(result.response.log, "exists"); + assert!(result.response.proof.is_none()); + assert_eq!(result.response.value, base64::decode("dmFsdWU=").unwrap()); + }, + "abci_query_with_non_existent_key" => { + let result = endpoint::abci_query::Response::from_string(content).unwrap(); + assert_eq!(result.response.code.value(), 0); + assert!(result.response.codespace.is_empty()); + assert_eq!(result.response.index, 0); + assert!(result.response.info.is_empty()); + assert_eq!( + result.response.key, + base64::decode("bm9uX2V4aXN0ZW50X2tleQ==").unwrap() + ); + assert_eq!(result.response.log, "does not exist"); + assert!(result.response.proof.is_none()); + assert!(result.response.value.is_empty()); + }, + "block_at_height_0" => { + let res = endpoint::block::Response::from_string(&content); + + match res { + Err(Error(ErrorDetail::Response(e), _)) => { + let response = e.source; + assert_eq!(response.code(), Code::InternalError); + assert_eq!(response.message(), "Internal error"); + assert_eq!( + response.data(), + Some("height must be greater than 0, but got 0") + ); + }, + _ => panic!("expected Response error"), + } + }, + "block_at_height_1" => { + let result = endpoint::block::Response::from_string(content).unwrap(); + assert!(result.block.data.get(0).is_none()); + assert!(result.block.evidence.iter().next().is_none()); + assert!(result.block.header.app_hash.as_bytes().is_empty()); + assert_eq!(result.block.header.chain_id.as_str(), CHAIN_ID); + assert!(!result.block.header.consensus_hash.is_empty()); + assert_eq!(result.block.header.data_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.evidence_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.height.value(), 1); + assert!(result.block.header.last_block_id.is_none()); + assert_eq!(result.block.header.last_commit_hash, empty_merkle_root_hash); + assert_eq!( + result.block.header.last_results_hash, + empty_merkle_root_hash + ); + assert!(!result.block.header.next_validators_hash.is_empty()); + assert_ne!( + result.block.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + result + .block + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!result.block.header.validators_hash.is_empty()); + assert_eq!( + result.block.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + assert!(result.block.last_commit.is_none()); + assert!(!result.block_id.hash.is_empty()); + assert!(!result.block_id.part_set_header.hash.is_empty()); + assert_eq!(result.block_id.part_set_header.total, 1); + }, + "block_at_height_10" => { + let result = endpoint::block::Response::from_string(content).unwrap(); + assert!(result.block.data.get(0).is_none()); + assert!(result.block.evidence.iter().next().is_none()); + assert_eq!(result.block.header.app_hash.as_bytes(), &[0u8; 8]); + assert_eq!(result.block.header.chain_id.as_str(), CHAIN_ID); + assert!(!result.block.header.consensus_hash.is_empty()); + assert_eq!(result.block.header.data_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.evidence_hash, empty_merkle_root_hash); + assert_eq!(result.block.header.height.value(), 10); + assert!(result.block.header.last_block_id.is_some()); + assert!(result.block.header.last_commit_hash.is_some()); + assert!(result.block.header.last_results_hash.is_some()); + assert!(!result.block.header.next_validators_hash.is_empty()); + assert_ne!( + result.block.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + result + .block + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!result.block.header.validators_hash.is_empty()); + assert_eq!( + result.block.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = result.block.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.height.value(), 9); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + // It's weird but there is no implementation to get the signature out of CommitSig. + assert!(!result.block_id.hash.is_empty()); + assert!(!result.block_id.part_set_header.hash.is_empty()); + assert_eq!(result.block_id.part_set_header.total, 1); + }, + "block_results_at_height_10" => { + let result: endpoint::block_results::Response = + endpoint::block_results::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert!(result.begin_block_events.is_none()); + assert!(result.consensus_param_updates.is_none()); + assert!(result.end_block_events.is_none()); + assert_eq!(result.height.value(), 10); + assert!(result.txs_results.is_none()); + assert!(result.validator_updates.is_empty()); + }, + "block_by_hash" => { + let result = endpoint::block_by_hash::Response::from_string(content).unwrap(); + assert_eq!( + result.block_id.hash.to_string(), + "BCF3DB412E80A396D10BF5B5E6D3E63D3B06DEB25AA958BCB8CE18D023838042" + ); + }, + "block_search" => { + let result = endpoint::block_search::Response::from_string(content).unwrap(); + assert_eq!(result.total_count as usize, result.blocks.len()); + for response in result.blocks { + assert!(response.block.header.height.value() > 1); + } + }, + "block_search_evidence" => { + let result = endpoint::block_search::Response::from_string(content).unwrap(); + assert_eq!(result.total_count as usize, result.blocks.len()); + + // Test a few selected attributes of the results. + for block in result.blocks { + let evidence = block.block.evidence.iter().next().unwrap(); + + use tendermint::vote; + + fn check_vote(vote: &Vote) { + assert_eq!(vote.vote_type, vote::Type::Precommit); + assert_eq!(vote.height.value(), 8009); + assert_eq!(vote.round.value(), 0); + assert_eq!( + vote.validator_address, + "9319035301DA526CC78DCF174A47A74F81401291".parse().unwrap(), + ); + assert_eq!(vote.validator_index.value(), 8); + } + + if let Evidence::DuplicateVote(dup) = evidence { + assert_eq!(dup.total_voting_power.value(), 121); + assert_eq!(dup.validator_power.value(), 1); + assert_eq!( + dup.timestamp, + "2022-09-12T19:49:49.984608464Z".parse().unwrap() + ); + + check_vote(&dup.vote_a); + check_vote(&dup.vote_b); + } else { + panic!("not a duplicate vote: {evidence:?}"); + } + } + }, + "broadcast_tx_async" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "broadcast_tx_commit" => { + let result: endpoint::broadcast::tx_commit::Response = + endpoint::broadcast::tx_commit::DialectResponse::::from_string( + content, + ) + .unwrap() + .into(); + assert_eq!(result.check_tx.code, abci::Code::Ok); + assert!(result.check_tx.codespace.is_empty()); + assert!(result.check_tx.data.is_empty()); + assert!(result.check_tx.events.is_empty()); + assert_eq!(result.check_tx.gas_used, 0); + // Todo: https://github.com/informalsystems/tendermint-rs/issues/761 + // assert_eq!(result.check_tx.gas_wanted.value(), 1); + assert!(result.check_tx.info.to_string().is_empty()); + assert!(result.check_tx.log.is_empty()); + assert_eq!(result.deliver_tx.code, abci::Code::Ok); + assert!(result.deliver_tx.codespace.is_empty()); + assert!(result.deliver_tx.data.is_empty()); + assert_eq!(result.deliver_tx.events.len(), 1); + assert_eq!(result.deliver_tx.events[0].attributes.len(), 4); + assert_eq!(result.deliver_tx.events[0].attributes[0].key, "creator"); + assert_eq!( + result.deliver_tx.events[0].attributes[0].value, + "Cosmoshi Netowoko" + ); + assert_eq!(result.deliver_tx.events[0].attributes[1].key, "key"); + assert_eq!( + result.deliver_tx.events[0].attributes[1].value, + "commit-key" + ); + assert_eq!(result.deliver_tx.events[0].attributes[2].key, "index_key"); + assert_eq!( + result.deliver_tx.events[0].attributes[2].value, + "index is working" + ); + assert_eq!(result.deliver_tx.events[0].attributes[3].key, "noindex_key"); + assert_eq!( + result.deliver_tx.events[0].attributes[3].value, + "index is working" + ); + assert_eq!(result.deliver_tx.events[0].kind, "app"); + assert_eq!(result.deliver_tx.gas_used, 0); + assert_eq!(result.deliver_tx.gas_wanted, 0); + assert!(result.deliver_tx.info.to_string().is_empty()); + assert!(result.deliver_tx.log.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + }, + "broadcast_tx_sync" => { + let result = endpoint::broadcast::tx_sync::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "commit_at_height_10" => { + let result = endpoint::commit::Response::from_string(content).unwrap(); + assert!(!result.signed_header.commit.block_id.hash.is_empty()); + assert_eq!(result.signed_header.commit.height.value(), 10); + assert_eq!(result.signed_header.commit.round.value(), 0); + assert_eq!(result.signed_header.commit.signatures.len(), 1); + assert!(result.signed_header.commit.signatures[0].is_commit()); + assert!(result.signed_header.commit.signatures[0] + .validator_address() + .is_some()); + assert_eq!(result.signed_header.header.app_hash.as_bytes(), [0u8; 8]); + assert_eq!(result.signed_header.header.chain_id.as_str(), CHAIN_ID); + assert!(!result.signed_header.header.consensus_hash.is_empty()); + assert_eq!( + result.signed_header.header.data_hash, + empty_merkle_root_hash + ); + assert_eq!( + result.signed_header.header.evidence_hash, + empty_merkle_root_hash + ); + assert_eq!(result.signed_header.header.height.value(), 10); + assert!(result.signed_header.header.last_block_id.is_some()); + assert!(result.signed_header.header.last_commit_hash.is_some()); + assert!(result.signed_header.header.last_results_hash.is_some()); + assert!(!result.signed_header.header.next_validators_hash.is_empty()); + assert_ne!( + result.signed_header.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + result + .signed_header + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!result.signed_header.header.validators_hash.is_empty()); + assert_eq!( + result.signed_header.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + }, + "consensus_params" => { + let result = endpoint::consensus_params::Response::from_string(content).unwrap(); + assert_eq!(u64::from(result.block_height), 10_u64); + assert_eq!(result.consensus_params.block.max_bytes, 22020096_u64); + assert_eq!(result.consensus_params.block.max_gas, -1_i64); + assert_eq!(result.consensus_params.block.time_iota_ms, 500_i64); + assert_eq!( + result.consensus_params.evidence.max_age_duration, + Duration(core::time::Duration::from_nanos(172800000000000_u64)) + ); + assert_eq!( + result.consensus_params.evidence.max_age_num_blocks, + 100000_u64 + ); + assert_eq!(result.consensus_params.evidence.max_bytes, 1048576_i64); + assert_eq!( + result.consensus_params.validator.pub_key_types, + vec![public_key::Algorithm::Ed25519] + ); + }, + "consensus_state" => { + assert!(endpoint::consensus_state::Response::from_string(content).is_ok()); + }, + "genesis" => { + let result = + endpoint::genesis::Response::>::from_string(content) + .unwrap(); + assert!(result.genesis.app_hash.as_bytes().is_empty()); + assert_eq!(result.genesis.chain_id.as_str(), CHAIN_ID); + assert_eq!(result.genesis.consensus_params.block.max_bytes, 22020096); + assert_eq!(result.genesis.consensus_params.block.max_gas, -1); + assert_eq!( + result + .genesis + .consensus_params + .evidence + .max_age_duration + .0 + .as_nanos(), + 172800000000000 + ); + assert_eq!( + result.genesis.consensus_params.evidence.max_age_num_blocks, + 100000 + ); + assert_eq!(result.genesis.consensus_params.evidence.max_bytes, 1048576); + assert_eq!( + result + .genesis + .consensus_params + .validator + .pub_key_types + .len(), + 1 + ); + assert_eq!( + result.genesis.consensus_params.validator.pub_key_types[0], + tendermint::public_key::Algorithm::Ed25519 + ); + assert!(result.genesis.consensus_params.version.is_none()); + assert!( + result + .genesis + .genesis_time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert_eq!(result.genesis.validators.len(), 1); + assert_ne!( + result.genesis.validators[0].address.as_bytes(), + [0; tendermint::account::LENGTH] + ); + assert_eq!(result.genesis.validators[0].power(), 10); + assert!(result.genesis.validators[0].pub_key.ed25519().is_some()); + assert_eq!(result.genesis.validators[0].proposer_priority.value(), 0); + assert_eq!(result.genesis.consensus_params.block.time_iota_ms, 500); + }, + "net_info" => { + let result = endpoint::net_info::Response::from_string(content).unwrap(); + assert_eq!(result.listeners.len(), 1); + assert_eq!(result.listeners[0].to_string(), "Listener(@)"); + assert!(result.listening); + assert_eq!(result.n_peers, 0); + assert!(result.peers.is_empty()); + }, + "status" => { + let result = endpoint::status::Response::from_string(content).unwrap(); + assert_eq!( + Address::from_listen_address(&result.node_info.listen_addr).unwrap(), + Address::from_str("tcp://0.0.0.0:26656").unwrap() + ); + assert_eq!(result.node_info.moniker.to_string(), "dockernode"); + assert_eq!(result.node_info.network.to_string(), CHAIN_ID); + assert_eq!( + result.node_info.other.rpc_address, + format!("{}", Address::from_str("tcp://0.0.0.0:26657").unwrap()) + ); + assert_eq!( + result.node_info.other.tx_index, + tendermint::node::info::TxIndexStatus::On + ); + assert_eq!( + result.node_info.protocol_version, + tendermint::node::info::ProtocolVersionInfo { + p2p: 8, + block: 11, + app: 1 + } + ); + assert_eq!(result.node_info.version.to_string(), "0.34.21"); + assert!(!result.sync_info.catching_up); + assert_eq!( + result.sync_info.latest_app_hash.as_bytes(), + [6, 0, 0, 0, 0, 0, 0, 0] + ); + assert!(!result.sync_info.latest_block_hash.is_empty()); + assert!( + result + .sync_info + .latest_block_time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(result.validator_info.pub_key.ed25519().is_some()); + assert_eq!(result.validator_info.power.value(), 10); + }, + "blockchain_from_1_to_10" => { + let result = endpoint::blockchain::Response::from_string(content).unwrap(); + assert_eq!(result.block_metas.len(), 10); + for block_meta in result.block_metas { + assert!(!block_meta.block_id.hash.is_empty()); + assert!(!block_meta.block_id.part_set_header.hash.is_empty()); + assert_eq!(block_meta.block_id.part_set_header.total, 1); + assert!(block_meta.block_size > 0); + if block_meta.header.height.value() == 1 { + assert!(block_meta.header.app_hash.as_bytes().is_empty()); + assert_eq!(block_meta.header.data_hash, empty_merkle_root_hash); + assert_eq!(block_meta.header.evidence_hash, empty_merkle_root_hash); + assert!(block_meta.header.last_block_id.is_none()); + assert_eq!(block_meta.header.last_commit_hash, empty_merkle_root_hash); + assert_eq!(block_meta.header.last_results_hash, empty_merkle_root_hash); + } else { + assert!(!block_meta.header.app_hash.as_bytes().is_empty()); + assert!(block_meta.header.data_hash.is_some()); + assert!(block_meta.header.evidence_hash.is_some()); + assert!(block_meta.header.last_block_id.is_some()); + assert!(block_meta.header.last_commit_hash.is_some()); + assert!(block_meta.header.last_results_hash.is_some()); + } + assert_eq!(block_meta.header.chain_id.as_str(), CHAIN_ID); + assert!(!block_meta.header.consensus_hash.is_empty()); + assert!(!block_meta.header.next_validators_hash.is_empty()); + assert_ne!( + block_meta.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + block_meta + .header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!block_meta.header.validators_hash.is_empty()); + assert_eq!( + block_meta.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + assert_eq!(block_meta.num_txs, 0); + } + }, + "subscribe_malformed" => { + let result = endpoint::subscribe::Response::from_string(content); + + match result { + Err(Error(ErrorDetail::Response(e), _)) => { + let response = e.source; + + assert_eq!(response.code(), Code::InternalError); + assert_eq!(response.message(), "Internal error"); + assert_eq!(response.data().unwrap(),"failed to parse query: \nparse error near PegText (line 1 symbol 2 - line 1 symbol 11):\n\"malformed\"\n"); + }, + _ => panic!("expected Response error"), + } + }, + "subscribe_newblock" => { + let result = endpoint::subscribe::Response::from_string(content); + + match result { + Err(Error(ErrorDetail::Serde(_), _)) => {}, + _ => panic!("expected Serde parse error, instead got {result:?}"), + } + }, + "subscribe_newblock_0" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_1" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + let rbb = result_begin_block.unwrap(); + assert_eq!(rbb.events.len(), 2); + assert_eq!(rbb.events[0].kind, "transfer"); + assert_eq!(rbb.events[0].attributes.len(), 2); + assert_eq!(rbb.events[0].attributes[0].key, "recipient"); + assert_eq!( + rbb.events[0].attributes[0].value, + "cosmos17xpfvakm2amg962yls6f84z3kell8c5lserqta" + ); + assert!(rbb.events[0].attributes[0].index); + assert_eq!(rbb.events[0].attributes[1].key, "sender"); + assert_eq!( + rbb.events[0].attributes[1].value, + "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" + ); + assert!(!rbb.events[0].attributes[1].index); + assert_eq!(rbb.events[1].kind, "message"); + assert_eq!(rbb.events[1].attributes.len(), 1); + assert_eq!(rbb.events[1].attributes[0].key, "sender"); + assert_eq!( + rbb.events[1].attributes[0].value, + "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" + ); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_2" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_3" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_newblock_4" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + if let tendermint_rpc::event::EventData::NewBlock { + block, + result_begin_block, + result_end_block, + } = result.data.into() + { + let b = block.unwrap(); + assert!(b.data.get(0).is_none()); + assert!(b.evidence.iter().next().is_none()); + assert!(!b.header.app_hash.as_bytes().is_empty()); + assert_eq!(b.header.chain_id.as_str(), CHAIN_ID); + assert!(!b.header.consensus_hash.is_empty()); + assert_eq!(b.header.data_hash, empty_merkle_root_hash); + assert_eq!(b.header.evidence_hash, empty_merkle_root_hash); + assert!(b.header.last_block_id.is_some()); + assert!(b.header.last_commit_hash.is_some()); + assert!(b.header.last_results_hash.is_some()); + assert!(!b.header.next_validators_hash.is_empty()); + assert_ne!( + b.header.proposer_address.as_bytes(), + [0u8; tendermint::account::LENGTH] + ); + assert!( + b.header + .time + .duration_since(informal_epoch) + .unwrap() + .as_secs() + > 0 + ); + assert!(!b.header.validators_hash.is_empty()); + assert_eq!( + b.header.version, + tendermint::block::header::Version { block: 11, app: 1 } + ); + let last_commit = b.last_commit.unwrap(); + assert!(!last_commit.block_id.hash.is_empty()); + assert!(!last_commit.block_id.part_set_header.hash.is_empty()); + assert_eq!(last_commit.block_id.part_set_header.total, 1); + assert_eq!(last_commit.round.value(), 0); + assert_eq!(last_commit.signatures.len(), 1); + assert!(last_commit.signatures[0].is_commit()); + assert!(last_commit.signatures[0].validator_address().is_some()); + assert!(result_begin_block.unwrap().events.is_empty()); + let reb = result_end_block.unwrap(); + assert!(reb.validator_updates.is_empty()); + assert!(reb.consensus_param_updates.is_none()); + assert!(reb.events.is_empty()); + } else { + panic!("not a newblock"); + } + assert_eq!(result.query, "tm.event = 'NewBlock'"); + }, + "subscribe_txs" => { + assert!(endpoint::subscribe::Response::from_string(content).is_ok()); + }, + "subscribe_txs_0" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx0"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgwPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx0", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_1" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx1"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgxPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + + check_event_attrs(&result.events.unwrap(), "tx1", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_2" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx2"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgyPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx2", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_3" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx3"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHgzPXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx3", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_4" => { + let result = + tendermint_rpc::event::DialectEvent::::from_string(content).unwrap(); + let height; + if let tendermint_rpc::event::EventData::Tx { tx_result } = result.data.into() { + height = tx_result.height; + assert!(tx_result.result.log.is_none()); + assert!(tx_result.result.gas_wanted.is_none()); + assert!(tx_result.result.gas_used.is_none()); + assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events[0].kind, "app"); + for attr in &tx_result.result.events[0].attributes { + match attr.key.as_str() { + "creator" => { + assert_eq!(attr.value, "Cosmoshi Netowoko") + }, + "key" => assert_eq!(attr.value, "tx4"), + "index_key" => { + assert_eq!(attr.value, "index is working") + }, + "noindex_key" => { + assert_eq!(attr.value, "index is working") + }, + _ => panic!("unknown attribute found {}", attr.key), + } + } + assert_eq!(tx_result.tx, base64::decode("dHg0PXZhbHVl").unwrap()); + } else { + panic!("not a tx"); + } + check_event_attrs(&result.events.unwrap(), "tx4", height); + assert_eq!(result.query, "tm.event = 'Tx'"); + }, + "subscribe_txs_broadcast_tx_0" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_1" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_2" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_3" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_4" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "subscribe_txs_broadcast_tx_5" => { + let result = endpoint::broadcast::tx_async::Response::from_string(content).unwrap(); + assert_eq!(result.code, abci::Code::Ok); + assert!(result.data.is_empty()); + assert_ne!( + result.hash, + Hash::from_bytes(Algorithm::Sha256, &[0; 32]).unwrap() + ); + assert!(result.log.is_empty()); + }, + "tx" => { + let result: endpoint::tx::Response = + endpoint::tx::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert_eq!( + result.hash, + Hash::from_bytes( + Algorithm::Sha256, + &[ + 214, 63, 156, 35, 121, 30, 97, 4, 16, 181, 118, 216, 194, 123, 181, + 174, 172, 147, 204, 26, 88, 82, 36, 40, 167, 179, 42, 18, 118, 8, 88, + 96 + ] + ) + .unwrap() + ); + assert_eq!(u64::from(result.height), 12u64); + }, + "tx_search_no_prove" => { + let result: endpoint::tx_search::Response = + endpoint::tx_search::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert_eq!(result.total_count as usize, result.txs.len()); + // Test a few selected attributes of the results. + for tx in result.txs { + assert_ne!(tx.hash.as_bytes(), [0; 32]); + assert_eq!(tx.tx_result.code, abci::Code::Ok); + assert_eq!(tx.tx_result.events.len(), 1); + assert_eq!(tx.tx_result.events[0].kind, "app"); + assert_eq!(tx.tx_result.gas_used, 0); + assert_eq!(tx.tx_result.gas_wanted, 0); + assert!(tx.tx_result.info.to_string().is_empty()); + assert!(tx.tx_result.log.is_empty()); + assert!(tx.proof.is_none()); + } + }, + "tx_search_with_prove" => { + let result: endpoint::tx_search::Response = + endpoint::tx_search::DialectResponse::::from_string(content) + .unwrap() + .into(); + assert_eq!(result.total_count as usize, result.txs.len()); + // Test a few selected attributes of the results. + for tx in result.txs { + assert_ne!(tx.hash.as_bytes(), [0; 32]); + assert_eq!(tx.tx_result.code, abci::Code::Ok); + assert_eq!(tx.tx_result.events.len(), 1); + assert_eq!(tx.tx_result.events[0].kind, "app"); + assert_eq!(tx.tx_result.gas_used, 0); + assert_eq!(tx.tx_result.gas_wanted, 0); + assert!(tx.tx_result.info.to_string().is_empty()); + assert!(tx.tx_result.log.is_empty()); + let proof = tx.proof.unwrap(); + assert_eq!(proof.data, tx.tx); + assert_eq!(proof.proof.total, 1); + assert_eq!(proof.proof.index, 0); + assert_ne!(proof.root_hash.as_bytes(), [0; 32]); + } + }, + _ => { + panic!("cannot parse file name: {file_name}"); + }, + } + } +} diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json new file mode 100644 index 000000000..354f9be15 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json @@ -0,0 +1,13 @@ +{ + "id": "4cdabace-7cae-4347-9675-e69a71a3b19a", + "jsonrpc": "2.0", + "result": { + "response": { + "app_version": "1", + "data": "{\"size\":0}", + "last_block_app_hash": "AAAAAAAAAAA=", + "last_block_height": "200", + "version": "1.0.0" + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json new file mode 100644 index 000000000..059d11785 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json @@ -0,0 +1,17 @@ +{ + "id": "49193475-5bbf-4820-a878-360f8c3c6072", + "jsonrpc": "2.0", + "result": { + "response": { + "code": 0, + "codespace": "", + "height": "256", + "index": "0", + "info": "", + "key": "dHgw", + "log": "exists", + "proofOps": null, + "value": "dmFsdWU=" + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json new file mode 100644 index 000000000..3759a74b9 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json @@ -0,0 +1,17 @@ +{ + "id": "6c6583ab-27ed-44ac-b704-78abe4723da9", + "jsonrpc": "2.0", + "result": { + "response": { + "code": 0, + "codespace": "", + "height": "202", + "index": "0", + "info": "", + "key": "bm9uX2V4aXN0ZW50X2tleQ==", + "log": "does not exist", + "proofOps": null, + "value": null + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json new file mode 100644 index 000000000..7bd847802 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json @@ -0,0 +1,9 @@ +{ + "error": { + "code": -32603, + "data": "height must be greater than 0, but got 0", + "message": "Internal error" + }, + "id": "2f4bc09e-7e2d-4514-a833-16e86d1af67e", + "jsonrpc": "2.0" +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json new file mode 100644 index 000000000..d331f8649 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json @@ -0,0 +1,58 @@ +{ + "id": "1356e29e-da5d-451a-b42d-cd3931bdb8f6", + "jsonrpc": "2.0", + "result": { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "1", + "last_block_id": { + "hash": "", + "parts": { + "hash": "", + "total": 0 + } + }, + "last_commit_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:35.386925428Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "", + "parts": { + "hash": "", + "total": 0 + } + }, + "height": "0", + "round": 0, + "signatures": [] + } + }, + "block_id": { + "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "parts": { + "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "total": 1 + } + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json new file mode 100644 index 000000000..226628cd4 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json @@ -0,0 +1,65 @@ +{ + "id": "1fa8bed7-d111-484d-abee-902fa1454069", + "jsonrpc": "2.0", + "result": { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "10", + "last_block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + }, + "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:40.123954449Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + }, + "height": "9", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "V8j/4eDj/LWDhjiCBvYZgBZXOp891keTHM1y9tpAMiUHrnDllS6DWuq9EYxftB9hA31pGvZKHM5v5SdNRFV4DA==", + "timestamp": "2023-02-24T15:09:40.123954449Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "parts": { + "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "total": 1 + } + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json new file mode 100644 index 000000000..026fedbff --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json @@ -0,0 +1,14 @@ +{ + "id": "abd9f0d1-5b80-424a-8f7d-94b2d854707c", + "jsonrpc": "2.0", + "result": { + "block": null, + "block_id": { + "hash": "", + "parts": { + "hash": "", + "total": 0 + } + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json new file mode 100644 index 000000000..c22e95e07 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json @@ -0,0 +1,12 @@ +{ + "id": "a5154e64-bf10-4b5f-960a-ed4eec5e261d", + "jsonrpc": "2.0", + "result": { + "begin_block_events": null, + "consensus_param_updates": null, + "end_block_events": null, + "height": "10", + "txs_results": null, + "validator_updates": null + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json new file mode 100644 index 000000000..d6e399469 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json @@ -0,0 +1,6109 @@ +{ + "id": "35b99dba-c7c1-4229-be9c-23fa795e4432", + "jsonrpc": "2.0", + "result": { + "blocks": [ + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "2", + "last_block_id": { + "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "parts": { + "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "total": 1 + } + }, + "last_commit_hash": "227D78AC78B219692FC3EE18BCE5FD46E86F382979628FB6BE01DDF4C9E66750", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:35.982946125Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "parts": { + "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "total": 1 + } + }, + "height": "1", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "0ALiGU3vSUd1Gg349Uzxv9BhyVVbk0R8PpEmBnBeuccKx9RoREEt7UZaqHNUIwfR2PkTpM9yNsG+7vteMD0HCA==", + "timestamp": "2023-02-24T15:09:35.982946125Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "parts": { + "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "3", + "last_block_id": { + "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "parts": { + "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "total": 1 + } + }, + "last_commit_hash": "6237CD7F07174FB28966A889F6A9B4D26DC6D7F104D0B4333007E6C2AB7D61C1", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:36.499560496Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "parts": { + "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "total": 1 + } + }, + "height": "2", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "0UeNQrmaSfjb41umFq3N4DoRWzU2yRpDquN43+Kp5u5VGpUS3Ps2mF+zFO1ndy8u3Ta3GFnYdjW9nlqTaK0WAQ==", + "timestamp": "2023-02-24T15:09:36.499560496Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "parts": { + "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "4", + "last_block_id": { + "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "parts": { + "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "total": 1 + } + }, + "last_commit_hash": "6DDE3F5FEB4E7E88FCF3A9B8E5A9B178B525E68817C1EC05E2DE9E03AB164D96", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:37.018159177Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "parts": { + "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "total": 1 + } + }, + "height": "3", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "jCRCbsEIyj1qiAeTgB83J0/R8O8nFhkCA5MDr8yfH3ktL5xD/gC4ZLJL2yhobtD+jyWYLdX0QhXlUQ+O9SiNBw==", + "timestamp": "2023-02-24T15:09:37.018159177Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "parts": { + "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "5", + "last_block_id": { + "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "parts": { + "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "total": 1 + } + }, + "last_commit_hash": "EDC03890397D8183CD0FE0A25A729BFC5192851DC8ADA3642B7D23E0B7B51A21", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:37.533687433Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "parts": { + "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "total": 1 + } + }, + "height": "4", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "HY0ROA2/fYJhlG29zkkKtyiFIR6KN0b6DmwQmds4UuPcHWcySGBn5JzjSC/9BtRa+39/F+UOx52qq1YrqpGiBQ==", + "timestamp": "2023-02-24T15:09:37.533687433Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "parts": { + "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "6", + "last_block_id": { + "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "parts": { + "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "total": 1 + } + }, + "last_commit_hash": "769E5D10F6B90219BB10D7DA6600728E02A760476A3F0216914B4E3D758E0ED6", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:38.051624453Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "parts": { + "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "total": 1 + } + }, + "height": "5", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "yCUdVX41Vg6BKjN2Drz1buvxYnAE1QVJ3VfXXPSQpb/5cCUsBwbmlzGr7lW4pG+Up8esuRPvw5rVd10WOeq1CA==", + "timestamp": "2023-02-24T15:09:38.051624453Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "parts": { + "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "7", + "last_block_id": { + "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "parts": { + "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "total": 1 + } + }, + "last_commit_hash": "266129248C2C0D2684F1D1BE8E5A119742520BAA03F740BE5C612E8CFB245DB7", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:38.570297947Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "parts": { + "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "total": 1 + } + }, + "height": "6", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "w2xBk7ki4DjfsfKWUsROgMRnfZpGpdCE6QA2OTM91lo/Eh/J3tguP8KNNoVxrkYyaHgKT/SvFN2WXLYwIOrNCQ==", + "timestamp": "2023-02-24T15:09:38.570297947Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "parts": { + "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "8", + "last_block_id": { + "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "parts": { + "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "total": 1 + } + }, + "last_commit_hash": "D12B708778B847858029349205FD4BE0F8B22A8DE61943D5C2D4B49396767775", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:39.090086292Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "parts": { + "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "total": 1 + } + }, + "height": "7", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "wnmCESLo6NRG1jVcd9ki3b3kXOyQ2iVf35b7fVqymzdk4ggG/TZqXM17t9SUhaJNCEhLSwdVTkW7dBSKDWO/Bg==", + "timestamp": "2023-02-24T15:09:39.090086292Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "parts": { + "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "9", + "last_block_id": { + "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "parts": { + "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "total": 1 + } + }, + "last_commit_hash": "22FC31E6CCA7D5C580B14FC94E506524041B2064C9DB27D54A5AC3254950CBA9", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:39.606408964Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "parts": { + "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "total": 1 + } + }, + "height": "8", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "4psdDfHZVZmi5IvswMNFIOKtoSXzN3AwbLIzO0ZlC2owyKzS01UMyJGvYD+ttvb4ZkC1jzmkum+NpnkXh3IlDw==", + "timestamp": "2023-02-24T15:09:39.606408964Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "10", + "last_block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + }, + "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:40.123954449Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + }, + "height": "9", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "V8j/4eDj/LWDhjiCBvYZgBZXOp891keTHM1y9tpAMiUHrnDllS6DWuq9EYxftB9hA31pGvZKHM5v5SdNRFV4DA==", + "timestamp": "2023-02-24T15:09:40.123954449Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "parts": { + "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "11", + "last_block_id": { + "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "parts": { + "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "total": 1 + } + }, + "last_commit_hash": "20740E1EEE8BF0AD07A1FA0A39F3165C1F5F8E287AF3F62B6566D9099692005E", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:40.640670992Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "parts": { + "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "total": 1 + } + }, + "height": "10", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "gozurqzPCl9et0LQgKksMg60fdU1cPOoDfIEUwMCWMZt8/5cRYiUbr7+kJj9AHF2/C1w3Abs8a+QxtVJPnWlBw==", + "timestamp": "2023-02-24T15:09:40.640670992Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "EC2860F0F808D60E6A19C95E96B5DB1414214D0A8DCF86FBA240AE197FED4CA3", + "parts": { + "hash": "DD6095B5570A6866BBB4E5CF768A328845CCC5D50FDA1D14426939D4A3D625B1", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "12", + "last_block_id": { + "hash": "EC2860F0F808D60E6A19C95E96B5DB1414214D0A8DCF86FBA240AE197FED4CA3", + "parts": { + "hash": "DD6095B5570A6866BBB4E5CF768A328845CCC5D50FDA1D14426939D4A3D625B1", + "total": 1 + } + }, + "last_commit_hash": "7A6A90DD48958C694F693A3E9CA9C19350EBF73BB9369CEDE042C097C728BD0F", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:41.161270689Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "EC2860F0F808D60E6A19C95E96B5DB1414214D0A8DCF86FBA240AE197FED4CA3", + "parts": { + "hash": "DD6095B5570A6866BBB4E5CF768A328845CCC5D50FDA1D14426939D4A3D625B1", + "total": 1 + } + }, + "height": "11", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "dHCRg3DqkdBynbFLRCwzunj5TXj05hJHmAtYxS+oCZAAm3vlm1GQD786AyaAEGr5PnNqLJjMbkzBAxm/E/nDBw==", + "timestamp": "2023-02-24T15:09:41.161270689Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "92196E832E0003A4682F3C2DFBE92474985B9D84F778D767BE604C08B368A1DE", + "parts": { + "hash": "DDEE670BF9199CC306BC96D2FE530BE8719621CBC873E35054A4E93F457264F1", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "13", + "last_block_id": { + "hash": "92196E832E0003A4682F3C2DFBE92474985B9D84F778D767BE604C08B368A1DE", + "parts": { + "hash": "DDEE670BF9199CC306BC96D2FE530BE8719621CBC873E35054A4E93F457264F1", + "total": 1 + } + }, + "last_commit_hash": "8B7D6067E63570F7BA68C2AA54015FF125619F32D80774EEB35EB2AEA8EA22A7", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:41.681034391Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "92196E832E0003A4682F3C2DFBE92474985B9D84F778D767BE604C08B368A1DE", + "parts": { + "hash": "DDEE670BF9199CC306BC96D2FE530BE8719621CBC873E35054A4E93F457264F1", + "total": 1 + } + }, + "height": "12", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "TTn4qezR2fvqoDPtPsztmqAmOCe6uzOmeqEgyRXZBnEkIl7pb71p1AX70lJ60jXypPPnty8X/58BbJ91yMKyAg==", + "timestamp": "2023-02-24T15:09:41.681034391Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "D2A849200541C2098BE9FC8DDD71CC3C39D20BD01E586E5EBECBC3A0A3165D0A", + "parts": { + "hash": "1A9EF94D3335F90EC70ED282B781F342644881FC9FD58ECE346BFEBED2B05D7F", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "14", + "last_block_id": { + "hash": "D2A849200541C2098BE9FC8DDD71CC3C39D20BD01E586E5EBECBC3A0A3165D0A", + "parts": { + "hash": "1A9EF94D3335F90EC70ED282B781F342644881FC9FD58ECE346BFEBED2B05D7F", + "total": 1 + } + }, + "last_commit_hash": "43DCD089D5DC227CFD77E1F241BCD926C36ABA0916081337573986FE8C6B1A97", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:42.197919966Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "D2A849200541C2098BE9FC8DDD71CC3C39D20BD01E586E5EBECBC3A0A3165D0A", + "parts": { + "hash": "1A9EF94D3335F90EC70ED282B781F342644881FC9FD58ECE346BFEBED2B05D7F", + "total": 1 + } + }, + "height": "13", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "R2e7N0xmmUqGVpuFFVMJFFSyTc8bU4+6/CWubsnWldzQkjeuzxn4HA2ThLjm37zA7gnx1w5yXUHs8obnmMgsBg==", + "timestamp": "2023-02-24T15:09:42.197919966Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "5A1C50A51AEA032362DCA6C901EA88BD8C59B526A043F8EE7FCFBC695D5C0771", + "parts": { + "hash": "77B5D493AA74A559F60CEB90CBA0404850D017038EF8D5350C815EA9D6EC2CFF", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "15", + "last_block_id": { + "hash": "5A1C50A51AEA032362DCA6C901EA88BD8C59B526A043F8EE7FCFBC695D5C0771", + "parts": { + "hash": "77B5D493AA74A559F60CEB90CBA0404850D017038EF8D5350C815EA9D6EC2CFF", + "total": 1 + } + }, + "last_commit_hash": "D2581E01B7A18A56E9AA343C59FDC529288DF78A90C17A0D2626515C38B94A19", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:42.717219422Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "5A1C50A51AEA032362DCA6C901EA88BD8C59B526A043F8EE7FCFBC695D5C0771", + "parts": { + "hash": "77B5D493AA74A559F60CEB90CBA0404850D017038EF8D5350C815EA9D6EC2CFF", + "total": 1 + } + }, + "height": "14", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "NIkKM0RynRc+S68R8XLxQSURuyNTq3tlbKFrFEd2fnm6BXSqInaDWOO3bMEAtUxWfpfW4XlrSd0oKnYWQ516AA==", + "timestamp": "2023-02-24T15:09:42.717219422Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "6B3DC1BFED5A035C1FF4F7E961FF4CD4D76691F80FE4E2FFC7F6FA5C6379F628", + "parts": { + "hash": "6E8CE26D895B7855D4284CA40CE54883F667D8900362037CB2B8E68FF28F5A25", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "16", + "last_block_id": { + "hash": "6B3DC1BFED5A035C1FF4F7E961FF4CD4D76691F80FE4E2FFC7F6FA5C6379F628", + "parts": { + "hash": "6E8CE26D895B7855D4284CA40CE54883F667D8900362037CB2B8E68FF28F5A25", + "total": 1 + } + }, + "last_commit_hash": "F1359E50F69A3AB3EE3C67F5C96949C2FB6253BEB84D4371B28AFF29E0577D31", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:43.23356283Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "6B3DC1BFED5A035C1FF4F7E961FF4CD4D76691F80FE4E2FFC7F6FA5C6379F628", + "parts": { + "hash": "6E8CE26D895B7855D4284CA40CE54883F667D8900362037CB2B8E68FF28F5A25", + "total": 1 + } + }, + "height": "15", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "WsMS4UPyn/vuCBxC1KLn6qE0qtD4UXxRFVZe/96gb3L2ofxion5IRgZreYalWL0bO/DPmkJ7h123K1Sg7adRBQ==", + "timestamp": "2023-02-24T15:09:43.23356283Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "105B21A7A19EA9C985D7183DC064DF26865C9AB3996F658769935BEDEA0731F8", + "parts": { + "hash": "D05E710BE17FF05DF587F447CEF48C309ED37200BF094BAD08A5B1075EF717B7", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "17", + "last_block_id": { + "hash": "105B21A7A19EA9C985D7183DC064DF26865C9AB3996F658769935BEDEA0731F8", + "parts": { + "hash": "D05E710BE17FF05DF587F447CEF48C309ED37200BF094BAD08A5B1075EF717B7", + "total": 1 + } + }, + "last_commit_hash": "2B1A55AEA195E64774202C36C107C9ABAB85A9D145090A8DE6EC6969D423C020", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:43.75150372Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "105B21A7A19EA9C985D7183DC064DF26865C9AB3996F658769935BEDEA0731F8", + "parts": { + "hash": "D05E710BE17FF05DF587F447CEF48C309ED37200BF094BAD08A5B1075EF717B7", + "total": 1 + } + }, + "height": "16", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "udQiCxsqQeJ3U89Z2e0RM86OgeNt+pDxy5N0i1n3Wpa5Ik5dqVYAhxcSCfcFMW6AEbJyvg4VoqzR79X7IZsQCw==", + "timestamp": "2023-02-24T15:09:43.75150372Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "0773E4FD7C13BA8A6E6AB2A90C0E1F7830232F23DEDB415A6D2B7146D20554F4", + "parts": { + "hash": "6323199FC03237192A2EB4D3C2EBC3CC43F47750CFFF8CAB19362F0D8614DD2A", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "18", + "last_block_id": { + "hash": "0773E4FD7C13BA8A6E6AB2A90C0E1F7830232F23DEDB415A6D2B7146D20554F4", + "parts": { + "hash": "6323199FC03237192A2EB4D3C2EBC3CC43F47750CFFF8CAB19362F0D8614DD2A", + "total": 1 + } + }, + "last_commit_hash": "0BF662A790AF94F89021D9BE35F9F761D1356BCCEEB32BCD4349B8F707ADDB74", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:44.268716621Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "0773E4FD7C13BA8A6E6AB2A90C0E1F7830232F23DEDB415A6D2B7146D20554F4", + "parts": { + "hash": "6323199FC03237192A2EB4D3C2EBC3CC43F47750CFFF8CAB19362F0D8614DD2A", + "total": 1 + } + }, + "height": "17", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "hN5R5V5rRru5xa4C8V+L6g6DWM9IEFhd75xX7FKYjpWpP+8KumKqljlxFpcoOmFiy1Kp0MwSVH9kkPpE0VPIBw==", + "timestamp": "2023-02-24T15:09:44.268716621Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "B443CE1F79ABE95B2A8D75BE4E098FA22001CDC5473E5AC2A08CA10EFB25AD27", + "parts": { + "hash": "D9F8AD4E23D035F7074DA593A0B21A12DDB20266436393BA70377782822D38BE", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "19", + "last_block_id": { + "hash": "B443CE1F79ABE95B2A8D75BE4E098FA22001CDC5473E5AC2A08CA10EFB25AD27", + "parts": { + "hash": "D9F8AD4E23D035F7074DA593A0B21A12DDB20266436393BA70377782822D38BE", + "total": 1 + } + }, + "last_commit_hash": "9E263405AB365CA26036A8FE0BE4BF12C2194C84C50C409B2D961AA23292F247", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:44.790264757Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "B443CE1F79ABE95B2A8D75BE4E098FA22001CDC5473E5AC2A08CA10EFB25AD27", + "parts": { + "hash": "D9F8AD4E23D035F7074DA593A0B21A12DDB20266436393BA70377782822D38BE", + "total": 1 + } + }, + "height": "18", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "v5T2UVvpVNg4+HRVdTWjzYzEVpO7XkosJqT1HuXJV6QHuFSz5dlkpvlzMKLAbjQ2Jvt4/8q429Mjt679CWS2DA==", + "timestamp": "2023-02-24T15:09:44.790264757Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "B236DD786A3DE401D0D11E4175F7047E8676F6D9DB0F20B7D989E7733D64D8D3", + "parts": { + "hash": "E3045E7505869EA24E95F37D6ECF32AA46C6922CE697403739AAE85DE5BD1EAC", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "20", + "last_block_id": { + "hash": "B236DD786A3DE401D0D11E4175F7047E8676F6D9DB0F20B7D989E7733D64D8D3", + "parts": { + "hash": "E3045E7505869EA24E95F37D6ECF32AA46C6922CE697403739AAE85DE5BD1EAC", + "total": 1 + } + }, + "last_commit_hash": "A1B124868735F1A193E266DB8B8F4ECDC6DB09C6D72910A531499B6AFC8D00BF", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:45.310831215Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "B236DD786A3DE401D0D11E4175F7047E8676F6D9DB0F20B7D989E7733D64D8D3", + "parts": { + "hash": "E3045E7505869EA24E95F37D6ECF32AA46C6922CE697403739AAE85DE5BD1EAC", + "total": 1 + } + }, + "height": "19", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "8YBkchV3YkBIs27As5D3/pfqyi4M6OOoknokof28n7PxWG1eNgYPDvu4yqpAH9BiVm1QUDSNLhPixUkJmHIdBg==", + "timestamp": "2023-02-24T15:09:45.310831215Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "7C89853BC86B9B866CC3544AF99876718D3C18F8CE79A5EC4BD2E9A0EA0ED2B0", + "parts": { + "hash": "ECC19F719AA76C644F6C059AEF092788591D0A391090EB7CE8DBDF1305007872", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "21", + "last_block_id": { + "hash": "7C89853BC86B9B866CC3544AF99876718D3C18F8CE79A5EC4BD2E9A0EA0ED2B0", + "parts": { + "hash": "ECC19F719AA76C644F6C059AEF092788591D0A391090EB7CE8DBDF1305007872", + "total": 1 + } + }, + "last_commit_hash": "147F50B634C3F16B4D901D6A1CA0F04EB389555169BF3A09895D3D9DD0CE3DD3", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:45.829978265Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "7C89853BC86B9B866CC3544AF99876718D3C18F8CE79A5EC4BD2E9A0EA0ED2B0", + "parts": { + "hash": "ECC19F719AA76C644F6C059AEF092788591D0A391090EB7CE8DBDF1305007872", + "total": 1 + } + }, + "height": "20", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "HgRnoRe2U6lRj9LAHjGozj8ncT2nUfrdqbJW/RE72TBnKM4xjonYVuLdckQaD6rvlH8tHqB2QId0V8z1ltX3Dg==", + "timestamp": "2023-02-24T15:09:45.829978265Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "9FF25957F2AA46C7A06519462CF791AF27F6AEE491040F3A5D4296CBB1494950", + "parts": { + "hash": "338148ACCCAAC648F493797141D9834A22EC14656A83C1AB3EE34E2EBD420AC3", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "22", + "last_block_id": { + "hash": "9FF25957F2AA46C7A06519462CF791AF27F6AEE491040F3A5D4296CBB1494950", + "parts": { + "hash": "338148ACCCAAC648F493797141D9834A22EC14656A83C1AB3EE34E2EBD420AC3", + "total": 1 + } + }, + "last_commit_hash": "D73F54CCD86AE60933DF8DD4AEAC6815564954BD486E342560E93E6AE42639B9", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:46.34697564Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "9FF25957F2AA46C7A06519462CF791AF27F6AEE491040F3A5D4296CBB1494950", + "parts": { + "hash": "338148ACCCAAC648F493797141D9834A22EC14656A83C1AB3EE34E2EBD420AC3", + "total": 1 + } + }, + "height": "21", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "lt9PUqM3uqIwG/mX4r5fRSt75P4fsX4gQXYFBJrLkdxRVn7VxPYGGBAVeNlpoGFC+yCagfW14xrx/EZT9CwvDQ==", + "timestamp": "2023-02-24T15:09:46.34697564Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "F71158D636F640E2F2EB4C46E471EFFD41FC2B430009D589FB0C3EB4BC177A5A", + "parts": { + "hash": "D31D9380F1941E7D94A97EC8D87EF7DC841AD7B9A2FAA82CCFB846D4CAF67CF0", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "23", + "last_block_id": { + "hash": "F71158D636F640E2F2EB4C46E471EFFD41FC2B430009D589FB0C3EB4BC177A5A", + "parts": { + "hash": "D31D9380F1941E7D94A97EC8D87EF7DC841AD7B9A2FAA82CCFB846D4CAF67CF0", + "total": 1 + } + }, + "last_commit_hash": "0F3AFD99E60F5D4E218FF1C335453AFD80B574FFF4393881A9D3ECE3E57880F2", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:46.865219137Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "F71158D636F640E2F2EB4C46E471EFFD41FC2B430009D589FB0C3EB4BC177A5A", + "parts": { + "hash": "D31D9380F1941E7D94A97EC8D87EF7DC841AD7B9A2FAA82CCFB846D4CAF67CF0", + "total": 1 + } + }, + "height": "22", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "A0hu5vJS3tK0tyYF17tR7IPJ3BKwVjZS4UfXmz0Dkn7T7+XfjGLc1BB1g2JQnk8pvl8Vl5/S0WKOE4bHPKfVCA==", + "timestamp": "2023-02-24T15:09:46.865219137Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "17DAECBE0F3CE63F6AEDD260463839E00EFF39A0C09BA4F86E238A2F9FDB7DF2", + "parts": { + "hash": "5205D9AD8338ADF3FA04195C9481F87D4997C4DF504E14B44735414E6E80ADAA", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "24", + "last_block_id": { + "hash": "17DAECBE0F3CE63F6AEDD260463839E00EFF39A0C09BA4F86E238A2F9FDB7DF2", + "parts": { + "hash": "5205D9AD8338ADF3FA04195C9481F87D4997C4DF504E14B44735414E6E80ADAA", + "total": 1 + } + }, + "last_commit_hash": "AC71D8B0567DCB417D05F98721D0A19CD9C0E6A584CB818FEAEC5EF235979F71", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:47.385204611Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "17DAECBE0F3CE63F6AEDD260463839E00EFF39A0C09BA4F86E238A2F9FDB7DF2", + "parts": { + "hash": "5205D9AD8338ADF3FA04195C9481F87D4997C4DF504E14B44735414E6E80ADAA", + "total": 1 + } + }, + "height": "23", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "7Fb16J97ZRfzdUMVJYx3Y9xOPszXNcHmhyjsqDXebJlA9yvEZhdGwWT4m6locO5GywP2g8muuxCkosEZ7wVDBw==", + "timestamp": "2023-02-24T15:09:47.385204611Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "1A363F2CBA0C7CE46EC21B0E089F24922487E9353571BF7BF15C45D8B9F35899", + "parts": { + "hash": "C438BD76FCA7AF54E479ADF8C6C7B7C41DA9C86758AD26A661CBCBA38F5CAE2D", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "25", + "last_block_id": { + "hash": "1A363F2CBA0C7CE46EC21B0E089F24922487E9353571BF7BF15C45D8B9F35899", + "parts": { + "hash": "C438BD76FCA7AF54E479ADF8C6C7B7C41DA9C86758AD26A661CBCBA38F5CAE2D", + "total": 1 + } + }, + "last_commit_hash": "EF5559062008C6061D569FE460A5EE543D5A7172E1E9D255D8D19283546BA6CA", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:47.905699456Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "1A363F2CBA0C7CE46EC21B0E089F24922487E9353571BF7BF15C45D8B9F35899", + "parts": { + "hash": "C438BD76FCA7AF54E479ADF8C6C7B7C41DA9C86758AD26A661CBCBA38F5CAE2D", + "total": 1 + } + }, + "height": "24", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "jRrS7ZS3rJD9y/EUeoGIQqIyC70Sy1fpbox6hGCwsrUZ53LyqD+s5O1fKlfwfTzk/p5MT2dJvLW2+eGJmXeCCQ==", + "timestamp": "2023-02-24T15:09:47.905699456Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "E649CD1349CB3D968E147A1B7A9711073265336E67EF05467358DCAC9E498417", + "parts": { + "hash": "06A2D43F265C0235D44D84E0B6CE2C9B4D7652051CB105C15225E9463F8BCD32", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "26", + "last_block_id": { + "hash": "E649CD1349CB3D968E147A1B7A9711073265336E67EF05467358DCAC9E498417", + "parts": { + "hash": "06A2D43F265C0235D44D84E0B6CE2C9B4D7652051CB105C15225E9463F8BCD32", + "total": 1 + } + }, + "last_commit_hash": "E641E72B4D83E9041D00CF63E26FD69038C4F1EF0DBCCF1882D91E0C8024F34D", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:48.422959333Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "E649CD1349CB3D968E147A1B7A9711073265336E67EF05467358DCAC9E498417", + "parts": { + "hash": "06A2D43F265C0235D44D84E0B6CE2C9B4D7652051CB105C15225E9463F8BCD32", + "total": 1 + } + }, + "height": "25", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "uTJsjYFHBZHke3jAHGSTGFPkmdcMdMuopNNLd0XKWKqetn0dJWHJxsHRaaYog3AuPh7be/dGEm1dZ+duU31SCw==", + "timestamp": "2023-02-24T15:09:48.422959333Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "EFEF9D1BE75E14BDF5A8297770332E0A89042CE55F7AEF6F0E015CD1FEB32F00", + "parts": { + "hash": "BD83A062FFEBB895ECA77BC63056F5141874CAE7200E0CEAEE86C95B83A85417", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "27", + "last_block_id": { + "hash": "EFEF9D1BE75E14BDF5A8297770332E0A89042CE55F7AEF6F0E015CD1FEB32F00", + "parts": { + "hash": "BD83A062FFEBB895ECA77BC63056F5141874CAE7200E0CEAEE86C95B83A85417", + "total": 1 + } + }, + "last_commit_hash": "C14E43C1ED7AA86DD61EF7000EB7551CF518915857CF9BEA3E99C15B1EEF9978", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:48.940870986Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "EFEF9D1BE75E14BDF5A8297770332E0A89042CE55F7AEF6F0E015CD1FEB32F00", + "parts": { + "hash": "BD83A062FFEBB895ECA77BC63056F5141874CAE7200E0CEAEE86C95B83A85417", + "total": 1 + } + }, + "height": "26", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "hfWavhAYBm7ZGcNZXIdJi6rzn+KSmLZgbtkA3unnFPKwkZ6s2RjWVc8aLmOymA8FDt8CYu9v0wGUE77/T992AQ==", + "timestamp": "2023-02-24T15:09:48.940870986Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "12BC4D20F1B9D7FA0741F9DFFC390553B27EAD7180A5B138F0E7B4F791327EFC", + "parts": { + "hash": "9781684D4B2F707006A52015605DB5A7723CA2E87739B30BA76A9C755E39D98E", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "28", + "last_block_id": { + "hash": "12BC4D20F1B9D7FA0741F9DFFC390553B27EAD7180A5B138F0E7B4F791327EFC", + "parts": { + "hash": "9781684D4B2F707006A52015605DB5A7723CA2E87739B30BA76A9C755E39D98E", + "total": 1 + } + }, + "last_commit_hash": "C1EE26645F9274D8C1124A1863BA05950D6B30B322CB37E5E574622DE60DCDC0", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:49.457911779Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "12BC4D20F1B9D7FA0741F9DFFC390553B27EAD7180A5B138F0E7B4F791327EFC", + "parts": { + "hash": "9781684D4B2F707006A52015605DB5A7723CA2E87739B30BA76A9C755E39D98E", + "total": 1 + } + }, + "height": "27", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "mm1nOQBU+TXzb2pX9Zvf3d/1ewXZnoOWmdu+SXzdcDtjvUxGbThVHwDd5PHKPwNdvR60p3zvYeCbpW6gUHSpAA==", + "timestamp": "2023-02-24T15:09:49.457911779Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "75E9C485C60DD6F950888E8BF214591AF4883F830FCA3E47CCC5AEC14CDEC731", + "parts": { + "hash": "02BD1D5BD119AFC3C3FA12466BDEEA67B512A42B88BF9E98C80FBBE6A6CDA379", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "29", + "last_block_id": { + "hash": "75E9C485C60DD6F950888E8BF214591AF4883F830FCA3E47CCC5AEC14CDEC731", + "parts": { + "hash": "02BD1D5BD119AFC3C3FA12466BDEEA67B512A42B88BF9E98C80FBBE6A6CDA379", + "total": 1 + } + }, + "last_commit_hash": "2792A5F3CAEC5C55789EC49BCCD2882E7A49830979B42A80A7EF9349D3930A03", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:49.977943197Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "75E9C485C60DD6F950888E8BF214591AF4883F830FCA3E47CCC5AEC14CDEC731", + "parts": { + "hash": "02BD1D5BD119AFC3C3FA12466BDEEA67B512A42B88BF9E98C80FBBE6A6CDA379", + "total": 1 + } + }, + "height": "28", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "/LX/RZcfb8CAUwsiwO8xKKtduXVaOhX9GW2lEmrC0HuzCG0b1b5ElDr4R7+egNZBcr4AEGiGgE/ti3kvjXrxDg==", + "timestamp": "2023-02-24T15:09:49.977943197Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "9E053F4193763F3D1229D427D2109ABF29AFBFCA58C71279C0EF510B807866A3", + "parts": { + "hash": "08B358112F01781DBD89FD2EDE6E485A8B175BB5F7CB39BDE8D3AC369D1E9DFC", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "30", + "last_block_id": { + "hash": "9E053F4193763F3D1229D427D2109ABF29AFBFCA58C71279C0EF510B807866A3", + "parts": { + "hash": "08B358112F01781DBD89FD2EDE6E485A8B175BB5F7CB39BDE8D3AC369D1E9DFC", + "total": 1 + } + }, + "last_commit_hash": "9B8F1998102BFD8EC2BE211E241D7F737EB6D46FA0DDBC80832564512C41480A", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:50.495537773Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "9E053F4193763F3D1229D427D2109ABF29AFBFCA58C71279C0EF510B807866A3", + "parts": { + "hash": "08B358112F01781DBD89FD2EDE6E485A8B175BB5F7CB39BDE8D3AC369D1E9DFC", + "total": 1 + } + }, + "height": "29", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "h99svjsWfKynfm58Kczz7/q2IjBhGT0El36i52iaZ5Y1+VweK2MxCurBUvTo/bmCdE84hWe4/vLcdnEgw+RNDg==", + "timestamp": "2023-02-24T15:09:50.495537773Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "02BD0F6A3FEE4FC5A4B6FFA3B23177FE2D4BC2885835BA247C92E900CE216851", + "parts": { + "hash": "729F1DC8FBC33D17DCFBEE452AE53704B679FF39CC4FE77F007244F044E6129F", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "31", + "last_block_id": { + "hash": "02BD0F6A3FEE4FC5A4B6FFA3B23177FE2D4BC2885835BA247C92E900CE216851", + "parts": { + "hash": "729F1DC8FBC33D17DCFBEE452AE53704B679FF39CC4FE77F007244F044E6129F", + "total": 1 + } + }, + "last_commit_hash": "D9CF9BC6ECDCFB4AC81672D770B1875BB5A8546A36705E8B5169638C12AC58E2", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:51.013493418Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "02BD0F6A3FEE4FC5A4B6FFA3B23177FE2D4BC2885835BA247C92E900CE216851", + "parts": { + "hash": "729F1DC8FBC33D17DCFBEE452AE53704B679FF39CC4FE77F007244F044E6129F", + "total": 1 + } + }, + "height": "30", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "pQLY02cZ1xoxIxD9NqNasuVvmr1Jqf5648hKSwWAExdszj8kRXnzp24G1AzPv81yLpfrpKyHWTyVIBO3kgJQAA==", + "timestamp": "2023-02-24T15:09:51.013493418Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "47FE7FE2212A8F4A6569EB89EFF9354D73E894F4DDB2E9F15438CEA4882693E4", + "parts": { + "hash": "61B145853738DDA5BA10DE12BD2B4F3C5FC2A709712121FB307729B50E3AD707", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "32", + "last_block_id": { + "hash": "47FE7FE2212A8F4A6569EB89EFF9354D73E894F4DDB2E9F15438CEA4882693E4", + "parts": { + "hash": "61B145853738DDA5BA10DE12BD2B4F3C5FC2A709712121FB307729B50E3AD707", + "total": 1 + } + }, + "last_commit_hash": "C4DB33FAD541886678C7E0850E16F2B8AF49B414B8748A15FDE3183EAC46CF36", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:51.532421598Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "47FE7FE2212A8F4A6569EB89EFF9354D73E894F4DDB2E9F15438CEA4882693E4", + "parts": { + "hash": "61B145853738DDA5BA10DE12BD2B4F3C5FC2A709712121FB307729B50E3AD707", + "total": 1 + } + }, + "height": "31", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "GMVE9bD4VJQWJ2EdGBu7NNBZ9/pti7KPFjR+R739dABIMt0KCY1G6pU8u/UAf1ZPwbFu6VSOmHaonQhGS/b3AA==", + "timestamp": "2023-02-24T15:09:51.532421598Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "E934D9772BFC0F30FE35170C598122350279B6902F8195F2E4D20757E9423BBD", + "parts": { + "hash": "043396430E6C410F0A57217418B83384464CE3FF5AA52A22DF20D22191D612A6", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "33", + "last_block_id": { + "hash": "E934D9772BFC0F30FE35170C598122350279B6902F8195F2E4D20757E9423BBD", + "parts": { + "hash": "043396430E6C410F0A57217418B83384464CE3FF5AA52A22DF20D22191D612A6", + "total": 1 + } + }, + "last_commit_hash": "79B0D0698E1214AD13B90539FAAEFD4DDFE208BDF5BC0BAD12C169EA5C826339", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:52.050779736Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "E934D9772BFC0F30FE35170C598122350279B6902F8195F2E4D20757E9423BBD", + "parts": { + "hash": "043396430E6C410F0A57217418B83384464CE3FF5AA52A22DF20D22191D612A6", + "total": 1 + } + }, + "height": "32", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "O/IkLhYLG+SzbuBD9XWjOTD+L6/NEJtjsgyR/ClNyz+vddyZ5ktqexIpE6Z68GqOkc1jvBglaHmZFqBBeKKeBw==", + "timestamp": "2023-02-24T15:09:52.050779736Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "288DF763209A88F724838A317C98A6EA598BA4A97228A5AE5EEFD09B26487813", + "parts": { + "hash": "AB7EE95A5A9CC78F0293FBAD37259641E217D6C291BB32E2D09A1DF5E13380FF", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "34", + "last_block_id": { + "hash": "288DF763209A88F724838A317C98A6EA598BA4A97228A5AE5EEFD09B26487813", + "parts": { + "hash": "AB7EE95A5A9CC78F0293FBAD37259641E217D6C291BB32E2D09A1DF5E13380FF", + "total": 1 + } + }, + "last_commit_hash": "2EBF6CDCCE4AEBD55EB5532A535A809340F6C69A04515354797A40D6D44494DA", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:52.566839174Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "288DF763209A88F724838A317C98A6EA598BA4A97228A5AE5EEFD09B26487813", + "parts": { + "hash": "AB7EE95A5A9CC78F0293FBAD37259641E217D6C291BB32E2D09A1DF5E13380FF", + "total": 1 + } + }, + "height": "33", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "LRRtzavKg7U4eEkFOgJ7VNkalmVGEtj2J45fNSZwJyxCIaioZ6QT6yv+T7KilP0rYQ3XSMKHOxmvEGfCNNVBBQ==", + "timestamp": "2023-02-24T15:09:52.566839174Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "7959636BDDB9C76034675239906C8B6E7588B685B73B9E73258D7E6398B7877E", + "parts": { + "hash": "050340F8516139B861149395A837882F15898430E5FA5C0162BEDC68EA2958F6", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "35", + "last_block_id": { + "hash": "7959636BDDB9C76034675239906C8B6E7588B685B73B9E73258D7E6398B7877E", + "parts": { + "hash": "050340F8516139B861149395A837882F15898430E5FA5C0162BEDC68EA2958F6", + "total": 1 + } + }, + "last_commit_hash": "9E0F53A59241BD3E135561239D849CFAD29A62ACC9C0F23FFD825DE44B546800", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:53.086080698Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "7959636BDDB9C76034675239906C8B6E7588B685B73B9E73258D7E6398B7877E", + "parts": { + "hash": "050340F8516139B861149395A837882F15898430E5FA5C0162BEDC68EA2958F6", + "total": 1 + } + }, + "height": "34", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "dvHG9nqKtuI2Hy9fEtwBOmFT4uGtNOKvNaOT2CXZ66xGGRiFUBSfvAOx9s8lxzjgzIDlerRU7dF0yIFQGrVeBg==", + "timestamp": "2023-02-24T15:09:53.086080698Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "589A9F3ADF634C44DF449F27D8F96CF5A1BCE1BBDC0974A3C549A989EFC483FF", + "parts": { + "hash": "B0CF879E0A3AD5F9D8D9DB81BA603D56FAD32BF497F61248486190DB6F371BE1", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "36", + "last_block_id": { + "hash": "589A9F3ADF634C44DF449F27D8F96CF5A1BCE1BBDC0974A3C549A989EFC483FF", + "parts": { + "hash": "B0CF879E0A3AD5F9D8D9DB81BA603D56FAD32BF497F61248486190DB6F371BE1", + "total": 1 + } + }, + "last_commit_hash": "17C97B144649BB2EDB6E64E1A62B405E6F0C5CABC6AD45F66CD81E1434EE9AF5", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:53.609178055Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "589A9F3ADF634C44DF449F27D8F96CF5A1BCE1BBDC0974A3C549A989EFC483FF", + "parts": { + "hash": "B0CF879E0A3AD5F9D8D9DB81BA603D56FAD32BF497F61248486190DB6F371BE1", + "total": 1 + } + }, + "height": "35", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "kBoL9uKWDnNP06Icflh0Zec9N8pbWPToylsaE+YUXL9v/D4wLuqP9nvsWOnSRFZtts8BvgfedzLJf1xyRbxQCg==", + "timestamp": "2023-02-24T15:09:53.609178055Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "D315512FB2052D4E442DBA73346816AC917228A50CFE230497538D088F73A439", + "parts": { + "hash": "3E310517AED22CC42A8A86BD938E7D5D859398AEE69E503DC84C37FAC95FBD56", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "37", + "last_block_id": { + "hash": "D315512FB2052D4E442DBA73346816AC917228A50CFE230497538D088F73A439", + "parts": { + "hash": "3E310517AED22CC42A8A86BD938E7D5D859398AEE69E503DC84C37FAC95FBD56", + "total": 1 + } + }, + "last_commit_hash": "B5EFEE08293D2CFAB975E07F062CE3EB108FC79F437E09CFF0146FD74E627CDF", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:54.125988527Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "D315512FB2052D4E442DBA73346816AC917228A50CFE230497538D088F73A439", + "parts": { + "hash": "3E310517AED22CC42A8A86BD938E7D5D859398AEE69E503DC84C37FAC95FBD56", + "total": 1 + } + }, + "height": "36", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "+7g9VI6FkZK0KKGhBsZbCrvXbrYWtccQsVJJ5b3nFkLq7ppEO1WLai3NR/eHE07fGUyybpDArz3IGK3XcKVyCw==", + "timestamp": "2023-02-24T15:09:54.125988527Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "477384280D571F4A8C22A8947241C54694105F7CF0CC1B1791A68C0539FED046", + "parts": { + "hash": "C04AEB0D79A05E394C03633C961AD892EEB3900966573AEE76F4D2FCCEEEB9AB", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "38", + "last_block_id": { + "hash": "477384280D571F4A8C22A8947241C54694105F7CF0CC1B1791A68C0539FED046", + "parts": { + "hash": "C04AEB0D79A05E394C03633C961AD892EEB3900966573AEE76F4D2FCCEEEB9AB", + "total": 1 + } + }, + "last_commit_hash": "4257612B44B86C0A9FDF4FDBE8AE5E49C90B25B962D2984109797814169DCCC9", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:54.64273723Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "477384280D571F4A8C22A8947241C54694105F7CF0CC1B1791A68C0539FED046", + "parts": { + "hash": "C04AEB0D79A05E394C03633C961AD892EEB3900966573AEE76F4D2FCCEEEB9AB", + "total": 1 + } + }, + "height": "37", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "ASwe71Vr6gEhzII1rik82le8tzlHJxDe3m1Qbfo7NOyvucI79JTAQdzGaLPfRyBVgyE6g2xOo/hyK7+9U9rPAw==", + "timestamp": "2023-02-24T15:09:54.64273723Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "81F517B0B19CC51AA6349AD93CD3CA4E7B7D46F60F1F102608D311B27643FD27", + "parts": { + "hash": "5D02CF79ACAF874E1C553EA30DBF4B68ADD534A087C4CD2449716BB69B994B22", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "39", + "last_block_id": { + "hash": "81F517B0B19CC51AA6349AD93CD3CA4E7B7D46F60F1F102608D311B27643FD27", + "parts": { + "hash": "5D02CF79ACAF874E1C553EA30DBF4B68ADD534A087C4CD2449716BB69B994B22", + "total": 1 + } + }, + "last_commit_hash": "937956A47568EDB1C822B00B42B42394F5592308A3A2F2591AF75EEA5C3ED4C3", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:55.161080226Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "81F517B0B19CC51AA6349AD93CD3CA4E7B7D46F60F1F102608D311B27643FD27", + "parts": { + "hash": "5D02CF79ACAF874E1C553EA30DBF4B68ADD534A087C4CD2449716BB69B994B22", + "total": 1 + } + }, + "height": "38", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "yWzfWI4IkcrqzA/hT2o6fOLtOF0eC7GNsFCHW3gA4IU7Z29IszXQwd3uoqyCtPCWLF5i7jh/qCBDlqrxPDO4Bg==", + "timestamp": "2023-02-24T15:09:55.161080226Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "43AEA2412DF03949F8DF028C793007F6469B1C1FCFE5DFE74D1083650643A13D", + "parts": { + "hash": "268CEE8FB95D958AAD004CD8946184181B6D55572CC5F20317B20EF67E9430C6", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "40", + "last_block_id": { + "hash": "43AEA2412DF03949F8DF028C793007F6469B1C1FCFE5DFE74D1083650643A13D", + "parts": { + "hash": "268CEE8FB95D958AAD004CD8946184181B6D55572CC5F20317B20EF67E9430C6", + "total": 1 + } + }, + "last_commit_hash": "2A398230AE0D3B57600DF6E12808A488658F22E28F8CE94B1B330A45FF90C6EB", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:55.683166536Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "43AEA2412DF03949F8DF028C793007F6469B1C1FCFE5DFE74D1083650643A13D", + "parts": { + "hash": "268CEE8FB95D958AAD004CD8946184181B6D55572CC5F20317B20EF67E9430C6", + "total": 1 + } + }, + "height": "39", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "dkJtW/0vD9J7rmwN4a049Omi5Xetjo1G39U1lXZJKfUsTsfRuwh7xCXrI2UhHzc5edtCFdyj2QLwvGVXFxboBA==", + "timestamp": "2023-02-24T15:09:55.683166536Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4815EA81BD44847850ED5C491253296B683C6CEB6556C11814CDF6CECDE29F5F", + "parts": { + "hash": "3D44E4A484F44F94392945B0BF944C3A104242347C97D6867FE413274E03F420", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "41", + "last_block_id": { + "hash": "4815EA81BD44847850ED5C491253296B683C6CEB6556C11814CDF6CECDE29F5F", + "parts": { + "hash": "3D44E4A484F44F94392945B0BF944C3A104242347C97D6867FE413274E03F420", + "total": 1 + } + }, + "last_commit_hash": "9C292564ABBF6D9E3A4E222454C001C14CC8823C6205AB2E854F404B42030F41", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:56.202137485Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4815EA81BD44847850ED5C491253296B683C6CEB6556C11814CDF6CECDE29F5F", + "parts": { + "hash": "3D44E4A484F44F94392945B0BF944C3A104242347C97D6867FE413274E03F420", + "total": 1 + } + }, + "height": "40", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "fFOBxp7MmOREYwU5QEtatBap+PBRBiz/RxshtX8cwUMZeadmI6xULCnMR2WxL/am/flkP9oc3O44cF5XjSiFBQ==", + "timestamp": "2023-02-24T15:09:56.202137485Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "8C9504DC54B545DDE815A3BCE421C9A1ECCB8D41EE4ECA9EFEBE40EF3EE4AC01", + "parts": { + "hash": "A641188CA2553D52CBF529F69BE52CC33C364EE6F8EAFC78F2A7CF6D6E9FF745", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "42", + "last_block_id": { + "hash": "8C9504DC54B545DDE815A3BCE421C9A1ECCB8D41EE4ECA9EFEBE40EF3EE4AC01", + "parts": { + "hash": "A641188CA2553D52CBF529F69BE52CC33C364EE6F8EAFC78F2A7CF6D6E9FF745", + "total": 1 + } + }, + "last_commit_hash": "1DAEF8A30DA99C0157EE298AF94D78720C5606BCC4FE457BC6AF3FA60F36151C", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:56.720182604Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "8C9504DC54B545DDE815A3BCE421C9A1ECCB8D41EE4ECA9EFEBE40EF3EE4AC01", + "parts": { + "hash": "A641188CA2553D52CBF529F69BE52CC33C364EE6F8EAFC78F2A7CF6D6E9FF745", + "total": 1 + } + }, + "height": "41", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "+YyQALg9ZFZd6E4JzFtW6nlwRvlKvkmP2HkIdlQpYOvI60U4bTMbOFmDxNcAQMp7WG0ClBT1DvDnLBlMGw7SCQ==", + "timestamp": "2023-02-24T15:09:56.720182604Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "5256DD8C5B0FAD1E6B2F0FC0D09D248C70D81E1EFFC531AF4B33EC285DA932BE", + "parts": { + "hash": "4C31AB0809BD2724B0F858DD623FEC9A2B0EE024ED077F7516330DD53AC74482", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "43", + "last_block_id": { + "hash": "5256DD8C5B0FAD1E6B2F0FC0D09D248C70D81E1EFFC531AF4B33EC285DA932BE", + "parts": { + "hash": "4C31AB0809BD2724B0F858DD623FEC9A2B0EE024ED077F7516330DD53AC74482", + "total": 1 + } + }, + "last_commit_hash": "AF119CCC1DC98F4043097B40A4CE5598990C86DB1461FE7354079A2E80772D91", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:57.237099851Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "5256DD8C5B0FAD1E6B2F0FC0D09D248C70D81E1EFFC531AF4B33EC285DA932BE", + "parts": { + "hash": "4C31AB0809BD2724B0F858DD623FEC9A2B0EE024ED077F7516330DD53AC74482", + "total": 1 + } + }, + "height": "42", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "e6rRO+rK/ZQieV88zh40tP+oBp2Y8GpOZJ7ZLKqEf7XuJHQNHEmJCnDhJ4UOFiyny/UVjH+hz2/YRZyXUX18Cg==", + "timestamp": "2023-02-24T15:09:57.237099851Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "DDA9E3C772E343EC224AC3FE9DEF0DCDE0F711326CF2F1BFCE5E637D2FEBAD0D", + "parts": { + "hash": "94278D3352068F7052F8450DA5ADDDD83086F87F209130C39611B7D6A49DA052", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "44", + "last_block_id": { + "hash": "DDA9E3C772E343EC224AC3FE9DEF0DCDE0F711326CF2F1BFCE5E637D2FEBAD0D", + "parts": { + "hash": "94278D3352068F7052F8450DA5ADDDD83086F87F209130C39611B7D6A49DA052", + "total": 1 + } + }, + "last_commit_hash": "0B9986D11BB7E31E3B0F4A10CCB32E31BFBE2013B30C67DF2589A877AC4D83FC", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:57.755486393Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "DDA9E3C772E343EC224AC3FE9DEF0DCDE0F711326CF2F1BFCE5E637D2FEBAD0D", + "parts": { + "hash": "94278D3352068F7052F8450DA5ADDDD83086F87F209130C39611B7D6A49DA052", + "total": 1 + } + }, + "height": "43", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "b4wghAvyaPHlXeJdibwz8AuCRtBqb4MxFTaKXx80oPHEar1zlQ/idsl7GQNko/cdIS3uKot3KUvKj3lTStzSBg==", + "timestamp": "2023-02-24T15:09:57.755486393Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "DB1726D6A84B7A6EBEDC8E904E92B1533DDDDA0572C69BA18027FD1D2EFDE209", + "parts": { + "hash": "247062B68AD2BC76198AC8B3E33EED61671B171585D57D3CF8C8C4D89B7C7FD5", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "45", + "last_block_id": { + "hash": "DB1726D6A84B7A6EBEDC8E904E92B1533DDDDA0572C69BA18027FD1D2EFDE209", + "parts": { + "hash": "247062B68AD2BC76198AC8B3E33EED61671B171585D57D3CF8C8C4D89B7C7FD5", + "total": 1 + } + }, + "last_commit_hash": "F1199954161A7C8661E8B41DC67709E977124204CEFFDC79D5CC664D7A6686E1", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:58.27413433Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "DB1726D6A84B7A6EBEDC8E904E92B1533DDDDA0572C69BA18027FD1D2EFDE209", + "parts": { + "hash": "247062B68AD2BC76198AC8B3E33EED61671B171585D57D3CF8C8C4D89B7C7FD5", + "total": 1 + } + }, + "height": "44", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "ukA7mbgLEjKOkoBVRPKWWAfDwR/XLFtz2AlQ4PlrljckeSN2BVQxCUQhpeoi4oxaRAwMdXbnizS8XTQxuG6ABQ==", + "timestamp": "2023-02-24T15:09:58.27413433Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "AE11C11F530FA802991DF3AC9DDD70A75A8AFADB7AD45E5E372CA9698B88800A", + "parts": { + "hash": "13E4AC476A76C64B5906FAECC57DEE3921CD162CB509F9CF31C20682855F2269", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "46", + "last_block_id": { + "hash": "AE11C11F530FA802991DF3AC9DDD70A75A8AFADB7AD45E5E372CA9698B88800A", + "parts": { + "hash": "13E4AC476A76C64B5906FAECC57DEE3921CD162CB509F9CF31C20682855F2269", + "total": 1 + } + }, + "last_commit_hash": "351F9ACD2CEE366DB2F5957291F8DE3FB95AD3762DA57960A747B62A084D2CEF", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:58.791275345Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "AE11C11F530FA802991DF3AC9DDD70A75A8AFADB7AD45E5E372CA9698B88800A", + "parts": { + "hash": "13E4AC476A76C64B5906FAECC57DEE3921CD162CB509F9CF31C20682855F2269", + "total": 1 + } + }, + "height": "45", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "kMUJX98Ok1p1qmCYMTJKqX/IWBso8jniBAzwLyvJWt2TMB69uSpaX9Ip0uYx9X3TAb35XsLmXfxpWddP5ze9BQ==", + "timestamp": "2023-02-24T15:09:58.791275345Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4EEF667FD914D690EE391E69BFD3B49819AC77502801CB079F9BA4EC9BBBA3DD", + "parts": { + "hash": "088BAEA7FB5579D93EADFA47189BA8D1FFD4E5EC4A47C4B2EEBD36AF6EDEEE47", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "47", + "last_block_id": { + "hash": "4EEF667FD914D690EE391E69BFD3B49819AC77502801CB079F9BA4EC9BBBA3DD", + "parts": { + "hash": "088BAEA7FB5579D93EADFA47189BA8D1FFD4E5EC4A47C4B2EEBD36AF6EDEEE47", + "total": 1 + } + }, + "last_commit_hash": "08A73143D419A9214486E0704A0CACF39C085A20CB2027C9A4AABC9CA4585689", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:59.310865408Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4EEF667FD914D690EE391E69BFD3B49819AC77502801CB079F9BA4EC9BBBA3DD", + "parts": { + "hash": "088BAEA7FB5579D93EADFA47189BA8D1FFD4E5EC4A47C4B2EEBD36AF6EDEEE47", + "total": 1 + } + }, + "height": "46", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "snWpx4YZWoI99mY+UdrNs1l3Ba13U/OyTPFtbNbIdF3kbpgnOenClZUP3GX9InNOmffqqbHF64x0pKYCEGfYDQ==", + "timestamp": "2023-02-24T15:09:59.310865408Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "ACFB15047002B27347A69D94DADA62B8A591A471CBE26332C434D45F04405A4C", + "parts": { + "hash": "95E4532EC06273C46E3051C0044FCF4CC9EA198F259FE7554A59FA96C8A9F1DB", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "48", + "last_block_id": { + "hash": "ACFB15047002B27347A69D94DADA62B8A591A471CBE26332C434D45F04405A4C", + "parts": { + "hash": "95E4532EC06273C46E3051C0044FCF4CC9EA198F259FE7554A59FA96C8A9F1DB", + "total": 1 + } + }, + "last_commit_hash": "B6F5A0F1D16737F9F31506BB3E6782A4CFA3382F767086A601C7D9C0C6B39400", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:59.829744911Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "ACFB15047002B27347A69D94DADA62B8A591A471CBE26332C434D45F04405A4C", + "parts": { + "hash": "95E4532EC06273C46E3051C0044FCF4CC9EA198F259FE7554A59FA96C8A9F1DB", + "total": 1 + } + }, + "height": "47", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "B4DirL+iZ+fDzxyXLmr9XX9mAoHHJdqPMpPWWrlyVrHrJLXuzUev2PToO09ilcYbZIc7mK+iqhbQxaBRb5a6Cw==", + "timestamp": "2023-02-24T15:09:59.829744911Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "0BFD9CE7203F9589A39262E18C73B88078D10BB8EB65614B20BF7A6FDC9044CF", + "parts": { + "hash": "C16B50035851157EACBE505EE86175AFF3991B39067E324C4E555F4D1A9888D4", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "49", + "last_block_id": { + "hash": "0BFD9CE7203F9589A39262E18C73B88078D10BB8EB65614B20BF7A6FDC9044CF", + "parts": { + "hash": "C16B50035851157EACBE505EE86175AFF3991B39067E324C4E555F4D1A9888D4", + "total": 1 + } + }, + "last_commit_hash": "297AF39DEA39E4900BC68DC71E47A4826068B9249A97EADA5395090EF1E5FC90", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:00.345816202Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "0BFD9CE7203F9589A39262E18C73B88078D10BB8EB65614B20BF7A6FDC9044CF", + "parts": { + "hash": "C16B50035851157EACBE505EE86175AFF3991B39067E324C4E555F4D1A9888D4", + "total": 1 + } + }, + "height": "48", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "nYWvhC6HIDBmiTlhkLn86DAPcoMtAwNCScghEPewzpjAX3G6A8ilfJUHKDuKSC7VopjtgHmJm+07etBTlBojBQ==", + "timestamp": "2023-02-24T15:10:00.345816202Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "1138B16CAA5AE14E91EE7267D656BD60B060C556D3953FD12EF93CF4D4787BAC", + "parts": { + "hash": "01A62519FAEB16D352E71D2AB9CDD9BC99E02D0DE384C0D6E60FE7282A1235DA", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "50", + "last_block_id": { + "hash": "1138B16CAA5AE14E91EE7267D656BD60B060C556D3953FD12EF93CF4D4787BAC", + "parts": { + "hash": "01A62519FAEB16D352E71D2AB9CDD9BC99E02D0DE384C0D6E60FE7282A1235DA", + "total": 1 + } + }, + "last_commit_hash": "185E80D1FFFDE7D9972BBFA09E6DE2E109B328EEF14572E0CFB83C65894C9B82", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:00.862694537Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "1138B16CAA5AE14E91EE7267D656BD60B060C556D3953FD12EF93CF4D4787BAC", + "parts": { + "hash": "01A62519FAEB16D352E71D2AB9CDD9BC99E02D0DE384C0D6E60FE7282A1235DA", + "total": 1 + } + }, + "height": "49", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "M0BHMrQVqH6rKbDO0FUvQ5E37ZVRaHftX3Tf+/8M1kG8tZTwc01ypEK7/zFL0sL8PD1DSmBlu0Wl1D2AEIu8Ag==", + "timestamp": "2023-02-24T15:10:00.862694537Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "A7F5B166249797B42C19859830F55B75DD4D187B6FE01C20B6EFBF5F3B44FC36", + "parts": { + "hash": "E2BAB27A47C70C5291045725EBFAB1BAED8292CC06B0232D877BB697E0BB9BFF", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "51", + "last_block_id": { + "hash": "A7F5B166249797B42C19859830F55B75DD4D187B6FE01C20B6EFBF5F3B44FC36", + "parts": { + "hash": "E2BAB27A47C70C5291045725EBFAB1BAED8292CC06B0232D877BB697E0BB9BFF", + "total": 1 + } + }, + "last_commit_hash": "EF6EF07F3386E69F54CC4481532DAFBFA055F1DB9A10CC4BF1548B33FDAA8F12", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:01.382585057Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "A7F5B166249797B42C19859830F55B75DD4D187B6FE01C20B6EFBF5F3B44FC36", + "parts": { + "hash": "E2BAB27A47C70C5291045725EBFAB1BAED8292CC06B0232D877BB697E0BB9BFF", + "total": 1 + } + }, + "height": "50", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "QQ9O+qki+5vPGBbNqg4Ea1WtZBpekXPW2JK8fZ6672S4MtkFRgncjMxsJl1x+uK0PZ4y1AblYdx55l7nYybmAg==", + "timestamp": "2023-02-24T15:10:01.382585057Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4346EB43EF285225BE125A2A96BD9DAE0E49B5565E1FCE823A1000FE44136D20", + "parts": { + "hash": "22B96890CD4AC15EEF3F89B473CDC94390388648FF9B3F7DEE2154A35EE074C1", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "52", + "last_block_id": { + "hash": "4346EB43EF285225BE125A2A96BD9DAE0E49B5565E1FCE823A1000FE44136D20", + "parts": { + "hash": "22B96890CD4AC15EEF3F89B473CDC94390388648FF9B3F7DEE2154A35EE074C1", + "total": 1 + } + }, + "last_commit_hash": "B62E8A1470D4D8C125483D39F107F932C1A36D66648E3A59ABF0468C4967EAE6", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:01.900861369Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4346EB43EF285225BE125A2A96BD9DAE0E49B5565E1FCE823A1000FE44136D20", + "parts": { + "hash": "22B96890CD4AC15EEF3F89B473CDC94390388648FF9B3F7DEE2154A35EE074C1", + "total": 1 + } + }, + "height": "51", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "JbcnBRVk8n8ypklwJX4t41dXVJ9bbfmCp4kfUkzwF5ueepMHyuvA+MZbc39TCB3chrk9X19avAHpCRomja5KDw==", + "timestamp": "2023-02-24T15:10:01.900861369Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "EBCFD028C67DBBC265BD293BBD83A4658FBFA7B185FF0F17994A22862A36C43A", + "parts": { + "hash": "199C0D0120AA3D756907FEF7D94DC6E1008C1537EBB9196B46679E35A507C132", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "53", + "last_block_id": { + "hash": "EBCFD028C67DBBC265BD293BBD83A4658FBFA7B185FF0F17994A22862A36C43A", + "parts": { + "hash": "199C0D0120AA3D756907FEF7D94DC6E1008C1537EBB9196B46679E35A507C132", + "total": 1 + } + }, + "last_commit_hash": "6648B3341958BD568CAC927282B78C472C6D91C87492051F0FD634BF9CD56AB3", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:02.417494221Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "EBCFD028C67DBBC265BD293BBD83A4658FBFA7B185FF0F17994A22862A36C43A", + "parts": { + "hash": "199C0D0120AA3D756907FEF7D94DC6E1008C1537EBB9196B46679E35A507C132", + "total": 1 + } + }, + "height": "52", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "YkEO7DA6Y/H5i4/WJQ+6cY0QZbfhrtpPlkTh1gDnQ7kXMJNJh7fiiY8lHV+o2pjqhEs9HR3hTIQeKZMnG1GqBA==", + "timestamp": "2023-02-24T15:10:02.417494221Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "44F13A3FC052C0259F11977A333B97D24944694FC9E5409684325225446582FE", + "parts": { + "hash": "578999EFFAF66B0410AC609729E54CD76D76CEF596D06CE5E9EC4B13B1E9B619", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "54", + "last_block_id": { + "hash": "44F13A3FC052C0259F11977A333B97D24944694FC9E5409684325225446582FE", + "parts": { + "hash": "578999EFFAF66B0410AC609729E54CD76D76CEF596D06CE5E9EC4B13B1E9B619", + "total": 1 + } + }, + "last_commit_hash": "D2D14CBAF0BA4F25BEC6ECA648DC4ECCD3485F7AE88071836DB84C853EBCC69C", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:02.93519888Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "44F13A3FC052C0259F11977A333B97D24944694FC9E5409684325225446582FE", + "parts": { + "hash": "578999EFFAF66B0410AC609729E54CD76D76CEF596D06CE5E9EC4B13B1E9B619", + "total": 1 + } + }, + "height": "53", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "O9/N96JhVNNd+xnxMnKKUmb7J18uApb+bH3galqCyFCr/RN0FL94Z7JGJNqQh59+O12Vv/ns5tyn4OdF0Yx2DA==", + "timestamp": "2023-02-24T15:10:02.93519888Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "945F1F4FB3843E144E22DF6F830AA54FC42EF4131C75957B3CBED36F05BCD089", + "parts": { + "hash": "EF54799764ED32A13FF6EA22952C089960540A4749BA6CCBB5050F2BC6BFA302", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "55", + "last_block_id": { + "hash": "945F1F4FB3843E144E22DF6F830AA54FC42EF4131C75957B3CBED36F05BCD089", + "parts": { + "hash": "EF54799764ED32A13FF6EA22952C089960540A4749BA6CCBB5050F2BC6BFA302", + "total": 1 + } + }, + "last_commit_hash": "E680B37F0A6BAC7E4EAE6FBB89BC5071F423D8AB60B46975CF26364104A1F01B", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:03.454677478Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "945F1F4FB3843E144E22DF6F830AA54FC42EF4131C75957B3CBED36F05BCD089", + "parts": { + "hash": "EF54799764ED32A13FF6EA22952C089960540A4749BA6CCBB5050F2BC6BFA302", + "total": 1 + } + }, + "height": "54", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "0e6lvC2vARY7UPbBAa9JsHHaTTkxo2uLB/0422Ac8PCt+Nk2QwADVJAHkAXD82pQsDmYIy+yoLENdz+9nHm1BQ==", + "timestamp": "2023-02-24T15:10:03.454677478Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "722326DEBFA1C7B21BAAB1AB35F3A02CA96B6BA7E8C5F7FAA71B3F096D6DD57F", + "parts": { + "hash": "0692FE6899695E6CFAF000E9245E7411842FB471353470C1F491526B1E0A4549", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "56", + "last_block_id": { + "hash": "722326DEBFA1C7B21BAAB1AB35F3A02CA96B6BA7E8C5F7FAA71B3F096D6DD57F", + "parts": { + "hash": "0692FE6899695E6CFAF000E9245E7411842FB471353470C1F491526B1E0A4549", + "total": 1 + } + }, + "last_commit_hash": "C388551B70D0395BE9AFF8E18A49107557B5EC0ECCFCC6F837F8F0830010057B", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:03.97193517Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "722326DEBFA1C7B21BAAB1AB35F3A02CA96B6BA7E8C5F7FAA71B3F096D6DD57F", + "parts": { + "hash": "0692FE6899695E6CFAF000E9245E7411842FB471353470C1F491526B1E0A4549", + "total": 1 + } + }, + "height": "55", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "KnYKFqPntf3qV+xOBZ3sdHXtbl7j6OjgQhf73PmHriRpqi6Y2fY8biNB4zBg+kGqdqfL2ed8igH6OrL7yB7mAw==", + "timestamp": "2023-02-24T15:10:03.97193517Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "C553B4508DD88168766B5FB7BA6F9684EA6BFAA77BB3EF9EFC40466512D2D7ED", + "parts": { + "hash": "161BC57D6EF22467FCA2E1727EEBF6449935EFEC345E3A1280B2119C60BC44B0", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "57", + "last_block_id": { + "hash": "C553B4508DD88168766B5FB7BA6F9684EA6BFAA77BB3EF9EFC40466512D2D7ED", + "parts": { + "hash": "161BC57D6EF22467FCA2E1727EEBF6449935EFEC345E3A1280B2119C60BC44B0", + "total": 1 + } + }, + "last_commit_hash": "27D1EC557EF2B04AB95919D5992BB63C710A21972D9A87AF422483F9286242B1", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:04.490286491Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "C553B4508DD88168766B5FB7BA6F9684EA6BFAA77BB3EF9EFC40466512D2D7ED", + "parts": { + "hash": "161BC57D6EF22467FCA2E1727EEBF6449935EFEC345E3A1280B2119C60BC44B0", + "total": 1 + } + }, + "height": "56", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "liX6NFce2HZxdnTnHCobIwBUxAh0TYpAAJXy+FrhMokQ8FhiKPgggLLWLfWd5uobLB+1SAhLW5vJucLrQwFuDw==", + "timestamp": "2023-02-24T15:10:04.490286491Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "00B345394E9FEC254B30386AC58CC1445A79E32959BFF7CC55DBCB7B5540A5ED", + "parts": { + "hash": "FAA521F3228E4D97140387BDA8C052309585D7D5F5F994D0D2B0C3819EC09890", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "58", + "last_block_id": { + "hash": "00B345394E9FEC254B30386AC58CC1445A79E32959BFF7CC55DBCB7B5540A5ED", + "parts": { + "hash": "FAA521F3228E4D97140387BDA8C052309585D7D5F5F994D0D2B0C3819EC09890", + "total": 1 + } + }, + "last_commit_hash": "F839F9F294C2E5C03C618FA07EB745F3A3139C7D4E2DF2343F73A96FED10857B", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:05.009517719Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "00B345394E9FEC254B30386AC58CC1445A79E32959BFF7CC55DBCB7B5540A5ED", + "parts": { + "hash": "FAA521F3228E4D97140387BDA8C052309585D7D5F5F994D0D2B0C3819EC09890", + "total": 1 + } + }, + "height": "57", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "RWcwSPYRLliBiVOFEV77+yCuSY8V3jqv1dS2edA90BHeaNoK1clr/hDkxNlk8ik2iAy6Rp5LJug9oH4QYeWWCQ==", + "timestamp": "2023-02-24T15:10:05.009517719Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "589BFEECF02FFDFD120248029A01A72D07D4A0C8BB40D456846B95644E6E60E3", + "parts": { + "hash": "725A0551FDC4DDEE4E6BF95E575FCF5512A9EE728C10B4948DC09C964C9C0269", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "59", + "last_block_id": { + "hash": "589BFEECF02FFDFD120248029A01A72D07D4A0C8BB40D456846B95644E6E60E3", + "parts": { + "hash": "725A0551FDC4DDEE4E6BF95E575FCF5512A9EE728C10B4948DC09C964C9C0269", + "total": 1 + } + }, + "last_commit_hash": "284A2344BE8E65552650DA36560BA254CF5EE55789B33E1DCAC1DDFFD53C3A57", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:05.528223517Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "589BFEECF02FFDFD120248029A01A72D07D4A0C8BB40D456846B95644E6E60E3", + "parts": { + "hash": "725A0551FDC4DDEE4E6BF95E575FCF5512A9EE728C10B4948DC09C964C9C0269", + "total": 1 + } + }, + "height": "58", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "+zE1EmAgvCfvIgpCa8yZfRr/+y6uz+kJ5opDoL6EHva9vHFYh4mc5rs6l7/DVnxBa+SycSG7qN5GuF21x40JAw==", + "timestamp": "2023-02-24T15:10:05.528223517Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4077519E09B0A29E81038787837C5AB382C6E4E9D0001A6E1CEC5CE14019FDBC", + "parts": { + "hash": "459C51BDD00DCFFD9CE399A619983EC1BC3E4A03EAA05096BBDCC2FA2064D6D5", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "60", + "last_block_id": { + "hash": "4077519E09B0A29E81038787837C5AB382C6E4E9D0001A6E1CEC5CE14019FDBC", + "parts": { + "hash": "459C51BDD00DCFFD9CE399A619983EC1BC3E4A03EAA05096BBDCC2FA2064D6D5", + "total": 1 + } + }, + "last_commit_hash": "19EEE50F3D6E61E78C7B17D38951673CE5A628C68F98A3A10352A2D39C7600FF", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:06.048285633Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4077519E09B0A29E81038787837C5AB382C6E4E9D0001A6E1CEC5CE14019FDBC", + "parts": { + "hash": "459C51BDD00DCFFD9CE399A619983EC1BC3E4A03EAA05096BBDCC2FA2064D6D5", + "total": 1 + } + }, + "height": "59", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "I4J9LLi1AQoC+SfJexmDlATv1x7Kdp87gnuPiwtAqJfdQStm6mMnv8SyDDUfUM9zK56tziWgqgBlpCfuyQXZCA==", + "timestamp": "2023-02-24T15:10:06.048285633Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "1FDA3C17D26FA606914484F42E9723874A4D6654C411CCA2BABC52EFC38869FA", + "parts": { + "hash": "79216BF6D2572FB21FFE464B044FE5F2651DA7747E4533E1DCF45E15F6113562", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "61", + "last_block_id": { + "hash": "1FDA3C17D26FA606914484F42E9723874A4D6654C411CCA2BABC52EFC38869FA", + "parts": { + "hash": "79216BF6D2572FB21FFE464B044FE5F2651DA7747E4533E1DCF45E15F6113562", + "total": 1 + } + }, + "last_commit_hash": "C0FA52EBF2BC00D5DB7F183782C6C7F180C220907F90AD887761C5951D367362", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:06.5672674Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "1FDA3C17D26FA606914484F42E9723874A4D6654C411CCA2BABC52EFC38869FA", + "parts": { + "hash": "79216BF6D2572FB21FFE464B044FE5F2651DA7747E4533E1DCF45E15F6113562", + "total": 1 + } + }, + "height": "60", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "REaa8pz4sV6EsRKytM6jBS8JxUHMi3vlOht43VpqO/Nhe8hIU4GXE+Qj0K9SFJGXrQ8HRmqmDb5Cdq+99D0iAQ==", + "timestamp": "2023-02-24T15:10:06.5672674Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "B28CF883F6A1064A1763E1738E151A4306DBD58C0A0458CF2BFBDE31447C7F15", + "parts": { + "hash": "84B60EC48D723DE9D35E772150E8E68A6275E33B4D5A6A6890BD75FF3A99B44B", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "62", + "last_block_id": { + "hash": "B28CF883F6A1064A1763E1738E151A4306DBD58C0A0458CF2BFBDE31447C7F15", + "parts": { + "hash": "84B60EC48D723DE9D35E772150E8E68A6275E33B4D5A6A6890BD75FF3A99B44B", + "total": 1 + } + }, + "last_commit_hash": "DCE9DA5E7B640390CCA3046424542DEB7467E15341C9C44451186ECBAD5DEA98", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:07.088001066Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "B28CF883F6A1064A1763E1738E151A4306DBD58C0A0458CF2BFBDE31447C7F15", + "parts": { + "hash": "84B60EC48D723DE9D35E772150E8E68A6275E33B4D5A6A6890BD75FF3A99B44B", + "total": 1 + } + }, + "height": "61", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "A2dhOHjBFUHXblNQqXm+1zoD5fV03qw3/Cns+JWDesSQvbqg2m0nC/Ycv39eQye0n4gl5mErbdm/2rhNDDSQCQ==", + "timestamp": "2023-02-24T15:10:07.088001066Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "9452A0B1C8F5C645737C67EABE3E7285FF6301357A51EB759BF71B8232C8C108", + "parts": { + "hash": "2B9BE99ACDB21F94275DF310E1A3C7E93A8FF0EEB8002A21711C92CB6C8FE1D6", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "63", + "last_block_id": { + "hash": "9452A0B1C8F5C645737C67EABE3E7285FF6301357A51EB759BF71B8232C8C108", + "parts": { + "hash": "2B9BE99ACDB21F94275DF310E1A3C7E93A8FF0EEB8002A21711C92CB6C8FE1D6", + "total": 1 + } + }, + "last_commit_hash": "72B3A030F970CBC1627F510E56F7F935857AA55B9F0CAF66AAC273AD4591AA07", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:07.608109818Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "9452A0B1C8F5C645737C67EABE3E7285FF6301357A51EB759BF71B8232C8C108", + "parts": { + "hash": "2B9BE99ACDB21F94275DF310E1A3C7E93A8FF0EEB8002A21711C92CB6C8FE1D6", + "total": 1 + } + }, + "height": "62", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "dq651qbWSLPczch/MLoFNbp8dwP8ngUMQs5Ia2UBvAai/D3g5CW1Ng/gfPDeQRnvsi/Hmg9Y8EvPEXAdLOMpCA==", + "timestamp": "2023-02-24T15:10:07.608109818Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "BC9099C7A95E859F3A9E905712D34F18CED5CEAC7AE6B9A927898D6B2ADD6CE7", + "parts": { + "hash": "4B116F05D9526F43B1438816D4DDB454578D845938CE8E27E93364EB798DD64C", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "64", + "last_block_id": { + "hash": "BC9099C7A95E859F3A9E905712D34F18CED5CEAC7AE6B9A927898D6B2ADD6CE7", + "parts": { + "hash": "4B116F05D9526F43B1438816D4DDB454578D845938CE8E27E93364EB798DD64C", + "total": 1 + } + }, + "last_commit_hash": "F78B46F66664E902DF3ED26B4D9CD25330E6B2EA958BFC730974819BD8BBD4A0", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:08.126167057Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "BC9099C7A95E859F3A9E905712D34F18CED5CEAC7AE6B9A927898D6B2ADD6CE7", + "parts": { + "hash": "4B116F05D9526F43B1438816D4DDB454578D845938CE8E27E93364EB798DD64C", + "total": 1 + } + }, + "height": "63", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "0a+jkvXSgvYkM4Yx91Ro5BZU7xF26He3du6NEwNQVRxtyq7ybMyFFqoY0IgU0wENeaSrnry0tn89ZFXGdB+iAw==", + "timestamp": "2023-02-24T15:10:08.126167057Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "C75C315961C270D255BCFCB48A68105EF872907CA267FA269C39605E807838D7", + "parts": { + "hash": "8012C504A65312F971F84F9C6B7C4A82607E8B896DCA53A7926B487649B3598C", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "65", + "last_block_id": { + "hash": "C75C315961C270D255BCFCB48A68105EF872907CA267FA269C39605E807838D7", + "parts": { + "hash": "8012C504A65312F971F84F9C6B7C4A82607E8B896DCA53A7926B487649B3598C", + "total": 1 + } + }, + "last_commit_hash": "E52A557C451F152B1F1651B91E0AA55E369163D2DE57A21601974EAEC9021401", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:08.642802272Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "C75C315961C270D255BCFCB48A68105EF872907CA267FA269C39605E807838D7", + "parts": { + "hash": "8012C504A65312F971F84F9C6B7C4A82607E8B896DCA53A7926B487649B3598C", + "total": 1 + } + }, + "height": "64", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "FJffAu1Gqo+SjQflRWFW6Z/29WPEwaXGFX/QmcrzOAA91fU7pALqPiGkPzxKDp/ScBLOvafKamGWlDmlTwVsBQ==", + "timestamp": "2023-02-24T15:10:08.642802272Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "CFBAE91A297491D6940FE8A722493E6D1947E2BC56F5F4A575D025F179F680C9", + "parts": { + "hash": "D9D801CD62D75F56AEEAC865BDCB90B4C73AB7A657F2C1FD190D12E2690E9345", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "66", + "last_block_id": { + "hash": "CFBAE91A297491D6940FE8A722493E6D1947E2BC56F5F4A575D025F179F680C9", + "parts": { + "hash": "D9D801CD62D75F56AEEAC865BDCB90B4C73AB7A657F2C1FD190D12E2690E9345", + "total": 1 + } + }, + "last_commit_hash": "18C9646BA42588E486572C6622C134ECF2E4335D1A90BFB8E3E7610142DDDA36", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:09.158466835Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "CFBAE91A297491D6940FE8A722493E6D1947E2BC56F5F4A575D025F179F680C9", + "parts": { + "hash": "D9D801CD62D75F56AEEAC865BDCB90B4C73AB7A657F2C1FD190D12E2690E9345", + "total": 1 + } + }, + "height": "65", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "IhydbNLjlmZChv6nkwr046bMobBDUNI9ufmOp3SkyqRgSd0ozoRseuL9VUQimhV35jYnUQUAamkp/6nt58lPAQ==", + "timestamp": "2023-02-24T15:10:09.158466835Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "8034C311C36C911ACAE3734593BB425B976863111053F71B84A4D59964C8EBBC", + "parts": { + "hash": "BFCC0ACA7FE08FC00E417B012DC7DC05B831F63184250FEFFF6E8C6BB1A572F4", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "67", + "last_block_id": { + "hash": "8034C311C36C911ACAE3734593BB425B976863111053F71B84A4D59964C8EBBC", + "parts": { + "hash": "BFCC0ACA7FE08FC00E417B012DC7DC05B831F63184250FEFFF6E8C6BB1A572F4", + "total": 1 + } + }, + "last_commit_hash": "103E69E502EDD0A6B027FEF11DB75EBBF80FA05D91AB354FFC5D121BF7F949D4", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:09.675815851Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "8034C311C36C911ACAE3734593BB425B976863111053F71B84A4D59964C8EBBC", + "parts": { + "hash": "BFCC0ACA7FE08FC00E417B012DC7DC05B831F63184250FEFFF6E8C6BB1A572F4", + "total": 1 + } + }, + "height": "66", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "kRXINPczoPVW08ldgXHmhp0x3QoXkBWR3kUyNhsWbLk1OdhYPbDhZA+6bfxa5clPHCYgiszdmOO2rp3SibreBQ==", + "timestamp": "2023-02-24T15:10:09.675815851Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "E1BAFCB8C5EB13ED74CE8ABA9CE0272608B433EF45FEB7D61DDA2CC092D03CC1", + "parts": { + "hash": "A650A48FE89862F7F68E37333CBDA466B9090F0F80E95902BB4A11E83D853456", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "68", + "last_block_id": { + "hash": "E1BAFCB8C5EB13ED74CE8ABA9CE0272608B433EF45FEB7D61DDA2CC092D03CC1", + "parts": { + "hash": "A650A48FE89862F7F68E37333CBDA466B9090F0F80E95902BB4A11E83D853456", + "total": 1 + } + }, + "last_commit_hash": "9C2975EB38DF9E80B4EF705DC2320240054D5118F28145A033256E55D16FC120", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:10.193696136Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "E1BAFCB8C5EB13ED74CE8ABA9CE0272608B433EF45FEB7D61DDA2CC092D03CC1", + "parts": { + "hash": "A650A48FE89862F7F68E37333CBDA466B9090F0F80E95902BB4A11E83D853456", + "total": 1 + } + }, + "height": "67", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "+ILWvGu2iZw/c4zOj1BM/FFEOPFeWCBh0XdSbJU20wVqYghbYkU9IZ5Iz8yAb8aDiw1Wfss77U7xYyT3nSFMAg==", + "timestamp": "2023-02-24T15:10:10.193696136Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "BC91E3FD8F8AF6FCD72D490699A476259EC824ECD6F65CD615028FE5BBEA423B", + "parts": { + "hash": "BD46C8DABADA4EC0A6F3FC0A1AFC6A2E1AA5E85848B93ACA6053B1142031165A", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "69", + "last_block_id": { + "hash": "BC91E3FD8F8AF6FCD72D490699A476259EC824ECD6F65CD615028FE5BBEA423B", + "parts": { + "hash": "BD46C8DABADA4EC0A6F3FC0A1AFC6A2E1AA5E85848B93ACA6053B1142031165A", + "total": 1 + } + }, + "last_commit_hash": "B6C40A5DF49FC327AB8477B0F7A54E0E7CE438BA74361D80149963A70C6F532A", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:10.710776945Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "BC91E3FD8F8AF6FCD72D490699A476259EC824ECD6F65CD615028FE5BBEA423B", + "parts": { + "hash": "BD46C8DABADA4EC0A6F3FC0A1AFC6A2E1AA5E85848B93ACA6053B1142031165A", + "total": 1 + } + }, + "height": "68", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "6Hl33Jv/5iMOj/jLDptpb5npgCWJyGPdtLl0yfVAOu0a6JASXukktxHMp0vVMbMBasO8jNGSxoNhxUeG333rBw==", + "timestamp": "2023-02-24T15:10:10.710776945Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "298A99B3185C90E8E549F4CE82F9888F957107D6B3B7A5461608680B68D5DF90", + "parts": { + "hash": "9908ECF363A08757BB37DE31B412E8816A1C48EB282407B9E362AAEC4F0406BE", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "70", + "last_block_id": { + "hash": "298A99B3185C90E8E549F4CE82F9888F957107D6B3B7A5461608680B68D5DF90", + "parts": { + "hash": "9908ECF363A08757BB37DE31B412E8816A1C48EB282407B9E362AAEC4F0406BE", + "total": 1 + } + }, + "last_commit_hash": "45C4603344CD0E4536C7D9A7DC2D29AD3AB085B868C3ECD847DA6FF25241C746", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:11.230812463Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "298A99B3185C90E8E549F4CE82F9888F957107D6B3B7A5461608680B68D5DF90", + "parts": { + "hash": "9908ECF363A08757BB37DE31B412E8816A1C48EB282407B9E362AAEC4F0406BE", + "total": 1 + } + }, + "height": "69", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "0v25MRGpcUA8YD5WBmWE9fB/i+YWmASyHdD+NyRI1+dxQb2LZ4J+MyLFYbtob3db1AhQO8j0gH5WjidEbBNVCA==", + "timestamp": "2023-02-24T15:10:11.230812463Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "02C20FCA68E8F8D4CAF801819C018CCAAF687E4A7D3AE46D56DEAE7B321DA3EF", + "parts": { + "hash": "8B757F00F150A78E9025D0F7675D780214045C43A7C7D5038605B797C0A52443", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "71", + "last_block_id": { + "hash": "02C20FCA68E8F8D4CAF801819C018CCAAF687E4A7D3AE46D56DEAE7B321DA3EF", + "parts": { + "hash": "8B757F00F150A78E9025D0F7675D780214045C43A7C7D5038605B797C0A52443", + "total": 1 + } + }, + "last_commit_hash": "F5AB1A3EE23558D41E014B0EEE9EF97221A553B48C4FF225904A84ADA39CF943", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:11.748416415Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "02C20FCA68E8F8D4CAF801819C018CCAAF687E4A7D3AE46D56DEAE7B321DA3EF", + "parts": { + "hash": "8B757F00F150A78E9025D0F7675D780214045C43A7C7D5038605B797C0A52443", + "total": 1 + } + }, + "height": "70", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "0PCP8DD780dkF1Donw5kh9efICrCkpsb87mjsnPzllc72k1FKsBZjnwKTtmAqUDd/X2vd1//DL8JuNLRTJo5Cg==", + "timestamp": "2023-02-24T15:10:11.748416415Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "AD5101727F834ABE362A0461794FA96FBDF1AF24059D28FAECF7D4088D0A1459", + "parts": { + "hash": "C48562DF5B842CF8C0865F2D70BE11C62A186DC3017805BDD4FC9FD172C41EA7", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "72", + "last_block_id": { + "hash": "AD5101727F834ABE362A0461794FA96FBDF1AF24059D28FAECF7D4088D0A1459", + "parts": { + "hash": "C48562DF5B842CF8C0865F2D70BE11C62A186DC3017805BDD4FC9FD172C41EA7", + "total": 1 + } + }, + "last_commit_hash": "A7AA3E25BFAAE46912CB90494DCF4F68F8205A55FB4891D5B53324D790DD3A31", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:12.269703898Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "AD5101727F834ABE362A0461794FA96FBDF1AF24059D28FAECF7D4088D0A1459", + "parts": { + "hash": "C48562DF5B842CF8C0865F2D70BE11C62A186DC3017805BDD4FC9FD172C41EA7", + "total": 1 + } + }, + "height": "71", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "k3McP4ok6Roz5bAap2qtKQ+7rpX9NdixJOWCZc6LYiZxJsMDeWXh0zUtHbERUchIc8NoOULJZhbS4iFTTlKYCQ==", + "timestamp": "2023-02-24T15:10:12.269703898Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "619C63949C052D89975B40BF9CD4A19DDB58E8EEA276667D996B3B0B1869A349", + "parts": { + "hash": "9CF47D0B506FEC1FE92AD74680F3151790781CE5050F2308F980BF639591BD42", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "73", + "last_block_id": { + "hash": "619C63949C052D89975B40BF9CD4A19DDB58E8EEA276667D996B3B0B1869A349", + "parts": { + "hash": "9CF47D0B506FEC1FE92AD74680F3151790781CE5050F2308F980BF639591BD42", + "total": 1 + } + }, + "last_commit_hash": "0D6D7DF87EA8456E284496374D126B83DF2359D179F82A35F3B4F0037FBAC9CF", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:12.787236166Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "619C63949C052D89975B40BF9CD4A19DDB58E8EEA276667D996B3B0B1869A349", + "parts": { + "hash": "9CF47D0B506FEC1FE92AD74680F3151790781CE5050F2308F980BF639591BD42", + "total": 1 + } + }, + "height": "72", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "vQQQ7PAlx/KEPsQ+yeN0tsrGjz9f7KHdaAr5pAdpvIAlfofEq3nmOi4mxEO0Q1Aj4lfi8+TVpKjfQn759dg/Cg==", + "timestamp": "2023-02-24T15:10:12.787236166Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "6921568AF3CEBBFC7D5B2FC4E0980DEF9A353673CD104B4BE153A57D69625746", + "parts": { + "hash": "E24C56A064A47680BF97121B878BE864C1F29291D78E558E3AF61CD8BB74D74D", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "74", + "last_block_id": { + "hash": "6921568AF3CEBBFC7D5B2FC4E0980DEF9A353673CD104B4BE153A57D69625746", + "parts": { + "hash": "E24C56A064A47680BF97121B878BE864C1F29291D78E558E3AF61CD8BB74D74D", + "total": 1 + } + }, + "last_commit_hash": "52386D5C3E1D56E0F7CA267422C4F830C2B3D3CF07A8D49FCA2456B56A9819D2", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:13.303922027Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "6921568AF3CEBBFC7D5B2FC4E0980DEF9A353673CD104B4BE153A57D69625746", + "parts": { + "hash": "E24C56A064A47680BF97121B878BE864C1F29291D78E558E3AF61CD8BB74D74D", + "total": 1 + } + }, + "height": "73", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "vDm3hJ82xvRKQSvJWaDJI3sKSbTdP64V2IGE4FxvZOoI+8AUhuLpFDdngDza1LXNVfhPZV0dOI4CzTP0L0nfCA==", + "timestamp": "2023-02-24T15:10:13.303922027Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "FD8C2208476F33EF9C76C265CAECEA01A81F559AD2A5A5404E2564629A05B0B7", + "parts": { + "hash": "1AD5A83DA188470C49D2B5AB5ADD5F91564D69F82E0DA15DBA502213EF2A514D", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "75", + "last_block_id": { + "hash": "FD8C2208476F33EF9C76C265CAECEA01A81F559AD2A5A5404E2564629A05B0B7", + "parts": { + "hash": "1AD5A83DA188470C49D2B5AB5ADD5F91564D69F82E0DA15DBA502213EF2A514D", + "total": 1 + } + }, + "last_commit_hash": "53343C1DE93CB501AA957B755E1039167F52CCD53E423E7AD5CEB14C14ABB2D7", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:13.823154238Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "FD8C2208476F33EF9C76C265CAECEA01A81F559AD2A5A5404E2564629A05B0B7", + "parts": { + "hash": "1AD5A83DA188470C49D2B5AB5ADD5F91564D69F82E0DA15DBA502213EF2A514D", + "total": 1 + } + }, + "height": "74", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "qgD64AZj/Vw/z33hyCTKzE7d6wGpbsOndH/xihqaWU9+aLtn2B4o6cR2fn5LFr14UfXlDaWDSyJ8v6rqL8VACg==", + "timestamp": "2023-02-24T15:10:13.823154238Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "E05954016AC3CF6F26EE03C91B40C49AF819A6F10F93642E8FCC5A6E7C33C207", + "parts": { + "hash": "EC8F0ED25E45E19146C1981E0D3655A3EDE556E27138C9999E1999306F418BCA", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "76", + "last_block_id": { + "hash": "E05954016AC3CF6F26EE03C91B40C49AF819A6F10F93642E8FCC5A6E7C33C207", + "parts": { + "hash": "EC8F0ED25E45E19146C1981E0D3655A3EDE556E27138C9999E1999306F418BCA", + "total": 1 + } + }, + "last_commit_hash": "18E7512FFF3AEFD6B019AC5AC8D1B193701AB2BBB1110B0E63E256D8AE433CDB", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:14.339504898Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "E05954016AC3CF6F26EE03C91B40C49AF819A6F10F93642E8FCC5A6E7C33C207", + "parts": { + "hash": "EC8F0ED25E45E19146C1981E0D3655A3EDE556E27138C9999E1999306F418BCA", + "total": 1 + } + }, + "height": "75", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "8LzvsSr1R4U6NweHN7rRrr59UAaS1RGwlMvpCE3T+B+UbW4TTx4Nlw4tBL17LjRt4R9F40QDJt0Tpq3sXNGDBQ==", + "timestamp": "2023-02-24T15:10:14.339504898Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "5EBB07051D6A1CBE87B82F13EAB1486AE108CCA69AB1858F96933AC7CCE7477F", + "parts": { + "hash": "BB90594B623173C9AA6BF3999434D8C95675460DD8E43F19EA832CE671B614A6", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "77", + "last_block_id": { + "hash": "5EBB07051D6A1CBE87B82F13EAB1486AE108CCA69AB1858F96933AC7CCE7477F", + "parts": { + "hash": "BB90594B623173C9AA6BF3999434D8C95675460DD8E43F19EA832CE671B614A6", + "total": 1 + } + }, + "last_commit_hash": "C46C988EA7866C0495512D243E6C966139A1B4D4ED64F51C2D2B56B977DD9C84", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:14.858160995Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "5EBB07051D6A1CBE87B82F13EAB1486AE108CCA69AB1858F96933AC7CCE7477F", + "parts": { + "hash": "BB90594B623173C9AA6BF3999434D8C95675460DD8E43F19EA832CE671B614A6", + "total": 1 + } + }, + "height": "76", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "7pUfd8RgtscrwwISg8a3Qna/l9nPKbBAIZa07WyR8JBkZiIV45vJHSNBPviZjeOvMGlqMx8XQIYnP2v6RRwCDg==", + "timestamp": "2023-02-24T15:10:14.858160995Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "562D52FB2419AD0765B07CB90CAAB0CF1601F91ED1B9F2B4E936A6BD61A16DD8", + "parts": { + "hash": "B61B664CB5653EDD554561827F5D0A0646CD9A815A3F982E6CE34742893E53CB", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "78", + "last_block_id": { + "hash": "562D52FB2419AD0765B07CB90CAAB0CF1601F91ED1B9F2B4E936A6BD61A16DD8", + "parts": { + "hash": "B61B664CB5653EDD554561827F5D0A0646CD9A815A3F982E6CE34742893E53CB", + "total": 1 + } + }, + "last_commit_hash": "198F5AB1C616849CB232E69A1AAE52A818526B8B6638F61E8FA54ABB4A7FECBF", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:15.374906279Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "562D52FB2419AD0765B07CB90CAAB0CF1601F91ED1B9F2B4E936A6BD61A16DD8", + "parts": { + "hash": "B61B664CB5653EDD554561827F5D0A0646CD9A815A3F982E6CE34742893E53CB", + "total": 1 + } + }, + "height": "77", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "quE9tzBtBY5uuALnTwkEfdl8Y41RFWZX+OhuXZ0a74CxGp6SYN90v5+Svp3QiK9wD2aaa/Z/4fRXASDea1n+Cg==", + "timestamp": "2023-02-24T15:10:15.374906279Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "7731239F6E06407382C42964D25D2DC7D2F9DF7E467667452CC3B1E72343601E", + "parts": { + "hash": "1939C79965CFD63B099F4CE4302DF3B50F6C3D3DC86AE41379710E975F786FC2", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "79", + "last_block_id": { + "hash": "7731239F6E06407382C42964D25D2DC7D2F9DF7E467667452CC3B1E72343601E", + "parts": { + "hash": "1939C79965CFD63B099F4CE4302DF3B50F6C3D3DC86AE41379710E975F786FC2", + "total": 1 + } + }, + "last_commit_hash": "C4BA3B3B9DAB60EBA4B012B66CE0267138C9980E4C8CB20B959308F7AD41F773", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:15.891763799Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "7731239F6E06407382C42964D25D2DC7D2F9DF7E467667452CC3B1E72343601E", + "parts": { + "hash": "1939C79965CFD63B099F4CE4302DF3B50F6C3D3DC86AE41379710E975F786FC2", + "total": 1 + } + }, + "height": "78", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "l2ByE017TV2bquetHbe6HABenlwLTDjh0hLpkMKKQyewOJmPVoSqov7lj+saBZhXMIUSoJRht/+tzddBA1YMAA==", + "timestamp": "2023-02-24T15:10:15.891763799Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "51FF3B2D890CED166D5253B0982AEC4E8A2B58219D3F90162F562B6A36CB7B6E", + "parts": { + "hash": "682BB96896129320C025A416FEBBDFDB8E493FA6C743A6D31696CF7B6C70A175", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "80", + "last_block_id": { + "hash": "51FF3B2D890CED166D5253B0982AEC4E8A2B58219D3F90162F562B6A36CB7B6E", + "parts": { + "hash": "682BB96896129320C025A416FEBBDFDB8E493FA6C743A6D31696CF7B6C70A175", + "total": 1 + } + }, + "last_commit_hash": "06D4D1ACE7E5418D42CB0FCC2D443DD1BC2C7D5DF89B2D65E710993A1BB27431", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:16.41039064Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "51FF3B2D890CED166D5253B0982AEC4E8A2B58219D3F90162F562B6A36CB7B6E", + "parts": { + "hash": "682BB96896129320C025A416FEBBDFDB8E493FA6C743A6D31696CF7B6C70A175", + "total": 1 + } + }, + "height": "79", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "y8tLgfGzDYTuloQ68u7YGyu7fFYx0wBz5CAYZWMiK4WH0eyVxhYnpl5HrrdvHzRpDBMTg2xdUIKEymPdPnxfCw==", + "timestamp": "2023-02-24T15:10:16.41039064Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "CCD624AE61388F88999E59604FE99F7A96F96D65807D7C0A5DB759FD6B84F4A8", + "parts": { + "hash": "A6B984E6CD72539FFF0D7B6D57D69AEF5642317F240E76EAC4FDE03889DAFEF3", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "81", + "last_block_id": { + "hash": "CCD624AE61388F88999E59604FE99F7A96F96D65807D7C0A5DB759FD6B84F4A8", + "parts": { + "hash": "A6B984E6CD72539FFF0D7B6D57D69AEF5642317F240E76EAC4FDE03889DAFEF3", + "total": 1 + } + }, + "last_commit_hash": "BCC5D3317EB9826607AF35F07309D7A950E4BD37A26C69AC3F2FBD44EE1DE9F0", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:16.934171765Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "CCD624AE61388F88999E59604FE99F7A96F96D65807D7C0A5DB759FD6B84F4A8", + "parts": { + "hash": "A6B984E6CD72539FFF0D7B6D57D69AEF5642317F240E76EAC4FDE03889DAFEF3", + "total": 1 + } + }, + "height": "80", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "qv24320MnUQkAQEheODsNB/u+DBGt7ll5NdR3O9s7DxYWfzJcdMhDVdV9/bQVe6S6NMT1vfMsDjHpbgyyT99DA==", + "timestamp": "2023-02-24T15:10:16.934171765Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4F1592A748C6C95FF62DEF707F5D588B1AF97674921627B94D7FDF169091CAEC", + "parts": { + "hash": "796B12053DB0FCBAA82C1651C907CAB015808348C5808E43B035910B715020BC", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "82", + "last_block_id": { + "hash": "4F1592A748C6C95FF62DEF707F5D588B1AF97674921627B94D7FDF169091CAEC", + "parts": { + "hash": "796B12053DB0FCBAA82C1651C907CAB015808348C5808E43B035910B715020BC", + "total": 1 + } + }, + "last_commit_hash": "67487102E76F42A5B89855D93C02A0EEF411052064E2651C69843C9FF116EC3B", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:17.452343627Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4F1592A748C6C95FF62DEF707F5D588B1AF97674921627B94D7FDF169091CAEC", + "parts": { + "hash": "796B12053DB0FCBAA82C1651C907CAB015808348C5808E43B035910B715020BC", + "total": 1 + } + }, + "height": "81", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "5R+BwF8CZOgZgKAL/Pymf9VkMvwMapveRyNnfYouZhbGM4C43Jg+ZoSnWsKHsBXqIqe7mF1EVi2HMjzj4st0Cg==", + "timestamp": "2023-02-24T15:10:17.452343627Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "45679F83A14AD70BD7B2FA534D1664D7CF5F2DBA485C25373C5A3FBAA6E5BEF5", + "parts": { + "hash": "0A1DAD862F1625291E4AB57E9F88AED895F845753DD81A76DFB68E2C076B0A9F", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "83", + "last_block_id": { + "hash": "45679F83A14AD70BD7B2FA534D1664D7CF5F2DBA485C25373C5A3FBAA6E5BEF5", + "parts": { + "hash": "0A1DAD862F1625291E4AB57E9F88AED895F845753DD81A76DFB68E2C076B0A9F", + "total": 1 + } + }, + "last_commit_hash": "C3DCF91D33BDD4298BB39C8856499C5EF9A3E42840B599551A14712EB1E8789B", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:17.971214064Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "45679F83A14AD70BD7B2FA534D1664D7CF5F2DBA485C25373C5A3FBAA6E5BEF5", + "parts": { + "hash": "0A1DAD862F1625291E4AB57E9F88AED895F845753DD81A76DFB68E2C076B0A9F", + "total": 1 + } + }, + "height": "82", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "fGH5IheksxE/g1fSCOSUV2t7qSgSc4uH31/svjwnu67ZG6GAVyggWM8PsXtRe71ZUeEEkA3PwYFqkKH6I6O6AQ==", + "timestamp": "2023-02-24T15:10:17.971214064Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "862D2E36683F40F85FFB10F55F98EBE837F2D4CF0954ED0C03898978E9C646BB", + "parts": { + "hash": "FDF5A292F49CE9633D99F2BAA242E071C05839C2FDDAF232611DED217879D6E3", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "84", + "last_block_id": { + "hash": "862D2E36683F40F85FFB10F55F98EBE837F2D4CF0954ED0C03898978E9C646BB", + "parts": { + "hash": "FDF5A292F49CE9633D99F2BAA242E071C05839C2FDDAF232611DED217879D6E3", + "total": 1 + } + }, + "last_commit_hash": "BE02FD4CF77E1CDEE61347A2588516FFE837020CC82F971E8A6F3F52325735AA", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:18.488097512Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "862D2E36683F40F85FFB10F55F98EBE837F2D4CF0954ED0C03898978E9C646BB", + "parts": { + "hash": "FDF5A292F49CE9633D99F2BAA242E071C05839C2FDDAF232611DED217879D6E3", + "total": 1 + } + }, + "height": "83", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "A4i59qhCZkUi9DB8iJNzGYmbJdkp/cWASwH5MnfCF1s7vFAHZTddRlhpP0oF6ZBVaI0j2lRaS2DhLBUSdPwnCg==", + "timestamp": "2023-02-24T15:10:18.488097512Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "83E0F87D192C136F93832C2138A00221C23B640E7A847E8FEBAC667C5F6B2A1C", + "parts": { + "hash": "1D6A4F646BD09FFA2B6123673BF638C080F1DB2F9D8DF16AAFB07FD32A156BF8", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "85", + "last_block_id": { + "hash": "83E0F87D192C136F93832C2138A00221C23B640E7A847E8FEBAC667C5F6B2A1C", + "parts": { + "hash": "1D6A4F646BD09FFA2B6123673BF638C080F1DB2F9D8DF16AAFB07FD32A156BF8", + "total": 1 + } + }, + "last_commit_hash": "8604E909D5D72E1B562A813C4C49505F13E14348A9BF6B502DB33944DAC0724A", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:19.006948118Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "83E0F87D192C136F93832C2138A00221C23B640E7A847E8FEBAC667C5F6B2A1C", + "parts": { + "hash": "1D6A4F646BD09FFA2B6123673BF638C080F1DB2F9D8DF16AAFB07FD32A156BF8", + "total": 1 + } + }, + "height": "84", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "oTTnjJBwXJBeWLp8fmn26dxU+tzNPD2fqCzd8geTWp+rjKCHWBNarNbjnsZhbI1KmLYnF33Kv2WuqNdcnVxqDw==", + "timestamp": "2023-02-24T15:10:19.006948118Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "CDD6EF160F00CD3A23564ADB3222412271B7ED8135EDB1FC6A1D8487A5168D9E", + "parts": { + "hash": "6F6E762C60A48B794C603F5AE6A923D2F4FA41E586D94B9A9FA9EA67BBB4F828", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "86", + "last_block_id": { + "hash": "CDD6EF160F00CD3A23564ADB3222412271B7ED8135EDB1FC6A1D8487A5168D9E", + "parts": { + "hash": "6F6E762C60A48B794C603F5AE6A923D2F4FA41E586D94B9A9FA9EA67BBB4F828", + "total": 1 + } + }, + "last_commit_hash": "3E6154E76D7B31E2CB70E4F632AD2839A661FC0670E56F2B7572AED5BD73CFD3", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:19.524829754Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "CDD6EF160F00CD3A23564ADB3222412271B7ED8135EDB1FC6A1D8487A5168D9E", + "parts": { + "hash": "6F6E762C60A48B794C603F5AE6A923D2F4FA41E586D94B9A9FA9EA67BBB4F828", + "total": 1 + } + }, + "height": "85", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "eD3xz+xNnT9YInvPLSxwzZ6QAcMm0uLcRHxF29pmiObD6E7E8lXxmxJlStXA9oyOl0KLsKRJuPxOGAMAQHDSCw==", + "timestamp": "2023-02-24T15:10:19.524829754Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "492DDC4ADF93C0AD9AE891B52EB83C23281C8B118F54B9CD6632DCF11667725D", + "parts": { + "hash": "95EEC124BBFE90931C80A870EC25EE39A5BBF00C97BABEEDA2AB4CA5EABC8560", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "87", + "last_block_id": { + "hash": "492DDC4ADF93C0AD9AE891B52EB83C23281C8B118F54B9CD6632DCF11667725D", + "parts": { + "hash": "95EEC124BBFE90931C80A870EC25EE39A5BBF00C97BABEEDA2AB4CA5EABC8560", + "total": 1 + } + }, + "last_commit_hash": "6951D8CD5B739A4059A6A004CCEF35F20DCE0E0BD246B1B52DD4B07033087284", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:20.042384566Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "492DDC4ADF93C0AD9AE891B52EB83C23281C8B118F54B9CD6632DCF11667725D", + "parts": { + "hash": "95EEC124BBFE90931C80A870EC25EE39A5BBF00C97BABEEDA2AB4CA5EABC8560", + "total": 1 + } + }, + "height": "86", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "PjqugrLNuSOyR6k4DOHMCNZ2yek7ex1oTWXpXZMeg+6dK0OAFyVSNX1jZJLxp5TpH3P6pjTfDe2iIbNAjWvCAA==", + "timestamp": "2023-02-24T15:10:20.042384566Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "5E17F7AB3D8F3F299812FFA3AC9C8F723242CD5B4AF1428F22008A6DE7B7A9F4", + "parts": { + "hash": "542B0E2E78CD2EDD9BE127ABA7FF702AC4769923842BF5AB02372F381FF4EA59", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "88", + "last_block_id": { + "hash": "5E17F7AB3D8F3F299812FFA3AC9C8F723242CD5B4AF1428F22008A6DE7B7A9F4", + "parts": { + "hash": "542B0E2E78CD2EDD9BE127ABA7FF702AC4769923842BF5AB02372F381FF4EA59", + "total": 1 + } + }, + "last_commit_hash": "EEF7D63B20F7D7D45B15CF247F74228EB016DDE6A9D020F6E61B1A06911C98D9", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:20.559940169Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "5E17F7AB3D8F3F299812FFA3AC9C8F723242CD5B4AF1428F22008A6DE7B7A9F4", + "parts": { + "hash": "542B0E2E78CD2EDD9BE127ABA7FF702AC4769923842BF5AB02372F381FF4EA59", + "total": 1 + } + }, + "height": "87", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "TpFxdfWpRSTADXLobRMb0DYHTFpd15Vv8nzoqXhdGzKSIv6MhtCF8TBeCnsJ49grSzsPH9EKrCflzu1ChsG/Bg==", + "timestamp": "2023-02-24T15:10:20.559940169Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "9CA4519BF6B7B6F8B444B9283CFF4882B025F29013308BF5BACF685A1BC31073", + "parts": { + "hash": "324A2C31DA12B8EA3F64215E7894650F2FE6A2609A6EC293050884B7C92CC9C3", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "89", + "last_block_id": { + "hash": "9CA4519BF6B7B6F8B444B9283CFF4882B025F29013308BF5BACF685A1BC31073", + "parts": { + "hash": "324A2C31DA12B8EA3F64215E7894650F2FE6A2609A6EC293050884B7C92CC9C3", + "total": 1 + } + }, + "last_commit_hash": "ADBC09F53226B878C36EC808FB053F6607B1580818941CF7B6D50AB7516C4561", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:21.076058301Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "9CA4519BF6B7B6F8B444B9283CFF4882B025F29013308BF5BACF685A1BC31073", + "parts": { + "hash": "324A2C31DA12B8EA3F64215E7894650F2FE6A2609A6EC293050884B7C92CC9C3", + "total": 1 + } + }, + "height": "88", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "jNsSA82uue8dr4A41135ZlvM5yKCI01/XlBw0/cHOZdD5UvI0tmmM8JaNFHep7D2W//XJ0bQul6CN9MV8wA5Ag==", + "timestamp": "2023-02-24T15:10:21.076058301Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "0CB7734218EDADD34ADE5592EA3A84588671F52F5EA8A170BFF8961544CD8F97", + "parts": { + "hash": "419294D85AC8E5EEBDF07DC3B74B96C349151CB6C7BFF82012388C3275855572", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "90", + "last_block_id": { + "hash": "0CB7734218EDADD34ADE5592EA3A84588671F52F5EA8A170BFF8961544CD8F97", + "parts": { + "hash": "419294D85AC8E5EEBDF07DC3B74B96C349151CB6C7BFF82012388C3275855572", + "total": 1 + } + }, + "last_commit_hash": "C69E392FF00BE1BB9137DFAD0E753FB3BF284A8C8773A823C1BCCA36E820FD54", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:21.592582419Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "0CB7734218EDADD34ADE5592EA3A84588671F52F5EA8A170BFF8961544CD8F97", + "parts": { + "hash": "419294D85AC8E5EEBDF07DC3B74B96C349151CB6C7BFF82012388C3275855572", + "total": 1 + } + }, + "height": "89", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "lKUG3bFeEfel61drclGjw3AXtfBEkJpK09c/dDsdcE6JPZ30xOAZ89lQbZHDprK4VasAmBGq+cG/sbRYDzToDg==", + "timestamp": "2023-02-24T15:10:21.592582419Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4C58CB754A6BDAE5885039C3C5F69B45312F2EE58F2A0037C2BF61361DA98601", + "parts": { + "hash": "0621B594D1CA6E09D6FE6902AAE060A8A6856489DD5CF130AC09F7510AAA9AC7", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "91", + "last_block_id": { + "hash": "4C58CB754A6BDAE5885039C3C5F69B45312F2EE58F2A0037C2BF61361DA98601", + "parts": { + "hash": "0621B594D1CA6E09D6FE6902AAE060A8A6856489DD5CF130AC09F7510AAA9AC7", + "total": 1 + } + }, + "last_commit_hash": "9DE1760CA6549A3659E0067DAC9ADEB7EBCCA08442A252A5CCADAA2214EFB612", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:22.108085559Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4C58CB754A6BDAE5885039C3C5F69B45312F2EE58F2A0037C2BF61361DA98601", + "parts": { + "hash": "0621B594D1CA6E09D6FE6902AAE060A8A6856489DD5CF130AC09F7510AAA9AC7", + "total": 1 + } + }, + "height": "90", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "B2JPXJZQf7vtp+og9kN4JNB802THzm8Eab8+eF2wI1ithaYVxkR/T1yVG0p/leH0vviPFuztjgyjtO2fakaNAw==", + "timestamp": "2023-02-24T15:10:22.108085559Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "60AA3E793D1DCA3B52752B1B2EFC76786729BB0205A9767BD315D0CC977EB0BD", + "parts": { + "hash": "5EEA3E2F658E696B24FF1E52CE4BC44FC4AE2B1B49E298E9D1E0CBD1134C9FCB", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "92", + "last_block_id": { + "hash": "60AA3E793D1DCA3B52752B1B2EFC76786729BB0205A9767BD315D0CC977EB0BD", + "parts": { + "hash": "5EEA3E2F658E696B24FF1E52CE4BC44FC4AE2B1B49E298E9D1E0CBD1134C9FCB", + "total": 1 + } + }, + "last_commit_hash": "004E153EB4178F225899750F55928E9A99F6BE935C3154BEFDB2C57ED410E117", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:22.627935121Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "60AA3E793D1DCA3B52752B1B2EFC76786729BB0205A9767BD315D0CC977EB0BD", + "parts": { + "hash": "5EEA3E2F658E696B24FF1E52CE4BC44FC4AE2B1B49E298E9D1E0CBD1134C9FCB", + "total": 1 + } + }, + "height": "91", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "8sR1nY5HI+MNc4UoiMg68z307YKjNaA9doU8LSCFoVlixKJ2MBJ4wZNK4GEMhlNPXV7ApPtLb18LR4j57TmrAg==", + "timestamp": "2023-02-24T15:10:22.627935121Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "EC6D4D7E18FA0A9146AA286EEC655867DFEFB2DA212A6773DE9E931B86FC4657", + "parts": { + "hash": "467542D1F4CE86B304782A8A69362E2D23187A6381EDDBA0AA95C2D11102A9FD", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "93", + "last_block_id": { + "hash": "EC6D4D7E18FA0A9146AA286EEC655867DFEFB2DA212A6773DE9E931B86FC4657", + "parts": { + "hash": "467542D1F4CE86B304782A8A69362E2D23187A6381EDDBA0AA95C2D11102A9FD", + "total": 1 + } + }, + "last_commit_hash": "F41FE46DA57C3433811E6F97F29AFF7122F094DF620F8610682ECA2703684AC1", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:23.147322944Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "EC6D4D7E18FA0A9146AA286EEC655867DFEFB2DA212A6773DE9E931B86FC4657", + "parts": { + "hash": "467542D1F4CE86B304782A8A69362E2D23187A6381EDDBA0AA95C2D11102A9FD", + "total": 1 + } + }, + "height": "92", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "donSKvwSA4bKEBoZACNz9C7FMA6XDU2J+wT9fzWIToi/Q35cweIUUnkDXtxC8wMHbESQNOXqqvLBVCftp+VBCA==", + "timestamp": "2023-02-24T15:10:23.147322944Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "365A77310094971325F336131FC6C707CD96912E1E7638FE54EF21B61E184DDF", + "parts": { + "hash": "806E84CA75FA5CCC0A1D4B11B219385FD7EDEF7BE75FC9635DC938A197D101B6", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "94", + "last_block_id": { + "hash": "365A77310094971325F336131FC6C707CD96912E1E7638FE54EF21B61E184DDF", + "parts": { + "hash": "806E84CA75FA5CCC0A1D4B11B219385FD7EDEF7BE75FC9635DC938A197D101B6", + "total": 1 + } + }, + "last_commit_hash": "8700C3DBD867E572FF65088CD5EBFD91AB9D2B2D818088CF034216DDE957A52E", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:23.664407624Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "365A77310094971325F336131FC6C707CD96912E1E7638FE54EF21B61E184DDF", + "parts": { + "hash": "806E84CA75FA5CCC0A1D4B11B219385FD7EDEF7BE75FC9635DC938A197D101B6", + "total": 1 + } + }, + "height": "93", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "349uZ2aFpkHCxvLE1+XUoK5MjN9EWJY5BN88mnTzYMeGoSyPTjdXArEZi+ahhHFzp9i95Xbz2+6UvOD4mz4uBg==", + "timestamp": "2023-02-24T15:10:23.664407624Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "4DE4E60D077F6F0CEAF71C7775A42C37592C8A26000714E766C64E12EB9B155F", + "parts": { + "hash": "9D04D896B0DB8C6C84800489B0BA03AB49F6F8DB7BAED2118D09B25676AA5358", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "95", + "last_block_id": { + "hash": "4DE4E60D077F6F0CEAF71C7775A42C37592C8A26000714E766C64E12EB9B155F", + "parts": { + "hash": "9D04D896B0DB8C6C84800489B0BA03AB49F6F8DB7BAED2118D09B25676AA5358", + "total": 1 + } + }, + "last_commit_hash": "3B7F666C62429CFE0B60367BBDC22E03DF2A5A9383F0BB9D6E907D18F14E6D7E", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:24.185861666Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "4DE4E60D077F6F0CEAF71C7775A42C37592C8A26000714E766C64E12EB9B155F", + "parts": { + "hash": "9D04D896B0DB8C6C84800489B0BA03AB49F6F8DB7BAED2118D09B25676AA5358", + "total": 1 + } + }, + "height": "94", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "xOdi2LNyWOiD+1ppcUTFW3Me4h2R8lOVgqM2Fr2j/3ujMihW3Sayr7ZLafKXgGvkLHIAOWBrJ18W3j6tjDkgBA==", + "timestamp": "2023-02-24T15:10:24.185861666Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "207601FFAC6D9C3B32B9361F4DC8E020A3F3D1FD771491B128103C2B6E652E79", + "parts": { + "hash": "E2C5A82E26ABC9F7A0966A82BA1E54EC03AA0D2A94FC7FFC532988B7EA4E600A", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "96", + "last_block_id": { + "hash": "207601FFAC6D9C3B32B9361F4DC8E020A3F3D1FD771491B128103C2B6E652E79", + "parts": { + "hash": "E2C5A82E26ABC9F7A0966A82BA1E54EC03AA0D2A94FC7FFC532988B7EA4E600A", + "total": 1 + } + }, + "last_commit_hash": "4651B25292ED60F01490E7274B8B7603906A937ABF630323E785F7F2DBD023AB", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:24.704428204Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "207601FFAC6D9C3B32B9361F4DC8E020A3F3D1FD771491B128103C2B6E652E79", + "parts": { + "hash": "E2C5A82E26ABC9F7A0966A82BA1E54EC03AA0D2A94FC7FFC532988B7EA4E600A", + "total": 1 + } + }, + "height": "95", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "3CXBmj7wA/d3o9TG4zm0U+eN4SbHeDqlKsI2FKIBmtZmB2xO+oJMNjn6sUnMVitkiS/92t9EisJB5od7fxirAA==", + "timestamp": "2023-02-24T15:10:24.704428204Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "7D824E6F79144AA944AAA0496AA259E29724759880CF0F3F2B4E10381CE3BC6B", + "parts": { + "hash": "068E0E25CC3CCA4DA820B43C28B9D061C784AF31F82CDECC986F407181C6E68C", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "97", + "last_block_id": { + "hash": "7D824E6F79144AA944AAA0496AA259E29724759880CF0F3F2B4E10381CE3BC6B", + "parts": { + "hash": "068E0E25CC3CCA4DA820B43C28B9D061C784AF31F82CDECC986F407181C6E68C", + "total": 1 + } + }, + "last_commit_hash": "99E0A3EE0594B1869745146C0BAC12AB0ACC0D3983BBC14AF26AA50D9A55477D", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:25.221701277Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "7D824E6F79144AA944AAA0496AA259E29724759880CF0F3F2B4E10381CE3BC6B", + "parts": { + "hash": "068E0E25CC3CCA4DA820B43C28B9D061C784AF31F82CDECC986F407181C6E68C", + "total": 1 + } + }, + "height": "96", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "zQ40QR95nPnWstq5uqmr8l56sM0x5m0a0vr7U2Pg1eU0zsoX/kofZO1/jMWD8nWyiGZm6C0NxpMO4RZWIHoADg==", + "timestamp": "2023-02-24T15:10:25.221701277Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "8BF089E09C461AD27EA7D9C4AEB993B2E13B31F5A90552B83951E88B9E7D6487", + "parts": { + "hash": "E5A14CFB467046DF5C9482491E2F15751C15735755723BB2178CC81FFCF8E98B", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "98", + "last_block_id": { + "hash": "8BF089E09C461AD27EA7D9C4AEB993B2E13B31F5A90552B83951E88B9E7D6487", + "parts": { + "hash": "E5A14CFB467046DF5C9482491E2F15751C15735755723BB2178CC81FFCF8E98B", + "total": 1 + } + }, + "last_commit_hash": "6C9BFDBE036356873F5852813F2ECD3427CD6BA55B58A3814128FE5971AA4FCE", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:25.737308548Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "8BF089E09C461AD27EA7D9C4AEB993B2E13B31F5A90552B83951E88B9E7D6487", + "parts": { + "hash": "E5A14CFB467046DF5C9482491E2F15751C15735755723BB2178CC81FFCF8E98B", + "total": 1 + } + }, + "height": "97", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "0UKiZ7J+zV5THP2IeB/v9XrH836d4pknGL5YSVhjuqbPu0KW9ZjwlS0v01GvQiQHbOsKntN1nd56hulOnKDuBA==", + "timestamp": "2023-02-24T15:10:25.737308548Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "D7415E09EAEBF2CD3C25970AD3199E365A50A719E218731D4F06ADF692DE0213", + "parts": { + "hash": "BF56F8DD97827A06D2AE619EFFDC531640E2BC3089C4A8D360906D1F812B6AC0", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "99", + "last_block_id": { + "hash": "D7415E09EAEBF2CD3C25970AD3199E365A50A719E218731D4F06ADF692DE0213", + "parts": { + "hash": "BF56F8DD97827A06D2AE619EFFDC531640E2BC3089C4A8D360906D1F812B6AC0", + "total": 1 + } + }, + "last_commit_hash": "8D3CF0BEFF5410E2654380A60F004B2FF5B1C5B1B4266D7ED05DE51B801AC0F2", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:26.252637052Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "D7415E09EAEBF2CD3C25970AD3199E365A50A719E218731D4F06ADF692DE0213", + "parts": { + "hash": "BF56F8DD97827A06D2AE619EFFDC531640E2BC3089C4A8D360906D1F812B6AC0", + "total": 1 + } + }, + "height": "98", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "VcZ0iMNa7ZVgnBzrDc66Fh3Rxp0Fj135Etl1MZIOx4rJ2v74K3uxFUEH7QFNldyaApYb7zxkOVCgnR8fECoiBA==", + "timestamp": "2023-02-24T15:10:26.252637052Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "566AE1C48174C2664ADB0514D8968FF13C993D1E7898638D52F1BDAC21295D05", + "parts": { + "hash": "91D28FBA1F49C71618A36342E59AC9DE427587E9F2CC13459D2D68D21BEBFE4B", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "100", + "last_block_id": { + "hash": "566AE1C48174C2664ADB0514D8968FF13C993D1E7898638D52F1BDAC21295D05", + "parts": { + "hash": "91D28FBA1F49C71618A36342E59AC9DE427587E9F2CC13459D2D68D21BEBFE4B", + "total": 1 + } + }, + "last_commit_hash": "E2842496547C1069C2ECDD16B3DD2B33E03023FFBB2257198FFF360FDD908CE2", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:26.772972231Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "566AE1C48174C2664ADB0514D8968FF13C993D1E7898638D52F1BDAC21295D05", + "parts": { + "hash": "91D28FBA1F49C71618A36342E59AC9DE427587E9F2CC13459D2D68D21BEBFE4B", + "total": 1 + } + }, + "height": "99", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "lN78RMeHD7JpYEmQ++1N2vXM44mqDbMoqoHZRPnNAzTyeafiRp7XvBzbY9TOnzd92tNhU6pw6HXrbEJWL66+BA==", + "timestamp": "2023-02-24T15:10:26.772972231Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "5032349B18DF6761088F415B0946CCF113B59E05638CA1E18DA11CAB02CBD71F", + "parts": { + "hash": "8A72621074DCF3ADDD2BB520601D7D1070A970894E4FC77B52E971CB453B5F55", + "total": 1 + } + } + }, + { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "101", + "last_block_id": { + "hash": "5032349B18DF6761088F415B0946CCF113B59E05638CA1E18DA11CAB02CBD71F", + "parts": { + "hash": "8A72621074DCF3ADDD2BB520601D7D1070A970894E4FC77B52E971CB453B5F55", + "total": 1 + } + }, + "last_commit_hash": "900B690F191D6EB0B29280084A5FC8A30B4778C6DF8A857EE02AA2D05E72C196", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:10:27.290383356Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "5032349B18DF6761088F415B0946CCF113B59E05638CA1E18DA11CAB02CBD71F", + "parts": { + "hash": "8A72621074DCF3ADDD2BB520601D7D1070A970894E4FC77B52E971CB453B5F55", + "total": 1 + } + }, + "height": "100", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "oKrR1shXwkeD2j6uW1HMSQPjekjKGtnvwtojLoAzPQ+pqeC3d1/F9MR5Vf6Vzy59fk6J+DZja9Wg7kJscsg4CQ==", + "timestamp": "2023-02-24T15:10:27.290383356Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "block_id": { + "hash": "78587FB12AAF743AC278DB6E4E551AF7842BC509B40436115C195AE641E6CB06", + "parts": { + "hash": "872B22B5E0DB935A2A309320B13D73D14B8DB351AB823BA0E215AD141F1E02DB", + "total": 1 + } + } + } + ], + "total_count": "213" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json new file mode 100644 index 000000000..aca48bc37 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json @@ -0,0 +1,369 @@ +{ + "id": "8b6f991a-4a2c-4dcf-9411-5c706f413235", + "jsonrpc": "2.0", + "result": { + "block_metas": [ + { + "block_id": { + "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "parts": { + "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "total": 1 + } + }, + "block_size": "569", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "10", + "last_block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + }, + "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:40.123954449Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + }, + "block_size": "571", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "9", + "last_block_id": { + "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "parts": { + "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "total": 1 + } + }, + "last_commit_hash": "22FC31E6CCA7D5C580B14FC94E506524041B2064C9DB27D54A5AC3254950CBA9", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:39.606408964Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "parts": { + "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "total": 1 + } + }, + "block_size": "569", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "8", + "last_block_id": { + "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "parts": { + "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "total": 1 + } + }, + "last_commit_hash": "D12B708778B847858029349205FD4BE0F8B22A8DE61943D5C2D4B49396767775", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:39.090086292Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "parts": { + "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "total": 1 + } + }, + "block_size": "571", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "7", + "last_block_id": { + "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "parts": { + "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "total": 1 + } + }, + "last_commit_hash": "266129248C2C0D2684F1D1BE8E5A119742520BAA03F740BE5C612E8CFB245DB7", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:38.570297947Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "parts": { + "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "total": 1 + } + }, + "block_size": "569", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "6", + "last_block_id": { + "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "parts": { + "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "total": 1 + } + }, + "last_commit_hash": "769E5D10F6B90219BB10D7DA6600728E02A760476A3F0216914B4E3D758E0ED6", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:38.051624453Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "parts": { + "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "total": 1 + } + }, + "block_size": "571", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "5", + "last_block_id": { + "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "parts": { + "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "total": 1 + } + }, + "last_commit_hash": "EDC03890397D8183CD0FE0A25A729BFC5192851DC8ADA3642B7D23E0B7B51A21", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:37.533687433Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "parts": { + "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "total": 1 + } + }, + "block_size": "569", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "4", + "last_block_id": { + "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "parts": { + "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "total": 1 + } + }, + "last_commit_hash": "6DDE3F5FEB4E7E88FCF3A9B8E5A9B178B525E68817C1EC05E2DE9E03AB164D96", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:37.018159177Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "parts": { + "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "total": 1 + } + }, + "block_size": "571", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "3", + "last_block_id": { + "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "parts": { + "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "total": 1 + } + }, + "last_commit_hash": "6237CD7F07174FB28966A889F6A9B4D26DC6D7F104D0B4333007E6C2AB7D61C1", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:36.499560496Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "parts": { + "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "total": 1 + } + }, + "block_size": "571", + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "2", + "last_block_id": { + "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "parts": { + "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "total": 1 + } + }, + "last_commit_hash": "227D78AC78B219692FC3EE18BCE5FD46E86F382979628FB6BE01DDF4C9E66750", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:35.982946125Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + }, + { + "block_id": { + "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "parts": { + "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "total": 1 + } + }, + "block_size": "312", + "header": { + "app_hash": "", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "1", + "last_block_id": { + "hash": "", + "parts": { + "hash": "", + "total": 0 + } + }, + "last_commit_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:35.386925428Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "num_txs": "0" + } + ], + "last_height": "216" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json new file mode 100644 index 000000000..26a9b2234 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json @@ -0,0 +1,11 @@ +{ + "id": "37104243-1a80-4b5f-a917-cf38c863171f", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "9F28904F9C0F3AB74A81CBA48E39124DA1C680B47FBFCBA0126870DB722BCC30", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json new file mode 100644 index 000000000..ed5e29119 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json @@ -0,0 +1,82 @@ +{ + "id": "be2a11c5-e6b3-4803-9f0e-140330c65f43", + "jsonrpc": "2.0", + "result": { + "check_tx": { + "code": 0, + "codespace": "", + "data": null, + "events": [], + "gas_used": "0", + "gas_wanted": "1", + "info": "", + "log": "", + "mempoolError": "", + "priority": "0", + "sender": "" + }, + "deliver_tx": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "commit-key" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + }, + "hash": "D63F9C23791E610410B576D8C27BB5AEAC93CC1A58522428A7B32A1276085860", + "height": "229" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json new file mode 100644 index 000000000..544560af0 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json @@ -0,0 +1,11 @@ +{ + "id": "c0bbfd1a-6b75-421e-ba3f-07dec9c1ba98", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "57018296EE0919C9D351F2FFEA82A8D28DE223724D79965FC8D00A7477ED48BC", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json new file mode 100644 index 000000000..b68008365 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json @@ -0,0 +1,53 @@ +{ + "id": "435978e8-89ed-4128-a94e-1f25dcd46c28", + "jsonrpc": "2.0", + "result": { + "canonical": true, + "signed_header": { + "commit": { + "block_id": { + "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "parts": { + "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "total": 1 + } + }, + "height": "10", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "gozurqzPCl9et0LQgKksMg60fdU1cPOoDfIEUwMCWMZt8/5cRYiUbr7+kJj9AHF2/C1w3Abs8a+QxtVJPnWlBw==", + "timestamp": "2023-02-24T15:09:40.640670992Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + }, + "header": { + "app_hash": "0000000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "10", + "last_block_id": { + "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "parts": { + "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "total": 1 + } + }, + "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:09:40.123954449Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + } + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json new file mode 100644 index 000000000..78a1ec028 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json @@ -0,0 +1,26 @@ +{ + "id": "abbcacd1-ff31-4725-b5ff-c46e21c02736", + "jsonrpc": "2.0", + "result": { + "block_height": "10", + "consensus_params": { + "block": { + "max_bytes": "22020096", + "max_gas": "-1" + }, + "evidence": { + "max_age_duration": "172800000000000", + "max_age_num_blocks": "100000", + "max_bytes": "1048576" + }, + "validator": { + "pub_key_types": [ + "ed25519" + ] + }, + "version": { + "app": "0" + } + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json new file mode 100644 index 000000000..06507d396 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json @@ -0,0 +1,30 @@ +{ + "id": "6954460c-8b30-41e9-9752-261e063dda0c", + "jsonrpc": "2.0", + "result": { + "round_state": { + "height/round/step": "223/0/1", + "height_vote_set": [ + { + "precommits": [ + "nil-Vote" + ], + "precommits_bit_array": "BA{1:_} 0/10 = 0.00", + "prevotes": [ + "nil-Vote" + ], + "prevotes_bit_array": "BA{1:_} 0/10 = 0.00", + "round": 0 + } + ], + "locked_block_hash": "", + "proposal_block_hash": "", + "proposer": { + "address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "index": 0 + }, + "start_time": "2023-02-24T15:11:31.310596522Z", + "valid_block_hash": "" + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json new file mode 100644 index 000000000..5e15d5a4d --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json @@ -0,0 +1,42 @@ +{ + "id": "30777544-c3da-4444-bef1-6035ece3b1c0", + "jsonrpc": "2.0", + "result": { + "genesis": { + "app_hash": "", + "chain_id": "dockerchain", + "consensus_params": { + "block": { + "max_bytes": "22020096", + "max_gas": "-1" + }, + "evidence": { + "max_age_duration": "172800000000000", + "max_age_num_blocks": "100000", + "max_bytes": "1048576" + }, + "validator": { + "pub_key_types": [ + "ed25519" + ] + }, + "version": { + "app": "0" + } + }, + "genesis_time": "2023-02-24T15:09:35.386925428Z", + "initial_height": "1", + "validators": [ + { + "address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "name": "", + "power": "10", + "pub_key": { + "type": "tendermint/PubKeyEd25519", + "value": "z/0hzsnbHD6bSLl+2Nmmg0C8vLMo0ZkUHnNCUaXBAgQ=" + } + } + ] + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json new file mode 100644 index 000000000..3f0397f86 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json @@ -0,0 +1,12 @@ +{ + "id": "e6cd2152-119e-4349-bf6d-ec8b1e5e077f", + "jsonrpc": "2.0", + "result": { + "listeners": [ + "Listener(@)" + ], + "listening": true, + "n_peers": "0", + "peers": [] + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/status.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/status.json new file mode 100644 index 000000000..6ad4bfa43 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/status.json @@ -0,0 +1,42 @@ +{ + "id": "cd2af599-b99a-4fdb-a7ed-ee2734e77ebb", + "jsonrpc": "2.0", + "result": { + "node_info": { + "channels": "40202122233038606100", + "id": "56b7224d0a726d7ebeace322ac98c3654673dd4d", + "listen_addr": "tcp://0.0.0.0:26656", + "moniker": "dockernode", + "network": "dockerchain", + "other": { + "rpc_address": "tcp://0.0.0.0:26657", + "tx_index": "on" + }, + "protocol_version": { + "app": "1", + "block": "11", + "p2p": "8" + }, + "version": "0.37.0-alpha.3" + }, + "sync_info": { + "catching_up": false, + "earliest_app_hash": "", + "earliest_block_hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "earliest_block_height": "1", + "earliest_block_time": "2023-02-24T15:09:35.386925428Z", + "latest_app_hash": "0600000000000000", + "latest_block_hash": "8C6B41DE8CF6A72E435413EDB1FA1AC270B61F75297CEEE4938378E109AD0560", + "latest_block_height": "234", + "latest_block_time": "2023-02-24T15:11:36.508177149Z" + }, + "validator_info": { + "address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "pub_key": { + "type": "tendermint/PubKeyEd25519", + "value": "z/0hzsnbHD6bSLl+2Nmmg0C8vLMo0ZkUHnNCUaXBAgQ=" + }, + "voting_power": "10" + } + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json new file mode 100644 index 000000000..1093a9a03 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json @@ -0,0 +1,9 @@ +{ + "error": { + "code": -32603, + "data": "failed to parse query: \nparse error near PegText (line 1 symbol 2 - line 1 symbol 11):\n\"malformed\"\n", + "message": "Internal error" + }, + "id": "8c013455-ab08-4b8a-a08f-deb884644319", + "jsonrpc": "2.0" +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock.json new file mode 100644 index 000000000..9e26dfeeb --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock.json @@ -0,0 +1 @@ +{} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json new file mode 100644 index 000000000..3449a4cfa --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json @@ -0,0 +1,73 @@ +{ + "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/NewBlock", + "value": { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0600000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "237", + "last_block_id": { + "hash": "1593E40FB45914C56AB57388EC8F687536D815411F574186A5C1178FC65AEE30", + "parts": { + "hash": "450C775C1FC4E37B747F45EB9DC99593E4D3A8CB831786ED1A9D80EBE3AF17F1", + "total": 1 + } + }, + "last_commit_hash": "DF9784413CE9D2D548728192DF9973B7A29ABC8DCB48D6DFB6AEBC519CC8D7DB", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:11:38.062402874Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "1593E40FB45914C56AB57388EC8F687536D815411F574186A5C1178FC65AEE30", + "parts": { + "hash": "450C775C1FC4E37B747F45EB9DC99593E4D3A8CB831786ED1A9D80EBE3AF17F1", + "total": 1 + } + }, + "height": "236", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "7RvLshAh+YLLWVqFtdDP6eQgMdfaE5YyX1uFj/vk30WWjWxa6ChIWtZVlMz4yjIQ7TwFAVua1gKZdcIYI6zcBw==", + "timestamp": "2023-02-24T15:11:38.062402874Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "result_begin_block": {}, + "result_end_block": { + "validator_updates": null + } + } + }, + "events": { + "tm.event": [ + "NewBlock" + ] + }, + "query": "tm.event = 'NewBlock'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json new file mode 100644 index 000000000..ac271f661 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json @@ -0,0 +1,73 @@ +{ + "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/NewBlock", + "value": { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0600000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "238", + "last_block_id": { + "hash": "CE67E8FAECB5CCBC0ED9CBC33FA4C62E4714F05C115A6FEDBBA7BCA003E0E299", + "parts": { + "hash": "6BF6AC83B283D927A9C75349350D1F2705D3F8A19F056ECB1E872B6CD178654A", + "total": 1 + } + }, + "last_commit_hash": "839ECB7DA2A777EAA2FC082E77797F839638227976FF58A683A189EA83737B27", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:11:38.579201448Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "CE67E8FAECB5CCBC0ED9CBC33FA4C62E4714F05C115A6FEDBBA7BCA003E0E299", + "parts": { + "hash": "6BF6AC83B283D927A9C75349350D1F2705D3F8A19F056ECB1E872B6CD178654A", + "total": 1 + } + }, + "height": "237", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "Dn0TS9EVlDC49tUyTvaQSqassCWYWOdqOQ1srEpzT2fdNTM4ovzXCeXsQgIdyGKxi+1GJge90ljVOOPc/lo3Ag==", + "timestamp": "2023-02-24T15:11:38.579201448Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "result_begin_block": {}, + "result_end_block": { + "validator_updates": null + } + } + }, + "events": { + "tm.event": [ + "NewBlock" + ] + }, + "query": "tm.event = 'NewBlock'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json new file mode 100644 index 000000000..191af4c0f --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json @@ -0,0 +1,73 @@ +{ + "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/NewBlock", + "value": { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0600000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "239", + "last_block_id": { + "hash": "562CC9E027599E2E6EF5DBC0F4BFEAE3B0CA2EE419E9181C4F000F4C6937E970", + "parts": { + "hash": "F3434293749106B5861D97EB8C617EAFE66F3A7705CCB53C818ACEDF089FB9B8", + "total": 1 + } + }, + "last_commit_hash": "61B0F7374BA2D42A637B22ADB13AC6877AB3D0F7FADDFF1DBCAF50C3B03A4ECE", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:11:39.096768039Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "562CC9E027599E2E6EF5DBC0F4BFEAE3B0CA2EE419E9181C4F000F4C6937E970", + "parts": { + "hash": "F3434293749106B5861D97EB8C617EAFE66F3A7705CCB53C818ACEDF089FB9B8", + "total": 1 + } + }, + "height": "238", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "V+17mMoSu+9HLPJ4joKXpd+SflRc0AQXI3kiMXz+zeVGWNLdRrfjWVoMOm9JkvI7Llm4eLzNsOkoUk0OhEAEBA==", + "timestamp": "2023-02-24T15:11:39.096768039Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "result_begin_block": {}, + "result_end_block": { + "validator_updates": null + } + } + }, + "events": { + "tm.event": [ + "NewBlock" + ] + }, + "query": "tm.event = 'NewBlock'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json new file mode 100644 index 000000000..cf4668893 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json @@ -0,0 +1,73 @@ +{ + "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/NewBlock", + "value": { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0600000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "240", + "last_block_id": { + "hash": "CD762D6BE3E309711B614B34EB07B9DA517612376051B7ECFC908B7ADC473304", + "parts": { + "hash": "A1B8CD48BE42269C0858715B757CE75BCD05BA8C86752820D78A386EF8391B92", + "total": 1 + } + }, + "last_commit_hash": "05CAC30F4EE7378FF3EB02C41DD735CAC0AA2D71CBCA6E07FB5E05355190BD16", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:11:39.615658185Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "CD762D6BE3E309711B614B34EB07B9DA517612376051B7ECFC908B7ADC473304", + "parts": { + "hash": "A1B8CD48BE42269C0858715B757CE75BCD05BA8C86752820D78A386EF8391B92", + "total": 1 + } + }, + "height": "239", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "8yW43rI/8kR60jaeb9ccWd32QG5HNGzh5zBtnRuAIZKJfCrezLYqegGHmNE0ufSS3IiiM3Pq2oExbnh2HrbGCA==", + "timestamp": "2023-02-24T15:11:39.615658185Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "result_begin_block": {}, + "result_end_block": { + "validator_updates": null + } + } + }, + "events": { + "tm.event": [ + "NewBlock" + ] + }, + "query": "tm.event = 'NewBlock'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json new file mode 100644 index 000000000..a7ac2ed39 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json @@ -0,0 +1,73 @@ +{ + "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/NewBlock", + "value": { + "block": { + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "header": { + "app_hash": "0600000000000000", + "chain_id": "dockerchain", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "height": "241", + "last_block_id": { + "hash": "F60AD9534BDE152760F3F5EE3BAD0063B0D5D50C88E4EF47A6ED724C5B7CDF4A", + "parts": { + "hash": "C4BB7FC8E4B586A1C72137B422E577C19871F750A1C5DF0ABD30374F95EA1550", + "total": 1 + } + }, + "last_commit_hash": "92FA36538F6EBD2586A541B9E27D86AE3412FFEC74827059AFB87E5CABEC9972", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "time": "2023-02-24T15:11:40.133649473Z", + "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "version": { + "app": "1", + "block": "11" + } + }, + "last_commit": { + "block_id": { + "hash": "F60AD9534BDE152760F3F5EE3BAD0063B0D5D50C88E4EF47A6ED724C5B7CDF4A", + "parts": { + "hash": "C4BB7FC8E4B586A1C72137B422E577C19871F750A1C5DF0ABD30374F95EA1550", + "total": 1 + } + }, + "height": "240", + "round": 0, + "signatures": [ + { + "block_id_flag": 2, + "signature": "5eC+jWB2KaTJ7JwR9Ntbf2eJBYfpgfH2Gqq8ehQB9ORoE1SYlU/TmrcMahQnWViaZUm/7bCGtjn7QVJouqS8CQ==", + "timestamp": "2023-02-24T15:11:40.133649473Z", + "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + } + ] + } + }, + "result_begin_block": {}, + "result_end_block": { + "validator_updates": null + } + } + }, + "events": { + "tm.event": [ + "NewBlock" + ] + }, + "query": "tm.event = 'NewBlock'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json new file mode 100644 index 000000000..9b271a28b --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json @@ -0,0 +1,5 @@ +{ + "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "jsonrpc": "2.0", + "result": {} +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json new file mode 100644 index 000000000..ce120c42f --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json @@ -0,0 +1,97 @@ +{ + "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/Tx", + "value": { + "TxResult": { + "height": "245", + "result": { + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx0" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ] + }, + "tx": "dHgwPXZhbHVl" + } + } + }, + "events": { + "app.creator": [ + "Cosmoshi Netowoko", + "Cosmoshi" + ], + "app.index_key": [ + "index is working", + "index is working" + ], + "app.key": [ + "tx0", + "value" + ], + "app.noindex_key": [ + "index is working", + "index is working" + ], + "tm.event": [ + "Tx" + ], + "tx.hash": [ + "FCB86F71C4EFF43E13C51FA12791F6DD1DDB8600A51131BE2289614D6882F6BE" + ], + "tx.height": [ + "245" + ] + }, + "query": "tm.event = 'Tx'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json new file mode 100644 index 000000000..ac29a6ba5 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json @@ -0,0 +1,97 @@ +{ + "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/Tx", + "value": { + "TxResult": { + "height": "247", + "result": { + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx1" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ] + }, + "tx": "dHgxPXZhbHVl" + } + } + }, + "events": { + "app.creator": [ + "Cosmoshi Netowoko", + "Cosmoshi" + ], + "app.index_key": [ + "index is working", + "index is working" + ], + "app.key": [ + "tx1", + "value" + ], + "app.noindex_key": [ + "index is working", + "index is working" + ], + "tm.event": [ + "Tx" + ], + "tx.hash": [ + "9F424A8E634AAF63CFA61151A306AA788C9CC792F16B370F7867ED0BD972476C" + ], + "tx.height": [ + "247" + ] + }, + "query": "tm.event = 'Tx'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json new file mode 100644 index 000000000..b475e8ce3 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json @@ -0,0 +1,97 @@ +{ + "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/Tx", + "value": { + "TxResult": { + "height": "249", + "result": { + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx2" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ] + }, + "tx": "dHgyPXZhbHVl" + } + } + }, + "events": { + "app.creator": [ + "Cosmoshi Netowoko", + "Cosmoshi" + ], + "app.index_key": [ + "index is working", + "index is working" + ], + "app.key": [ + "tx2", + "value" + ], + "app.noindex_key": [ + "index is working", + "index is working" + ], + "tm.event": [ + "Tx" + ], + "tx.hash": [ + "C9D123E2CF19B9F0EC3CA1F64CD3BF0735397C84778B40B3EB5C49A752D53BF4" + ], + "tx.height": [ + "249" + ] + }, + "query": "tm.event = 'Tx'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json new file mode 100644 index 000000000..9f4f0b861 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json @@ -0,0 +1,97 @@ +{ + "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/Tx", + "value": { + "TxResult": { + "height": "251", + "result": { + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx3" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ] + }, + "tx": "dHgzPXZhbHVl" + } + } + }, + "events": { + "app.creator": [ + "Cosmoshi Netowoko", + "Cosmoshi" + ], + "app.index_key": [ + "index is working", + "index is working" + ], + "app.key": [ + "tx3", + "value" + ], + "app.noindex_key": [ + "index is working", + "index is working" + ], + "tm.event": [ + "Tx" + ], + "tx.hash": [ + "73117D6A783E4A37C1D9AD48744AD9FCC0D094C48AB8322FA11CD901C5174CFD" + ], + "tx.height": [ + "251" + ] + }, + "query": "tm.event = 'Tx'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json new file mode 100644 index 000000000..2bbdbc7e4 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json @@ -0,0 +1,97 @@ +{ + "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "jsonrpc": "2.0", + "result": { + "data": { + "type": "tendermint/event/Tx", + "value": { + "TxResult": { + "height": "253", + "result": { + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx4" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ] + }, + "tx": "dHg0PXZhbHVl" + } + } + }, + "events": { + "app.creator": [ + "Cosmoshi Netowoko", + "Cosmoshi" + ], + "app.index_key": [ + "index is working", + "index is working" + ], + "app.key": [ + "tx4", + "value" + ], + "app.noindex_key": [ + "index is working", + "index is working" + ], + "tm.event": [ + "Tx" + ], + "tx.hash": [ + "C349F213F04B4E8E749C6656E4C299E3BF22F4FAF141291A5C083336AD1A413B" + ], + "tx.height": [ + "253" + ] + }, + "query": "tm.event = 'Tx'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json new file mode 100644 index 000000000..fddaeb395 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json @@ -0,0 +1,11 @@ +{ + "id": "7ad4d2b9-0d9b-4ee4-be3f-f602ecf8f5b1", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "FCB86F71C4EFF43E13C51FA12791F6DD1DDB8600A51131BE2289614D6882F6BE", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json new file mode 100644 index 000000000..a1e912b86 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json @@ -0,0 +1,11 @@ +{ + "id": "83abc9bc-379d-4a3d-93cd-973393006161", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "9F424A8E634AAF63CFA61151A306AA788C9CC792F16B370F7867ED0BD972476C", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json new file mode 100644 index 000000000..dd0bf32e3 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json @@ -0,0 +1,11 @@ +{ + "id": "5a5bbc9c-4b06-4d61-9efc-076d8863aae3", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "C9D123E2CF19B9F0EC3CA1F64CD3BF0735397C84778B40B3EB5C49A752D53BF4", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json new file mode 100644 index 000000000..8ed5577bb --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json @@ -0,0 +1,11 @@ +{ + "id": "07cd909f-796e-448f-a16f-3c120c0d1b5a", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "73117D6A783E4A37C1D9AD48744AD9FCC0D094C48AB8322FA11CD901C5174CFD", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json new file mode 100644 index 000000000..283935cb6 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json @@ -0,0 +1,11 @@ +{ + "id": "0fcbb94c-853b-43fd-bf56-aea2b0156fab", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "C349F213F04B4E8E749C6656E4C299E3BF22F4FAF141291A5C083336AD1A413B", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json new file mode 100644 index 000000000..05e02d37b --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json @@ -0,0 +1,11 @@ +{ + "id": "cb7ccde0-6d42-47c3-a772-6355f8c7befa", + "jsonrpc": "2.0", + "result": { + "code": 0, + "codespace": "", + "data": "", + "hash": "CC4AC5C231481DD2ED2EA15789483B94565BF41612B6FEDE5BE7694F882CC202", + "log": "" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json new file mode 100644 index 000000000..79f8ef376 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json @@ -0,0 +1,612 @@ +{ + "id": "7167bf23-1869-4578-8d37-d6f6387d70a7", + "jsonrpc": "2.0", + "result": { + "total_count": "9", + "txs": [ + { + "hash": "9F28904F9C0F3AB74A81CBA48E39124DA1C680B47FBFCBA0126870DB722BCC30", + "height": "225", + "index": 0, + "tx": "YXN5bmMta2V5PXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "async-key" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "57018296EE0919C9D351F2FFEA82A8D28DE223724D79965FC8D00A7477ED48BC", + "height": "227", + "index": 0, + "tx": "c3luYy1rZXk9dmFsdWU=", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "sync-key" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "D63F9C23791E610410B576D8C27BB5AEAC93CC1A58522428A7B32A1276085860", + "height": "229", + "index": 0, + "tx": "Y29tbWl0LWtleT12YWx1ZQ==", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "commit-key" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "FCB86F71C4EFF43E13C51FA12791F6DD1DDB8600A51131BE2289614D6882F6BE", + "height": "245", + "index": 0, + "tx": "dHgwPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx0" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "9F424A8E634AAF63CFA61151A306AA788C9CC792F16B370F7867ED0BD972476C", + "height": "247", + "index": 0, + "tx": "dHgxPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx1" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "C9D123E2CF19B9F0EC3CA1F64CD3BF0735397C84778B40B3EB5C49A752D53BF4", + "height": "249", + "index": 0, + "tx": "dHgyPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx2" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "73117D6A783E4A37C1D9AD48744AD9FCC0D094C48AB8322FA11CD901C5174CFD", + "height": "251", + "index": 0, + "tx": "dHgzPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx3" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "C349F213F04B4E8E749C6656E4C299E3BF22F4FAF141291A5C083336AD1A413B", + "height": "253", + "index": 0, + "tx": "dHg0PXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx4" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "CC4AC5C231481DD2ED2EA15789483B94565BF41612B6FEDE5BE7694F882CC202", + "height": "255", + "index": 0, + "tx": "dHg1PXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx5" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + } + ] + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json new file mode 100644 index 000000000..6c45b5623 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json @@ -0,0 +1,702 @@ +{ + "id": "d1b4904e-c0d4-4b37-b6ac-0730c7144e04", + "jsonrpc": "2.0", + "result": { + "total_count": "9", + "txs": [ + { + "hash": "9F28904F9C0F3AB74A81CBA48E39124DA1C680B47FBFCBA0126870DB722BCC30", + "height": "225", + "index": 0, + "proof": { + "data": "YXN5bmMta2V5PXZhbHVl", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "MIH5kVBA0TizrX+JVzLSdnwp6Ful2EOI0E4XpdgmK3o=", + "total": "1" + }, + "root_hash": "3081F9915040D138B3AD7F895732D2767C29E85BA5D84388D04E17A5D8262B7A" + }, + "tx": "YXN5bmMta2V5PXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "async-key" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "57018296EE0919C9D351F2FFEA82A8D28DE223724D79965FC8D00A7477ED48BC", + "height": "227", + "index": 0, + "proof": { + "data": "c3luYy1rZXk9dmFsdWU=", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "oL+OYRo6LtD+lKo0W5A2kcPlbt4Of3c/VN57Ag54iEk=", + "total": "1" + }, + "root_hash": "A0BF8E611A3A2ED0FE94AA345B903691C3E56EDE0E7F773F54DE7B020E788849" + }, + "tx": "c3luYy1rZXk9dmFsdWU=", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "sync-key" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "D63F9C23791E610410B576D8C27BB5AEAC93CC1A58522428A7B32A1276085860", + "height": "229", + "index": 0, + "proof": { + "data": "Y29tbWl0LWtleT12YWx1ZQ==", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "wq4Wy/oF+/0xsH+eJq1SqY2BgYS2FVXbLAXNcCLkB74=", + "total": "1" + }, + "root_hash": "C2AE16CBFA05FBFD31B07F9E26AD52A98D818184B61555DB2C05CD7022E407BE" + }, + "tx": "Y29tbWl0LWtleT12YWx1ZQ==", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "commit-key" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "FCB86F71C4EFF43E13C51FA12791F6DD1DDB8600A51131BE2289614D6882F6BE", + "height": "245", + "index": 0, + "proof": { + "data": "dHgwPXZhbHVl", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "3UnhxGnCw+sKtov5uD2YZbCP79vHFwLMc1ZPTaVocKQ=", + "total": "1" + }, + "root_hash": "DD49E1C469C2C3EB0AB68BF9B83D9865B08FEFDBC71702CC73564F4DA56870A4" + }, + "tx": "dHgwPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx0" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "9F424A8E634AAF63CFA61151A306AA788C9CC792F16B370F7867ED0BD972476C", + "height": "247", + "index": 0, + "proof": { + "data": "dHgxPXZhbHVl", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "QnwQk7ERU9NjeD1GlLa4H8lscIRFD3evj6SZulKp3T8=", + "total": "1" + }, + "root_hash": "427C1093B11153D363783D4694B6B81FC96C7084450F77AF8FA499BA52A9DD3F" + }, + "tx": "dHgxPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx1" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "C9D123E2CF19B9F0EC3CA1F64CD3BF0735397C84778B40B3EB5C49A752D53BF4", + "height": "249", + "index": 0, + "proof": { + "data": "dHgyPXZhbHVl", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "0eF/BEMF82Y/mIMIM0HX/isU2jI44Z2rAor5MA0PrKM=", + "total": "1" + }, + "root_hash": "D1E17F044305F3663F9883083341D7FE2B14DA3238E19DAB028AF9300D0FACA3" + }, + "tx": "dHgyPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx2" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "73117D6A783E4A37C1D9AD48744AD9FCC0D094C48AB8322FA11CD901C5174CFD", + "height": "251", + "index": 0, + "proof": { + "data": "dHgzPXZhbHVl", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "jt+3kmBnxAUZK7c0gytFbKegUaR38TB3aAlKsIZ0RNU=", + "total": "1" + }, + "root_hash": "8EDFB7926067C405192BB734832B456CA7A051A477F1307768094AB0867444D5" + }, + "tx": "dHgzPXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx3" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "C349F213F04B4E8E749C6656E4C299E3BF22F4FAF141291A5C083336AD1A413B", + "height": "253", + "index": 0, + "proof": { + "data": "dHg0PXZhbHVl", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "oZPOdbpVGhDcNY2OaPjybbnfL2SMaDmXm9ufOgruPCA=", + "total": "1" + }, + "root_hash": "A193CE75BA551A10DC358D8E68F8F26DB9DF2F648C6839979BDB9F3A0AEE3C20" + }, + "tx": "dHg0PXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx4" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + }, + { + "hash": "CC4AC5C231481DD2ED2EA15789483B94565BF41612B6FEDE5BE7694F882CC202", + "height": "255", + "index": 0, + "proof": { + "data": "dHg1PXZhbHVl", + "proof": { + "aunts": [], + "index": "0", + "leaf_hash": "53wfU57GnWQ6Q46hc19t7bxY7SaY7WD4T6fy+TOPizM=", + "total": "1" + }, + "root_hash": "E77C1F539EC69D643A438EA1735F6DEDBC58ED2698ED60F84FA7F2F9338F8B33" + }, + "tx": "dHg1PXZhbHVl", + "tx_result": { + "code": 0, + "codespace": "", + "data": null, + "events": [ + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi Netowoko" + }, + { + "index": true, + "key": "key", + "value": "tx5" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + }, + { + "attributes": [ + { + "index": true, + "key": "creator", + "value": "Cosmoshi" + }, + { + "index": true, + "key": "key", + "value": "value" + }, + { + "index": true, + "key": "index_key", + "value": "index is working" + }, + { + "index": false, + "key": "noindex_key", + "value": "index is working" + } + ], + "type": "app" + } + ], + "gas_used": "0", + "gas_wanted": "0", + "info": "", + "log": "" + } + } + ] + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json new file mode 100644 index 000000000..1c05ffed7 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json @@ -0,0 +1,6 @@ +{ + "id": "4cdabace-7cae-4347-9675-e69a71a3b19a", + "jsonrpc": "2.0", + "method": "abci_info", + "params": null +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json new file mode 100644 index 000000000..28f01df62 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json @@ -0,0 +1,8 @@ +{ + "id": "49193475-5bbf-4820-a878-360f8c3c6072", + "jsonrpc": "2.0", + "method": "abci_query", + "params": { + "data": "747830" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json new file mode 100644 index 000000000..1d61822f8 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json @@ -0,0 +1,8 @@ +{ + "id": "6c6583ab-27ed-44ac-b704-78abe4723da9", + "jsonrpc": "2.0", + "method": "abci_query", + "params": { + "data": "6e6f6e5f6578697374656e745f6b6579" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json new file mode 100644 index 000000000..9d82f9833 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json @@ -0,0 +1,8 @@ +{ + "id": "2f4bc09e-7e2d-4514-a833-16e86d1af67e", + "jsonrpc": "2.0", + "method": "block", + "params": { + "height": "0" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json new file mode 100644 index 000000000..3b7100391 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json @@ -0,0 +1,8 @@ +{ + "id": "1356e29e-da5d-451a-b42d-cd3931bdb8f6", + "jsonrpc": "2.0", + "method": "block", + "params": { + "height": "1" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json new file mode 100644 index 000000000..54542be8c --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json @@ -0,0 +1,8 @@ +{ + "id": "1fa8bed7-d111-484d-abee-902fa1454069", + "jsonrpc": "2.0", + "method": "block", + "params": { + "height": "10" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json new file mode 100644 index 000000000..733bd48c1 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json @@ -0,0 +1,8 @@ +{ + "id": "abd9f0d1-5b80-424a-8f7d-94b2d854707c", + "jsonrpc": "2.0", + "method": "block_by_hash", + "params": { + "hash": "ABEiM0RVZneImaq7zN3u/wARIjNEVWZ3iJmqu8zd7v8=" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json new file mode 100644 index 000000000..e7523f57a --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json @@ -0,0 +1,8 @@ +{ + "id": "a5154e64-bf10-4b5f-960a-ed4eec5e261d", + "jsonrpc": "2.0", + "method": "block_results", + "params": { + "height": "10" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json new file mode 100644 index 000000000..6d63a31a3 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json @@ -0,0 +1,11 @@ +{ + "id": "35b99dba-c7c1-4229-be9c-23fa795e4432", + "jsonrpc": "2.0", + "method": "block_search", + "params": { + "order_by": "asc", + "page": "1", + "per_page": "100", + "query": "block.height > 1" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json new file mode 100644 index 000000000..0228e6e54 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json @@ -0,0 +1,9 @@ +{ + "id": "8b6f991a-4a2c-4dcf-9411-5c706f413235", + "jsonrpc": "2.0", + "method": "blockchain", + "params": { + "maxHeight": "10", + "minHeight": "1" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json new file mode 100644 index 000000000..9a32b2c05 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json @@ -0,0 +1,8 @@ +{ + "id": "37104243-1a80-4b5f-a917-cf38c863171f", + "jsonrpc": "2.0", + "method": "broadcast_tx_async", + "params": { + "tx": "YXN5bmMta2V5PXZhbHVl" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json new file mode 100644 index 000000000..ae45fea3b --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json @@ -0,0 +1,8 @@ +{ + "id": "be2a11c5-e6b3-4803-9f0e-140330c65f43", + "jsonrpc": "2.0", + "method": "broadcast_tx_commit", + "params": { + "tx": "Y29tbWl0LWtleT12YWx1ZQ==" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json new file mode 100644 index 000000000..fab1c5c51 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json @@ -0,0 +1,8 @@ +{ + "id": "c0bbfd1a-6b75-421e-ba3f-07dec9c1ba98", + "jsonrpc": "2.0", + "method": "broadcast_tx_sync", + "params": { + "tx": "c3luYy1rZXk9dmFsdWU=" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json new file mode 100644 index 000000000..347c92f8e --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json @@ -0,0 +1,8 @@ +{ + "id": "435978e8-89ed-4128-a94e-1f25dcd46c28", + "jsonrpc": "2.0", + "method": "commit", + "params": { + "height": "10" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json new file mode 100644 index 000000000..52494a5a3 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json @@ -0,0 +1,8 @@ +{ + "id": "abbcacd1-ff31-4725-b5ff-c46e21c02736", + "jsonrpc": "2.0", + "method": "consensus_params", + "params": { + "height": "10" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json new file mode 100644 index 000000000..c2a7163dd --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json @@ -0,0 +1,6 @@ +{ + "id": "6954460c-8b30-41e9-9752-261e063dda0c", + "jsonrpc": "2.0", + "method": "consensus_state", + "params": null +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json new file mode 100644 index 000000000..d6abed72a --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json @@ -0,0 +1,6 @@ +{ + "id": "30777544-c3da-4444-bef1-6035ece3b1c0", + "jsonrpc": "2.0", + "method": "genesis", + "params": null +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json new file mode 100644 index 000000000..bb0e69097 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json @@ -0,0 +1,6 @@ +{ + "id": "e6cd2152-119e-4349-bf6d-ec8b1e5e077f", + "jsonrpc": "2.0", + "method": "net_info", + "params": null +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json new file mode 100644 index 000000000..f2dc1be31 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json @@ -0,0 +1,6 @@ +{ + "id": "cd2af599-b99a-4fdb-a7ed-ee2734e77ebb", + "jsonrpc": "2.0", + "method": "status", + "params": null +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json new file mode 100644 index 000000000..2a90bfb15 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json @@ -0,0 +1,8 @@ +{ + "id": "e408a1ef-b634-4c92-864d-e9c5c59345d1", + "jsonrpc": "2.0", + "method": "subscribe", + "params": { + "query": "malformed query" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json new file mode 100644 index 000000000..2fa5f3237 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json @@ -0,0 +1,8 @@ +{ + "id": "9d27bbcf-657b-4c6e-8622-b83aa19a74d1", + "jsonrpc": "2.0", + "method": "subscribe", + "params": { + "query": "tm.event = 'NewBlock'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json new file mode 100644 index 000000000..1260beef9 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json @@ -0,0 +1,8 @@ +{ + "id": "43fad15f-cac8-4f38-b376-76c658e0b743", + "jsonrpc": "2.0", + "method": "subscribe", + "params": { + "query": "tm.event = 'Tx'" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json new file mode 100644 index 000000000..43666eaa6 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json @@ -0,0 +1,8 @@ +{ + "id": "7ad4d2b9-0d9b-4ee4-be3f-f602ecf8f5b1", + "jsonrpc": "2.0", + "method": "broadcast_tx_async", + "params": { + "tx": "dHgwPXZhbHVl" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json new file mode 100644 index 000000000..6dee5c11f --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json @@ -0,0 +1,8 @@ +{ + "id": "83abc9bc-379d-4a3d-93cd-973393006161", + "jsonrpc": "2.0", + "method": "broadcast_tx_async", + "params": { + "tx": "dHgxPXZhbHVl" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json new file mode 100644 index 000000000..4d023a7b0 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json @@ -0,0 +1,8 @@ +{ + "id": "5a5bbc9c-4b06-4d61-9efc-076d8863aae3", + "jsonrpc": "2.0", + "method": "broadcast_tx_async", + "params": { + "tx": "dHgyPXZhbHVl" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json new file mode 100644 index 000000000..f6703d26e --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json @@ -0,0 +1,8 @@ +{ + "id": "07cd909f-796e-448f-a16f-3c120c0d1b5a", + "jsonrpc": "2.0", + "method": "broadcast_tx_async", + "params": { + "tx": "dHgzPXZhbHVl" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json new file mode 100644 index 000000000..9ca953375 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json @@ -0,0 +1,8 @@ +{ + "id": "0fcbb94c-853b-43fd-bf56-aea2b0156fab", + "jsonrpc": "2.0", + "method": "broadcast_tx_async", + "params": { + "tx": "dHg0PXZhbHVl" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json new file mode 100644 index 000000000..841d737d1 --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json @@ -0,0 +1,8 @@ +{ + "id": "cb7ccde0-6d42-47c3-a772-6355f8c7befa", + "jsonrpc": "2.0", + "method": "broadcast_tx_async", + "params": { + "tx": "dHg1PXZhbHVl" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json new file mode 100644 index 000000000..262cff66a --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json @@ -0,0 +1,12 @@ +{ + "id": "7167bf23-1869-4578-8d37-d6f6387d70a7", + "jsonrpc": "2.0", + "method": "tx_search", + "params": { + "order_by": "asc", + "page": "1", + "per_page": "10", + "prove": false, + "query": "tx.height > 1" + } +} \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json new file mode 100644 index 000000000..5c0408eec --- /dev/null +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json @@ -0,0 +1,12 @@ +{ + "id": "d1b4904e-c0d4-4b37-b6ac-0730c7144e04", + "jsonrpc": "2.0", + "method": "tx_search", + "params": { + "order_by": "asc", + "page": "1", + "per_page": "10", + "prove": true, + "query": "tx.height > 1" + } +} \ No newline at end of file From bacb64b51879506c2429824c5a5c5d25b76e0526 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 27 Feb 2023 10:11:54 +0200 Subject: [PATCH 67/77] rpc: adjust some v0_37 tests to match fixtures Some of the fixtures needed adjusting as well, due to time-dependent assumptions made by tests, or randomness that could not be guessed ahead of time (incoming/block_by_hash). --- rpc/tests/kvstore_fixtures/v0_37.rs | 17 +- .../v0_37/incoming/abci_info.json | 8 +- .../abci_query_with_existing_key.json | 4 +- .../abci_query_with_non_existent_key.json | 4 +- .../v0_37/incoming/block_at_height_0.json | 2 +- .../v0_37/incoming/block_at_height_1.json | 14 +- .../v0_37/incoming/block_at_height_10.json | 30 +- .../v0_37/incoming/block_by_hash.json | 61 +- .../incoming/block_results_at_height_10.json | 2 +- .../v0_37/incoming/block_search.json | 4637 +++-------------- .../incoming/blockchain_from_1_to_10.json | 178 +- .../v0_37/incoming/broadcast_tx_async.json | 2 +- .../v0_37/incoming/broadcast_tx_commit.json | 4 +- .../v0_37/incoming/broadcast_tx_sync.json | 2 +- .../v0_37/incoming/commit_at_height_10.json | 26 +- .../v0_37/incoming/consensus_params.json | 2 +- .../v0_37/incoming/consensus_state.json | 8 +- .../v0_37/incoming/genesis.json | 8 +- .../v0_37/incoming/net_info.json | 2 +- .../v0_37/incoming/status.json | 18 +- .../v0_37/incoming/subscribe_malformed.json | 2 +- .../v0_37/incoming/subscribe_newblock_0.json | 30 +- .../v0_37/incoming/subscribe_newblock_1.json | 30 +- .../v0_37/incoming/subscribe_newblock_2.json | 30 +- .../v0_37/incoming/subscribe_newblock_3.json | 30 +- .../v0_37/incoming/subscribe_newblock_4.json | 30 +- .../v0_37/incoming/subscribe_txs.json | 2 +- .../v0_37/incoming/subscribe_txs_0.json | 6 +- .../v0_37/incoming/subscribe_txs_1.json | 6 +- .../v0_37/incoming/subscribe_txs_2.json | 6 +- .../v0_37/incoming/subscribe_txs_3.json | 6 +- .../v0_37/incoming/subscribe_txs_4.json | 6 +- .../subscribe_txs_broadcast_tx_0.json | 2 +- .../subscribe_txs_broadcast_tx_1.json | 2 +- .../subscribe_txs_broadcast_tx_2.json | 2 +- .../subscribe_txs_broadcast_tx_3.json | 2 +- .../subscribe_txs_broadcast_tx_4.json | 2 +- .../subscribe_txs_broadcast_tx_5.json | 2 +- .../v0_37/incoming/tx_search_no_prove.json | 20 +- .../v0_37/incoming/tx_search_with_prove.json | 20 +- .../v0_37/outgoing/abci_info.json | 2 +- .../abci_query_with_existing_key.json | 2 +- .../abci_query_with_non_existent_key.json | 2 +- .../v0_37/outgoing/block_at_height_0.json | 2 +- .../v0_37/outgoing/block_at_height_1.json | 2 +- .../v0_37/outgoing/block_at_height_10.json | 2 +- .../v0_37/outgoing/block_by_hash.json | 4 +- .../outgoing/block_results_at_height_10.json | 2 +- .../v0_37/outgoing/block_search.json | 2 +- .../outgoing/blockchain_from_1_to_10.json | 2 +- .../v0_37/outgoing/broadcast_tx_async.json | 2 +- .../v0_37/outgoing/broadcast_tx_commit.json | 2 +- .../v0_37/outgoing/broadcast_tx_sync.json | 2 +- .../v0_37/outgoing/commit_at_height_10.json | 2 +- .../v0_37/outgoing/consensus_params.json | 2 +- .../v0_37/outgoing/consensus_state.json | 2 +- .../v0_37/outgoing/genesis.json | 2 +- .../v0_37/outgoing/net_info.json | 2 +- .../v0_37/outgoing/status.json | 2 +- .../v0_37/outgoing/subscribe_malformed.json | 2 +- .../v0_37/outgoing/subscribe_newblock.json | 2 +- .../v0_37/outgoing/subscribe_txs.json | 2 +- .../subscribe_txs_broadcast_tx_0.json | 2 +- .../subscribe_txs_broadcast_tx_1.json | 2 +- .../subscribe_txs_broadcast_tx_2.json | 2 +- .../subscribe_txs_broadcast_tx_3.json | 2 +- .../subscribe_txs_broadcast_tx_4.json | 2 +- .../subscribe_txs_broadcast_tx_5.json | 2 +- .../v0_37/outgoing/tx_search_no_prove.json | 2 +- .../v0_37/outgoing/tx_search_with_prove.json | 2 +- tools/rpc-probe/src/kvstore.rs | 7 +- 71 files changed, 1015 insertions(+), 4319 deletions(-) diff --git a/rpc/tests/kvstore_fixtures/v0_37.rs b/rpc/tests/kvstore_fixtures/v0_37.rs index 448d48d95..55a00bb3c 100644 --- a/rpc/tests/kvstore_fixtures/v0_37.rs +++ b/rpc/tests/kvstore_fixtures/v0_37.rs @@ -56,14 +56,13 @@ fn outgoing_fixtures() { assert_eq!(wrapped.params().height.unwrap().value(), 10); }, "block_by_hash" => { - // First, get the hash at height 1. let wrapped = serde_json::from_str::< RequestWrapper, >(&content) .unwrap(); assert_eq!( wrapped.params().hash.unwrap().to_string(), - "00112233445566778899AABBCCDDEEFF00112233445566778899AABBCCDDEEFF" + "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639" ); }, "block_results_at_height_10" => { @@ -282,10 +281,10 @@ fn incoming_fixtures() { "abci_info" => { let result = endpoint::abci_info::Response::from_string(content).unwrap(); assert_eq!(result.response.app_version, 1); - assert_eq!(result.response.data, "{\"size\":0}"); + assert_eq!(result.response.data, "{\"size\":9}"); assert_eq!( result.response.last_block_app_hash.as_bytes(), - b"AAAAAAAAAAA=" + b"EgAAAAAAAAA=" ); assert_eq!(result.response.version, "1.0.0"); }, @@ -434,7 +433,7 @@ fn incoming_fixtures() { let result = endpoint::block_by_hash::Response::from_string(content).unwrap(); assert_eq!( result.block_id.hash.to_string(), - "BCF3DB412E80A396D10BF5B5E6D3E63D3B06DEB25AA958BCB8CE18D023838042" + "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639" ); }, "block_search" => { @@ -509,7 +508,7 @@ fn incoming_fixtures() { assert_eq!(result.deliver_tx.code, abci::Code::Ok); assert!(result.deliver_tx.codespace.is_empty()); assert!(result.deliver_tx.data.is_empty()); - assert_eq!(result.deliver_tx.events.len(), 1); + assert_eq!(result.deliver_tx.events.len(), 2); assert_eq!(result.deliver_tx.events[0].attributes.len(), 4); assert_eq!(result.deliver_tx.events[0].attributes[0].key, "creator"); assert_eq!( @@ -602,7 +601,7 @@ fn incoming_fixtures() { assert_eq!(u64::from(result.block_height), 10_u64); assert_eq!(result.consensus_params.block.max_bytes, 22020096_u64); assert_eq!(result.consensus_params.block.max_gas, -1_i64); - assert_eq!(result.consensus_params.block.time_iota_ms, 500_i64); + assert_eq!(result.consensus_params.block.time_iota_ms, 1000_i64); assert_eq!( result.consensus_params.evidence.max_age_duration, Duration(core::time::Duration::from_nanos(172800000000000_u64)) @@ -674,7 +673,7 @@ fn incoming_fixtures() { assert_eq!(result.genesis.validators[0].power(), 10); assert!(result.genesis.validators[0].pub_key.ed25519().is_some()); assert_eq!(result.genesis.validators[0].proposer_priority.value(), 0); - assert_eq!(result.genesis.consensus_params.block.time_iota_ms, 500); + assert_eq!(result.genesis.consensus_params.block.time_iota_ms, 1000); }, "net_info" => { let result = endpoint::net_info::Response::from_string(content).unwrap(); @@ -708,7 +707,7 @@ fn incoming_fixtures() { app: 1 } ); - assert_eq!(result.node_info.version.to_string(), "0.34.21"); + assert_eq!(result.node_info.version.to_string(), "0.37.0-alpha.3"); assert!(!result.sync_info.catching_up); assert_eq!( result.sync_info.latest_app_hash.as_bytes(), diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json index 354f9be15..303d67f9d 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_info.json @@ -1,12 +1,12 @@ { - "id": "4cdabace-7cae-4347-9675-e69a71a3b19a", + "id": "4e158c90-577c-4408-b8f6-d3680b84e7e9", "jsonrpc": "2.0", "result": { "response": { "app_version": "1", - "data": "{\"size\":0}", - "last_block_app_hash": "AAAAAAAAAAA=", - "last_block_height": "200", + "data": "{\"size\":9}", + "last_block_app_hash": "EgAAAAAAAAA=", + "last_block_height": "161", "version": "1.0.0" } } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json index 059d11785..63dc552bd 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_existing_key.json @@ -1,11 +1,11 @@ { - "id": "49193475-5bbf-4820-a878-360f8c3c6072", + "id": "4c088a2c-e01c-4d8b-aadc-009753b68d04", "jsonrpc": "2.0", "result": { "response": { "code": 0, "codespace": "", - "height": "256", + "height": "75", "index": "0", "info": "", "key": "dHgw", diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json index 3759a74b9..dde08d830 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/abci_query_with_non_existent_key.json @@ -1,11 +1,11 @@ { - "id": "6c6583ab-27ed-44ac-b704-78abe4723da9", + "id": "437f6c65-b4b2-4417-9e03-2b584a75403f", "jsonrpc": "2.0", "result": { "response": { "code": 0, "codespace": "", - "height": "202", + "height": "163", "index": "0", "info": "", "key": "bm9uX2V4aXN0ZW50X2tleQ==", diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json index 7bd847802..fb69121fd 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_0.json @@ -4,6 +4,6 @@ "data": "height must be greater than 0, but got 0", "message": "Internal error" }, - "id": "2f4bc09e-7e2d-4514-a833-16e86d1af67e", + "id": "c1144ac0-8c4d-46cc-9430-8c14c598a029", "jsonrpc": "2.0" } \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json index d331f8649..056d76ab7 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_1.json @@ -1,5 +1,5 @@ { - "id": "1356e29e-da5d-451a-b42d-cd3931bdb8f6", + "id": "5f66ff6f-8283-4c9a-8437-b120248182d8", "jsonrpc": "2.0", "result": { "block": { @@ -25,10 +25,10 @@ }, "last_commit_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:35.386925428Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:03.391799721Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -48,9 +48,9 @@ } }, "block_id": { - "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "hash": "D55CD72165688BE21F2DF8C9AE46FA2BCA423223E99FC665DD2E621066F443C5", "parts": { - "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "hash": "372520F1B93CD0EC3901006DE2E3CD752C9141628A7B430088DF912171355DDA", "total": 1 } } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json index 226628cd4..cf482b096 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_at_height_10.json @@ -1,5 +1,5 @@ { - "id": "1fa8bed7-d111-484d-abee-902fa1454069", + "id": "a24afd41-dbab-453d-8734-f599f84eb653", "jsonrpc": "2.0", "result": { "block": { @@ -17,18 +17,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "10", "last_block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } }, - "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_commit_hash": "E8DE5F9749FA5785B9B9F106C82233C910C75AE8A0903D1FAB146C1DD4E7A0EC", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:40.123954449Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:08.140032018Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -36,9 +36,9 @@ }, "last_commit": { "block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } }, @@ -47,17 +47,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "V8j/4eDj/LWDhjiCBvYZgBZXOp891keTHM1y9tpAMiUHrnDllS6DWuq9EYxftB9hA31pGvZKHM5v5SdNRFV4DA==", - "timestamp": "2023-02-24T15:09:40.123954449Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "HZvchSiSLgqdRmsZ+KIpkztV7ZbEBhRU5CKHUy0enSHoma8jTk9BC69s4fPvHHLiAtSNausFd83g0KR08bQhCw==", + "timestamp": "2023-02-27T07:13:08.140032018Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "hash": "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639", "parts": { - "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "hash": "E16EDCB0EC135191F5C017FDF232967F50919E06B0F2F419FA93D006E606CF05", "total": 1 } } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json index 026fedbff..5cf5431f5 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_by_hash.json @@ -1,13 +1,64 @@ { - "id": "abd9f0d1-5b80-424a-8f7d-94b2d854707c", "jsonrpc": "2.0", + "id": "56d4851a-1f30-4d73-9f86-c1a084e8aa97", "result": { - "block": null, "block_id": { - "hash": "", + "hash": "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639", "parts": { - "hash": "", - "total": 0 + "total": 1, + "hash": "E16EDCB0EC135191F5C017FDF232967F50919E06B0F2F419FA93D006E606CF05" + } + }, + "block": { + "header": { + "version": { + "block": "11", + "app": "1" + }, + "chain_id": "dockerchain", + "height": "10", + "time": "2023-02-27T07:13:08.140032018Z", + "last_block_id": { + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", + "parts": { + "total": 1, + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D" + } + }, + "last_commit_hash": "E8DE5F9749FA5785B9B9F106C82233C910C75AE8A0903D1FAB146C1DD4E7A0EC", + "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", + "app_hash": "0000000000000000", + "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371" + }, + "data": { + "txs": [] + }, + "evidence": { + "evidence": [] + }, + "last_commit": { + "height": "9", + "round": 0, + "block_id": { + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", + "parts": { + "total": 1, + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D" + } + }, + "signatures": [ + { + "block_id_flag": 2, + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371", + "timestamp": "2023-02-27T07:13:08.140032018Z", + "signature": "HZvchSiSLgqdRmsZ+KIpkztV7ZbEBhRU5CKHUy0enSHoma8jTk9BC69s4fPvHHLiAtSNausFd83g0KR08bQhCw==" + } + ] } } } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json index c22e95e07..ee23b39ec 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_results_at_height_10.json @@ -1,5 +1,5 @@ { - "id": "a5154e64-bf10-4b5f-960a-ed4eec5e261d", + "id": "77cfdbe4-630e-4b73-b30d-90a1236f96a3", "jsonrpc": "2.0", "result": { "begin_block_events": null, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json index d6e399469..69c956186 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/block_search.json @@ -1,5 +1,5 @@ { - "id": "35b99dba-c7c1-4229-be9c-23fa795e4432", + "id": "60d0e76b-d645-4b37-adc0-42fc0fa7d394", "jsonrpc": "2.0", "result": { "blocks": [ @@ -19,18 +19,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "2", "last_block_id": { - "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "hash": "D55CD72165688BE21F2DF8C9AE46FA2BCA423223E99FC665DD2E621066F443C5", "parts": { - "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "hash": "372520F1B93CD0EC3901006DE2E3CD752C9141628A7B430088DF912171355DDA", "total": 1 } }, - "last_commit_hash": "227D78AC78B219692FC3EE18BCE5FD46E86F382979628FB6BE01DDF4C9E66750", + "last_commit_hash": "48018604B85D54DC6E49DB6E4CF12F67FC56337B84E378AE2357B3E2CE4F1EC9", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:35.982946125Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:03.991666836Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -38,9 +38,9 @@ }, "last_commit": { "block_id": { - "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "hash": "D55CD72165688BE21F2DF8C9AE46FA2BCA423223E99FC665DD2E621066F443C5", "parts": { - "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "hash": "372520F1B93CD0EC3901006DE2E3CD752C9141628A7B430088DF912171355DDA", "total": 1 } }, @@ -49,17 +49,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "0ALiGU3vSUd1Gg349Uzxv9BhyVVbk0R8PpEmBnBeuccKx9RoREEt7UZaqHNUIwfR2PkTpM9yNsG+7vteMD0HCA==", - "timestamp": "2023-02-24T15:09:35.982946125Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "cHV87SDszjwySZojpEm59gEXsIn77kchx5HubP1Aw+w9nwAiTiKoVua/rIbSyc6l18Jj3YAtuZ0TiP9bEJv5AQ==", + "timestamp": "2023-02-27T07:13:03.991666836Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "hash": "618E263A7265C42E04D4C5DE3370F7B64C0AC8271435D17A20360C09A702E353", "parts": { - "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "hash": "23296CEC8762B62711D174F14FFE5807F910AE3360F24BE55B58C1E8911FD01F", "total": 1 } } @@ -80,18 +80,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "3", "last_block_id": { - "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "hash": "618E263A7265C42E04D4C5DE3370F7B64C0AC8271435D17A20360C09A702E353", "parts": { - "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "hash": "23296CEC8762B62711D174F14FFE5807F910AE3360F24BE55B58C1E8911FD01F", "total": 1 } }, - "last_commit_hash": "6237CD7F07174FB28966A889F6A9B4D26DC6D7F104D0B4333007E6C2AB7D61C1", + "last_commit_hash": "7183ED105A3A3FF34CBAEB2CDCA13F3C3437EF0A140C40EABA425709AD44C066", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:36.499560496Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:04.508252675Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -99,9 +99,9 @@ }, "last_commit": { "block_id": { - "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "hash": "618E263A7265C42E04D4C5DE3370F7B64C0AC8271435D17A20360C09A702E353", "parts": { - "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "hash": "23296CEC8762B62711D174F14FFE5807F910AE3360F24BE55B58C1E8911FD01F", "total": 1 } }, @@ -110,17 +110,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "0UeNQrmaSfjb41umFq3N4DoRWzU2yRpDquN43+Kp5u5VGpUS3Ps2mF+zFO1ndy8u3Ta3GFnYdjW9nlqTaK0WAQ==", - "timestamp": "2023-02-24T15:09:36.499560496Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "KqsqRLvybtHs5pj/G5GH3uVv+9SLWmHxK3eh/omUL026LkpDXiOg70W6ryiurSGVv5CG16q/RI9K4YdFEGNPAQ==", + "timestamp": "2023-02-27T07:13:04.508252675Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "hash": "AFEB65E07422484A7295D2ABFEB66621386B98E8FC022B8BD177C14BDB4A3DB2", "parts": { - "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "hash": "BC99391E5E093CEEE17A888CE4FA0E13BD06A0BA026336B662D445F5B1455DA9", "total": 1 } } @@ -141,18 +141,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "4", "last_block_id": { - "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "hash": "AFEB65E07422484A7295D2ABFEB66621386B98E8FC022B8BD177C14BDB4A3DB2", "parts": { - "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "hash": "BC99391E5E093CEEE17A888CE4FA0E13BD06A0BA026336B662D445F5B1455DA9", "total": 1 } }, - "last_commit_hash": "6DDE3F5FEB4E7E88FCF3A9B8E5A9B178B525E68817C1EC05E2DE9E03AB164D96", + "last_commit_hash": "97FFFE3763FFAB168334C271B859483B95BF393CF4E61C91590CF3F6F55C4204", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:37.018159177Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:05.026580561Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -160,9 +160,9 @@ }, "last_commit": { "block_id": { - "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "hash": "AFEB65E07422484A7295D2ABFEB66621386B98E8FC022B8BD177C14BDB4A3DB2", "parts": { - "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "hash": "BC99391E5E093CEEE17A888CE4FA0E13BD06A0BA026336B662D445F5B1455DA9", "total": 1 } }, @@ -171,17 +171,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "jCRCbsEIyj1qiAeTgB83J0/R8O8nFhkCA5MDr8yfH3ktL5xD/gC4ZLJL2yhobtD+jyWYLdX0QhXlUQ+O9SiNBw==", - "timestamp": "2023-02-24T15:09:37.018159177Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "flGrk8tDwO0+n1QayE7pusw1ZViNwYck7fAHyDkyGCNxqeqttNqchoWSrfHMbBZGjxwqjASPU3HU2GhQ5SDCBA==", + "timestamp": "2023-02-27T07:13:05.026580561Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "hash": "7D162051AC61242B7613E085CA4E3488AE6A953E8BE3B72A9E6938E62F5212AF", "parts": { - "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "hash": "D9A258567016DE8D364C0E64E3882C7DAD6488B129CE4612B3D67EBFF7CFF288", "total": 1 } } @@ -202,18 +202,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "5", "last_block_id": { - "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "hash": "7D162051AC61242B7613E085CA4E3488AE6A953E8BE3B72A9E6938E62F5212AF", "parts": { - "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "hash": "D9A258567016DE8D364C0E64E3882C7DAD6488B129CE4612B3D67EBFF7CFF288", "total": 1 } }, - "last_commit_hash": "EDC03890397D8183CD0FE0A25A729BFC5192851DC8ADA3642B7D23E0B7B51A21", + "last_commit_hash": "4D95F1B754571826AA7C01E521D1D73A309880714C81DE48255DA2D57D55C756", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:37.533687433Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:05.545291963Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -221,9 +221,9 @@ }, "last_commit": { "block_id": { - "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "hash": "7D162051AC61242B7613E085CA4E3488AE6A953E8BE3B72A9E6938E62F5212AF", "parts": { - "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "hash": "D9A258567016DE8D364C0E64E3882C7DAD6488B129CE4612B3D67EBFF7CFF288", "total": 1 } }, @@ -232,17 +232,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "HY0ROA2/fYJhlG29zkkKtyiFIR6KN0b6DmwQmds4UuPcHWcySGBn5JzjSC/9BtRa+39/F+UOx52qq1YrqpGiBQ==", - "timestamp": "2023-02-24T15:09:37.533687433Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "5P0/jbLaaV9ziN8LYHf9lspfU3VqnWVDo4jDx1gBaC2hvUBG1abRqQufylCzZk1Dq1FOfHOx9snUXULk/Xe0Bw==", + "timestamp": "2023-02-27T07:13:05.545291963Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "hash": "38070040A8D1365B66B0344664106193ECF1D18444A769E51D2881B15087DCD7", "parts": { - "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "hash": "59876DFD84701B32F2AB5679D498E33A9AC26D11165B142D5E9EF3B2AF021BB9", "total": 1 } } @@ -263,18 +263,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "6", "last_block_id": { - "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "hash": "38070040A8D1365B66B0344664106193ECF1D18444A769E51D2881B15087DCD7", "parts": { - "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "hash": "59876DFD84701B32F2AB5679D498E33A9AC26D11165B142D5E9EF3B2AF021BB9", "total": 1 } }, - "last_commit_hash": "769E5D10F6B90219BB10D7DA6600728E02A760476A3F0216914B4E3D758E0ED6", + "last_commit_hash": "139381A60C8BCAF336ED8E8373FE52F7469DA76C054B9265921322046FD97B93", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:38.051624453Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:06.065052373Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -282,9 +282,9 @@ }, "last_commit": { "block_id": { - "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "hash": "38070040A8D1365B66B0344664106193ECF1D18444A769E51D2881B15087DCD7", "parts": { - "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "hash": "59876DFD84701B32F2AB5679D498E33A9AC26D11165B142D5E9EF3B2AF021BB9", "total": 1 } }, @@ -293,17 +293,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "yCUdVX41Vg6BKjN2Drz1buvxYnAE1QVJ3VfXXPSQpb/5cCUsBwbmlzGr7lW4pG+Up8esuRPvw5rVd10WOeq1CA==", - "timestamp": "2023-02-24T15:09:38.051624453Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "4unKYY8ShwcpEbS+dqFtHgJSN4Qt0OBKV+DvoWURU+GDFymH4z6yWUNjyVDkazwk0mxOx3NuIYt8oA75taLbDg==", + "timestamp": "2023-02-27T07:13:06.065052373Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "hash": "92DF7250265107D9FB3BAC7A97CA25AC2543B86E960632D11DDDE74FB5C2F41F", "parts": { - "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "hash": "9F7DCBC5879343913CFAA6365B68E34FEA17CB1E1D1B7044ED72131D1F5DE9F9", "total": 1 } } @@ -324,18 +324,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "7", "last_block_id": { - "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "hash": "92DF7250265107D9FB3BAC7A97CA25AC2543B86E960632D11DDDE74FB5C2F41F", "parts": { - "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "hash": "9F7DCBC5879343913CFAA6365B68E34FEA17CB1E1D1B7044ED72131D1F5DE9F9", "total": 1 } }, - "last_commit_hash": "266129248C2C0D2684F1D1BE8E5A119742520BAA03F740BE5C612E8CFB245DB7", + "last_commit_hash": "325A2D023AAA8705C2D9FF1593C8904EF16258825EC8212600BE98C69E20F3D2", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:38.570297947Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:06.580593612Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -343,9 +343,9 @@ }, "last_commit": { "block_id": { - "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "hash": "92DF7250265107D9FB3BAC7A97CA25AC2543B86E960632D11DDDE74FB5C2F41F", "parts": { - "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "hash": "9F7DCBC5879343913CFAA6365B68E34FEA17CB1E1D1B7044ED72131D1F5DE9F9", "total": 1 } }, @@ -354,17 +354,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "w2xBk7ki4DjfsfKWUsROgMRnfZpGpdCE6QA2OTM91lo/Eh/J3tguP8KNNoVxrkYyaHgKT/SvFN2WXLYwIOrNCQ==", - "timestamp": "2023-02-24T15:09:38.570297947Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "4Jr4PkKzZwDIfIs16jJtCfo8Gtce7yOmDwhq6ItoHh6eUkfC9uYVjLAi/GvRqCI7p/T0vGOtxKPt8E5H8N+EAA==", + "timestamp": "2023-02-27T07:13:06.580593612Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "hash": "29374DAF235CC5A1751E09A22DD6F200D1EA3BEB473A7820C4CC7F149DB032AB", "parts": { - "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "hash": "7AEA98F9C8658AF6B5DE7B41AF0658AACBDC54D882E17BCFB35727B95EAD9E50", "total": 1 } } @@ -385,18 +385,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "8", "last_block_id": { - "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "hash": "29374DAF235CC5A1751E09A22DD6F200D1EA3BEB473A7820C4CC7F149DB032AB", "parts": { - "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "hash": "7AEA98F9C8658AF6B5DE7B41AF0658AACBDC54D882E17BCFB35727B95EAD9E50", "total": 1 } }, - "last_commit_hash": "D12B708778B847858029349205FD4BE0F8B22A8DE61943D5C2D4B49396767775", + "last_commit_hash": "6B184CC5107EAD2DD682BD3A1A60B568ECB9EE2A75DA34F237E42550B69E3146", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:39.090086292Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:07.101498447Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -404,9 +404,9 @@ }, "last_commit": { "block_id": { - "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "hash": "29374DAF235CC5A1751E09A22DD6F200D1EA3BEB473A7820C4CC7F149DB032AB", "parts": { - "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "hash": "7AEA98F9C8658AF6B5DE7B41AF0658AACBDC54D882E17BCFB35727B95EAD9E50", "total": 1 } }, @@ -415,17 +415,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "wnmCESLo6NRG1jVcd9ki3b3kXOyQ2iVf35b7fVqymzdk4ggG/TZqXM17t9SUhaJNCEhLSwdVTkW7dBSKDWO/Bg==", - "timestamp": "2023-02-24T15:09:39.090086292Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "feAR9RewFN2wkmn0yfdN0hdwtrvqzF7wqHp/56SO970V4qw7PNP3npTa8lTyuvtWtga2u9ukQCbJuB8IuvP8AQ==", + "timestamp": "2023-02-27T07:13:07.101498447Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "hash": "875A50CDD812054D87A7F5CC6A0C7E224C6E2DF2F2A89EA51B9DCEE6136B469E", "parts": { - "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "hash": "74F62C8CEF42AF0A685D84C8422751CD2269E16A793FAC95B96A8C42132E8338", "total": 1 } } @@ -446,18 +446,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "9", "last_block_id": { - "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "hash": "875A50CDD812054D87A7F5CC6A0C7E224C6E2DF2F2A89EA51B9DCEE6136B469E", "parts": { - "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "hash": "74F62C8CEF42AF0A685D84C8422751CD2269E16A793FAC95B96A8C42132E8338", "total": 1 } }, - "last_commit_hash": "22FC31E6CCA7D5C580B14FC94E506524041B2064C9DB27D54A5AC3254950CBA9", + "last_commit_hash": "9EEDE09BD5848E1F97D54D4C2633582D152FEF610869E3D29815B5A2159D8631", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:39.606408964Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:07.619684947Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -465,9 +465,9 @@ }, "last_commit": { "block_id": { - "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "hash": "875A50CDD812054D87A7F5CC6A0C7E224C6E2DF2F2A89EA51B9DCEE6136B469E", "parts": { - "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "hash": "74F62C8CEF42AF0A685D84C8422751CD2269E16A793FAC95B96A8C42132E8338", "total": 1 } }, @@ -476,17 +476,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "4psdDfHZVZmi5IvswMNFIOKtoSXzN3AwbLIzO0ZlC2owyKzS01UMyJGvYD+ttvb4ZkC1jzmkum+NpnkXh3IlDw==", - "timestamp": "2023-02-24T15:09:39.606408964Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "wpir5zdPemjY2aY97Xoh9ioNmjc8Kt8eFB3skbYYfiY0AW92FOisfR98reIyoOLRlhnuarSsjZsYIYFn/L8iDw==", + "timestamp": "2023-02-27T07:13:07.619684947Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } } @@ -507,18 +507,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "10", "last_block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } }, - "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_commit_hash": "E8DE5F9749FA5785B9B9F106C82233C910C75AE8A0903D1FAB146C1DD4E7A0EC", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:40.123954449Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:08.140032018Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -526,9 +526,9 @@ }, "last_commit": { "block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } }, @@ -537,17 +537,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "V8j/4eDj/LWDhjiCBvYZgBZXOp891keTHM1y9tpAMiUHrnDllS6DWuq9EYxftB9hA31pGvZKHM5v5SdNRFV4DA==", - "timestamp": "2023-02-24T15:09:40.123954449Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "HZvchSiSLgqdRmsZ+KIpkztV7ZbEBhRU5CKHUy0enSHoma8jTk9BC69s4fPvHHLiAtSNausFd83g0KR08bQhCw==", + "timestamp": "2023-02-27T07:13:08.140032018Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "hash": "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639", "parts": { - "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "hash": "E16EDCB0EC135191F5C017FDF232967F50919E06B0F2F419FA93D006E606CF05", "total": 1 } } @@ -568,18 +568,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "11", "last_block_id": { - "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "hash": "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639", "parts": { - "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "hash": "E16EDCB0EC135191F5C017FDF232967F50919E06B0F2F419FA93D006E606CF05", "total": 1 } }, - "last_commit_hash": "20740E1EEE8BF0AD07A1FA0A39F3165C1F5F8E287AF3F62B6566D9099692005E", + "last_commit_hash": "62A7ADC65EEFBE1E7146542222F6613C49E037F76E8401AA72C5CD1B879E92EE", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:40.640670992Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:08.658439642Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -587,9 +587,9 @@ }, "last_commit": { "block_id": { - "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "hash": "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639", "parts": { - "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "hash": "E16EDCB0EC135191F5C017FDF232967F50919E06B0F2F419FA93D006E606CF05", "total": 1 } }, @@ -598,17 +598,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "gozurqzPCl9et0LQgKksMg60fdU1cPOoDfIEUwMCWMZt8/5cRYiUbr7+kJj9AHF2/C1w3Abs8a+QxtVJPnWlBw==", - "timestamp": "2023-02-24T15:09:40.640670992Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "qJblJeAl6OtGRKkOa91+HLzX3ZGl/Nlnl5K9RiT2gRSPgPSjxq+95mSQSJ3b3I38mdZvYLUML6kEGvC/zjlJCQ==", + "timestamp": "2023-02-27T07:13:08.658439642Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "EC2860F0F808D60E6A19C95E96B5DB1414214D0A8DCF86FBA240AE197FED4CA3", + "hash": "C3BB1826273AC94C4B2C2BCF7B576FA3F081B29D53B61D17A98D354CC37BB35D", "parts": { - "hash": "DD6095B5570A6866BBB4E5CF768A328845CCC5D50FDA1D14426939D4A3D625B1", + "hash": "79DF166677D4BFF3F062F83B71D2503E75D27D036B9B48A4577F6FA710D959E2", "total": 1 } } @@ -629,18 +629,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "12", "last_block_id": { - "hash": "EC2860F0F808D60E6A19C95E96B5DB1414214D0A8DCF86FBA240AE197FED4CA3", + "hash": "C3BB1826273AC94C4B2C2BCF7B576FA3F081B29D53B61D17A98D354CC37BB35D", "parts": { - "hash": "DD6095B5570A6866BBB4E5CF768A328845CCC5D50FDA1D14426939D4A3D625B1", + "hash": "79DF166677D4BFF3F062F83B71D2503E75D27D036B9B48A4577F6FA710D959E2", "total": 1 } }, - "last_commit_hash": "7A6A90DD48958C694F693A3E9CA9C19350EBF73BB9369CEDE042C097C728BD0F", + "last_commit_hash": "8A9D304F162B3D0DDD5627BE75A1392938798FD058B4A5394559CC980C7C80E8", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:41.161270689Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:09.177757554Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -648,9 +648,9 @@ }, "last_commit": { "block_id": { - "hash": "EC2860F0F808D60E6A19C95E96B5DB1414214D0A8DCF86FBA240AE197FED4CA3", + "hash": "C3BB1826273AC94C4B2C2BCF7B576FA3F081B29D53B61D17A98D354CC37BB35D", "parts": { - "hash": "DD6095B5570A6866BBB4E5CF768A328845CCC5D50FDA1D14426939D4A3D625B1", + "hash": "79DF166677D4BFF3F062F83B71D2503E75D27D036B9B48A4577F6FA710D959E2", "total": 1 } }, @@ -659,17 +659,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "dHCRg3DqkdBynbFLRCwzunj5TXj05hJHmAtYxS+oCZAAm3vlm1GQD786AyaAEGr5PnNqLJjMbkzBAxm/E/nDBw==", - "timestamp": "2023-02-24T15:09:41.161270689Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "AfQHggff6gF+cRzr7r5tAlgWysMoKLM80ukaGroGB8sFcnWqmVRPFYiNxRwRbkzFLKhBNWlajFoDxnESMB8iDg==", + "timestamp": "2023-02-27T07:13:09.177757554Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "92196E832E0003A4682F3C2DFBE92474985B9D84F778D767BE604C08B368A1DE", + "hash": "A498E33E12FBE7C1F1E9A76CAD1826AC4474A0FD2C402188B93F6674A18D7B08", "parts": { - "hash": "DDEE670BF9199CC306BC96D2FE530BE8719621CBC873E35054A4E93F457264F1", + "hash": "52619405D70E2FCC699567258AC9C2912F2CCEE4CB5EFC813B0CD2AF4D6B49C0", "total": 1 } } @@ -690,18 +690,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "13", "last_block_id": { - "hash": "92196E832E0003A4682F3C2DFBE92474985B9D84F778D767BE604C08B368A1DE", + "hash": "A498E33E12FBE7C1F1E9A76CAD1826AC4474A0FD2C402188B93F6674A18D7B08", "parts": { - "hash": "DDEE670BF9199CC306BC96D2FE530BE8719621CBC873E35054A4E93F457264F1", + "hash": "52619405D70E2FCC699567258AC9C2912F2CCEE4CB5EFC813B0CD2AF4D6B49C0", "total": 1 } }, - "last_commit_hash": "8B7D6067E63570F7BA68C2AA54015FF125619F32D80774EEB35EB2AEA8EA22A7", + "last_commit_hash": "C97CC7FF9E2B8F5627D3955B0CE9E030C848E8D7EBCE50E7A457B57D35A6B75D", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:41.681034391Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:09.69690345Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -709,9 +709,9 @@ }, "last_commit": { "block_id": { - "hash": "92196E832E0003A4682F3C2DFBE92474985B9D84F778D767BE604C08B368A1DE", + "hash": "A498E33E12FBE7C1F1E9A76CAD1826AC4474A0FD2C402188B93F6674A18D7B08", "parts": { - "hash": "DDEE670BF9199CC306BC96D2FE530BE8719621CBC873E35054A4E93F457264F1", + "hash": "52619405D70E2FCC699567258AC9C2912F2CCEE4CB5EFC813B0CD2AF4D6B49C0", "total": 1 } }, @@ -720,17 +720,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "TTn4qezR2fvqoDPtPsztmqAmOCe6uzOmeqEgyRXZBnEkIl7pb71p1AX70lJ60jXypPPnty8X/58BbJ91yMKyAg==", - "timestamp": "2023-02-24T15:09:41.681034391Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "HQPxHUxDszRfeefEWSwn5FovRLwaMySeBgyv625gRteCMprVANIKV/GHowhhhvobJSSBkRxC9l6HScWF5PIsBA==", + "timestamp": "2023-02-27T07:13:09.69690345Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "D2A849200541C2098BE9FC8DDD71CC3C39D20BD01E586E5EBECBC3A0A3165D0A", + "hash": "F882C8C72A5E6656C5D53D2C40915588800262669295AEE82D8308CDE968F842", "parts": { - "hash": "1A9EF94D3335F90EC70ED282B781F342644881FC9FD58ECE346BFEBED2B05D7F", + "hash": "81A9B689C0E49AC0FC938B7F48DE1D8711FEA53B31401656DB499FE5443DCACE", "total": 1 } } @@ -751,18 +751,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "14", "last_block_id": { - "hash": "D2A849200541C2098BE9FC8DDD71CC3C39D20BD01E586E5EBECBC3A0A3165D0A", + "hash": "F882C8C72A5E6656C5D53D2C40915588800262669295AEE82D8308CDE968F842", "parts": { - "hash": "1A9EF94D3335F90EC70ED282B781F342644881FC9FD58ECE346BFEBED2B05D7F", + "hash": "81A9B689C0E49AC0FC938B7F48DE1D8711FEA53B31401656DB499FE5443DCACE", "total": 1 } }, - "last_commit_hash": "43DCD089D5DC227CFD77E1F241BCD926C36ABA0916081337573986FE8C6B1A97", + "last_commit_hash": "7464603E3DCBC1BE1DD8EFC40B0692C3EBA4F75BB81ABFECDCEC1A21A8186DB3", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:42.197919966Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:10.216100068Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -770,9 +770,9 @@ }, "last_commit": { "block_id": { - "hash": "D2A849200541C2098BE9FC8DDD71CC3C39D20BD01E586E5EBECBC3A0A3165D0A", + "hash": "F882C8C72A5E6656C5D53D2C40915588800262669295AEE82D8308CDE968F842", "parts": { - "hash": "1A9EF94D3335F90EC70ED282B781F342644881FC9FD58ECE346BFEBED2B05D7F", + "hash": "81A9B689C0E49AC0FC938B7F48DE1D8711FEA53B31401656DB499FE5443DCACE", "total": 1 } }, @@ -781,17 +781,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "R2e7N0xmmUqGVpuFFVMJFFSyTc8bU4+6/CWubsnWldzQkjeuzxn4HA2ThLjm37zA7gnx1w5yXUHs8obnmMgsBg==", - "timestamp": "2023-02-24T15:09:42.197919966Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "xXJpugvhH06QSmLzfRpH1LZjSHdCmc4pKNr9PUEqQ4A7ghioi69bw9GLDahHHmjjK6nS3l5Wir+K04wHxbbwAQ==", + "timestamp": "2023-02-27T07:13:10.216100068Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "5A1C50A51AEA032362DCA6C901EA88BD8C59B526A043F8EE7FCFBC695D5C0771", + "hash": "0CA458488C5924973E879C0B0133096EC3EC163A402BDA53683119C357EF04FC", "parts": { - "hash": "77B5D493AA74A559F60CEB90CBA0404850D017038EF8D5350C815EA9D6EC2CFF", + "hash": "08E4B121093A202180C70A3253181FF2C5DE7ABBC14CA06EE900DF6DF591E53A", "total": 1 } } @@ -812,18 +812,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "15", "last_block_id": { - "hash": "5A1C50A51AEA032362DCA6C901EA88BD8C59B526A043F8EE7FCFBC695D5C0771", + "hash": "0CA458488C5924973E879C0B0133096EC3EC163A402BDA53683119C357EF04FC", "parts": { - "hash": "77B5D493AA74A559F60CEB90CBA0404850D017038EF8D5350C815EA9D6EC2CFF", + "hash": "08E4B121093A202180C70A3253181FF2C5DE7ABBC14CA06EE900DF6DF591E53A", "total": 1 } }, - "last_commit_hash": "D2581E01B7A18A56E9AA343C59FDC529288DF78A90C17A0D2626515C38B94A19", + "last_commit_hash": "545D3D4B88F316206E79710FF0AB37747A444A783F178FB7ED8502459BC098AC", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:42.717219422Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:10.733698145Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -831,9 +831,9 @@ }, "last_commit": { "block_id": { - "hash": "5A1C50A51AEA032362DCA6C901EA88BD8C59B526A043F8EE7FCFBC695D5C0771", + "hash": "0CA458488C5924973E879C0B0133096EC3EC163A402BDA53683119C357EF04FC", "parts": { - "hash": "77B5D493AA74A559F60CEB90CBA0404850D017038EF8D5350C815EA9D6EC2CFF", + "hash": "08E4B121093A202180C70A3253181FF2C5DE7ABBC14CA06EE900DF6DF591E53A", "total": 1 } }, @@ -842,17 +842,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "NIkKM0RynRc+S68R8XLxQSURuyNTq3tlbKFrFEd2fnm6BXSqInaDWOO3bMEAtUxWfpfW4XlrSd0oKnYWQ516AA==", - "timestamp": "2023-02-24T15:09:42.717219422Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "0gYlNlne7LCIKQ1f955kvioJGvEM7R/SntOLgEIN6F2TvhTp6ye2aNu1ai9hm7kYo7BUM5mdzUf9GMzbmqRqDw==", + "timestamp": "2023-02-27T07:13:10.733698145Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "6B3DC1BFED5A035C1FF4F7E961FF4CD4D76691F80FE4E2FFC7F6FA5C6379F628", + "hash": "B1874B46DC158BBE8F036907C4D3C41E6D8F93890B6A17748584EB00004454B9", "parts": { - "hash": "6E8CE26D895B7855D4284CA40CE54883F667D8900362037CB2B8E68FF28F5A25", + "hash": "869D4CEDD32658192B51BD6250AF66F8DCE002463E979F8C4ED1EF1C92FA4715", "total": 1 } } @@ -873,18 +873,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "16", "last_block_id": { - "hash": "6B3DC1BFED5A035C1FF4F7E961FF4CD4D76691F80FE4E2FFC7F6FA5C6379F628", + "hash": "B1874B46DC158BBE8F036907C4D3C41E6D8F93890B6A17748584EB00004454B9", "parts": { - "hash": "6E8CE26D895B7855D4284CA40CE54883F667D8900362037CB2B8E68FF28F5A25", + "hash": "869D4CEDD32658192B51BD6250AF66F8DCE002463E979F8C4ED1EF1C92FA4715", "total": 1 } }, - "last_commit_hash": "F1359E50F69A3AB3EE3C67F5C96949C2FB6253BEB84D4371B28AFF29E0577D31", + "last_commit_hash": "5FA881010BFCD1A31776F740D4E67E0C13D4D02FCF9ECE328B4CFC6EC527B435", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:43.23356283Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:11.253510665Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -892,9 +892,9 @@ }, "last_commit": { "block_id": { - "hash": "6B3DC1BFED5A035C1FF4F7E961FF4CD4D76691F80FE4E2FFC7F6FA5C6379F628", + "hash": "B1874B46DC158BBE8F036907C4D3C41E6D8F93890B6A17748584EB00004454B9", "parts": { - "hash": "6E8CE26D895B7855D4284CA40CE54883F667D8900362037CB2B8E68FF28F5A25", + "hash": "869D4CEDD32658192B51BD6250AF66F8DCE002463E979F8C4ED1EF1C92FA4715", "total": 1 } }, @@ -903,17 +903,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "WsMS4UPyn/vuCBxC1KLn6qE0qtD4UXxRFVZe/96gb3L2ofxion5IRgZreYalWL0bO/DPmkJ7h123K1Sg7adRBQ==", - "timestamp": "2023-02-24T15:09:43.23356283Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "4MyfaPJqTm/7xWzK9Mw0cSO2S3jqJ9kuWTnjVq9ijLnjEy3p8cWUPBsN5X/Lso0QjluucXgbXVLb2IwU9Lp2Aw==", + "timestamp": "2023-02-27T07:13:11.253510665Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "105B21A7A19EA9C985D7183DC064DF26865C9AB3996F658769935BEDEA0731F8", + "hash": "FA0C794B970417EF8571B92598F985B35ACE451489A1C6723327B38BC4E2ABFA", "parts": { - "hash": "D05E710BE17FF05DF587F447CEF48C309ED37200BF094BAD08A5B1075EF717B7", + "hash": "57EF53E1A703990AE79FAD55D1B40B98FE230BFE247230F2985E7851D99FB86B", "total": 1 } } @@ -934,18 +934,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "17", "last_block_id": { - "hash": "105B21A7A19EA9C985D7183DC064DF26865C9AB3996F658769935BEDEA0731F8", + "hash": "FA0C794B970417EF8571B92598F985B35ACE451489A1C6723327B38BC4E2ABFA", "parts": { - "hash": "D05E710BE17FF05DF587F447CEF48C309ED37200BF094BAD08A5B1075EF717B7", + "hash": "57EF53E1A703990AE79FAD55D1B40B98FE230BFE247230F2985E7851D99FB86B", "total": 1 } }, - "last_commit_hash": "2B1A55AEA195E64774202C36C107C9ABAB85A9D145090A8DE6EC6969D423C020", + "last_commit_hash": "DC79D7766DFC0184E47DBF721FF7D65C3180EF453820E095553E44DB48E8F03E", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:43.75150372Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:11.772048383Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -953,9 +953,9 @@ }, "last_commit": { "block_id": { - "hash": "105B21A7A19EA9C985D7183DC064DF26865C9AB3996F658769935BEDEA0731F8", + "hash": "FA0C794B970417EF8571B92598F985B35ACE451489A1C6723327B38BC4E2ABFA", "parts": { - "hash": "D05E710BE17FF05DF587F447CEF48C309ED37200BF094BAD08A5B1075EF717B7", + "hash": "57EF53E1A703990AE79FAD55D1B40B98FE230BFE247230F2985E7851D99FB86B", "total": 1 } }, @@ -964,17 +964,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "udQiCxsqQeJ3U89Z2e0RM86OgeNt+pDxy5N0i1n3Wpa5Ik5dqVYAhxcSCfcFMW6AEbJyvg4VoqzR79X7IZsQCw==", - "timestamp": "2023-02-24T15:09:43.75150372Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "kd81f5ePpxFfoj8dQNmXR4iNfP27LpvUkY84iC9SzoeYfSOLm78PgrCv1KQ87Od2JF3iTKtmqJ1CDu+6PXFyBw==", + "timestamp": "2023-02-27T07:13:11.772048383Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "0773E4FD7C13BA8A6E6AB2A90C0E1F7830232F23DEDB415A6D2B7146D20554F4", + "hash": "50BF72F2ABA6F724BCF775B4E4BC2221F0EF5F48678B67324D19A1E5A1C9AB6F", "parts": { - "hash": "6323199FC03237192A2EB4D3C2EBC3CC43F47750CFFF8CAB19362F0D8614DD2A", + "hash": "5ACF51411D81C8B286CD61D87F3A42C3BF0DA7DE664683CB058B28B5CA4A188D", "total": 1 } } @@ -995,18 +995,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "18", "last_block_id": { - "hash": "0773E4FD7C13BA8A6E6AB2A90C0E1F7830232F23DEDB415A6D2B7146D20554F4", + "hash": "50BF72F2ABA6F724BCF775B4E4BC2221F0EF5F48678B67324D19A1E5A1C9AB6F", "parts": { - "hash": "6323199FC03237192A2EB4D3C2EBC3CC43F47750CFFF8CAB19362F0D8614DD2A", + "hash": "5ACF51411D81C8B286CD61D87F3A42C3BF0DA7DE664683CB058B28B5CA4A188D", "total": 1 } }, - "last_commit_hash": "0BF662A790AF94F89021D9BE35F9F761D1356BCCEEB32BCD4349B8F707ADDB74", + "last_commit_hash": "4AC0F9D7369D83FA51520C6A550295F4A5EEA7E5727E8126C9482940C6FE5111", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:44.268716621Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:12.292293252Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1014,9 +1014,9 @@ }, "last_commit": { "block_id": { - "hash": "0773E4FD7C13BA8A6E6AB2A90C0E1F7830232F23DEDB415A6D2B7146D20554F4", + "hash": "50BF72F2ABA6F724BCF775B4E4BC2221F0EF5F48678B67324D19A1E5A1C9AB6F", "parts": { - "hash": "6323199FC03237192A2EB4D3C2EBC3CC43F47750CFFF8CAB19362F0D8614DD2A", + "hash": "5ACF51411D81C8B286CD61D87F3A42C3BF0DA7DE664683CB058B28B5CA4A188D", "total": 1 } }, @@ -1025,17 +1025,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "hN5R5V5rRru5xa4C8V+L6g6DWM9IEFhd75xX7FKYjpWpP+8KumKqljlxFpcoOmFiy1Kp0MwSVH9kkPpE0VPIBw==", - "timestamp": "2023-02-24T15:09:44.268716621Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "u8DKvXrbZGBULm4HOtffluaTwOAiG6/tWmgEoN851xF3mi1+vR9W3noubU80wp9DP55F5DtLKi6vg+6a4KqHAw==", + "timestamp": "2023-02-27T07:13:12.292293252Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "B443CE1F79ABE95B2A8D75BE4E098FA22001CDC5473E5AC2A08CA10EFB25AD27", + "hash": "8A00A66D9AC8BE49BCDA0B90587D3347111AF3CD255A5CEEE579B5BA4FCB189A", "parts": { - "hash": "D9F8AD4E23D035F7074DA593A0B21A12DDB20266436393BA70377782822D38BE", + "hash": "D5D7DAECB8F5FE498DBB4D4EC492470A0B3044FEA1C5FF3A5A3833F994AB8D37", "total": 1 } } @@ -1056,18 +1056,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "19", "last_block_id": { - "hash": "B443CE1F79ABE95B2A8D75BE4E098FA22001CDC5473E5AC2A08CA10EFB25AD27", + "hash": "8A00A66D9AC8BE49BCDA0B90587D3347111AF3CD255A5CEEE579B5BA4FCB189A", "parts": { - "hash": "D9F8AD4E23D035F7074DA593A0B21A12DDB20266436393BA70377782822D38BE", + "hash": "D5D7DAECB8F5FE498DBB4D4EC492470A0B3044FEA1C5FF3A5A3833F994AB8D37", "total": 1 } }, - "last_commit_hash": "9E263405AB365CA26036A8FE0BE4BF12C2194C84C50C409B2D961AA23292F247", + "last_commit_hash": "0B455D91296AA7790A6BFF5F78D75429483240511B52D97D85C0E2CDF902E505", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:44.790264757Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:12.811155987Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1075,9 +1075,9 @@ }, "last_commit": { "block_id": { - "hash": "B443CE1F79ABE95B2A8D75BE4E098FA22001CDC5473E5AC2A08CA10EFB25AD27", + "hash": "8A00A66D9AC8BE49BCDA0B90587D3347111AF3CD255A5CEEE579B5BA4FCB189A", "parts": { - "hash": "D9F8AD4E23D035F7074DA593A0B21A12DDB20266436393BA70377782822D38BE", + "hash": "D5D7DAECB8F5FE498DBB4D4EC492470A0B3044FEA1C5FF3A5A3833F994AB8D37", "total": 1 } }, @@ -1086,17 +1086,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "v5T2UVvpVNg4+HRVdTWjzYzEVpO7XkosJqT1HuXJV6QHuFSz5dlkpvlzMKLAbjQ2Jvt4/8q429Mjt679CWS2DA==", - "timestamp": "2023-02-24T15:09:44.790264757Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "1m1Atw77VtN46HCNtGYbZJ23Kw/NAEQaaW+QEjXoAEtiMK0cOw93nWTFROhSlsqdoB3r0lBf3dSGcFM1byD0CQ==", + "timestamp": "2023-02-27T07:13:12.811155987Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "B236DD786A3DE401D0D11E4175F7047E8676F6D9DB0F20B7D989E7733D64D8D3", + "hash": "CEF00B2DEB42D92DDAF40102A661C8FB6AFEF651197083563C1EEDAA4180E3ED", "parts": { - "hash": "E3045E7505869EA24E95F37D6ECF32AA46C6922CE697403739AAE85DE5BD1EAC", + "hash": "863AD4FF2F1FCC04E8289C5DC8B4B6DA50B097D887E9301FD1937390706A868F", "total": 1 } } @@ -1117,18 +1117,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "20", "last_block_id": { - "hash": "B236DD786A3DE401D0D11E4175F7047E8676F6D9DB0F20B7D989E7733D64D8D3", + "hash": "CEF00B2DEB42D92DDAF40102A661C8FB6AFEF651197083563C1EEDAA4180E3ED", "parts": { - "hash": "E3045E7505869EA24E95F37D6ECF32AA46C6922CE697403739AAE85DE5BD1EAC", + "hash": "863AD4FF2F1FCC04E8289C5DC8B4B6DA50B097D887E9301FD1937390706A868F", "total": 1 } }, - "last_commit_hash": "A1B124868735F1A193E266DB8B8F4ECDC6DB09C6D72910A531499B6AFC8D00BF", + "last_commit_hash": "C6687D1B3AB5DF780BF7DC42F0248D06CFD116DA97F1D21C10FE112334DC6377", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:45.310831215Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:13.330709592Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1136,9 +1136,9 @@ }, "last_commit": { "block_id": { - "hash": "B236DD786A3DE401D0D11E4175F7047E8676F6D9DB0F20B7D989E7733D64D8D3", + "hash": "CEF00B2DEB42D92DDAF40102A661C8FB6AFEF651197083563C1EEDAA4180E3ED", "parts": { - "hash": "E3045E7505869EA24E95F37D6ECF32AA46C6922CE697403739AAE85DE5BD1EAC", + "hash": "863AD4FF2F1FCC04E8289C5DC8B4B6DA50B097D887E9301FD1937390706A868F", "total": 1 } }, @@ -1147,17 +1147,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "8YBkchV3YkBIs27As5D3/pfqyi4M6OOoknokof28n7PxWG1eNgYPDvu4yqpAH9BiVm1QUDSNLhPixUkJmHIdBg==", - "timestamp": "2023-02-24T15:09:45.310831215Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "bnH5D+wDGZJkYDgil9MI0sgf5An2LgP7oK12Xqx530bPG1YHKnS4FTG9ZHX7TBult2zjixDvjjSTLmAcIvpWDA==", + "timestamp": "2023-02-27T07:13:13.330709592Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "7C89853BC86B9B866CC3544AF99876718D3C18F8CE79A5EC4BD2E9A0EA0ED2B0", + "hash": "2634DD91BA534C06FC1D2F7C8A28D47D23809A8AC8FBEC36BB97F9C25ED0B84E", "parts": { - "hash": "ECC19F719AA76C644F6C059AEF092788591D0A391090EB7CE8DBDF1305007872", + "hash": "2EE8FC2C3697C270058987C042E541B4FADCF2814D1613D5AF5A12F5D9F4CF57", "total": 1 } } @@ -1178,18 +1178,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "21", "last_block_id": { - "hash": "7C89853BC86B9B866CC3544AF99876718D3C18F8CE79A5EC4BD2E9A0EA0ED2B0", + "hash": "2634DD91BA534C06FC1D2F7C8A28D47D23809A8AC8FBEC36BB97F9C25ED0B84E", "parts": { - "hash": "ECC19F719AA76C644F6C059AEF092788591D0A391090EB7CE8DBDF1305007872", + "hash": "2EE8FC2C3697C270058987C042E541B4FADCF2814D1613D5AF5A12F5D9F4CF57", "total": 1 } }, - "last_commit_hash": "147F50B634C3F16B4D901D6A1CA0F04EB389555169BF3A09895D3D9DD0CE3DD3", + "last_commit_hash": "0E4FB3AB7E747FAB94B8A8CF48AEBE8A595792275F1078C3C9151660DE58F184", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:45.829978265Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:13.84781205Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1197,9 +1197,9 @@ }, "last_commit": { "block_id": { - "hash": "7C89853BC86B9B866CC3544AF99876718D3C18F8CE79A5EC4BD2E9A0EA0ED2B0", + "hash": "2634DD91BA534C06FC1D2F7C8A28D47D23809A8AC8FBEC36BB97F9C25ED0B84E", "parts": { - "hash": "ECC19F719AA76C644F6C059AEF092788591D0A391090EB7CE8DBDF1305007872", + "hash": "2EE8FC2C3697C270058987C042E541B4FADCF2814D1613D5AF5A12F5D9F4CF57", "total": 1 } }, @@ -1208,17 +1208,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "HgRnoRe2U6lRj9LAHjGozj8ncT2nUfrdqbJW/RE72TBnKM4xjonYVuLdckQaD6rvlH8tHqB2QId0V8z1ltX3Dg==", - "timestamp": "2023-02-24T15:09:45.829978265Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "TvQbxCI6cQUgj3PCayXyjQBxNn2En8l28tpbvbTGRQ5CcTkzJou4Z8gfvjGRV+VTfLfm8To+jv0cLP7d4VCwBQ==", + "timestamp": "2023-02-27T07:13:13.84781205Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "9FF25957F2AA46C7A06519462CF791AF27F6AEE491040F3A5D4296CBB1494950", + "hash": "EC16F423E1BDCAF735D57DF3228AFC4C4809EABB0DDCC5C5A5620F92E10C875B", "parts": { - "hash": "338148ACCCAAC648F493797141D9834A22EC14656A83C1AB3EE34E2EBD420AC3", + "hash": "A2BA8E783EE4BC0CC7A6A0B26136EFA055ECA37C6FB3B2BB582169B7BB9EC842", "total": 1 } } @@ -1239,18 +1239,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "22", "last_block_id": { - "hash": "9FF25957F2AA46C7A06519462CF791AF27F6AEE491040F3A5D4296CBB1494950", + "hash": "EC16F423E1BDCAF735D57DF3228AFC4C4809EABB0DDCC5C5A5620F92E10C875B", "parts": { - "hash": "338148ACCCAAC648F493797141D9834A22EC14656A83C1AB3EE34E2EBD420AC3", + "hash": "A2BA8E783EE4BC0CC7A6A0B26136EFA055ECA37C6FB3B2BB582169B7BB9EC842", "total": 1 } }, - "last_commit_hash": "D73F54CCD86AE60933DF8DD4AEAC6815564954BD486E342560E93E6AE42639B9", + "last_commit_hash": "77B2354E5AEC2D118E522FB017C7827D7A52AA6F8B32AE0A46CA389F1B90380A", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:46.34697564Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:14.367045487Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1258,9 +1258,9 @@ }, "last_commit": { "block_id": { - "hash": "9FF25957F2AA46C7A06519462CF791AF27F6AEE491040F3A5D4296CBB1494950", + "hash": "EC16F423E1BDCAF735D57DF3228AFC4C4809EABB0DDCC5C5A5620F92E10C875B", "parts": { - "hash": "338148ACCCAAC648F493797141D9834A22EC14656A83C1AB3EE34E2EBD420AC3", + "hash": "A2BA8E783EE4BC0CC7A6A0B26136EFA055ECA37C6FB3B2BB582169B7BB9EC842", "total": 1 } }, @@ -1269,17 +1269,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "lt9PUqM3uqIwG/mX4r5fRSt75P4fsX4gQXYFBJrLkdxRVn7VxPYGGBAVeNlpoGFC+yCagfW14xrx/EZT9CwvDQ==", - "timestamp": "2023-02-24T15:09:46.34697564Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "XTAJHuY8fqbTnJD0/QwR8E6528bQrY8NuZIJWMlagfOLX5ia/sdyhQMG+oXrpNFSJRREK44SkoViBA910gG/Dg==", + "timestamp": "2023-02-27T07:13:14.367045487Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "F71158D636F640E2F2EB4C46E471EFFD41FC2B430009D589FB0C3EB4BC177A5A", + "hash": "AA1C5F527207807EB5709FAB6BD2FF8FF34B81B4BB763F7C2720F349E5DA3A6F", "parts": { - "hash": "D31D9380F1941E7D94A97EC8D87EF7DC841AD7B9A2FAA82CCFB846D4CAF67CF0", + "hash": "71E731D91E384197F4744B7EE142DFD57820934EED592E4232A7C4482F00C1E9", "total": 1 } } @@ -1300,18 +1300,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "23", "last_block_id": { - "hash": "F71158D636F640E2F2EB4C46E471EFFD41FC2B430009D589FB0C3EB4BC177A5A", + "hash": "AA1C5F527207807EB5709FAB6BD2FF8FF34B81B4BB763F7C2720F349E5DA3A6F", "parts": { - "hash": "D31D9380F1941E7D94A97EC8D87EF7DC841AD7B9A2FAA82CCFB846D4CAF67CF0", + "hash": "71E731D91E384197F4744B7EE142DFD57820934EED592E4232A7C4482F00C1E9", "total": 1 } }, - "last_commit_hash": "0F3AFD99E60F5D4E218FF1C335453AFD80B574FFF4393881A9D3ECE3E57880F2", + "last_commit_hash": "7641A010A1A7AF124EE75C362487648AF979F7B0F79443C38348A3F1FB6903CA", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:46.865219137Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:14.883931989Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1319,9 +1319,9 @@ }, "last_commit": { "block_id": { - "hash": "F71158D636F640E2F2EB4C46E471EFFD41FC2B430009D589FB0C3EB4BC177A5A", + "hash": "AA1C5F527207807EB5709FAB6BD2FF8FF34B81B4BB763F7C2720F349E5DA3A6F", "parts": { - "hash": "D31D9380F1941E7D94A97EC8D87EF7DC841AD7B9A2FAA82CCFB846D4CAF67CF0", + "hash": "71E731D91E384197F4744B7EE142DFD57820934EED592E4232A7C4482F00C1E9", "total": 1 } }, @@ -1330,17 +1330,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "A0hu5vJS3tK0tyYF17tR7IPJ3BKwVjZS4UfXmz0Dkn7T7+XfjGLc1BB1g2JQnk8pvl8Vl5/S0WKOE4bHPKfVCA==", - "timestamp": "2023-02-24T15:09:46.865219137Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "j8+WpHt31HBcLW7eTvC7Utbsym5Rw0IIE7kqpEO4kPrpbLf76Gpa//IqrYU6Lli2S7YZYQUM96xu3Y5OCXWGAg==", + "timestamp": "2023-02-27T07:13:14.883931989Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "17DAECBE0F3CE63F6AEDD260463839E00EFF39A0C09BA4F86E238A2F9FDB7DF2", + "hash": "221E1A298F3673BBACF9C253D3D86458FFF33C2C04EF054DA6BEAD66A7F1F507", "parts": { - "hash": "5205D9AD8338ADF3FA04195C9481F87D4997C4DF504E14B44735414E6E80ADAA", + "hash": "45C107FA7763BF3E639E5281C0313D0AB96E17C57F538439775FBF2AA4DB4C97", "total": 1 } } @@ -1361,18 +1361,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "24", "last_block_id": { - "hash": "17DAECBE0F3CE63F6AEDD260463839E00EFF39A0C09BA4F86E238A2F9FDB7DF2", + "hash": "221E1A298F3673BBACF9C253D3D86458FFF33C2C04EF054DA6BEAD66A7F1F507", "parts": { - "hash": "5205D9AD8338ADF3FA04195C9481F87D4997C4DF504E14B44735414E6E80ADAA", + "hash": "45C107FA7763BF3E639E5281C0313D0AB96E17C57F538439775FBF2AA4DB4C97", "total": 1 } }, - "last_commit_hash": "AC71D8B0567DCB417D05F98721D0A19CD9C0E6A584CB818FEAEC5EF235979F71", + "last_commit_hash": "E5E10E13CECB5BFDA5E8EE9DC216742D01225296FD26BCD730BCD9604248B537", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:47.385204611Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:15.400851421Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1380,9 +1380,9 @@ }, "last_commit": { "block_id": { - "hash": "17DAECBE0F3CE63F6AEDD260463839E00EFF39A0C09BA4F86E238A2F9FDB7DF2", + "hash": "221E1A298F3673BBACF9C253D3D86458FFF33C2C04EF054DA6BEAD66A7F1F507", "parts": { - "hash": "5205D9AD8338ADF3FA04195C9481F87D4997C4DF504E14B44735414E6E80ADAA", + "hash": "45C107FA7763BF3E639E5281C0313D0AB96E17C57F538439775FBF2AA4DB4C97", "total": 1 } }, @@ -1391,17 +1391,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "7Fb16J97ZRfzdUMVJYx3Y9xOPszXNcHmhyjsqDXebJlA9yvEZhdGwWT4m6locO5GywP2g8muuxCkosEZ7wVDBw==", - "timestamp": "2023-02-24T15:09:47.385204611Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "VGTRKh5UWC6ZFwCIB9mQU+Jr13cuCWi98C2aqvfMmOZe7EsxAQO1gkOPBa5pDaPTi/QE4F4fhQbDnxVCecNKAg==", + "timestamp": "2023-02-27T07:13:15.400851421Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "1A363F2CBA0C7CE46EC21B0E089F24922487E9353571BF7BF15C45D8B9F35899", + "hash": "5375D153345342F2C89C28956D49552DAC8383E431E43D1ABDBA851C823C3FFF", "parts": { - "hash": "C438BD76FCA7AF54E479ADF8C6C7B7C41DA9C86758AD26A661CBCBA38F5CAE2D", + "hash": "4082B761350D2AEB86C4060E25C43202586C0134C74A70AB386A70A3E31264EF", "total": 1 } } @@ -1422,18 +1422,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "25", "last_block_id": { - "hash": "1A363F2CBA0C7CE46EC21B0E089F24922487E9353571BF7BF15C45D8B9F35899", + "hash": "5375D153345342F2C89C28956D49552DAC8383E431E43D1ABDBA851C823C3FFF", "parts": { - "hash": "C438BD76FCA7AF54E479ADF8C6C7B7C41DA9C86758AD26A661CBCBA38F5CAE2D", + "hash": "4082B761350D2AEB86C4060E25C43202586C0134C74A70AB386A70A3E31264EF", "total": 1 } }, - "last_commit_hash": "EF5559062008C6061D569FE460A5EE543D5A7172E1E9D255D8D19283546BA6CA", + "last_commit_hash": "724CD0C3D5132EF8DD2FA841F802544D4360378345976AB7EB5131821ED8FD0B", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:47.905699456Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:15.91961831Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1441,9 +1441,9 @@ }, "last_commit": { "block_id": { - "hash": "1A363F2CBA0C7CE46EC21B0E089F24922487E9353571BF7BF15C45D8B9F35899", + "hash": "5375D153345342F2C89C28956D49552DAC8383E431E43D1ABDBA851C823C3FFF", "parts": { - "hash": "C438BD76FCA7AF54E479ADF8C6C7B7C41DA9C86758AD26A661CBCBA38F5CAE2D", + "hash": "4082B761350D2AEB86C4060E25C43202586C0134C74A70AB386A70A3E31264EF", "total": 1 } }, @@ -1452,17 +1452,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "jRrS7ZS3rJD9y/EUeoGIQqIyC70Sy1fpbox6hGCwsrUZ53LyqD+s5O1fKlfwfTzk/p5MT2dJvLW2+eGJmXeCCQ==", - "timestamp": "2023-02-24T15:09:47.905699456Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "bntLcLPd35sdA/Pw7mAOrm3yh55Sfb5D1VV/CljoVF/qKmJ6pdLduE1ola6yuWThd1Q9qq/QDikj5Ytjt15fAQ==", + "timestamp": "2023-02-27T07:13:15.91961831Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "E649CD1349CB3D968E147A1B7A9711073265336E67EF05467358DCAC9E498417", + "hash": "21AD6D7033246D7B6CFA05FFDE19D4DF6A1C9FB9E090697B2993E4D59509EA46", "parts": { - "hash": "06A2D43F265C0235D44D84E0B6CE2C9B4D7652051CB105C15225E9463F8BCD32", + "hash": "0E1EDD0BC691BAA08751E4BEC83498724FDFB43E756FCB2D29139095C6B94D34", "total": 1 } } @@ -1483,18 +1483,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "26", "last_block_id": { - "hash": "E649CD1349CB3D968E147A1B7A9711073265336E67EF05467358DCAC9E498417", + "hash": "21AD6D7033246D7B6CFA05FFDE19D4DF6A1C9FB9E090697B2993E4D59509EA46", "parts": { - "hash": "06A2D43F265C0235D44D84E0B6CE2C9B4D7652051CB105C15225E9463F8BCD32", + "hash": "0E1EDD0BC691BAA08751E4BEC83498724FDFB43E756FCB2D29139095C6B94D34", "total": 1 } }, - "last_commit_hash": "E641E72B4D83E9041D00CF63E26FD69038C4F1EF0DBCCF1882D91E0C8024F34D", + "last_commit_hash": "C47978AE0D65FD44E94D09883E1C05138AC1BA66340F693FC29F74F8C105BFE8", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:48.422959333Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:16.438813001Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1502,9 +1502,9 @@ }, "last_commit": { "block_id": { - "hash": "E649CD1349CB3D968E147A1B7A9711073265336E67EF05467358DCAC9E498417", + "hash": "21AD6D7033246D7B6CFA05FFDE19D4DF6A1C9FB9E090697B2993E4D59509EA46", "parts": { - "hash": "06A2D43F265C0235D44D84E0B6CE2C9B4D7652051CB105C15225E9463F8BCD32", + "hash": "0E1EDD0BC691BAA08751E4BEC83498724FDFB43E756FCB2D29139095C6B94D34", "total": 1 } }, @@ -1513,17 +1513,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "uTJsjYFHBZHke3jAHGSTGFPkmdcMdMuopNNLd0XKWKqetn0dJWHJxsHRaaYog3AuPh7be/dGEm1dZ+duU31SCw==", - "timestamp": "2023-02-24T15:09:48.422959333Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "pxB5d8q+mDQF+AhHY4q6RwGUNsCZCkm6FWmCkLXfNQkd6MjnXTSBVdW8LTUGI0DXJzur7rtJ7+Ot5BeM4oemCw==", + "timestamp": "2023-02-27T07:13:16.438813001Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "EFEF9D1BE75E14BDF5A8297770332E0A89042CE55F7AEF6F0E015CD1FEB32F00", + "hash": "C397C5FCB0D02489BF9CF73CA2CB70F5B86D3EC6EF492D5D51765243FE41DEDC", "parts": { - "hash": "BD83A062FFEBB895ECA77BC63056F5141874CAE7200E0CEAEE86C95B83A85417", + "hash": "36196006C0636E4B205A5BDFDF5C1FA67A7E4B36FE278C3A73D3ED0314CB6673", "total": 1 } } @@ -1544,18 +1544,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "27", "last_block_id": { - "hash": "EFEF9D1BE75E14BDF5A8297770332E0A89042CE55F7AEF6F0E015CD1FEB32F00", + "hash": "C397C5FCB0D02489BF9CF73CA2CB70F5B86D3EC6EF492D5D51765243FE41DEDC", "parts": { - "hash": "BD83A062FFEBB895ECA77BC63056F5141874CAE7200E0CEAEE86C95B83A85417", + "hash": "36196006C0636E4B205A5BDFDF5C1FA67A7E4B36FE278C3A73D3ED0314CB6673", "total": 1 } }, - "last_commit_hash": "C14E43C1ED7AA86DD61EF7000EB7551CF518915857CF9BEA3E99C15B1EEF9978", + "last_commit_hash": "74315BD12E76A7790F3CEFCF3F7CFC0E4CE67C59F1BFAFFED428E56AA08CEE35", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:48.940870986Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:16.955412315Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1563,9 +1563,9 @@ }, "last_commit": { "block_id": { - "hash": "EFEF9D1BE75E14BDF5A8297770332E0A89042CE55F7AEF6F0E015CD1FEB32F00", + "hash": "C397C5FCB0D02489BF9CF73CA2CB70F5B86D3EC6EF492D5D51765243FE41DEDC", "parts": { - "hash": "BD83A062FFEBB895ECA77BC63056F5141874CAE7200E0CEAEE86C95B83A85417", + "hash": "36196006C0636E4B205A5BDFDF5C1FA67A7E4B36FE278C3A73D3ED0314CB6673", "total": 1 } }, @@ -1574,17 +1574,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "hfWavhAYBm7ZGcNZXIdJi6rzn+KSmLZgbtkA3unnFPKwkZ6s2RjWVc8aLmOymA8FDt8CYu9v0wGUE77/T992AQ==", - "timestamp": "2023-02-24T15:09:48.940870986Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "P4wVGRmrhGWxxNNXtIa/L+jYSkwlu4biRLSR8v3m+se+PP1J7NE1JfVV0E85SsWTkPO6MJi1GQKF0RNrPqUBBQ==", + "timestamp": "2023-02-27T07:13:16.955412315Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "12BC4D20F1B9D7FA0741F9DFFC390553B27EAD7180A5B138F0E7B4F791327EFC", + "hash": "A997EB5E71BA3605FFB2916D4025095F67E84064BC81FADD6EA818889DDC4C8B", "parts": { - "hash": "9781684D4B2F707006A52015605DB5A7723CA2E87739B30BA76A9C755E39D98E", + "hash": "62D6554CEFF8B6ECCA27022E7450768BFCB39CDADE3FB56C20334BFFE0E614A5", "total": 1 } } @@ -1605,18 +1605,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "28", "last_block_id": { - "hash": "12BC4D20F1B9D7FA0741F9DFFC390553B27EAD7180A5B138F0E7B4F791327EFC", + "hash": "A997EB5E71BA3605FFB2916D4025095F67E84064BC81FADD6EA818889DDC4C8B", "parts": { - "hash": "9781684D4B2F707006A52015605DB5A7723CA2E87739B30BA76A9C755E39D98E", + "hash": "62D6554CEFF8B6ECCA27022E7450768BFCB39CDADE3FB56C20334BFFE0E614A5", "total": 1 } }, - "last_commit_hash": "C1EE26645F9274D8C1124A1863BA05950D6B30B322CB37E5E574622DE60DCDC0", + "last_commit_hash": "622D840007961BD6135BA325A99B52C19108394AFE693E9F6DC3E64B7847DA37", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:49.457911779Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:17.473702171Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1624,9 +1624,9 @@ }, "last_commit": { "block_id": { - "hash": "12BC4D20F1B9D7FA0741F9DFFC390553B27EAD7180A5B138F0E7B4F791327EFC", + "hash": "A997EB5E71BA3605FFB2916D4025095F67E84064BC81FADD6EA818889DDC4C8B", "parts": { - "hash": "9781684D4B2F707006A52015605DB5A7723CA2E87739B30BA76A9C755E39D98E", + "hash": "62D6554CEFF8B6ECCA27022E7450768BFCB39CDADE3FB56C20334BFFE0E614A5", "total": 1 } }, @@ -1635,17 +1635,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "mm1nOQBU+TXzb2pX9Zvf3d/1ewXZnoOWmdu+SXzdcDtjvUxGbThVHwDd5PHKPwNdvR60p3zvYeCbpW6gUHSpAA==", - "timestamp": "2023-02-24T15:09:49.457911779Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "NE0Ps+1vBgXAWiOx2EVDIOoLhcx2pfpmUEEQ4h5XlLd+7cgvqtCF1ipCF7uEj/iWusMUaP2TU7IEUlXKxVEBBA==", + "timestamp": "2023-02-27T07:13:17.473702171Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "75E9C485C60DD6F950888E8BF214591AF4883F830FCA3E47CCC5AEC14CDEC731", + "hash": "332ADA488F8802C730A28D7E69FA88A8E20FD11F76C113A54C7834E4B1772F0E", "parts": { - "hash": "02BD1D5BD119AFC3C3FA12466BDEEA67B512A42B88BF9E98C80FBBE6A6CDA379", + "hash": "D61089F0DD5EEFFB84AC4FBEB2E61118754171B45D9DADF425A0BC94704531EE", "total": 1 } } @@ -1666,18 +1666,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "29", "last_block_id": { - "hash": "75E9C485C60DD6F950888E8BF214591AF4883F830FCA3E47CCC5AEC14CDEC731", + "hash": "332ADA488F8802C730A28D7E69FA88A8E20FD11F76C113A54C7834E4B1772F0E", "parts": { - "hash": "02BD1D5BD119AFC3C3FA12466BDEEA67B512A42B88BF9E98C80FBBE6A6CDA379", + "hash": "D61089F0DD5EEFFB84AC4FBEB2E61118754171B45D9DADF425A0BC94704531EE", "total": 1 } }, - "last_commit_hash": "2792A5F3CAEC5C55789EC49BCCD2882E7A49830979B42A80A7EF9349D3930A03", + "last_commit_hash": "C8BA6653CADB5C952818F5C5ED14ABD0AF7BEE8114D30870CFC05BBAADE668B8", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:49.977943197Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:17.99240594Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1685,9 +1685,9 @@ }, "last_commit": { "block_id": { - "hash": "75E9C485C60DD6F950888E8BF214591AF4883F830FCA3E47CCC5AEC14CDEC731", + "hash": "332ADA488F8802C730A28D7E69FA88A8E20FD11F76C113A54C7834E4B1772F0E", "parts": { - "hash": "02BD1D5BD119AFC3C3FA12466BDEEA67B512A42B88BF9E98C80FBBE6A6CDA379", + "hash": "D61089F0DD5EEFFB84AC4FBEB2E61118754171B45D9DADF425A0BC94704531EE", "total": 1 } }, @@ -1696,17 +1696,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "/LX/RZcfb8CAUwsiwO8xKKtduXVaOhX9GW2lEmrC0HuzCG0b1b5ElDr4R7+egNZBcr4AEGiGgE/ti3kvjXrxDg==", - "timestamp": "2023-02-24T15:09:49.977943197Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "RETPQXHWK4g8F9CjcZnz6uvvj41fkC8rCa4VZJbnF5PK2IAl/ZfhfG3XgrxM7/JqUJlXpavDcb3DrIV4KXz6Dw==", + "timestamp": "2023-02-27T07:13:17.99240594Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "9E053F4193763F3D1229D427D2109ABF29AFBFCA58C71279C0EF510B807866A3", + "hash": "4D02C7180E617EFD1A3B266ED68A6E97A9B79BAD86118D40A0701398759F3B2F", "parts": { - "hash": "08B358112F01781DBD89FD2EDE6E485A8B175BB5F7CB39BDE8D3AC369D1E9DFC", + "hash": "2654E6F0B0B7C8F067042A19C5EA85EBC2EC5BBBB1DE0137B78EAF6AC8B86A80", "total": 1 } } @@ -1727,18 +1727,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "30", "last_block_id": { - "hash": "9E053F4193763F3D1229D427D2109ABF29AFBFCA58C71279C0EF510B807866A3", + "hash": "4D02C7180E617EFD1A3B266ED68A6E97A9B79BAD86118D40A0701398759F3B2F", "parts": { - "hash": "08B358112F01781DBD89FD2EDE6E485A8B175BB5F7CB39BDE8D3AC369D1E9DFC", + "hash": "2654E6F0B0B7C8F067042A19C5EA85EBC2EC5BBBB1DE0137B78EAF6AC8B86A80", "total": 1 } }, - "last_commit_hash": "9B8F1998102BFD8EC2BE211E241D7F737EB6D46FA0DDBC80832564512C41480A", + "last_commit_hash": "8CE039485C6EBC7D0E35B42960EC9713768A87ADDD923849CD24C7CD358BA2C8", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:50.495537773Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:18.508531314Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1746,9 +1746,9 @@ }, "last_commit": { "block_id": { - "hash": "9E053F4193763F3D1229D427D2109ABF29AFBFCA58C71279C0EF510B807866A3", + "hash": "4D02C7180E617EFD1A3B266ED68A6E97A9B79BAD86118D40A0701398759F3B2F", "parts": { - "hash": "08B358112F01781DBD89FD2EDE6E485A8B175BB5F7CB39BDE8D3AC369D1E9DFC", + "hash": "2654E6F0B0B7C8F067042A19C5EA85EBC2EC5BBBB1DE0137B78EAF6AC8B86A80", "total": 1 } }, @@ -1757,17 +1757,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "h99svjsWfKynfm58Kczz7/q2IjBhGT0El36i52iaZ5Y1+VweK2MxCurBUvTo/bmCdE84hWe4/vLcdnEgw+RNDg==", - "timestamp": "2023-02-24T15:09:50.495537773Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "5L5B8U8HPUWInJTd2meNt8Y6HjPdai8d0WuSQF17UpGhNI+T9NmZWGmmpIYR6DgMxBor5p3friMhU41stRisAw==", + "timestamp": "2023-02-27T07:13:18.508531314Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "02BD0F6A3FEE4FC5A4B6FFA3B23177FE2D4BC2885835BA247C92E900CE216851", + "hash": "0BBED93EC119E0614BD942A2CF97054EAEB8F35B9F40E61E2BDDB618735E694D", "parts": { - "hash": "729F1DC8FBC33D17DCFBEE452AE53704B679FF39CC4FE77F007244F044E6129F", + "hash": "78B4E28177F5C19B34979E1F836419B16FDE82944FB9865B1A4A2BC4093DE51F", "total": 1 } } @@ -1788,18 +1788,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "31", "last_block_id": { - "hash": "02BD0F6A3FEE4FC5A4B6FFA3B23177FE2D4BC2885835BA247C92E900CE216851", + "hash": "0BBED93EC119E0614BD942A2CF97054EAEB8F35B9F40E61E2BDDB618735E694D", "parts": { - "hash": "729F1DC8FBC33D17DCFBEE452AE53704B679FF39CC4FE77F007244F044E6129F", + "hash": "78B4E28177F5C19B34979E1F836419B16FDE82944FB9865B1A4A2BC4093DE51F", "total": 1 } }, - "last_commit_hash": "D9CF9BC6ECDCFB4AC81672D770B1875BB5A8546A36705E8B5169638C12AC58E2", + "last_commit_hash": "299DC98899FDC5AF9E41F25749BCD0F3A2AEA4640A6EF98861DD0D7CA4771C51", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:51.013493418Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:19.026486127Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1807,9 +1807,9 @@ }, "last_commit": { "block_id": { - "hash": "02BD0F6A3FEE4FC5A4B6FFA3B23177FE2D4BC2885835BA247C92E900CE216851", + "hash": "0BBED93EC119E0614BD942A2CF97054EAEB8F35B9F40E61E2BDDB618735E694D", "parts": { - "hash": "729F1DC8FBC33D17DCFBEE452AE53704B679FF39CC4FE77F007244F044E6129F", + "hash": "78B4E28177F5C19B34979E1F836419B16FDE82944FB9865B1A4A2BC4093DE51F", "total": 1 } }, @@ -1818,17 +1818,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "pQLY02cZ1xoxIxD9NqNasuVvmr1Jqf5648hKSwWAExdszj8kRXnzp24G1AzPv81yLpfrpKyHWTyVIBO3kgJQAA==", - "timestamp": "2023-02-24T15:09:51.013493418Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "5TggCukcXyElGgBR216H2lY9p/yOKTzed36fmWlqlEQTbQgpbvE8v267TNteJ82gQN9BGv2XpeTbxqHRNLjKBw==", + "timestamp": "2023-02-27T07:13:19.026486127Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "47FE7FE2212A8F4A6569EB89EFF9354D73E894F4DDB2E9F15438CEA4882693E4", + "hash": "1586A4047F502F960CB77D0EA045AFA374380E6A63690D5E4182223DC5741919", "parts": { - "hash": "61B145853738DDA5BA10DE12BD2B4F3C5FC2A709712121FB307729B50E3AD707", + "hash": "3F9ACB43E54AAE66CC20B5187CFAD0E3F0844F7F52E6B578C283B16CED63E7A9", "total": 1 } } @@ -1849,18 +1849,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "32", "last_block_id": { - "hash": "47FE7FE2212A8F4A6569EB89EFF9354D73E894F4DDB2E9F15438CEA4882693E4", + "hash": "1586A4047F502F960CB77D0EA045AFA374380E6A63690D5E4182223DC5741919", "parts": { - "hash": "61B145853738DDA5BA10DE12BD2B4F3C5FC2A709712121FB307729B50E3AD707", + "hash": "3F9ACB43E54AAE66CC20B5187CFAD0E3F0844F7F52E6B578C283B16CED63E7A9", "total": 1 } }, - "last_commit_hash": "C4DB33FAD541886678C7E0850E16F2B8AF49B414B8748A15FDE3183EAC46CF36", + "last_commit_hash": "F84E5533989FE76D88BB66DDFA8DAB11142D99887EF89D78D45B73B9C2FE9AFC", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:51.532421598Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:19.546024738Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1868,9 +1868,9 @@ }, "last_commit": { "block_id": { - "hash": "47FE7FE2212A8F4A6569EB89EFF9354D73E894F4DDB2E9F15438CEA4882693E4", + "hash": "1586A4047F502F960CB77D0EA045AFA374380E6A63690D5E4182223DC5741919", "parts": { - "hash": "61B145853738DDA5BA10DE12BD2B4F3C5FC2A709712121FB307729B50E3AD707", + "hash": "3F9ACB43E54AAE66CC20B5187CFAD0E3F0844F7F52E6B578C283B16CED63E7A9", "total": 1 } }, @@ -1879,17 +1879,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "GMVE9bD4VJQWJ2EdGBu7NNBZ9/pti7KPFjR+R739dABIMt0KCY1G6pU8u/UAf1ZPwbFu6VSOmHaonQhGS/b3AA==", - "timestamp": "2023-02-24T15:09:51.532421598Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "d2BJXBNmf2kIvk5gXvUQ364BDUVcAbn5s9Rj21cE4alscThTddrpLmi4W2zEeT+kvVUArzxyfSSnoNpMy3eBCw==", + "timestamp": "2023-02-27T07:13:19.546024738Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "E934D9772BFC0F30FE35170C598122350279B6902F8195F2E4D20757E9423BBD", + "hash": "E4579B240F3768A0FE31685FC19856948E4822C6E8B2ACBC01ACC5E98AB182AA", "parts": { - "hash": "043396430E6C410F0A57217418B83384464CE3FF5AA52A22DF20D22191D612A6", + "hash": "E0FCFF10A52FB934412299A3715031FAE56DDB8007D6E60E11F839B26DDC256D", "total": 1 } } @@ -1910,18 +1910,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "33", "last_block_id": { - "hash": "E934D9772BFC0F30FE35170C598122350279B6902F8195F2E4D20757E9423BBD", + "hash": "E4579B240F3768A0FE31685FC19856948E4822C6E8B2ACBC01ACC5E98AB182AA", "parts": { - "hash": "043396430E6C410F0A57217418B83384464CE3FF5AA52A22DF20D22191D612A6", + "hash": "E0FCFF10A52FB934412299A3715031FAE56DDB8007D6E60E11F839B26DDC256D", "total": 1 } }, - "last_commit_hash": "79B0D0698E1214AD13B90539FAAEFD4DDFE208BDF5BC0BAD12C169EA5C826339", + "last_commit_hash": "88A6D85E49707A9097E9CEC884FDD02567774C4882AB78DFEDE008479A9E42C0", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:52.050779736Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:20.062271708Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1929,9 +1929,9 @@ }, "last_commit": { "block_id": { - "hash": "E934D9772BFC0F30FE35170C598122350279B6902F8195F2E4D20757E9423BBD", + "hash": "E4579B240F3768A0FE31685FC19856948E4822C6E8B2ACBC01ACC5E98AB182AA", "parts": { - "hash": "043396430E6C410F0A57217418B83384464CE3FF5AA52A22DF20D22191D612A6", + "hash": "E0FCFF10A52FB934412299A3715031FAE56DDB8007D6E60E11F839B26DDC256D", "total": 1 } }, @@ -1940,17 +1940,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "O/IkLhYLG+SzbuBD9XWjOTD+L6/NEJtjsgyR/ClNyz+vddyZ5ktqexIpE6Z68GqOkc1jvBglaHmZFqBBeKKeBw==", - "timestamp": "2023-02-24T15:09:52.050779736Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "LRUxW7Z2Y0WiZz7htYlLE6Q2YuqvysXglHOqp2kd7AQLEqZO3EO5bkDq14EfwlhF25VHu6N1x7FC+tXxLQMzDg==", + "timestamp": "2023-02-27T07:13:20.062271708Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "288DF763209A88F724838A317C98A6EA598BA4A97228A5AE5EEFD09B26487813", + "hash": "280529F1C02C8C5AD9CD7A2219ABE33075861A1340816CCDB66AF2AFF5417DF6", "parts": { - "hash": "AB7EE95A5A9CC78F0293FBAD37259641E217D6C291BB32E2D09A1DF5E13380FF", + "hash": "5C551163ECAE74A6AF25B7A66C3511D819BA7201417534FE1D46FE1F93A618E6", "total": 1 } } @@ -1971,18 +1971,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "34", "last_block_id": { - "hash": "288DF763209A88F724838A317C98A6EA598BA4A97228A5AE5EEFD09B26487813", + "hash": "280529F1C02C8C5AD9CD7A2219ABE33075861A1340816CCDB66AF2AFF5417DF6", "parts": { - "hash": "AB7EE95A5A9CC78F0293FBAD37259641E217D6C291BB32E2D09A1DF5E13380FF", + "hash": "5C551163ECAE74A6AF25B7A66C3511D819BA7201417534FE1D46FE1F93A618E6", "total": 1 } }, - "last_commit_hash": "2EBF6CDCCE4AEBD55EB5532A535A809340F6C69A04515354797A40D6D44494DA", + "last_commit_hash": "957AC5C102E4EBD57165C8E318C1FB22843BF295AEBF47A3C31EFF5F9BA0003C", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:52.566839174Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:20.579531491Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -1990,9 +1990,9 @@ }, "last_commit": { "block_id": { - "hash": "288DF763209A88F724838A317C98A6EA598BA4A97228A5AE5EEFD09B26487813", + "hash": "280529F1C02C8C5AD9CD7A2219ABE33075861A1340816CCDB66AF2AFF5417DF6", "parts": { - "hash": "AB7EE95A5A9CC78F0293FBAD37259641E217D6C291BB32E2D09A1DF5E13380FF", + "hash": "5C551163ECAE74A6AF25B7A66C3511D819BA7201417534FE1D46FE1F93A618E6", "total": 1 } }, @@ -2001,17 +2001,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "LRRtzavKg7U4eEkFOgJ7VNkalmVGEtj2J45fNSZwJyxCIaioZ6QT6yv+T7KilP0rYQ3XSMKHOxmvEGfCNNVBBQ==", - "timestamp": "2023-02-24T15:09:52.566839174Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "86HJERRnCVo7BT1VPN94JVvgqWZjB+qkf2aNCs9QItvJpjHyVbxXoIKVqK7dXXd9CJRn8EweOrESDuZa1EJTCA==", + "timestamp": "2023-02-27T07:13:20.579531491Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "7959636BDDB9C76034675239906C8B6E7588B685B73B9E73258D7E6398B7877E", + "hash": "0C292C18A10768F9BBE99FF584CBB748133D6B3B89CC09560A1765E82067B231", "parts": { - "hash": "050340F8516139B861149395A837882F15898430E5FA5C0162BEDC68EA2958F6", + "hash": "51076F051D5B73B5B5FAEEB09DF9DC047D30028A4E6AB2E39E55C9C4C92BBF1E", "total": 1 } } @@ -2032,18 +2032,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "35", "last_block_id": { - "hash": "7959636BDDB9C76034675239906C8B6E7588B685B73B9E73258D7E6398B7877E", + "hash": "0C292C18A10768F9BBE99FF584CBB748133D6B3B89CC09560A1765E82067B231", "parts": { - "hash": "050340F8516139B861149395A837882F15898430E5FA5C0162BEDC68EA2958F6", + "hash": "51076F051D5B73B5B5FAEEB09DF9DC047D30028A4E6AB2E39E55C9C4C92BBF1E", "total": 1 } }, - "last_commit_hash": "9E0F53A59241BD3E135561239D849CFAD29A62ACC9C0F23FFD825DE44B546800", + "last_commit_hash": "C256C5585769FE104B36F2381B3C9F769CFCA690B994457EFA837FD56A7D565E", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:53.086080698Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:21.097684701Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2051,9 +2051,9 @@ }, "last_commit": { "block_id": { - "hash": "7959636BDDB9C76034675239906C8B6E7588B685B73B9E73258D7E6398B7877E", + "hash": "0C292C18A10768F9BBE99FF584CBB748133D6B3B89CC09560A1765E82067B231", "parts": { - "hash": "050340F8516139B861149395A837882F15898430E5FA5C0162BEDC68EA2958F6", + "hash": "51076F051D5B73B5B5FAEEB09DF9DC047D30028A4E6AB2E39E55C9C4C92BBF1E", "total": 1 } }, @@ -2062,17 +2062,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "dvHG9nqKtuI2Hy9fEtwBOmFT4uGtNOKvNaOT2CXZ66xGGRiFUBSfvAOx9s8lxzjgzIDlerRU7dF0yIFQGrVeBg==", - "timestamp": "2023-02-24T15:09:53.086080698Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "8ER+3S/UWdC54DyWTlvOkUmEtXumrFI9wZ4d/Zw4dh/G1O+oWH3L+GFxLhH1NZxavzq5ZmG47PpILO9S09CfAA==", + "timestamp": "2023-02-27T07:13:21.097684701Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "589A9F3ADF634C44DF449F27D8F96CF5A1BCE1BBDC0974A3C549A989EFC483FF", + "hash": "C27CC8C16C955A10E9186D11DDCA8F22FCFE80772896D361A27A268813B3EE33", "parts": { - "hash": "B0CF879E0A3AD5F9D8D9DB81BA603D56FAD32BF497F61248486190DB6F371BE1", + "hash": "39FA6D103A177D71DA297AEAC225D9FBDD31F3226D2BC015EDBBEC19DB0D9688", "total": 1 } } @@ -2093,18 +2093,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "36", "last_block_id": { - "hash": "589A9F3ADF634C44DF449F27D8F96CF5A1BCE1BBDC0974A3C549A989EFC483FF", + "hash": "C27CC8C16C955A10E9186D11DDCA8F22FCFE80772896D361A27A268813B3EE33", "parts": { - "hash": "B0CF879E0A3AD5F9D8D9DB81BA603D56FAD32BF497F61248486190DB6F371BE1", + "hash": "39FA6D103A177D71DA297AEAC225D9FBDD31F3226D2BC015EDBBEC19DB0D9688", "total": 1 } }, - "last_commit_hash": "17C97B144649BB2EDB6E64E1A62B405E6F0C5CABC6AD45F66CD81E1434EE9AF5", + "last_commit_hash": "E1F345D8382871FA8CE2895D62948569A5F686BABB1C83450FD01AB8481A6F1E", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:53.609178055Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:21.613643515Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2112,9 +2112,9 @@ }, "last_commit": { "block_id": { - "hash": "589A9F3ADF634C44DF449F27D8F96CF5A1BCE1BBDC0974A3C549A989EFC483FF", + "hash": "C27CC8C16C955A10E9186D11DDCA8F22FCFE80772896D361A27A268813B3EE33", "parts": { - "hash": "B0CF879E0A3AD5F9D8D9DB81BA603D56FAD32BF497F61248486190DB6F371BE1", + "hash": "39FA6D103A177D71DA297AEAC225D9FBDD31F3226D2BC015EDBBEC19DB0D9688", "total": 1 } }, @@ -2123,17 +2123,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "kBoL9uKWDnNP06Icflh0Zec9N8pbWPToylsaE+YUXL9v/D4wLuqP9nvsWOnSRFZtts8BvgfedzLJf1xyRbxQCg==", - "timestamp": "2023-02-24T15:09:53.609178055Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "2a+7yo2Zq7zJ1R/m4q4dA3CaebeuErlKuyKq4IgUNKLQFWYfAaEl12gAoSVGXyMHuAX6tdgTty7JvabZXAT9AQ==", + "timestamp": "2023-02-27T07:13:21.613643515Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "D315512FB2052D4E442DBA73346816AC917228A50CFE230497538D088F73A439", + "hash": "D7C392D575FFFF42527F2D8B8BC344DBF1973946CB093FCE67C754E0879D9F5D", "parts": { - "hash": "3E310517AED22CC42A8A86BD938E7D5D859398AEE69E503DC84C37FAC95FBD56", + "hash": "3E9868A5FE6A64001E2F353EF163D4D652014FF173F6842FEDE5ABA208967786", "total": 1 } } @@ -2154,18 +2154,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "37", "last_block_id": { - "hash": "D315512FB2052D4E442DBA73346816AC917228A50CFE230497538D088F73A439", + "hash": "D7C392D575FFFF42527F2D8B8BC344DBF1973946CB093FCE67C754E0879D9F5D", "parts": { - "hash": "3E310517AED22CC42A8A86BD938E7D5D859398AEE69E503DC84C37FAC95FBD56", + "hash": "3E9868A5FE6A64001E2F353EF163D4D652014FF173F6842FEDE5ABA208967786", "total": 1 } }, - "last_commit_hash": "B5EFEE08293D2CFAB975E07F062CE3EB108FC79F437E09CFF0146FD74E627CDF", + "last_commit_hash": "9E577767C3956B8E35289B1AE84923B92ABD6AAEAE7169CFAB0FCA7E5E881E68", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:54.125988527Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:22.128368816Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2173,9 +2173,9 @@ }, "last_commit": { "block_id": { - "hash": "D315512FB2052D4E442DBA73346816AC917228A50CFE230497538D088F73A439", + "hash": "D7C392D575FFFF42527F2D8B8BC344DBF1973946CB093FCE67C754E0879D9F5D", "parts": { - "hash": "3E310517AED22CC42A8A86BD938E7D5D859398AEE69E503DC84C37FAC95FBD56", + "hash": "3E9868A5FE6A64001E2F353EF163D4D652014FF173F6842FEDE5ABA208967786", "total": 1 } }, @@ -2184,17 +2184,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "+7g9VI6FkZK0KKGhBsZbCrvXbrYWtccQsVJJ5b3nFkLq7ppEO1WLai3NR/eHE07fGUyybpDArz3IGK3XcKVyCw==", - "timestamp": "2023-02-24T15:09:54.125988527Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "FrWFxxpFxQjoTluJwBR/9EwKMMv1rf4SP1lgQHJbIiH1wq8gzcotmGJtrhMk0ctmFpLr+f57t5UXlnFrDB6aAg==", + "timestamp": "2023-02-27T07:13:22.128368816Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "477384280D571F4A8C22A8947241C54694105F7CF0CC1B1791A68C0539FED046", + "hash": "CC863DFF7148A845E97269742D31FAC667301EBAB3BF842100C7E1C304BB1569", "parts": { - "hash": "C04AEB0D79A05E394C03633C961AD892EEB3900966573AEE76F4D2FCCEEEB9AB", + "hash": "EE3D68BD7F4863AF4083007C0E6FFD6F09ABA63CD410256003F42BC0889A9E04", "total": 1 } } @@ -2215,18 +2215,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "38", "last_block_id": { - "hash": "477384280D571F4A8C22A8947241C54694105F7CF0CC1B1791A68C0539FED046", + "hash": "CC863DFF7148A845E97269742D31FAC667301EBAB3BF842100C7E1C304BB1569", "parts": { - "hash": "C04AEB0D79A05E394C03633C961AD892EEB3900966573AEE76F4D2FCCEEEB9AB", + "hash": "EE3D68BD7F4863AF4083007C0E6FFD6F09ABA63CD410256003F42BC0889A9E04", "total": 1 } }, - "last_commit_hash": "4257612B44B86C0A9FDF4FDBE8AE5E49C90B25B962D2984109797814169DCCC9", + "last_commit_hash": "C6A23E6D8D90F72EE07538E667B39ED046EF1E8F669A3AF08F440C425099F18F", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:54.64273723Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:22.647325562Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2234,9 +2234,9 @@ }, "last_commit": { "block_id": { - "hash": "477384280D571F4A8C22A8947241C54694105F7CF0CC1B1791A68C0539FED046", + "hash": "CC863DFF7148A845E97269742D31FAC667301EBAB3BF842100C7E1C304BB1569", "parts": { - "hash": "C04AEB0D79A05E394C03633C961AD892EEB3900966573AEE76F4D2FCCEEEB9AB", + "hash": "EE3D68BD7F4863AF4083007C0E6FFD6F09ABA63CD410256003F42BC0889A9E04", "total": 1 } }, @@ -2245,17 +2245,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "ASwe71Vr6gEhzII1rik82le8tzlHJxDe3m1Qbfo7NOyvucI79JTAQdzGaLPfRyBVgyE6g2xOo/hyK7+9U9rPAw==", - "timestamp": "2023-02-24T15:09:54.64273723Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "tXpMkMZPnUTeChxQJwufS34T7k2qdTT/n88WZJ+GiQfXe3UxVWsuxdc0v8j+GJ29SGncKNtyM8RV5mHr3uZnCA==", + "timestamp": "2023-02-27T07:13:22.647325562Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "81F517B0B19CC51AA6349AD93CD3CA4E7B7D46F60F1F102608D311B27643FD27", + "hash": "ADA6DCD31CBD4273F85E25DA046E90D12223A2916A2613E5A32B54A0FBEECDAC", "parts": { - "hash": "5D02CF79ACAF874E1C553EA30DBF4B68ADD534A087C4CD2449716BB69B994B22", + "hash": "AC4DF8CA17F14EE067830EDFFEEF59827AB4F83EDF1777937CA6578CF19534A8", "total": 1 } } @@ -2276,18 +2276,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "39", "last_block_id": { - "hash": "81F517B0B19CC51AA6349AD93CD3CA4E7B7D46F60F1F102608D311B27643FD27", + "hash": "ADA6DCD31CBD4273F85E25DA046E90D12223A2916A2613E5A32B54A0FBEECDAC", "parts": { - "hash": "5D02CF79ACAF874E1C553EA30DBF4B68ADD534A087C4CD2449716BB69B994B22", + "hash": "AC4DF8CA17F14EE067830EDFFEEF59827AB4F83EDF1777937CA6578CF19534A8", "total": 1 } }, - "last_commit_hash": "937956A47568EDB1C822B00B42B42394F5592308A3A2F2591AF75EEA5C3ED4C3", + "last_commit_hash": "2304ECDACC010368C6302ADE0989592BEC84A40DC099DD23A6DD9493DBA1B35D", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:55.161080226Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:23.163704537Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2295,9 +2295,9 @@ }, "last_commit": { "block_id": { - "hash": "81F517B0B19CC51AA6349AD93CD3CA4E7B7D46F60F1F102608D311B27643FD27", + "hash": "ADA6DCD31CBD4273F85E25DA046E90D12223A2916A2613E5A32B54A0FBEECDAC", "parts": { - "hash": "5D02CF79ACAF874E1C553EA30DBF4B68ADD534A087C4CD2449716BB69B994B22", + "hash": "AC4DF8CA17F14EE067830EDFFEEF59827AB4F83EDF1777937CA6578CF19534A8", "total": 1 } }, @@ -2306,17 +2306,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "yWzfWI4IkcrqzA/hT2o6fOLtOF0eC7GNsFCHW3gA4IU7Z29IszXQwd3uoqyCtPCWLF5i7jh/qCBDlqrxPDO4Bg==", - "timestamp": "2023-02-24T15:09:55.161080226Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "oryTv+Nza/Qb3ybWIjYunkLaGAx4QqfiKBSFda1VTsWRchgP/EH7StA1e2DrM4e+Uhzyzr5zBLxi5PmDwQRSAg==", + "timestamp": "2023-02-27T07:13:23.163704537Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "43AEA2412DF03949F8DF028C793007F6469B1C1FCFE5DFE74D1083650643A13D", + "hash": "ABCB2A724CAD1809B335D5FF41EE17A62D4A8ECB335F982BA0B319FD46B0D35C", "parts": { - "hash": "268CEE8FB95D958AAD004CD8946184181B6D55572CC5F20317B20EF67E9430C6", + "hash": "6E236B0A21E1E4DDCCCE5B9B0B783D1919FFF07EDCDECC113DF8D1C5949DA6DE", "total": 1 } } @@ -2337,18 +2337,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "40", "last_block_id": { - "hash": "43AEA2412DF03949F8DF028C793007F6469B1C1FCFE5DFE74D1083650643A13D", + "hash": "ABCB2A724CAD1809B335D5FF41EE17A62D4A8ECB335F982BA0B319FD46B0D35C", "parts": { - "hash": "268CEE8FB95D958AAD004CD8946184181B6D55572CC5F20317B20EF67E9430C6", + "hash": "6E236B0A21E1E4DDCCCE5B9B0B783D1919FFF07EDCDECC113DF8D1C5949DA6DE", "total": 1 } }, - "last_commit_hash": "2A398230AE0D3B57600DF6E12808A488658F22E28F8CE94B1B330A45FF90C6EB", + "last_commit_hash": "605159EE9CCB5F8E320604E4D910258FBE5E56933F023336EC5165D3F6058AC4", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:55.683166536Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:23.681914368Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2356,9 +2356,9 @@ }, "last_commit": { "block_id": { - "hash": "43AEA2412DF03949F8DF028C793007F6469B1C1FCFE5DFE74D1083650643A13D", + "hash": "ABCB2A724CAD1809B335D5FF41EE17A62D4A8ECB335F982BA0B319FD46B0D35C", "parts": { - "hash": "268CEE8FB95D958AAD004CD8946184181B6D55572CC5F20317B20EF67E9430C6", + "hash": "6E236B0A21E1E4DDCCCE5B9B0B783D1919FFF07EDCDECC113DF8D1C5949DA6DE", "total": 1 } }, @@ -2367,17 +2367,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "dkJtW/0vD9J7rmwN4a049Omi5Xetjo1G39U1lXZJKfUsTsfRuwh7xCXrI2UhHzc5edtCFdyj2QLwvGVXFxboBA==", - "timestamp": "2023-02-24T15:09:55.683166536Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "MtwMuC0q/Cj6ThSTpT2OI6prgfedVNUTGxKyIbVsZ0gM3p4KMJuzkVqsIUhoV26TYVFt8WW9xV0dx8n1eMU3Dg==", + "timestamp": "2023-02-27T07:13:23.681914368Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "4815EA81BD44847850ED5C491253296B683C6CEB6556C11814CDF6CECDE29F5F", + "hash": "EF683A46688EA9936423FA44AFBCFDFE5834D33F41FA39C4BC431FE4A40E5743", "parts": { - "hash": "3D44E4A484F44F94392945B0BF944C3A104242347C97D6867FE413274E03F420", + "hash": "663206DE5298F15EF96D5AC077B4A45D93EDFEACB2342871478A92ECB511632B", "total": 1 } } @@ -2398,18 +2398,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "41", "last_block_id": { - "hash": "4815EA81BD44847850ED5C491253296B683C6CEB6556C11814CDF6CECDE29F5F", + "hash": "EF683A46688EA9936423FA44AFBCFDFE5834D33F41FA39C4BC431FE4A40E5743", "parts": { - "hash": "3D44E4A484F44F94392945B0BF944C3A104242347C97D6867FE413274E03F420", + "hash": "663206DE5298F15EF96D5AC077B4A45D93EDFEACB2342871478A92ECB511632B", "total": 1 } }, - "last_commit_hash": "9C292564ABBF6D9E3A4E222454C001C14CC8823C6205AB2E854F404B42030F41", + "last_commit_hash": "02434C21AA2B70E377C4C8E70CAE91BD2B4006E8EADAC6BD5A3D1C8539042A3C", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:56.202137485Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:24.200368546Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2417,9 +2417,9 @@ }, "last_commit": { "block_id": { - "hash": "4815EA81BD44847850ED5C491253296B683C6CEB6556C11814CDF6CECDE29F5F", + "hash": "EF683A46688EA9936423FA44AFBCFDFE5834D33F41FA39C4BC431FE4A40E5743", "parts": { - "hash": "3D44E4A484F44F94392945B0BF944C3A104242347C97D6867FE413274E03F420", + "hash": "663206DE5298F15EF96D5AC077B4A45D93EDFEACB2342871478A92ECB511632B", "total": 1 } }, @@ -2428,17 +2428,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "fFOBxp7MmOREYwU5QEtatBap+PBRBiz/RxshtX8cwUMZeadmI6xULCnMR2WxL/am/flkP9oc3O44cF5XjSiFBQ==", - "timestamp": "2023-02-24T15:09:56.202137485Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "CM8N52IHprk8ULK8lYxPBpvcVdPjlfrt3TUAR8Y1ebn0mnPuPn83wZHkS+3lHyQoAkjqR6U16t4CYEMAkVOFAw==", + "timestamp": "2023-02-27T07:13:24.200368546Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "8C9504DC54B545DDE815A3BCE421C9A1ECCB8D41EE4ECA9EFEBE40EF3EE4AC01", + "hash": "CC7D4CB73447307A95ECBF1D0B837320DBC22D874834D14CAED655329A73C642", "parts": { - "hash": "A641188CA2553D52CBF529F69BE52CC33C364EE6F8EAFC78F2A7CF6D6E9FF745", + "hash": "D06054879F621E56B2192BA6E7304C3C46C127BDB6606EBAF56D0BEAD6DEA82C", "total": 1 } } @@ -2459,18 +2459,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "42", "last_block_id": { - "hash": "8C9504DC54B545DDE815A3BCE421C9A1ECCB8D41EE4ECA9EFEBE40EF3EE4AC01", + "hash": "CC7D4CB73447307A95ECBF1D0B837320DBC22D874834D14CAED655329A73C642", "parts": { - "hash": "A641188CA2553D52CBF529F69BE52CC33C364EE6F8EAFC78F2A7CF6D6E9FF745", + "hash": "D06054879F621E56B2192BA6E7304C3C46C127BDB6606EBAF56D0BEAD6DEA82C", "total": 1 } }, - "last_commit_hash": "1DAEF8A30DA99C0157EE298AF94D78720C5606BCC4FE457BC6AF3FA60F36151C", + "last_commit_hash": "7E3CDB1B0034B92CA1902F3DF7329731931F276A9CD4D34FAB6A1AF7648EB28A", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:56.720182604Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:24.718329395Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2478,9 +2478,9 @@ }, "last_commit": { "block_id": { - "hash": "8C9504DC54B545DDE815A3BCE421C9A1ECCB8D41EE4ECA9EFEBE40EF3EE4AC01", + "hash": "CC7D4CB73447307A95ECBF1D0B837320DBC22D874834D14CAED655329A73C642", "parts": { - "hash": "A641188CA2553D52CBF529F69BE52CC33C364EE6F8EAFC78F2A7CF6D6E9FF745", + "hash": "D06054879F621E56B2192BA6E7304C3C46C127BDB6606EBAF56D0BEAD6DEA82C", "total": 1 } }, @@ -2489,17 +2489,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "+YyQALg9ZFZd6E4JzFtW6nlwRvlKvkmP2HkIdlQpYOvI60U4bTMbOFmDxNcAQMp7WG0ClBT1DvDnLBlMGw7SCQ==", - "timestamp": "2023-02-24T15:09:56.720182604Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "BCnSE2GonfwP3HA3TLmj4WvGPB1evjb4v81a1GYq0iL2TUGfEj9T1TNJ1rxiNj9DU6zyVKswuMfu4XWnXm8xDQ==", + "timestamp": "2023-02-27T07:13:24.718329395Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "5256DD8C5B0FAD1E6B2F0FC0D09D248C70D81E1EFFC531AF4B33EC285DA932BE", + "hash": "D950D40AAAE1F6259FF935BEB3187FDEE0655929CD79FEC2F10191EA179A60CF", "parts": { - "hash": "4C31AB0809BD2724B0F858DD623FEC9A2B0EE024ED077F7516330DD53AC74482", + "hash": "7BB111FBD4AC0988D5844EAC762A8AAC0F669499EAE193F2FB3172F60E892B4E", "total": 1 } } @@ -2520,18 +2520,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "43", "last_block_id": { - "hash": "5256DD8C5B0FAD1E6B2F0FC0D09D248C70D81E1EFFC531AF4B33EC285DA932BE", + "hash": "D950D40AAAE1F6259FF935BEB3187FDEE0655929CD79FEC2F10191EA179A60CF", "parts": { - "hash": "4C31AB0809BD2724B0F858DD623FEC9A2B0EE024ED077F7516330DD53AC74482", + "hash": "7BB111FBD4AC0988D5844EAC762A8AAC0F669499EAE193F2FB3172F60E892B4E", "total": 1 } }, - "last_commit_hash": "AF119CCC1DC98F4043097B40A4CE5598990C86DB1461FE7354079A2E80772D91", + "last_commit_hash": "F863A4B7E2B7CA476D2D6DA428A44F14CD0259A2348951F568AAA1058EC4E0F1", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:57.237099851Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:25.234615677Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2539,9 +2539,9 @@ }, "last_commit": { "block_id": { - "hash": "5256DD8C5B0FAD1E6B2F0FC0D09D248C70D81E1EFFC531AF4B33EC285DA932BE", + "hash": "D950D40AAAE1F6259FF935BEB3187FDEE0655929CD79FEC2F10191EA179A60CF", "parts": { - "hash": "4C31AB0809BD2724B0F858DD623FEC9A2B0EE024ED077F7516330DD53AC74482", + "hash": "7BB111FBD4AC0988D5844EAC762A8AAC0F669499EAE193F2FB3172F60E892B4E", "total": 1 } }, @@ -2550,17 +2550,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "e6rRO+rK/ZQieV88zh40tP+oBp2Y8GpOZJ7ZLKqEf7XuJHQNHEmJCnDhJ4UOFiyny/UVjH+hz2/YRZyXUX18Cg==", - "timestamp": "2023-02-24T15:09:57.237099851Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "meGomIHoovUqNP6s8mjG7Is1tq5keX/0v8sHt9PL9JmZzLs0lcJdAJUudV2dPJ6npdbf4plFKh2YorXJA/BkDg==", + "timestamp": "2023-02-27T07:13:25.234615677Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "DDA9E3C772E343EC224AC3FE9DEF0DCDE0F711326CF2F1BFCE5E637D2FEBAD0D", + "hash": "1E09DE09FB873F2666804C0A205C485B8D6468D5D99C912E4ACC91581F5CD0C1", "parts": { - "hash": "94278D3352068F7052F8450DA5ADDDD83086F87F209130C39611B7D6A49DA052", + "hash": "20233DC994CDC8A68372D9667E8FE6C2C901D66B91D61F4A8DF9EED73FEBC3DF", "total": 1 } } @@ -2568,7 +2568,9 @@ { "block": { "data": { - "txs": [] + "txs": [ + "YXN5bmMta2V5PXZhbHVl" + ] }, "evidence": { "evidence": [] @@ -2577,22 +2579,22 @@ "app_hash": "0000000000000000", "chain_id": "dockerchain", "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "data_hash": "3081F9915040D138B3AD7F895732D2767C29E85BA5D84388D04E17A5D8262B7A", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "44", "last_block_id": { - "hash": "DDA9E3C772E343EC224AC3FE9DEF0DCDE0F711326CF2F1BFCE5E637D2FEBAD0D", + "hash": "1E09DE09FB873F2666804C0A205C485B8D6468D5D99C912E4ACC91581F5CD0C1", "parts": { - "hash": "94278D3352068F7052F8450DA5ADDDD83086F87F209130C39611B7D6A49DA052", + "hash": "20233DC994CDC8A68372D9667E8FE6C2C901D66B91D61F4A8DF9EED73FEBC3DF", "total": 1 } }, - "last_commit_hash": "0B9986D11BB7E31E3B0F4A10CCB32E31BFBE2013B30C67DF2589A877AC4D83FC", + "last_commit_hash": "0AC8B58D0377A745D0BF94E6DD9541566FE11352560FF198F51460C4D798EC98", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:57.755486393Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:25.753992404Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2600,9 +2602,9 @@ }, "last_commit": { "block_id": { - "hash": "DDA9E3C772E343EC224AC3FE9DEF0DCDE0F711326CF2F1BFCE5E637D2FEBAD0D", + "hash": "1E09DE09FB873F2666804C0A205C485B8D6468D5D99C912E4ACC91581F5CD0C1", "parts": { - "hash": "94278D3352068F7052F8450DA5ADDDD83086F87F209130C39611B7D6A49DA052", + "hash": "20233DC994CDC8A68372D9667E8FE6C2C901D66B91D61F4A8DF9EED73FEBC3DF", "total": 1 } }, @@ -2611,17 +2613,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "b4wghAvyaPHlXeJdibwz8AuCRtBqb4MxFTaKXx80oPHEar1zlQ/idsl7GQNko/cdIS3uKot3KUvKj3lTStzSBg==", - "timestamp": "2023-02-24T15:09:57.755486393Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "ouOHiTQh6PPLBnNbglHLD4OvBdk5DVsl7HKxgF5xVa7GsVbcvvNGubBhQhjH5TEkFwKofBFPmpjg2S9DIFXGDg==", + "timestamp": "2023-02-27T07:13:25.753992404Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "DB1726D6A84B7A6EBEDC8E904E92B1533DDDDA0572C69BA18027FD1D2EFDE209", + "hash": "471637D10971D4D4BC56465EEA4BA02789A99B12A54EDDEF422EC3E78F8A8692", "parts": { - "hash": "247062B68AD2BC76198AC8B3E33EED61671B171585D57D3CF8C8C4D89B7C7FD5", + "hash": "006E91F757AB76E6DE64ED6E837FA1225801687EB77B1CB882393784C388E067", "total": 1 } } @@ -2635,25 +2637,25 @@ "evidence": [] }, "header": { - "app_hash": "0000000000000000", + "app_hash": "0200000000000000", "chain_id": "dockerchain", "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "45", "last_block_id": { - "hash": "DB1726D6A84B7A6EBEDC8E904E92B1533DDDDA0572C69BA18027FD1D2EFDE209", + "hash": "471637D10971D4D4BC56465EEA4BA02789A99B12A54EDDEF422EC3E78F8A8692", "parts": { - "hash": "247062B68AD2BC76198AC8B3E33EED61671B171585D57D3CF8C8C4D89B7C7FD5", + "hash": "006E91F757AB76E6DE64ED6E837FA1225801687EB77B1CB882393784C388E067", "total": 1 } }, - "last_commit_hash": "F1199954161A7C8661E8B41DC67709E977124204CEFFDC79D5CC664D7A6686E1", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:58.27413433Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "last_commit_hash": "F0B4C270907079C04524BC33EDC008E9AD2EC973051011D3800C474D46712CFD", + "last_results_hash": "6E340B9CFFB37A989CA544E6BB780A2C78901D3FB33738768511A30617AFA01D", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:26.270685966Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -2661,9 +2663,9 @@ }, "last_commit": { "block_id": { - "hash": "DB1726D6A84B7A6EBEDC8E904E92B1533DDDDA0572C69BA18027FD1D2EFDE209", + "hash": "471637D10971D4D4BC56465EEA4BA02789A99B12A54EDDEF422EC3E78F8A8692", "parts": { - "hash": "247062B68AD2BC76198AC8B3E33EED61671B171585D57D3CF8C8C4D89B7C7FD5", + "hash": "006E91F757AB76E6DE64ED6E837FA1225801687EB77B1CB882393784C388E067", "total": 1 } }, @@ -2672,17 +2674,17 @@ "signatures": [ { "block_id_flag": 2, - "signature": "ukA7mbgLEjKOkoBVRPKWWAfDwR/XLFtz2AlQ4PlrljckeSN2BVQxCUQhpeoi4oxaRAwMdXbnizS8XTQxuG6ABQ==", - "timestamp": "2023-02-24T15:09:58.27413433Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "DI4FTJW7WPIZ/Jdm7c8jWoQzHKLPzq0gWoXme3YduptR+i8VBh08p6AkaeIqCQAJV1ZqsSDyenP2Spm0JCGJCQ==", + "timestamp": "2023-02-27T07:13:26.270685966Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "AE11C11F530FA802991DF3AC9DDD70A75A8AFADB7AD45E5E372CA9698B88800A", + "hash": "A85E6D6F23F865376ADB1509AFC2D13B58508D0E1F41DD20E81BAFA28AF79686", "parts": { - "hash": "13E4AC476A76C64B5906FAECC57DEE3921CD162CB509F9CF31C20682855F2269", + "hash": "83E8A7B94EC525DCFA31176D75F77A8F427AAAC716AB3C576B092D64AC934726", "total": 1 } } @@ -2690,336 +2692,33 @@ { "block": { "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "46", - "last_block_id": { - "hash": "AE11C11F530FA802991DF3AC9DDD70A75A8AFADB7AD45E5E372CA9698B88800A", - "parts": { - "hash": "13E4AC476A76C64B5906FAECC57DEE3921CD162CB509F9CF31C20682855F2269", - "total": 1 - } - }, - "last_commit_hash": "351F9ACD2CEE366DB2F5957291F8DE3FB95AD3762DA57960A747B62A084D2CEF", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:58.791275345Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "AE11C11F530FA802991DF3AC9DDD70A75A8AFADB7AD45E5E372CA9698B88800A", - "parts": { - "hash": "13E4AC476A76C64B5906FAECC57DEE3921CD162CB509F9CF31C20682855F2269", - "total": 1 - } - }, - "height": "45", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "kMUJX98Ok1p1qmCYMTJKqX/IWBso8jniBAzwLyvJWt2TMB69uSpaX9Ip0uYx9X3TAb35XsLmXfxpWddP5ze9BQ==", - "timestamp": "2023-02-24T15:09:58.791275345Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } + "txs": [ + "c3luYy1rZXk9dmFsdWU=" ] - } - }, - "block_id": { - "hash": "4EEF667FD914D690EE391E69BFD3B49819AC77502801CB079F9BA4EC9BBBA3DD", - "parts": { - "hash": "088BAEA7FB5579D93EADFA47189BA8D1FFD4E5EC4A47C4B2EEBD36AF6EDEEE47", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] }, "evidence": { "evidence": [] }, "header": { - "app_hash": "0000000000000000", + "app_hash": "0200000000000000", "chain_id": "dockerchain", "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", + "data_hash": "A0BF8E611A3A2ED0FE94AA345B903691C3E56EDE0E7F773F54DE7B020E788849", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "47", - "last_block_id": { - "hash": "4EEF667FD914D690EE391E69BFD3B49819AC77502801CB079F9BA4EC9BBBA3DD", - "parts": { - "hash": "088BAEA7FB5579D93EADFA47189BA8D1FFD4E5EC4A47C4B2EEBD36AF6EDEEE47", - "total": 1 - } - }, - "last_commit_hash": "08A73143D419A9214486E0704A0CACF39C085A20CB2027C9A4AABC9CA4585689", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:59.310865408Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "4EEF667FD914D690EE391E69BFD3B49819AC77502801CB079F9BA4EC9BBBA3DD", - "parts": { - "hash": "088BAEA7FB5579D93EADFA47189BA8D1FFD4E5EC4A47C4B2EEBD36AF6EDEEE47", - "total": 1 - } - }, "height": "46", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "snWpx4YZWoI99mY+UdrNs1l3Ba13U/OyTPFtbNbIdF3kbpgnOenClZUP3GX9InNOmffqqbHF64x0pKYCEGfYDQ==", - "timestamp": "2023-02-24T15:09:59.310865408Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "ACFB15047002B27347A69D94DADA62B8A591A471CBE26332C434D45F04405A4C", - "parts": { - "hash": "95E4532EC06273C46E3051C0044FCF4CC9EA198F259FE7554A59FA96C8A9F1DB", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "48", - "last_block_id": { - "hash": "ACFB15047002B27347A69D94DADA62B8A591A471CBE26332C434D45F04405A4C", - "parts": { - "hash": "95E4532EC06273C46E3051C0044FCF4CC9EA198F259FE7554A59FA96C8A9F1DB", - "total": 1 - } - }, - "last_commit_hash": "B6F5A0F1D16737F9F31506BB3E6782A4CFA3382F767086A601C7D9C0C6B39400", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:59.829744911Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "ACFB15047002B27347A69D94DADA62B8A591A471CBE26332C434D45F04405A4C", - "parts": { - "hash": "95E4532EC06273C46E3051C0044FCF4CC9EA198F259FE7554A59FA96C8A9F1DB", - "total": 1 - } - }, - "height": "47", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "B4DirL+iZ+fDzxyXLmr9XX9mAoHHJdqPMpPWWrlyVrHrJLXuzUev2PToO09ilcYbZIc7mK+iqhbQxaBRb5a6Cw==", - "timestamp": "2023-02-24T15:09:59.829744911Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "0BFD9CE7203F9589A39262E18C73B88078D10BB8EB65614B20BF7A6FDC9044CF", - "parts": { - "hash": "C16B50035851157EACBE505EE86175AFF3991B39067E324C4E555F4D1A9888D4", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "49", - "last_block_id": { - "hash": "0BFD9CE7203F9589A39262E18C73B88078D10BB8EB65614B20BF7A6FDC9044CF", - "parts": { - "hash": "C16B50035851157EACBE505EE86175AFF3991B39067E324C4E555F4D1A9888D4", - "total": 1 - } - }, - "last_commit_hash": "297AF39DEA39E4900BC68DC71E47A4826068B9249A97EADA5395090EF1E5FC90", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:00.345816202Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "0BFD9CE7203F9589A39262E18C73B88078D10BB8EB65614B20BF7A6FDC9044CF", - "parts": { - "hash": "C16B50035851157EACBE505EE86175AFF3991B39067E324C4E555F4D1A9888D4", - "total": 1 - } - }, - "height": "48", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "nYWvhC6HIDBmiTlhkLn86DAPcoMtAwNCScghEPewzpjAX3G6A8ilfJUHKDuKSC7VopjtgHmJm+07etBTlBojBQ==", - "timestamp": "2023-02-24T15:10:00.345816202Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "1138B16CAA5AE14E91EE7267D656BD60B060C556D3953FD12EF93CF4D4787BAC", - "parts": { - "hash": "01A62519FAEB16D352E71D2AB9CDD9BC99E02D0DE384C0D6E60FE7282A1235DA", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "50", - "last_block_id": { - "hash": "1138B16CAA5AE14E91EE7267D656BD60B060C556D3953FD12EF93CF4D4787BAC", - "parts": { - "hash": "01A62519FAEB16D352E71D2AB9CDD9BC99E02D0DE384C0D6E60FE7282A1235DA", - "total": 1 - } - }, - "last_commit_hash": "185E80D1FFFDE7D9972BBFA09E6DE2E109B328EEF14572E0CFB83C65894C9B82", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:00.862694537Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "1138B16CAA5AE14E91EE7267D656BD60B060C556D3953FD12EF93CF4D4787BAC", - "parts": { - "hash": "01A62519FAEB16D352E71D2AB9CDD9BC99E02D0DE384C0D6E60FE7282A1235DA", - "total": 1 - } - }, - "height": "49", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "M0BHMrQVqH6rKbDO0FUvQ5E37ZVRaHftX3Tf+/8M1kG8tZTwc01ypEK7/zFL0sL8PD1DSmBlu0Wl1D2AEIu8Ag==", - "timestamp": "2023-02-24T15:10:00.862694537Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "A7F5B166249797B42C19859830F55B75DD4D187B6FE01C20B6EFBF5F3B44FC36", - "parts": { - "hash": "E2BAB27A47C70C5291045725EBFAB1BAED8292CC06B0232D877BB697E0BB9BFF", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "51", "last_block_id": { - "hash": "A7F5B166249797B42C19859830F55B75DD4D187B6FE01C20B6EFBF5F3B44FC36", + "hash": "A85E6D6F23F865376ADB1509AFC2D13B58508D0E1F41DD20E81BAFA28AF79686", "parts": { - "hash": "E2BAB27A47C70C5291045725EBFAB1BAED8292CC06B0232D877BB697E0BB9BFF", + "hash": "83E8A7B94EC525DCFA31176D75F77A8F427AAAC716AB3C576B092D64AC934726", "total": 1 } }, - "last_commit_hash": "EF6EF07F3386E69F54CC4481532DAFBFA055F1DB9A10CC4BF1548B33FDAA8F12", + "last_commit_hash": "AFB39E43529CAA46B433C3AEEEF06AB1BB95E68E90F7037C0F477F16E420AE17", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:01.382585057Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:26.790394939Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -3027,3083 +2726,33 @@ }, "last_commit": { "block_id": { - "hash": "A7F5B166249797B42C19859830F55B75DD4D187B6FE01C20B6EFBF5F3B44FC36", + "hash": "A85E6D6F23F865376ADB1509AFC2D13B58508D0E1F41DD20E81BAFA28AF79686", "parts": { - "hash": "E2BAB27A47C70C5291045725EBFAB1BAED8292CC06B0232D877BB697E0BB9BFF", + "hash": "83E8A7B94EC525DCFA31176D75F77A8F427AAAC716AB3C576B092D64AC934726", "total": 1 } }, - "height": "50", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "QQ9O+qki+5vPGBbNqg4Ea1WtZBpekXPW2JK8fZ6672S4MtkFRgncjMxsJl1x+uK0PZ4y1AblYdx55l7nYybmAg==", - "timestamp": "2023-02-24T15:10:01.382585057Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "4346EB43EF285225BE125A2A96BD9DAE0E49B5565E1FCE823A1000FE44136D20", - "parts": { - "hash": "22B96890CD4AC15EEF3F89B473CDC94390388648FF9B3F7DEE2154A35EE074C1", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "52", - "last_block_id": { - "hash": "4346EB43EF285225BE125A2A96BD9DAE0E49B5565E1FCE823A1000FE44136D20", - "parts": { - "hash": "22B96890CD4AC15EEF3F89B473CDC94390388648FF9B3F7DEE2154A35EE074C1", - "total": 1 - } - }, - "last_commit_hash": "B62E8A1470D4D8C125483D39F107F932C1A36D66648E3A59ABF0468C4967EAE6", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:01.900861369Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "4346EB43EF285225BE125A2A96BD9DAE0E49B5565E1FCE823A1000FE44136D20", - "parts": { - "hash": "22B96890CD4AC15EEF3F89B473CDC94390388648FF9B3F7DEE2154A35EE074C1", - "total": 1 - } - }, - "height": "51", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "JbcnBRVk8n8ypklwJX4t41dXVJ9bbfmCp4kfUkzwF5ueepMHyuvA+MZbc39TCB3chrk9X19avAHpCRomja5KDw==", - "timestamp": "2023-02-24T15:10:01.900861369Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "EBCFD028C67DBBC265BD293BBD83A4658FBFA7B185FF0F17994A22862A36C43A", - "parts": { - "hash": "199C0D0120AA3D756907FEF7D94DC6E1008C1537EBB9196B46679E35A507C132", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "53", - "last_block_id": { - "hash": "EBCFD028C67DBBC265BD293BBD83A4658FBFA7B185FF0F17994A22862A36C43A", - "parts": { - "hash": "199C0D0120AA3D756907FEF7D94DC6E1008C1537EBB9196B46679E35A507C132", - "total": 1 - } - }, - "last_commit_hash": "6648B3341958BD568CAC927282B78C472C6D91C87492051F0FD634BF9CD56AB3", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:02.417494221Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "EBCFD028C67DBBC265BD293BBD83A4658FBFA7B185FF0F17994A22862A36C43A", - "parts": { - "hash": "199C0D0120AA3D756907FEF7D94DC6E1008C1537EBB9196B46679E35A507C132", - "total": 1 - } - }, - "height": "52", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "YkEO7DA6Y/H5i4/WJQ+6cY0QZbfhrtpPlkTh1gDnQ7kXMJNJh7fiiY8lHV+o2pjqhEs9HR3hTIQeKZMnG1GqBA==", - "timestamp": "2023-02-24T15:10:02.417494221Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "44F13A3FC052C0259F11977A333B97D24944694FC9E5409684325225446582FE", - "parts": { - "hash": "578999EFFAF66B0410AC609729E54CD76D76CEF596D06CE5E9EC4B13B1E9B619", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "54", - "last_block_id": { - "hash": "44F13A3FC052C0259F11977A333B97D24944694FC9E5409684325225446582FE", - "parts": { - "hash": "578999EFFAF66B0410AC609729E54CD76D76CEF596D06CE5E9EC4B13B1E9B619", - "total": 1 - } - }, - "last_commit_hash": "D2D14CBAF0BA4F25BEC6ECA648DC4ECCD3485F7AE88071836DB84C853EBCC69C", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:02.93519888Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "44F13A3FC052C0259F11977A333B97D24944694FC9E5409684325225446582FE", - "parts": { - "hash": "578999EFFAF66B0410AC609729E54CD76D76CEF596D06CE5E9EC4B13B1E9B619", - "total": 1 - } - }, - "height": "53", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "O9/N96JhVNNd+xnxMnKKUmb7J18uApb+bH3galqCyFCr/RN0FL94Z7JGJNqQh59+O12Vv/ns5tyn4OdF0Yx2DA==", - "timestamp": "2023-02-24T15:10:02.93519888Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "945F1F4FB3843E144E22DF6F830AA54FC42EF4131C75957B3CBED36F05BCD089", - "parts": { - "hash": "EF54799764ED32A13FF6EA22952C089960540A4749BA6CCBB5050F2BC6BFA302", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "55", - "last_block_id": { - "hash": "945F1F4FB3843E144E22DF6F830AA54FC42EF4131C75957B3CBED36F05BCD089", - "parts": { - "hash": "EF54799764ED32A13FF6EA22952C089960540A4749BA6CCBB5050F2BC6BFA302", - "total": 1 - } - }, - "last_commit_hash": "E680B37F0A6BAC7E4EAE6FBB89BC5071F423D8AB60B46975CF26364104A1F01B", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:03.454677478Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "945F1F4FB3843E144E22DF6F830AA54FC42EF4131C75957B3CBED36F05BCD089", - "parts": { - "hash": "EF54799764ED32A13FF6EA22952C089960540A4749BA6CCBB5050F2BC6BFA302", - "total": 1 - } - }, - "height": "54", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "0e6lvC2vARY7UPbBAa9JsHHaTTkxo2uLB/0422Ac8PCt+Nk2QwADVJAHkAXD82pQsDmYIy+yoLENdz+9nHm1BQ==", - "timestamp": "2023-02-24T15:10:03.454677478Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "722326DEBFA1C7B21BAAB1AB35F3A02CA96B6BA7E8C5F7FAA71B3F096D6DD57F", - "parts": { - "hash": "0692FE6899695E6CFAF000E9245E7411842FB471353470C1F491526B1E0A4549", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "56", - "last_block_id": { - "hash": "722326DEBFA1C7B21BAAB1AB35F3A02CA96B6BA7E8C5F7FAA71B3F096D6DD57F", - "parts": { - "hash": "0692FE6899695E6CFAF000E9245E7411842FB471353470C1F491526B1E0A4549", - "total": 1 - } - }, - "last_commit_hash": "C388551B70D0395BE9AFF8E18A49107557B5EC0ECCFCC6F837F8F0830010057B", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:03.97193517Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "722326DEBFA1C7B21BAAB1AB35F3A02CA96B6BA7E8C5F7FAA71B3F096D6DD57F", - "parts": { - "hash": "0692FE6899695E6CFAF000E9245E7411842FB471353470C1F491526B1E0A4549", - "total": 1 - } - }, - "height": "55", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "KnYKFqPntf3qV+xOBZ3sdHXtbl7j6OjgQhf73PmHriRpqi6Y2fY8biNB4zBg+kGqdqfL2ed8igH6OrL7yB7mAw==", - "timestamp": "2023-02-24T15:10:03.97193517Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "C553B4508DD88168766B5FB7BA6F9684EA6BFAA77BB3EF9EFC40466512D2D7ED", - "parts": { - "hash": "161BC57D6EF22467FCA2E1727EEBF6449935EFEC345E3A1280B2119C60BC44B0", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "57", - "last_block_id": { - "hash": "C553B4508DD88168766B5FB7BA6F9684EA6BFAA77BB3EF9EFC40466512D2D7ED", - "parts": { - "hash": "161BC57D6EF22467FCA2E1727EEBF6449935EFEC345E3A1280B2119C60BC44B0", - "total": 1 - } - }, - "last_commit_hash": "27D1EC557EF2B04AB95919D5992BB63C710A21972D9A87AF422483F9286242B1", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:04.490286491Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "C553B4508DD88168766B5FB7BA6F9684EA6BFAA77BB3EF9EFC40466512D2D7ED", - "parts": { - "hash": "161BC57D6EF22467FCA2E1727EEBF6449935EFEC345E3A1280B2119C60BC44B0", - "total": 1 - } - }, - "height": "56", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "liX6NFce2HZxdnTnHCobIwBUxAh0TYpAAJXy+FrhMokQ8FhiKPgggLLWLfWd5uobLB+1SAhLW5vJucLrQwFuDw==", - "timestamp": "2023-02-24T15:10:04.490286491Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "00B345394E9FEC254B30386AC58CC1445A79E32959BFF7CC55DBCB7B5540A5ED", - "parts": { - "hash": "FAA521F3228E4D97140387BDA8C052309585D7D5F5F994D0D2B0C3819EC09890", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "58", - "last_block_id": { - "hash": "00B345394E9FEC254B30386AC58CC1445A79E32959BFF7CC55DBCB7B5540A5ED", - "parts": { - "hash": "FAA521F3228E4D97140387BDA8C052309585D7D5F5F994D0D2B0C3819EC09890", - "total": 1 - } - }, - "last_commit_hash": "F839F9F294C2E5C03C618FA07EB745F3A3139C7D4E2DF2343F73A96FED10857B", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:05.009517719Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "00B345394E9FEC254B30386AC58CC1445A79E32959BFF7CC55DBCB7B5540A5ED", - "parts": { - "hash": "FAA521F3228E4D97140387BDA8C052309585D7D5F5F994D0D2B0C3819EC09890", - "total": 1 - } - }, - "height": "57", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "RWcwSPYRLliBiVOFEV77+yCuSY8V3jqv1dS2edA90BHeaNoK1clr/hDkxNlk8ik2iAy6Rp5LJug9oH4QYeWWCQ==", - "timestamp": "2023-02-24T15:10:05.009517719Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "589BFEECF02FFDFD120248029A01A72D07D4A0C8BB40D456846B95644E6E60E3", - "parts": { - "hash": "725A0551FDC4DDEE4E6BF95E575FCF5512A9EE728C10B4948DC09C964C9C0269", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "59", - "last_block_id": { - "hash": "589BFEECF02FFDFD120248029A01A72D07D4A0C8BB40D456846B95644E6E60E3", - "parts": { - "hash": "725A0551FDC4DDEE4E6BF95E575FCF5512A9EE728C10B4948DC09C964C9C0269", - "total": 1 - } - }, - "last_commit_hash": "284A2344BE8E65552650DA36560BA254CF5EE55789B33E1DCAC1DDFFD53C3A57", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:05.528223517Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "589BFEECF02FFDFD120248029A01A72D07D4A0C8BB40D456846B95644E6E60E3", - "parts": { - "hash": "725A0551FDC4DDEE4E6BF95E575FCF5512A9EE728C10B4948DC09C964C9C0269", - "total": 1 - } - }, - "height": "58", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "+zE1EmAgvCfvIgpCa8yZfRr/+y6uz+kJ5opDoL6EHva9vHFYh4mc5rs6l7/DVnxBa+SycSG7qN5GuF21x40JAw==", - "timestamp": "2023-02-24T15:10:05.528223517Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "4077519E09B0A29E81038787837C5AB382C6E4E9D0001A6E1CEC5CE14019FDBC", - "parts": { - "hash": "459C51BDD00DCFFD9CE399A619983EC1BC3E4A03EAA05096BBDCC2FA2064D6D5", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "60", - "last_block_id": { - "hash": "4077519E09B0A29E81038787837C5AB382C6E4E9D0001A6E1CEC5CE14019FDBC", - "parts": { - "hash": "459C51BDD00DCFFD9CE399A619983EC1BC3E4A03EAA05096BBDCC2FA2064D6D5", - "total": 1 - } - }, - "last_commit_hash": "19EEE50F3D6E61E78C7B17D38951673CE5A628C68F98A3A10352A2D39C7600FF", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:06.048285633Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "4077519E09B0A29E81038787837C5AB382C6E4E9D0001A6E1CEC5CE14019FDBC", - "parts": { - "hash": "459C51BDD00DCFFD9CE399A619983EC1BC3E4A03EAA05096BBDCC2FA2064D6D5", - "total": 1 - } - }, - "height": "59", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "I4J9LLi1AQoC+SfJexmDlATv1x7Kdp87gnuPiwtAqJfdQStm6mMnv8SyDDUfUM9zK56tziWgqgBlpCfuyQXZCA==", - "timestamp": "2023-02-24T15:10:06.048285633Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "1FDA3C17D26FA606914484F42E9723874A4D6654C411CCA2BABC52EFC38869FA", - "parts": { - "hash": "79216BF6D2572FB21FFE464B044FE5F2651DA7747E4533E1DCF45E15F6113562", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "61", - "last_block_id": { - "hash": "1FDA3C17D26FA606914484F42E9723874A4D6654C411CCA2BABC52EFC38869FA", - "parts": { - "hash": "79216BF6D2572FB21FFE464B044FE5F2651DA7747E4533E1DCF45E15F6113562", - "total": 1 - } - }, - "last_commit_hash": "C0FA52EBF2BC00D5DB7F183782C6C7F180C220907F90AD887761C5951D367362", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:06.5672674Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "1FDA3C17D26FA606914484F42E9723874A4D6654C411CCA2BABC52EFC38869FA", - "parts": { - "hash": "79216BF6D2572FB21FFE464B044FE5F2651DA7747E4533E1DCF45E15F6113562", - "total": 1 - } - }, - "height": "60", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "REaa8pz4sV6EsRKytM6jBS8JxUHMi3vlOht43VpqO/Nhe8hIU4GXE+Qj0K9SFJGXrQ8HRmqmDb5Cdq+99D0iAQ==", - "timestamp": "2023-02-24T15:10:06.5672674Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "B28CF883F6A1064A1763E1738E151A4306DBD58C0A0458CF2BFBDE31447C7F15", - "parts": { - "hash": "84B60EC48D723DE9D35E772150E8E68A6275E33B4D5A6A6890BD75FF3A99B44B", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "62", - "last_block_id": { - "hash": "B28CF883F6A1064A1763E1738E151A4306DBD58C0A0458CF2BFBDE31447C7F15", - "parts": { - "hash": "84B60EC48D723DE9D35E772150E8E68A6275E33B4D5A6A6890BD75FF3A99B44B", - "total": 1 - } - }, - "last_commit_hash": "DCE9DA5E7B640390CCA3046424542DEB7467E15341C9C44451186ECBAD5DEA98", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:07.088001066Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "B28CF883F6A1064A1763E1738E151A4306DBD58C0A0458CF2BFBDE31447C7F15", - "parts": { - "hash": "84B60EC48D723DE9D35E772150E8E68A6275E33B4D5A6A6890BD75FF3A99B44B", - "total": 1 - } - }, - "height": "61", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "A2dhOHjBFUHXblNQqXm+1zoD5fV03qw3/Cns+JWDesSQvbqg2m0nC/Ycv39eQye0n4gl5mErbdm/2rhNDDSQCQ==", - "timestamp": "2023-02-24T15:10:07.088001066Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "9452A0B1C8F5C645737C67EABE3E7285FF6301357A51EB759BF71B8232C8C108", - "parts": { - "hash": "2B9BE99ACDB21F94275DF310E1A3C7E93A8FF0EEB8002A21711C92CB6C8FE1D6", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "63", - "last_block_id": { - "hash": "9452A0B1C8F5C645737C67EABE3E7285FF6301357A51EB759BF71B8232C8C108", - "parts": { - "hash": "2B9BE99ACDB21F94275DF310E1A3C7E93A8FF0EEB8002A21711C92CB6C8FE1D6", - "total": 1 - } - }, - "last_commit_hash": "72B3A030F970CBC1627F510E56F7F935857AA55B9F0CAF66AAC273AD4591AA07", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:07.608109818Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "9452A0B1C8F5C645737C67EABE3E7285FF6301357A51EB759BF71B8232C8C108", - "parts": { - "hash": "2B9BE99ACDB21F94275DF310E1A3C7E93A8FF0EEB8002A21711C92CB6C8FE1D6", - "total": 1 - } - }, - "height": "62", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "dq651qbWSLPczch/MLoFNbp8dwP8ngUMQs5Ia2UBvAai/D3g5CW1Ng/gfPDeQRnvsi/Hmg9Y8EvPEXAdLOMpCA==", - "timestamp": "2023-02-24T15:10:07.608109818Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "BC9099C7A95E859F3A9E905712D34F18CED5CEAC7AE6B9A927898D6B2ADD6CE7", - "parts": { - "hash": "4B116F05D9526F43B1438816D4DDB454578D845938CE8E27E93364EB798DD64C", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "64", - "last_block_id": { - "hash": "BC9099C7A95E859F3A9E905712D34F18CED5CEAC7AE6B9A927898D6B2ADD6CE7", - "parts": { - "hash": "4B116F05D9526F43B1438816D4DDB454578D845938CE8E27E93364EB798DD64C", - "total": 1 - } - }, - "last_commit_hash": "F78B46F66664E902DF3ED26B4D9CD25330E6B2EA958BFC730974819BD8BBD4A0", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:08.126167057Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "BC9099C7A95E859F3A9E905712D34F18CED5CEAC7AE6B9A927898D6B2ADD6CE7", - "parts": { - "hash": "4B116F05D9526F43B1438816D4DDB454578D845938CE8E27E93364EB798DD64C", - "total": 1 - } - }, - "height": "63", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "0a+jkvXSgvYkM4Yx91Ro5BZU7xF26He3du6NEwNQVRxtyq7ybMyFFqoY0IgU0wENeaSrnry0tn89ZFXGdB+iAw==", - "timestamp": "2023-02-24T15:10:08.126167057Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "C75C315961C270D255BCFCB48A68105EF872907CA267FA269C39605E807838D7", - "parts": { - "hash": "8012C504A65312F971F84F9C6B7C4A82607E8B896DCA53A7926B487649B3598C", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "65", - "last_block_id": { - "hash": "C75C315961C270D255BCFCB48A68105EF872907CA267FA269C39605E807838D7", - "parts": { - "hash": "8012C504A65312F971F84F9C6B7C4A82607E8B896DCA53A7926B487649B3598C", - "total": 1 - } - }, - "last_commit_hash": "E52A557C451F152B1F1651B91E0AA55E369163D2DE57A21601974EAEC9021401", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:08.642802272Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "C75C315961C270D255BCFCB48A68105EF872907CA267FA269C39605E807838D7", - "parts": { - "hash": "8012C504A65312F971F84F9C6B7C4A82607E8B896DCA53A7926B487649B3598C", - "total": 1 - } - }, - "height": "64", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "FJffAu1Gqo+SjQflRWFW6Z/29WPEwaXGFX/QmcrzOAA91fU7pALqPiGkPzxKDp/ScBLOvafKamGWlDmlTwVsBQ==", - "timestamp": "2023-02-24T15:10:08.642802272Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "CFBAE91A297491D6940FE8A722493E6D1947E2BC56F5F4A575D025F179F680C9", - "parts": { - "hash": "D9D801CD62D75F56AEEAC865BDCB90B4C73AB7A657F2C1FD190D12E2690E9345", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "66", - "last_block_id": { - "hash": "CFBAE91A297491D6940FE8A722493E6D1947E2BC56F5F4A575D025F179F680C9", - "parts": { - "hash": "D9D801CD62D75F56AEEAC865BDCB90B4C73AB7A657F2C1FD190D12E2690E9345", - "total": 1 - } - }, - "last_commit_hash": "18C9646BA42588E486572C6622C134ECF2E4335D1A90BFB8E3E7610142DDDA36", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:09.158466835Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "CFBAE91A297491D6940FE8A722493E6D1947E2BC56F5F4A575D025F179F680C9", - "parts": { - "hash": "D9D801CD62D75F56AEEAC865BDCB90B4C73AB7A657F2C1FD190D12E2690E9345", - "total": 1 - } - }, - "height": "65", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "IhydbNLjlmZChv6nkwr046bMobBDUNI9ufmOp3SkyqRgSd0ozoRseuL9VUQimhV35jYnUQUAamkp/6nt58lPAQ==", - "timestamp": "2023-02-24T15:10:09.158466835Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "8034C311C36C911ACAE3734593BB425B976863111053F71B84A4D59964C8EBBC", - "parts": { - "hash": "BFCC0ACA7FE08FC00E417B012DC7DC05B831F63184250FEFFF6E8C6BB1A572F4", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "67", - "last_block_id": { - "hash": "8034C311C36C911ACAE3734593BB425B976863111053F71B84A4D59964C8EBBC", - "parts": { - "hash": "BFCC0ACA7FE08FC00E417B012DC7DC05B831F63184250FEFFF6E8C6BB1A572F4", - "total": 1 - } - }, - "last_commit_hash": "103E69E502EDD0A6B027FEF11DB75EBBF80FA05D91AB354FFC5D121BF7F949D4", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:09.675815851Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "8034C311C36C911ACAE3734593BB425B976863111053F71B84A4D59964C8EBBC", - "parts": { - "hash": "BFCC0ACA7FE08FC00E417B012DC7DC05B831F63184250FEFFF6E8C6BB1A572F4", - "total": 1 - } - }, - "height": "66", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "kRXINPczoPVW08ldgXHmhp0x3QoXkBWR3kUyNhsWbLk1OdhYPbDhZA+6bfxa5clPHCYgiszdmOO2rp3SibreBQ==", - "timestamp": "2023-02-24T15:10:09.675815851Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "E1BAFCB8C5EB13ED74CE8ABA9CE0272608B433EF45FEB7D61DDA2CC092D03CC1", - "parts": { - "hash": "A650A48FE89862F7F68E37333CBDA466B9090F0F80E95902BB4A11E83D853456", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "68", - "last_block_id": { - "hash": "E1BAFCB8C5EB13ED74CE8ABA9CE0272608B433EF45FEB7D61DDA2CC092D03CC1", - "parts": { - "hash": "A650A48FE89862F7F68E37333CBDA466B9090F0F80E95902BB4A11E83D853456", - "total": 1 - } - }, - "last_commit_hash": "9C2975EB38DF9E80B4EF705DC2320240054D5118F28145A033256E55D16FC120", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:10.193696136Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "E1BAFCB8C5EB13ED74CE8ABA9CE0272608B433EF45FEB7D61DDA2CC092D03CC1", - "parts": { - "hash": "A650A48FE89862F7F68E37333CBDA466B9090F0F80E95902BB4A11E83D853456", - "total": 1 - } - }, - "height": "67", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "+ILWvGu2iZw/c4zOj1BM/FFEOPFeWCBh0XdSbJU20wVqYghbYkU9IZ5Iz8yAb8aDiw1Wfss77U7xYyT3nSFMAg==", - "timestamp": "2023-02-24T15:10:10.193696136Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "BC91E3FD8F8AF6FCD72D490699A476259EC824ECD6F65CD615028FE5BBEA423B", - "parts": { - "hash": "BD46C8DABADA4EC0A6F3FC0A1AFC6A2E1AA5E85848B93ACA6053B1142031165A", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "69", - "last_block_id": { - "hash": "BC91E3FD8F8AF6FCD72D490699A476259EC824ECD6F65CD615028FE5BBEA423B", - "parts": { - "hash": "BD46C8DABADA4EC0A6F3FC0A1AFC6A2E1AA5E85848B93ACA6053B1142031165A", - "total": 1 - } - }, - "last_commit_hash": "B6C40A5DF49FC327AB8477B0F7A54E0E7CE438BA74361D80149963A70C6F532A", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:10.710776945Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "BC91E3FD8F8AF6FCD72D490699A476259EC824ECD6F65CD615028FE5BBEA423B", - "parts": { - "hash": "BD46C8DABADA4EC0A6F3FC0A1AFC6A2E1AA5E85848B93ACA6053B1142031165A", - "total": 1 - } - }, - "height": "68", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "6Hl33Jv/5iMOj/jLDptpb5npgCWJyGPdtLl0yfVAOu0a6JASXukktxHMp0vVMbMBasO8jNGSxoNhxUeG333rBw==", - "timestamp": "2023-02-24T15:10:10.710776945Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "298A99B3185C90E8E549F4CE82F9888F957107D6B3B7A5461608680B68D5DF90", - "parts": { - "hash": "9908ECF363A08757BB37DE31B412E8816A1C48EB282407B9E362AAEC4F0406BE", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "70", - "last_block_id": { - "hash": "298A99B3185C90E8E549F4CE82F9888F957107D6B3B7A5461608680B68D5DF90", - "parts": { - "hash": "9908ECF363A08757BB37DE31B412E8816A1C48EB282407B9E362AAEC4F0406BE", - "total": 1 - } - }, - "last_commit_hash": "45C4603344CD0E4536C7D9A7DC2D29AD3AB085B868C3ECD847DA6FF25241C746", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:11.230812463Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "298A99B3185C90E8E549F4CE82F9888F957107D6B3B7A5461608680B68D5DF90", - "parts": { - "hash": "9908ECF363A08757BB37DE31B412E8816A1C48EB282407B9E362AAEC4F0406BE", - "total": 1 - } - }, - "height": "69", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "0v25MRGpcUA8YD5WBmWE9fB/i+YWmASyHdD+NyRI1+dxQb2LZ4J+MyLFYbtob3db1AhQO8j0gH5WjidEbBNVCA==", - "timestamp": "2023-02-24T15:10:11.230812463Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "02C20FCA68E8F8D4CAF801819C018CCAAF687E4A7D3AE46D56DEAE7B321DA3EF", - "parts": { - "hash": "8B757F00F150A78E9025D0F7675D780214045C43A7C7D5038605B797C0A52443", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "71", - "last_block_id": { - "hash": "02C20FCA68E8F8D4CAF801819C018CCAAF687E4A7D3AE46D56DEAE7B321DA3EF", - "parts": { - "hash": "8B757F00F150A78E9025D0F7675D780214045C43A7C7D5038605B797C0A52443", - "total": 1 - } - }, - "last_commit_hash": "F5AB1A3EE23558D41E014B0EEE9EF97221A553B48C4FF225904A84ADA39CF943", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:11.748416415Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "02C20FCA68E8F8D4CAF801819C018CCAAF687E4A7D3AE46D56DEAE7B321DA3EF", - "parts": { - "hash": "8B757F00F150A78E9025D0F7675D780214045C43A7C7D5038605B797C0A52443", - "total": 1 - } - }, - "height": "70", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "0PCP8DD780dkF1Donw5kh9efICrCkpsb87mjsnPzllc72k1FKsBZjnwKTtmAqUDd/X2vd1//DL8JuNLRTJo5Cg==", - "timestamp": "2023-02-24T15:10:11.748416415Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "AD5101727F834ABE362A0461794FA96FBDF1AF24059D28FAECF7D4088D0A1459", - "parts": { - "hash": "C48562DF5B842CF8C0865F2D70BE11C62A186DC3017805BDD4FC9FD172C41EA7", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "72", - "last_block_id": { - "hash": "AD5101727F834ABE362A0461794FA96FBDF1AF24059D28FAECF7D4088D0A1459", - "parts": { - "hash": "C48562DF5B842CF8C0865F2D70BE11C62A186DC3017805BDD4FC9FD172C41EA7", - "total": 1 - } - }, - "last_commit_hash": "A7AA3E25BFAAE46912CB90494DCF4F68F8205A55FB4891D5B53324D790DD3A31", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:12.269703898Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "AD5101727F834ABE362A0461794FA96FBDF1AF24059D28FAECF7D4088D0A1459", - "parts": { - "hash": "C48562DF5B842CF8C0865F2D70BE11C62A186DC3017805BDD4FC9FD172C41EA7", - "total": 1 - } - }, - "height": "71", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "k3McP4ok6Roz5bAap2qtKQ+7rpX9NdixJOWCZc6LYiZxJsMDeWXh0zUtHbERUchIc8NoOULJZhbS4iFTTlKYCQ==", - "timestamp": "2023-02-24T15:10:12.269703898Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "619C63949C052D89975B40BF9CD4A19DDB58E8EEA276667D996B3B0B1869A349", - "parts": { - "hash": "9CF47D0B506FEC1FE92AD74680F3151790781CE5050F2308F980BF639591BD42", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "73", - "last_block_id": { - "hash": "619C63949C052D89975B40BF9CD4A19DDB58E8EEA276667D996B3B0B1869A349", - "parts": { - "hash": "9CF47D0B506FEC1FE92AD74680F3151790781CE5050F2308F980BF639591BD42", - "total": 1 - } - }, - "last_commit_hash": "0D6D7DF87EA8456E284496374D126B83DF2359D179F82A35F3B4F0037FBAC9CF", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:12.787236166Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "619C63949C052D89975B40BF9CD4A19DDB58E8EEA276667D996B3B0B1869A349", - "parts": { - "hash": "9CF47D0B506FEC1FE92AD74680F3151790781CE5050F2308F980BF639591BD42", - "total": 1 - } - }, - "height": "72", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "vQQQ7PAlx/KEPsQ+yeN0tsrGjz9f7KHdaAr5pAdpvIAlfofEq3nmOi4mxEO0Q1Aj4lfi8+TVpKjfQn759dg/Cg==", - "timestamp": "2023-02-24T15:10:12.787236166Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "6921568AF3CEBBFC7D5B2FC4E0980DEF9A353673CD104B4BE153A57D69625746", - "parts": { - "hash": "E24C56A064A47680BF97121B878BE864C1F29291D78E558E3AF61CD8BB74D74D", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "74", - "last_block_id": { - "hash": "6921568AF3CEBBFC7D5B2FC4E0980DEF9A353673CD104B4BE153A57D69625746", - "parts": { - "hash": "E24C56A064A47680BF97121B878BE864C1F29291D78E558E3AF61CD8BB74D74D", - "total": 1 - } - }, - "last_commit_hash": "52386D5C3E1D56E0F7CA267422C4F830C2B3D3CF07A8D49FCA2456B56A9819D2", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:13.303922027Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "6921568AF3CEBBFC7D5B2FC4E0980DEF9A353673CD104B4BE153A57D69625746", - "parts": { - "hash": "E24C56A064A47680BF97121B878BE864C1F29291D78E558E3AF61CD8BB74D74D", - "total": 1 - } - }, - "height": "73", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "vDm3hJ82xvRKQSvJWaDJI3sKSbTdP64V2IGE4FxvZOoI+8AUhuLpFDdngDza1LXNVfhPZV0dOI4CzTP0L0nfCA==", - "timestamp": "2023-02-24T15:10:13.303922027Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "FD8C2208476F33EF9C76C265CAECEA01A81F559AD2A5A5404E2564629A05B0B7", - "parts": { - "hash": "1AD5A83DA188470C49D2B5AB5ADD5F91564D69F82E0DA15DBA502213EF2A514D", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "75", - "last_block_id": { - "hash": "FD8C2208476F33EF9C76C265CAECEA01A81F559AD2A5A5404E2564629A05B0B7", - "parts": { - "hash": "1AD5A83DA188470C49D2B5AB5ADD5F91564D69F82E0DA15DBA502213EF2A514D", - "total": 1 - } - }, - "last_commit_hash": "53343C1DE93CB501AA957B755E1039167F52CCD53E423E7AD5CEB14C14ABB2D7", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:13.823154238Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "FD8C2208476F33EF9C76C265CAECEA01A81F559AD2A5A5404E2564629A05B0B7", - "parts": { - "hash": "1AD5A83DA188470C49D2B5AB5ADD5F91564D69F82E0DA15DBA502213EF2A514D", - "total": 1 - } - }, - "height": "74", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "qgD64AZj/Vw/z33hyCTKzE7d6wGpbsOndH/xihqaWU9+aLtn2B4o6cR2fn5LFr14UfXlDaWDSyJ8v6rqL8VACg==", - "timestamp": "2023-02-24T15:10:13.823154238Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "E05954016AC3CF6F26EE03C91B40C49AF819A6F10F93642E8FCC5A6E7C33C207", - "parts": { - "hash": "EC8F0ED25E45E19146C1981E0D3655A3EDE556E27138C9999E1999306F418BCA", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "76", - "last_block_id": { - "hash": "E05954016AC3CF6F26EE03C91B40C49AF819A6F10F93642E8FCC5A6E7C33C207", - "parts": { - "hash": "EC8F0ED25E45E19146C1981E0D3655A3EDE556E27138C9999E1999306F418BCA", - "total": 1 - } - }, - "last_commit_hash": "18E7512FFF3AEFD6B019AC5AC8D1B193701AB2BBB1110B0E63E256D8AE433CDB", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:14.339504898Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "E05954016AC3CF6F26EE03C91B40C49AF819A6F10F93642E8FCC5A6E7C33C207", - "parts": { - "hash": "EC8F0ED25E45E19146C1981E0D3655A3EDE556E27138C9999E1999306F418BCA", - "total": 1 - } - }, - "height": "75", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "8LzvsSr1R4U6NweHN7rRrr59UAaS1RGwlMvpCE3T+B+UbW4TTx4Nlw4tBL17LjRt4R9F40QDJt0Tpq3sXNGDBQ==", - "timestamp": "2023-02-24T15:10:14.339504898Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "5EBB07051D6A1CBE87B82F13EAB1486AE108CCA69AB1858F96933AC7CCE7477F", - "parts": { - "hash": "BB90594B623173C9AA6BF3999434D8C95675460DD8E43F19EA832CE671B614A6", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "77", - "last_block_id": { - "hash": "5EBB07051D6A1CBE87B82F13EAB1486AE108CCA69AB1858F96933AC7CCE7477F", - "parts": { - "hash": "BB90594B623173C9AA6BF3999434D8C95675460DD8E43F19EA832CE671B614A6", - "total": 1 - } - }, - "last_commit_hash": "C46C988EA7866C0495512D243E6C966139A1B4D4ED64F51C2D2B56B977DD9C84", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:14.858160995Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "5EBB07051D6A1CBE87B82F13EAB1486AE108CCA69AB1858F96933AC7CCE7477F", - "parts": { - "hash": "BB90594B623173C9AA6BF3999434D8C95675460DD8E43F19EA832CE671B614A6", - "total": 1 - } - }, - "height": "76", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "7pUfd8RgtscrwwISg8a3Qna/l9nPKbBAIZa07WyR8JBkZiIV45vJHSNBPviZjeOvMGlqMx8XQIYnP2v6RRwCDg==", - "timestamp": "2023-02-24T15:10:14.858160995Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "562D52FB2419AD0765B07CB90CAAB0CF1601F91ED1B9F2B4E936A6BD61A16DD8", - "parts": { - "hash": "B61B664CB5653EDD554561827F5D0A0646CD9A815A3F982E6CE34742893E53CB", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "78", - "last_block_id": { - "hash": "562D52FB2419AD0765B07CB90CAAB0CF1601F91ED1B9F2B4E936A6BD61A16DD8", - "parts": { - "hash": "B61B664CB5653EDD554561827F5D0A0646CD9A815A3F982E6CE34742893E53CB", - "total": 1 - } - }, - "last_commit_hash": "198F5AB1C616849CB232E69A1AAE52A818526B8B6638F61E8FA54ABB4A7FECBF", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:15.374906279Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "562D52FB2419AD0765B07CB90CAAB0CF1601F91ED1B9F2B4E936A6BD61A16DD8", - "parts": { - "hash": "B61B664CB5653EDD554561827F5D0A0646CD9A815A3F982E6CE34742893E53CB", - "total": 1 - } - }, - "height": "77", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "quE9tzBtBY5uuALnTwkEfdl8Y41RFWZX+OhuXZ0a74CxGp6SYN90v5+Svp3QiK9wD2aaa/Z/4fRXASDea1n+Cg==", - "timestamp": "2023-02-24T15:10:15.374906279Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "7731239F6E06407382C42964D25D2DC7D2F9DF7E467667452CC3B1E72343601E", - "parts": { - "hash": "1939C79965CFD63B099F4CE4302DF3B50F6C3D3DC86AE41379710E975F786FC2", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "79", - "last_block_id": { - "hash": "7731239F6E06407382C42964D25D2DC7D2F9DF7E467667452CC3B1E72343601E", - "parts": { - "hash": "1939C79965CFD63B099F4CE4302DF3B50F6C3D3DC86AE41379710E975F786FC2", - "total": 1 - } - }, - "last_commit_hash": "C4BA3B3B9DAB60EBA4B012B66CE0267138C9980E4C8CB20B959308F7AD41F773", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:15.891763799Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "7731239F6E06407382C42964D25D2DC7D2F9DF7E467667452CC3B1E72343601E", - "parts": { - "hash": "1939C79965CFD63B099F4CE4302DF3B50F6C3D3DC86AE41379710E975F786FC2", - "total": 1 - } - }, - "height": "78", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "l2ByE017TV2bquetHbe6HABenlwLTDjh0hLpkMKKQyewOJmPVoSqov7lj+saBZhXMIUSoJRht/+tzddBA1YMAA==", - "timestamp": "2023-02-24T15:10:15.891763799Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "51FF3B2D890CED166D5253B0982AEC4E8A2B58219D3F90162F562B6A36CB7B6E", - "parts": { - "hash": "682BB96896129320C025A416FEBBDFDB8E493FA6C743A6D31696CF7B6C70A175", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "80", - "last_block_id": { - "hash": "51FF3B2D890CED166D5253B0982AEC4E8A2B58219D3F90162F562B6A36CB7B6E", - "parts": { - "hash": "682BB96896129320C025A416FEBBDFDB8E493FA6C743A6D31696CF7B6C70A175", - "total": 1 - } - }, - "last_commit_hash": "06D4D1ACE7E5418D42CB0FCC2D443DD1BC2C7D5DF89B2D65E710993A1BB27431", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:16.41039064Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "51FF3B2D890CED166D5253B0982AEC4E8A2B58219D3F90162F562B6A36CB7B6E", - "parts": { - "hash": "682BB96896129320C025A416FEBBDFDB8E493FA6C743A6D31696CF7B6C70A175", - "total": 1 - } - }, - "height": "79", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "y8tLgfGzDYTuloQ68u7YGyu7fFYx0wBz5CAYZWMiK4WH0eyVxhYnpl5HrrdvHzRpDBMTg2xdUIKEymPdPnxfCw==", - "timestamp": "2023-02-24T15:10:16.41039064Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "CCD624AE61388F88999E59604FE99F7A96F96D65807D7C0A5DB759FD6B84F4A8", - "parts": { - "hash": "A6B984E6CD72539FFF0D7B6D57D69AEF5642317F240E76EAC4FDE03889DAFEF3", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "81", - "last_block_id": { - "hash": "CCD624AE61388F88999E59604FE99F7A96F96D65807D7C0A5DB759FD6B84F4A8", - "parts": { - "hash": "A6B984E6CD72539FFF0D7B6D57D69AEF5642317F240E76EAC4FDE03889DAFEF3", - "total": 1 - } - }, - "last_commit_hash": "BCC5D3317EB9826607AF35F07309D7A950E4BD37A26C69AC3F2FBD44EE1DE9F0", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:16.934171765Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "CCD624AE61388F88999E59604FE99F7A96F96D65807D7C0A5DB759FD6B84F4A8", - "parts": { - "hash": "A6B984E6CD72539FFF0D7B6D57D69AEF5642317F240E76EAC4FDE03889DAFEF3", - "total": 1 - } - }, - "height": "80", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "qv24320MnUQkAQEheODsNB/u+DBGt7ll5NdR3O9s7DxYWfzJcdMhDVdV9/bQVe6S6NMT1vfMsDjHpbgyyT99DA==", - "timestamp": "2023-02-24T15:10:16.934171765Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "4F1592A748C6C95FF62DEF707F5D588B1AF97674921627B94D7FDF169091CAEC", - "parts": { - "hash": "796B12053DB0FCBAA82C1651C907CAB015808348C5808E43B035910B715020BC", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "82", - "last_block_id": { - "hash": "4F1592A748C6C95FF62DEF707F5D588B1AF97674921627B94D7FDF169091CAEC", - "parts": { - "hash": "796B12053DB0FCBAA82C1651C907CAB015808348C5808E43B035910B715020BC", - "total": 1 - } - }, - "last_commit_hash": "67487102E76F42A5B89855D93C02A0EEF411052064E2651C69843C9FF116EC3B", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:17.452343627Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "4F1592A748C6C95FF62DEF707F5D588B1AF97674921627B94D7FDF169091CAEC", - "parts": { - "hash": "796B12053DB0FCBAA82C1651C907CAB015808348C5808E43B035910B715020BC", - "total": 1 - } - }, - "height": "81", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "5R+BwF8CZOgZgKAL/Pymf9VkMvwMapveRyNnfYouZhbGM4C43Jg+ZoSnWsKHsBXqIqe7mF1EVi2HMjzj4st0Cg==", - "timestamp": "2023-02-24T15:10:17.452343627Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "45679F83A14AD70BD7B2FA534D1664D7CF5F2DBA485C25373C5A3FBAA6E5BEF5", - "parts": { - "hash": "0A1DAD862F1625291E4AB57E9F88AED895F845753DD81A76DFB68E2C076B0A9F", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "83", - "last_block_id": { - "hash": "45679F83A14AD70BD7B2FA534D1664D7CF5F2DBA485C25373C5A3FBAA6E5BEF5", - "parts": { - "hash": "0A1DAD862F1625291E4AB57E9F88AED895F845753DD81A76DFB68E2C076B0A9F", - "total": 1 - } - }, - "last_commit_hash": "C3DCF91D33BDD4298BB39C8856499C5EF9A3E42840B599551A14712EB1E8789B", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:17.971214064Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "45679F83A14AD70BD7B2FA534D1664D7CF5F2DBA485C25373C5A3FBAA6E5BEF5", - "parts": { - "hash": "0A1DAD862F1625291E4AB57E9F88AED895F845753DD81A76DFB68E2C076B0A9F", - "total": 1 - } - }, - "height": "82", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "fGH5IheksxE/g1fSCOSUV2t7qSgSc4uH31/svjwnu67ZG6GAVyggWM8PsXtRe71ZUeEEkA3PwYFqkKH6I6O6AQ==", - "timestamp": "2023-02-24T15:10:17.971214064Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "862D2E36683F40F85FFB10F55F98EBE837F2D4CF0954ED0C03898978E9C646BB", - "parts": { - "hash": "FDF5A292F49CE9633D99F2BAA242E071C05839C2FDDAF232611DED217879D6E3", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "84", - "last_block_id": { - "hash": "862D2E36683F40F85FFB10F55F98EBE837F2D4CF0954ED0C03898978E9C646BB", - "parts": { - "hash": "FDF5A292F49CE9633D99F2BAA242E071C05839C2FDDAF232611DED217879D6E3", - "total": 1 - } - }, - "last_commit_hash": "BE02FD4CF77E1CDEE61347A2588516FFE837020CC82F971E8A6F3F52325735AA", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:18.488097512Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "862D2E36683F40F85FFB10F55F98EBE837F2D4CF0954ED0C03898978E9C646BB", - "parts": { - "hash": "FDF5A292F49CE9633D99F2BAA242E071C05839C2FDDAF232611DED217879D6E3", - "total": 1 - } - }, - "height": "83", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "A4i59qhCZkUi9DB8iJNzGYmbJdkp/cWASwH5MnfCF1s7vFAHZTddRlhpP0oF6ZBVaI0j2lRaS2DhLBUSdPwnCg==", - "timestamp": "2023-02-24T15:10:18.488097512Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "83E0F87D192C136F93832C2138A00221C23B640E7A847E8FEBAC667C5F6B2A1C", - "parts": { - "hash": "1D6A4F646BD09FFA2B6123673BF638C080F1DB2F9D8DF16AAFB07FD32A156BF8", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "85", - "last_block_id": { - "hash": "83E0F87D192C136F93832C2138A00221C23B640E7A847E8FEBAC667C5F6B2A1C", - "parts": { - "hash": "1D6A4F646BD09FFA2B6123673BF638C080F1DB2F9D8DF16AAFB07FD32A156BF8", - "total": 1 - } - }, - "last_commit_hash": "8604E909D5D72E1B562A813C4C49505F13E14348A9BF6B502DB33944DAC0724A", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:19.006948118Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "83E0F87D192C136F93832C2138A00221C23B640E7A847E8FEBAC667C5F6B2A1C", - "parts": { - "hash": "1D6A4F646BD09FFA2B6123673BF638C080F1DB2F9D8DF16AAFB07FD32A156BF8", - "total": 1 - } - }, - "height": "84", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "oTTnjJBwXJBeWLp8fmn26dxU+tzNPD2fqCzd8geTWp+rjKCHWBNarNbjnsZhbI1KmLYnF33Kv2WuqNdcnVxqDw==", - "timestamp": "2023-02-24T15:10:19.006948118Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "CDD6EF160F00CD3A23564ADB3222412271B7ED8135EDB1FC6A1D8487A5168D9E", - "parts": { - "hash": "6F6E762C60A48B794C603F5AE6A923D2F4FA41E586D94B9A9FA9EA67BBB4F828", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "86", - "last_block_id": { - "hash": "CDD6EF160F00CD3A23564ADB3222412271B7ED8135EDB1FC6A1D8487A5168D9E", - "parts": { - "hash": "6F6E762C60A48B794C603F5AE6A923D2F4FA41E586D94B9A9FA9EA67BBB4F828", - "total": 1 - } - }, - "last_commit_hash": "3E6154E76D7B31E2CB70E4F632AD2839A661FC0670E56F2B7572AED5BD73CFD3", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:19.524829754Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "CDD6EF160F00CD3A23564ADB3222412271B7ED8135EDB1FC6A1D8487A5168D9E", - "parts": { - "hash": "6F6E762C60A48B794C603F5AE6A923D2F4FA41E586D94B9A9FA9EA67BBB4F828", - "total": 1 - } - }, - "height": "85", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "eD3xz+xNnT9YInvPLSxwzZ6QAcMm0uLcRHxF29pmiObD6E7E8lXxmxJlStXA9oyOl0KLsKRJuPxOGAMAQHDSCw==", - "timestamp": "2023-02-24T15:10:19.524829754Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "492DDC4ADF93C0AD9AE891B52EB83C23281C8B118F54B9CD6632DCF11667725D", - "parts": { - "hash": "95EEC124BBFE90931C80A870EC25EE39A5BBF00C97BABEEDA2AB4CA5EABC8560", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "87", - "last_block_id": { - "hash": "492DDC4ADF93C0AD9AE891B52EB83C23281C8B118F54B9CD6632DCF11667725D", - "parts": { - "hash": "95EEC124BBFE90931C80A870EC25EE39A5BBF00C97BABEEDA2AB4CA5EABC8560", - "total": 1 - } - }, - "last_commit_hash": "6951D8CD5B739A4059A6A004CCEF35F20DCE0E0BD246B1B52DD4B07033087284", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:20.042384566Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "492DDC4ADF93C0AD9AE891B52EB83C23281C8B118F54B9CD6632DCF11667725D", - "parts": { - "hash": "95EEC124BBFE90931C80A870EC25EE39A5BBF00C97BABEEDA2AB4CA5EABC8560", - "total": 1 - } - }, - "height": "86", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "PjqugrLNuSOyR6k4DOHMCNZ2yek7ex1oTWXpXZMeg+6dK0OAFyVSNX1jZJLxp5TpH3P6pjTfDe2iIbNAjWvCAA==", - "timestamp": "2023-02-24T15:10:20.042384566Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "5E17F7AB3D8F3F299812FFA3AC9C8F723242CD5B4AF1428F22008A6DE7B7A9F4", - "parts": { - "hash": "542B0E2E78CD2EDD9BE127ABA7FF702AC4769923842BF5AB02372F381FF4EA59", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "88", - "last_block_id": { - "hash": "5E17F7AB3D8F3F299812FFA3AC9C8F723242CD5B4AF1428F22008A6DE7B7A9F4", - "parts": { - "hash": "542B0E2E78CD2EDD9BE127ABA7FF702AC4769923842BF5AB02372F381FF4EA59", - "total": 1 - } - }, - "last_commit_hash": "EEF7D63B20F7D7D45B15CF247F74228EB016DDE6A9D020F6E61B1A06911C98D9", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:20.559940169Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "5E17F7AB3D8F3F299812FFA3AC9C8F723242CD5B4AF1428F22008A6DE7B7A9F4", - "parts": { - "hash": "542B0E2E78CD2EDD9BE127ABA7FF702AC4769923842BF5AB02372F381FF4EA59", - "total": 1 - } - }, - "height": "87", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "TpFxdfWpRSTADXLobRMb0DYHTFpd15Vv8nzoqXhdGzKSIv6MhtCF8TBeCnsJ49grSzsPH9EKrCflzu1ChsG/Bg==", - "timestamp": "2023-02-24T15:10:20.559940169Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "9CA4519BF6B7B6F8B444B9283CFF4882B025F29013308BF5BACF685A1BC31073", - "parts": { - "hash": "324A2C31DA12B8EA3F64215E7894650F2FE6A2609A6EC293050884B7C92CC9C3", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "89", - "last_block_id": { - "hash": "9CA4519BF6B7B6F8B444B9283CFF4882B025F29013308BF5BACF685A1BC31073", - "parts": { - "hash": "324A2C31DA12B8EA3F64215E7894650F2FE6A2609A6EC293050884B7C92CC9C3", - "total": 1 - } - }, - "last_commit_hash": "ADBC09F53226B878C36EC808FB053F6607B1580818941CF7B6D50AB7516C4561", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:21.076058301Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "9CA4519BF6B7B6F8B444B9283CFF4882B025F29013308BF5BACF685A1BC31073", - "parts": { - "hash": "324A2C31DA12B8EA3F64215E7894650F2FE6A2609A6EC293050884B7C92CC9C3", - "total": 1 - } - }, - "height": "88", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "jNsSA82uue8dr4A41135ZlvM5yKCI01/XlBw0/cHOZdD5UvI0tmmM8JaNFHep7D2W//XJ0bQul6CN9MV8wA5Ag==", - "timestamp": "2023-02-24T15:10:21.076058301Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "0CB7734218EDADD34ADE5592EA3A84588671F52F5EA8A170BFF8961544CD8F97", - "parts": { - "hash": "419294D85AC8E5EEBDF07DC3B74B96C349151CB6C7BFF82012388C3275855572", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "90", - "last_block_id": { - "hash": "0CB7734218EDADD34ADE5592EA3A84588671F52F5EA8A170BFF8961544CD8F97", - "parts": { - "hash": "419294D85AC8E5EEBDF07DC3B74B96C349151CB6C7BFF82012388C3275855572", - "total": 1 - } - }, - "last_commit_hash": "C69E392FF00BE1BB9137DFAD0E753FB3BF284A8C8773A823C1BCCA36E820FD54", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:21.592582419Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "0CB7734218EDADD34ADE5592EA3A84588671F52F5EA8A170BFF8961544CD8F97", - "parts": { - "hash": "419294D85AC8E5EEBDF07DC3B74B96C349151CB6C7BFF82012388C3275855572", - "total": 1 - } - }, - "height": "89", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "lKUG3bFeEfel61drclGjw3AXtfBEkJpK09c/dDsdcE6JPZ30xOAZ89lQbZHDprK4VasAmBGq+cG/sbRYDzToDg==", - "timestamp": "2023-02-24T15:10:21.592582419Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "4C58CB754A6BDAE5885039C3C5F69B45312F2EE58F2A0037C2BF61361DA98601", - "parts": { - "hash": "0621B594D1CA6E09D6FE6902AAE060A8A6856489DD5CF130AC09F7510AAA9AC7", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "91", - "last_block_id": { - "hash": "4C58CB754A6BDAE5885039C3C5F69B45312F2EE58F2A0037C2BF61361DA98601", - "parts": { - "hash": "0621B594D1CA6E09D6FE6902AAE060A8A6856489DD5CF130AC09F7510AAA9AC7", - "total": 1 - } - }, - "last_commit_hash": "9DE1760CA6549A3659E0067DAC9ADEB7EBCCA08442A252A5CCADAA2214EFB612", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:22.108085559Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "4C58CB754A6BDAE5885039C3C5F69B45312F2EE58F2A0037C2BF61361DA98601", - "parts": { - "hash": "0621B594D1CA6E09D6FE6902AAE060A8A6856489DD5CF130AC09F7510AAA9AC7", - "total": 1 - } - }, - "height": "90", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "B2JPXJZQf7vtp+og9kN4JNB802THzm8Eab8+eF2wI1ithaYVxkR/T1yVG0p/leH0vviPFuztjgyjtO2fakaNAw==", - "timestamp": "2023-02-24T15:10:22.108085559Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "60AA3E793D1DCA3B52752B1B2EFC76786729BB0205A9767BD315D0CC977EB0BD", - "parts": { - "hash": "5EEA3E2F658E696B24FF1E52CE4BC44FC4AE2B1B49E298E9D1E0CBD1134C9FCB", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "92", - "last_block_id": { - "hash": "60AA3E793D1DCA3B52752B1B2EFC76786729BB0205A9767BD315D0CC977EB0BD", - "parts": { - "hash": "5EEA3E2F658E696B24FF1E52CE4BC44FC4AE2B1B49E298E9D1E0CBD1134C9FCB", - "total": 1 - } - }, - "last_commit_hash": "004E153EB4178F225899750F55928E9A99F6BE935C3154BEFDB2C57ED410E117", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:22.627935121Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "60AA3E793D1DCA3B52752B1B2EFC76786729BB0205A9767BD315D0CC977EB0BD", - "parts": { - "hash": "5EEA3E2F658E696B24FF1E52CE4BC44FC4AE2B1B49E298E9D1E0CBD1134C9FCB", - "total": 1 - } - }, - "height": "91", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "8sR1nY5HI+MNc4UoiMg68z307YKjNaA9doU8LSCFoVlixKJ2MBJ4wZNK4GEMhlNPXV7ApPtLb18LR4j57TmrAg==", - "timestamp": "2023-02-24T15:10:22.627935121Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "EC6D4D7E18FA0A9146AA286EEC655867DFEFB2DA212A6773DE9E931B86FC4657", - "parts": { - "hash": "467542D1F4CE86B304782A8A69362E2D23187A6381EDDBA0AA95C2D11102A9FD", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "93", - "last_block_id": { - "hash": "EC6D4D7E18FA0A9146AA286EEC655867DFEFB2DA212A6773DE9E931B86FC4657", - "parts": { - "hash": "467542D1F4CE86B304782A8A69362E2D23187A6381EDDBA0AA95C2D11102A9FD", - "total": 1 - } - }, - "last_commit_hash": "F41FE46DA57C3433811E6F97F29AFF7122F094DF620F8610682ECA2703684AC1", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:23.147322944Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "EC6D4D7E18FA0A9146AA286EEC655867DFEFB2DA212A6773DE9E931B86FC4657", - "parts": { - "hash": "467542D1F4CE86B304782A8A69362E2D23187A6381EDDBA0AA95C2D11102A9FD", - "total": 1 - } - }, - "height": "92", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "donSKvwSA4bKEBoZACNz9C7FMA6XDU2J+wT9fzWIToi/Q35cweIUUnkDXtxC8wMHbESQNOXqqvLBVCftp+VBCA==", - "timestamp": "2023-02-24T15:10:23.147322944Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "365A77310094971325F336131FC6C707CD96912E1E7638FE54EF21B61E184DDF", - "parts": { - "hash": "806E84CA75FA5CCC0A1D4B11B219385FD7EDEF7BE75FC9635DC938A197D101B6", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "94", - "last_block_id": { - "hash": "365A77310094971325F336131FC6C707CD96912E1E7638FE54EF21B61E184DDF", - "parts": { - "hash": "806E84CA75FA5CCC0A1D4B11B219385FD7EDEF7BE75FC9635DC938A197D101B6", - "total": 1 - } - }, - "last_commit_hash": "8700C3DBD867E572FF65088CD5EBFD91AB9D2B2D818088CF034216DDE957A52E", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:23.664407624Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "365A77310094971325F336131FC6C707CD96912E1E7638FE54EF21B61E184DDF", - "parts": { - "hash": "806E84CA75FA5CCC0A1D4B11B219385FD7EDEF7BE75FC9635DC938A197D101B6", - "total": 1 - } - }, - "height": "93", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "349uZ2aFpkHCxvLE1+XUoK5MjN9EWJY5BN88mnTzYMeGoSyPTjdXArEZi+ahhHFzp9i95Xbz2+6UvOD4mz4uBg==", - "timestamp": "2023-02-24T15:10:23.664407624Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "4DE4E60D077F6F0CEAF71C7775A42C37592C8A26000714E766C64E12EB9B155F", - "parts": { - "hash": "9D04D896B0DB8C6C84800489B0BA03AB49F6F8DB7BAED2118D09B25676AA5358", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "95", - "last_block_id": { - "hash": "4DE4E60D077F6F0CEAF71C7775A42C37592C8A26000714E766C64E12EB9B155F", - "parts": { - "hash": "9D04D896B0DB8C6C84800489B0BA03AB49F6F8DB7BAED2118D09B25676AA5358", - "total": 1 - } - }, - "last_commit_hash": "3B7F666C62429CFE0B60367BBDC22E03DF2A5A9383F0BB9D6E907D18F14E6D7E", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:24.185861666Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "4DE4E60D077F6F0CEAF71C7775A42C37592C8A26000714E766C64E12EB9B155F", - "parts": { - "hash": "9D04D896B0DB8C6C84800489B0BA03AB49F6F8DB7BAED2118D09B25676AA5358", - "total": 1 - } - }, - "height": "94", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "xOdi2LNyWOiD+1ppcUTFW3Me4h2R8lOVgqM2Fr2j/3ujMihW3Sayr7ZLafKXgGvkLHIAOWBrJ18W3j6tjDkgBA==", - "timestamp": "2023-02-24T15:10:24.185861666Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "207601FFAC6D9C3B32B9361F4DC8E020A3F3D1FD771491B128103C2B6E652E79", - "parts": { - "hash": "E2C5A82E26ABC9F7A0966A82BA1E54EC03AA0D2A94FC7FFC532988B7EA4E600A", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "96", - "last_block_id": { - "hash": "207601FFAC6D9C3B32B9361F4DC8E020A3F3D1FD771491B128103C2B6E652E79", - "parts": { - "hash": "E2C5A82E26ABC9F7A0966A82BA1E54EC03AA0D2A94FC7FFC532988B7EA4E600A", - "total": 1 - } - }, - "last_commit_hash": "4651B25292ED60F01490E7274B8B7603906A937ABF630323E785F7F2DBD023AB", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:24.704428204Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "207601FFAC6D9C3B32B9361F4DC8E020A3F3D1FD771491B128103C2B6E652E79", - "parts": { - "hash": "E2C5A82E26ABC9F7A0966A82BA1E54EC03AA0D2A94FC7FFC532988B7EA4E600A", - "total": 1 - } - }, - "height": "95", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "3CXBmj7wA/d3o9TG4zm0U+eN4SbHeDqlKsI2FKIBmtZmB2xO+oJMNjn6sUnMVitkiS/92t9EisJB5od7fxirAA==", - "timestamp": "2023-02-24T15:10:24.704428204Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "7D824E6F79144AA944AAA0496AA259E29724759880CF0F3F2B4E10381CE3BC6B", - "parts": { - "hash": "068E0E25CC3CCA4DA820B43C28B9D061C784AF31F82CDECC986F407181C6E68C", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "97", - "last_block_id": { - "hash": "7D824E6F79144AA944AAA0496AA259E29724759880CF0F3F2B4E10381CE3BC6B", - "parts": { - "hash": "068E0E25CC3CCA4DA820B43C28B9D061C784AF31F82CDECC986F407181C6E68C", - "total": 1 - } - }, - "last_commit_hash": "99E0A3EE0594B1869745146C0BAC12AB0ACC0D3983BBC14AF26AA50D9A55477D", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:25.221701277Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "7D824E6F79144AA944AAA0496AA259E29724759880CF0F3F2B4E10381CE3BC6B", - "parts": { - "hash": "068E0E25CC3CCA4DA820B43C28B9D061C784AF31F82CDECC986F407181C6E68C", - "total": 1 - } - }, - "height": "96", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "zQ40QR95nPnWstq5uqmr8l56sM0x5m0a0vr7U2Pg1eU0zsoX/kofZO1/jMWD8nWyiGZm6C0NxpMO4RZWIHoADg==", - "timestamp": "2023-02-24T15:10:25.221701277Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "8BF089E09C461AD27EA7D9C4AEB993B2E13B31F5A90552B83951E88B9E7D6487", - "parts": { - "hash": "E5A14CFB467046DF5C9482491E2F15751C15735755723BB2178CC81FFCF8E98B", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "98", - "last_block_id": { - "hash": "8BF089E09C461AD27EA7D9C4AEB993B2E13B31F5A90552B83951E88B9E7D6487", - "parts": { - "hash": "E5A14CFB467046DF5C9482491E2F15751C15735755723BB2178CC81FFCF8E98B", - "total": 1 - } - }, - "last_commit_hash": "6C9BFDBE036356873F5852813F2ECD3427CD6BA55B58A3814128FE5971AA4FCE", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:25.737308548Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "8BF089E09C461AD27EA7D9C4AEB993B2E13B31F5A90552B83951E88B9E7D6487", - "parts": { - "hash": "E5A14CFB467046DF5C9482491E2F15751C15735755723BB2178CC81FFCF8E98B", - "total": 1 - } - }, - "height": "97", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "0UKiZ7J+zV5THP2IeB/v9XrH836d4pknGL5YSVhjuqbPu0KW9ZjwlS0v01GvQiQHbOsKntN1nd56hulOnKDuBA==", - "timestamp": "2023-02-24T15:10:25.737308548Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "D7415E09EAEBF2CD3C25970AD3199E365A50A719E218731D4F06ADF692DE0213", - "parts": { - "hash": "BF56F8DD97827A06D2AE619EFFDC531640E2BC3089C4A8D360906D1F812B6AC0", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "99", - "last_block_id": { - "hash": "D7415E09EAEBF2CD3C25970AD3199E365A50A719E218731D4F06ADF692DE0213", - "parts": { - "hash": "BF56F8DD97827A06D2AE619EFFDC531640E2BC3089C4A8D360906D1F812B6AC0", - "total": 1 - } - }, - "last_commit_hash": "8D3CF0BEFF5410E2654380A60F004B2FF5B1C5B1B4266D7ED05DE51B801AC0F2", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:26.252637052Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "D7415E09EAEBF2CD3C25970AD3199E365A50A719E218731D4F06ADF692DE0213", - "parts": { - "hash": "BF56F8DD97827A06D2AE619EFFDC531640E2BC3089C4A8D360906D1F812B6AC0", - "total": 1 - } - }, - "height": "98", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "VcZ0iMNa7ZVgnBzrDc66Fh3Rxp0Fj135Etl1MZIOx4rJ2v74K3uxFUEH7QFNldyaApYb7zxkOVCgnR8fECoiBA==", - "timestamp": "2023-02-24T15:10:26.252637052Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "566AE1C48174C2664ADB0514D8968FF13C993D1E7898638D52F1BDAC21295D05", - "parts": { - "hash": "91D28FBA1F49C71618A36342E59AC9DE427587E9F2CC13459D2D68D21BEBFE4B", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "100", - "last_block_id": { - "hash": "566AE1C48174C2664ADB0514D8968FF13C993D1E7898638D52F1BDAC21295D05", - "parts": { - "hash": "91D28FBA1F49C71618A36342E59AC9DE427587E9F2CC13459D2D68D21BEBFE4B", - "total": 1 - } - }, - "last_commit_hash": "E2842496547C1069C2ECDD16B3DD2B33E03023FFBB2257198FFF360FDD908CE2", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:26.772972231Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "566AE1C48174C2664ADB0514D8968FF13C993D1E7898638D52F1BDAC21295D05", - "parts": { - "hash": "91D28FBA1F49C71618A36342E59AC9DE427587E9F2CC13459D2D68D21BEBFE4B", - "total": 1 - } - }, - "height": "99", - "round": 0, - "signatures": [ - { - "block_id_flag": 2, - "signature": "lN78RMeHD7JpYEmQ++1N2vXM44mqDbMoqoHZRPnNAzTyeafiRp7XvBzbY9TOnzd92tNhU6pw6HXrbEJWL66+BA==", - "timestamp": "2023-02-24T15:10:26.772972231Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" - } - ] - } - }, - "block_id": { - "hash": "5032349B18DF6761088F415B0946CCF113B59E05638CA1E18DA11CAB02CBD71F", - "parts": { - "hash": "8A72621074DCF3ADDD2BB520601D7D1070A970894E4FC77B52E971CB453B5F55", - "total": 1 - } - } - }, - { - "block": { - "data": { - "txs": [] - }, - "evidence": { - "evidence": [] - }, - "header": { - "app_hash": "0000000000000000", - "chain_id": "dockerchain", - "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", - "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "101", - "last_block_id": { - "hash": "5032349B18DF6761088F415B0946CCF113B59E05638CA1E18DA11CAB02CBD71F", - "parts": { - "hash": "8A72621074DCF3ADDD2BB520601D7D1070A970894E4FC77B52E971CB453B5F55", - "total": 1 - } - }, - "last_commit_hash": "900B690F191D6EB0B29280084A5FC8A30B4778C6DF8A857EE02AA2D05E72C196", - "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:10:27.290383356Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "version": { - "app": "1", - "block": "11" - } - }, - "last_commit": { - "block_id": { - "hash": "5032349B18DF6761088F415B0946CCF113B59E05638CA1E18DA11CAB02CBD71F", - "parts": { - "hash": "8A72621074DCF3ADDD2BB520601D7D1070A970894E4FC77B52E971CB453B5F55", - "total": 1 - } - }, - "height": "100", + "height": "45", "round": 0, "signatures": [ { "block_id_flag": 2, - "signature": "oKrR1shXwkeD2j6uW1HMSQPjekjKGtnvwtojLoAzPQ+pqeC3d1/F9MR5Vf6Vzy59fk6J+DZja9Wg7kJscsg4CQ==", - "timestamp": "2023-02-24T15:10:27.290383356Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "CL378kU/Vcq9YBymUUopYln16O9e14w044GPz2R9rp+mLr/wz+HO4ZRPDEGJh3+y84+dfmO1xJk8VAZxUBBlBw==", + "timestamp": "2023-02-27T07:13:26.790394939Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } }, "block_id": { - "hash": "78587FB12AAF743AC278DB6E4E551AF7842BC509B40436115C195AE641E6CB06", + "hash": "2490417BFCE699B5C64AF27F28839C7F4D401C8C4C8095308E9247991BABE21C", "parts": { - "hash": "872B22B5E0DB935A2A309320B13D73D14B8DB351AB823BA0E215AD141F1E02DB", + "hash": "4801AC89D71EFAF2244E4AB4D4EEBA43CE4D00DC1AA0F620E3CE1FC5C5B0E658", "total": 1 } } } ], - "total_count": "213" + "total_count": "45" } } \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json index aca48bc37..3eb4ef677 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/blockchain_from_1_to_10.json @@ -1,13 +1,13 @@ { - "id": "8b6f991a-4a2c-4dcf-9411-5c706f413235", + "id": "318f73b5-0fe6-43cc-935f-ef76f6c61cd4", "jsonrpc": "2.0", "result": { "block_metas": [ { "block_id": { - "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "hash": "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639", "parts": { - "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "hash": "E16EDCB0EC135191F5C017FDF232967F50919E06B0F2F419FA93D006E606CF05", "total": 1 } }, @@ -20,18 +20,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "10", "last_block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } }, - "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_commit_hash": "E8DE5F9749FA5785B9B9F106C82233C910C75AE8A0903D1FAB146C1DD4E7A0EC", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:40.123954449Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:08.140032018Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -41,9 +41,9 @@ }, { "block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } }, @@ -56,18 +56,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "9", "last_block_id": { - "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "hash": "875A50CDD812054D87A7F5CC6A0C7E224C6E2DF2F2A89EA51B9DCEE6136B469E", "parts": { - "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "hash": "74F62C8CEF42AF0A685D84C8422751CD2269E16A793FAC95B96A8C42132E8338", "total": 1 } }, - "last_commit_hash": "22FC31E6CCA7D5C580B14FC94E506524041B2064C9DB27D54A5AC3254950CBA9", + "last_commit_hash": "9EEDE09BD5848E1F97D54D4C2633582D152FEF610869E3D29815B5A2159D8631", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:39.606408964Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:07.619684947Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -77,9 +77,9 @@ }, { "block_id": { - "hash": "A571BEE30FB64F9E168F3C9A87AE5350D53F576B9392FFA078BDEE507998A380", + "hash": "875A50CDD812054D87A7F5CC6A0C7E224C6E2DF2F2A89EA51B9DCEE6136B469E", "parts": { - "hash": "417610B573D6BEADBD1D29A990AD52D61D6E842F955F849259E22574EC609464", + "hash": "74F62C8CEF42AF0A685D84C8422751CD2269E16A793FAC95B96A8C42132E8338", "total": 1 } }, @@ -92,18 +92,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "8", "last_block_id": { - "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "hash": "29374DAF235CC5A1751E09A22DD6F200D1EA3BEB473A7820C4CC7F149DB032AB", "parts": { - "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "hash": "7AEA98F9C8658AF6B5DE7B41AF0658AACBDC54D882E17BCFB35727B95EAD9E50", "total": 1 } }, - "last_commit_hash": "D12B708778B847858029349205FD4BE0F8B22A8DE61943D5C2D4B49396767775", + "last_commit_hash": "6B184CC5107EAD2DD682BD3A1A60B568ECB9EE2A75DA34F237E42550B69E3146", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:39.090086292Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:07.101498447Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -113,9 +113,9 @@ }, { "block_id": { - "hash": "C5A55F994166071F320940F27CD29A2963A9CC4C26F084A15955166D039865E2", + "hash": "29374DAF235CC5A1751E09A22DD6F200D1EA3BEB473A7820C4CC7F149DB032AB", "parts": { - "hash": "B4458AAAD3097CA6D476037EE025B7300FC1ED38AB4789815A640CAB0DCAADE7", + "hash": "7AEA98F9C8658AF6B5DE7B41AF0658AACBDC54D882E17BCFB35727B95EAD9E50", "total": 1 } }, @@ -128,18 +128,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "7", "last_block_id": { - "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "hash": "92DF7250265107D9FB3BAC7A97CA25AC2543B86E960632D11DDDE74FB5C2F41F", "parts": { - "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "hash": "9F7DCBC5879343913CFAA6365B68E34FEA17CB1E1D1B7044ED72131D1F5DE9F9", "total": 1 } }, - "last_commit_hash": "266129248C2C0D2684F1D1BE8E5A119742520BAA03F740BE5C612E8CFB245DB7", + "last_commit_hash": "325A2D023AAA8705C2D9FF1593C8904EF16258825EC8212600BE98C69E20F3D2", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:38.570297947Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:06.580593612Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -149,9 +149,9 @@ }, { "block_id": { - "hash": "4BD88ACC437AA1A866FAE2CDCC74EE56F65B2FC0784D5465E41EBAA43475D79F", + "hash": "92DF7250265107D9FB3BAC7A97CA25AC2543B86E960632D11DDDE74FB5C2F41F", "parts": { - "hash": "F603C1B923871B81A17528875725713AE3C364838D86182588EF0FBE1DCEFC21", + "hash": "9F7DCBC5879343913CFAA6365B68E34FEA17CB1E1D1B7044ED72131D1F5DE9F9", "total": 1 } }, @@ -164,18 +164,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "6", "last_block_id": { - "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "hash": "38070040A8D1365B66B0344664106193ECF1D18444A769E51D2881B15087DCD7", "parts": { - "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "hash": "59876DFD84701B32F2AB5679D498E33A9AC26D11165B142D5E9EF3B2AF021BB9", "total": 1 } }, - "last_commit_hash": "769E5D10F6B90219BB10D7DA6600728E02A760476A3F0216914B4E3D758E0ED6", + "last_commit_hash": "139381A60C8BCAF336ED8E8373FE52F7469DA76C054B9265921322046FD97B93", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:38.051624453Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:06.065052373Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -185,9 +185,9 @@ }, { "block_id": { - "hash": "A73D58893304C4FDA7368CE91E435F4E1CB584C6837FEDFBF294AE157B17367B", + "hash": "38070040A8D1365B66B0344664106193ECF1D18444A769E51D2881B15087DCD7", "parts": { - "hash": "19BF8BE26F7F52770F6CA7162B0AE1F57E3D8A0B2EF748BD8DC94C1337B07FC3", + "hash": "59876DFD84701B32F2AB5679D498E33A9AC26D11165B142D5E9EF3B2AF021BB9", "total": 1 } }, @@ -200,18 +200,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "5", "last_block_id": { - "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "hash": "7D162051AC61242B7613E085CA4E3488AE6A953E8BE3B72A9E6938E62F5212AF", "parts": { - "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "hash": "D9A258567016DE8D364C0E64E3882C7DAD6488B129CE4612B3D67EBFF7CFF288", "total": 1 } }, - "last_commit_hash": "EDC03890397D8183CD0FE0A25A729BFC5192851DC8ADA3642B7D23E0B7B51A21", + "last_commit_hash": "4D95F1B754571826AA7C01E521D1D73A309880714C81DE48255DA2D57D55C756", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:37.533687433Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:05.545291963Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -221,9 +221,9 @@ }, { "block_id": { - "hash": "1BD4217022FBF0DC1EAABCC11E0844DCBAF509A8D1DBE55B403D3AEAD3DBC023", + "hash": "7D162051AC61242B7613E085CA4E3488AE6A953E8BE3B72A9E6938E62F5212AF", "parts": { - "hash": "1358DAB96CD26C3E54AD6CE8FFF58F2CAFEDAD3FADD79FD65BFCEBE29BCF3DD6", + "hash": "D9A258567016DE8D364C0E64E3882C7DAD6488B129CE4612B3D67EBFF7CFF288", "total": 1 } }, @@ -236,18 +236,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "4", "last_block_id": { - "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "hash": "AFEB65E07422484A7295D2ABFEB66621386B98E8FC022B8BD177C14BDB4A3DB2", "parts": { - "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "hash": "BC99391E5E093CEEE17A888CE4FA0E13BD06A0BA026336B662D445F5B1455DA9", "total": 1 } }, - "last_commit_hash": "6DDE3F5FEB4E7E88FCF3A9B8E5A9B178B525E68817C1EC05E2DE9E03AB164D96", + "last_commit_hash": "97FFFE3763FFAB168334C271B859483B95BF393CF4E61C91590CF3F6F55C4204", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:37.018159177Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:05.026580561Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -257,9 +257,9 @@ }, { "block_id": { - "hash": "DD5D3E9DAEBDC24302BD1023D0A98DDC4DDC2B2ABD299A12BB64A7D20F0BFF9B", + "hash": "AFEB65E07422484A7295D2ABFEB66621386B98E8FC022B8BD177C14BDB4A3DB2", "parts": { - "hash": "7A8898E1FDA700B889F6EB71B4C5C8E57463AF148745A996C02FD112F250BD28", + "hash": "BC99391E5E093CEEE17A888CE4FA0E13BD06A0BA026336B662D445F5B1455DA9", "total": 1 } }, @@ -272,18 +272,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "3", "last_block_id": { - "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "hash": "618E263A7265C42E04D4C5DE3370F7B64C0AC8271435D17A20360C09A702E353", "parts": { - "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "hash": "23296CEC8762B62711D174F14FFE5807F910AE3360F24BE55B58C1E8911FD01F", "total": 1 } }, - "last_commit_hash": "6237CD7F07174FB28966A889F6A9B4D26DC6D7F104D0B4333007E6C2AB7D61C1", + "last_commit_hash": "7183ED105A3A3FF34CBAEB2CDCA13F3C3437EF0A140C40EABA425709AD44C066", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:36.499560496Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:04.508252675Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -293,9 +293,9 @@ }, { "block_id": { - "hash": "91378634A223F02FD4F18B97A73CFD8A2A6715577B652E5248CBAD322B47809B", + "hash": "618E263A7265C42E04D4C5DE3370F7B64C0AC8271435D17A20360C09A702E353", "parts": { - "hash": "2D902188B694769B15CF629B609F01EE68F0620A9D85383849FC779F9FF8C7F5", + "hash": "23296CEC8762B62711D174F14FFE5807F910AE3360F24BE55B58C1E8911FD01F", "total": 1 } }, @@ -308,18 +308,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "2", "last_block_id": { - "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "hash": "D55CD72165688BE21F2DF8C9AE46FA2BCA423223E99FC665DD2E621066F443C5", "parts": { - "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "hash": "372520F1B93CD0EC3901006DE2E3CD752C9141628A7B430088DF912171355DDA", "total": 1 } }, - "last_commit_hash": "227D78AC78B219692FC3EE18BCE5FD46E86F382979628FB6BE01DDF4C9E66750", + "last_commit_hash": "48018604B85D54DC6E49DB6E4CF12F67FC56337B84E378AE2357B3E2CE4F1EC9", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:35.982946125Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:03.991666836Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -329,9 +329,9 @@ }, { "block_id": { - "hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "hash": "D55CD72165688BE21F2DF8C9AE46FA2BCA423223E99FC665DD2E621066F443C5", "parts": { - "hash": "A922EC01B8A22C012EB71141759984766CDC1ABE409BCB8D45B2594999D68C6E", + "hash": "372520F1B93CD0EC3901006DE2E3CD752C9141628A7B430088DF912171355DDA", "total": 1 } }, @@ -352,10 +352,10 @@ }, "last_commit_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:35.386925428Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:03.391799721Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -364,6 +364,6 @@ "num_txs": "0" } ], - "last_height": "216" + "last_height": "177" } } \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json index 26a9b2234..c09dbb1f0 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_async.json @@ -1,5 +1,5 @@ { - "id": "37104243-1a80-4b5f-a917-cf38c863171f", + "id": "58d2cc61-6e49-480a-9bc1-584f90203d4d", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json index ed5e29119..5ebffd3b6 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_commit.json @@ -1,5 +1,5 @@ { - "id": "be2a11c5-e6b3-4803-9f0e-140330c65f43", + "id": "c1b2fe8d-ac41-4c65-aad1-15ff0b156fe1", "jsonrpc": "2.0", "result": { "check_tx": { @@ -77,6 +77,6 @@ "log": "" }, "hash": "D63F9C23791E610410B576D8C27BB5AEAC93CC1A58522428A7B32A1276085860", - "height": "229" + "height": "48" } } \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json index 544560af0..4c1874068 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/broadcast_tx_sync.json @@ -1,5 +1,5 @@ { - "id": "c0bbfd1a-6b75-421e-ba3f-07dec9c1ba98", + "id": "5daaaf5b-d964-4333-9866-9caab5c8efdc", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json index b68008365..0d75f9208 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/commit_at_height_10.json @@ -1,14 +1,14 @@ { - "id": "435978e8-89ed-4128-a94e-1f25dcd46c28", + "id": "9493368d-025d-49b3-a3f8-486e55835e3a", "jsonrpc": "2.0", "result": { "canonical": true, "signed_header": { "commit": { "block_id": { - "hash": "3DBFE1F970CD3BAC420F0149829ED41524CAED2189BA57AC07902D27D5CE993A", + "hash": "FCF9C2537FC3534CA71001FE1F14C4F769090948C1A521682F612E7CF73AE639", "parts": { - "hash": "A3E9DB877E05A4D5D4430643873F3C6D40F108ACA9136721832FD355729F9361", + "hash": "E16EDCB0EC135191F5C017FDF232967F50919E06B0F2F419FA93D006E606CF05", "total": 1 } }, @@ -17,9 +17,9 @@ "signatures": [ { "block_id_flag": 2, - "signature": "gozurqzPCl9et0LQgKksMg60fdU1cPOoDfIEUwMCWMZt8/5cRYiUbr7+kJj9AHF2/C1w3Abs8a+QxtVJPnWlBw==", - "timestamp": "2023-02-24T15:09:40.640670992Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "qJblJeAl6OtGRKkOa91+HLzX3ZGl/Nlnl5K9RiT2gRSPgPSjxq+95mSQSJ3b3I38mdZvYLUML6kEGvC/zjlJCQ==", + "timestamp": "2023-02-27T07:13:08.658439642Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] }, @@ -31,18 +31,18 @@ "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "height": "10", "last_block_id": { - "hash": "77F05A5D95801D058CC77BF21A55F5DEC9208ECC34F256108CCAD13A4BCB0C2E", + "hash": "9D9521F13DCA0C63C395F943F5A68B270A053B608145577F32907A70D8332E56", "parts": { - "hash": "E743BDF978FE1FD3A1F24BBF31E9AB175DC0F8AFC0EAC2F75422DE8628CD55F3", + "hash": "6760DBDF3B785148DB885DA08143118C6C30850995FF3C99E0A3303650E2430D", "total": 1 } }, - "last_commit_hash": "98CA1A98C4FB74B77553739E0297E451E2B748EEA0A59B8035D3AD92A674F471", + "last_commit_hash": "E8DE5F9749FA5785B9B9F106C82233C910C75AE8A0903D1FAB146C1DD4E7A0EC", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:09:40.123954449Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:08.140032018Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json index 78a1ec028..970cd99d7 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_params.json @@ -1,5 +1,5 @@ { - "id": "abbcacd1-ff31-4725-b5ff-c46e21c02736", + "id": "6713de4d-11cc-4725-9dff-1dad524f2d44", "jsonrpc": "2.0", "result": { "block_height": "10", diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json index 06507d396..05f3fc6f9 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/consensus_state.json @@ -1,9 +1,9 @@ { - "id": "6954460c-8b30-41e9-9752-261e063dda0c", + "id": "d741eb15-a8cf-4b87-ae31-689ee9bcb1e2", "jsonrpc": "2.0", "result": { "round_state": { - "height/round/step": "223/0/1", + "height/round/step": "184/0/1", "height_vote_set": [ { "precommits": [ @@ -20,10 +20,10 @@ "locked_block_hash": "", "proposal_block_hash": "", "proposer": { - "address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "address": "DD8A65495B6240145764A74E78CF203D51510371", "index": 0 }, - "start_time": "2023-02-24T15:11:31.310596522Z", + "start_time": "2023-02-27T07:14:38.877277579Z", "valid_block_hash": "" } } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json index 5e15d5a4d..f298ff2ec 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/genesis.json @@ -1,5 +1,5 @@ { - "id": "30777544-c3da-4444-bef1-6035ece3b1c0", + "id": "217c0860-637e-4368-9346-052ffbdee73c", "jsonrpc": "2.0", "result": { "genesis": { @@ -24,16 +24,16 @@ "app": "0" } }, - "genesis_time": "2023-02-24T15:09:35.386925428Z", + "genesis_time": "2023-02-27T07:13:03.391799721Z", "initial_height": "1", "validators": [ { - "address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "address": "DD8A65495B6240145764A74E78CF203D51510371", "name": "", "power": "10", "pub_key": { "type": "tendermint/PubKeyEd25519", - "value": "z/0hzsnbHD6bSLl+2Nmmg0C8vLMo0ZkUHnNCUaXBAgQ=" + "value": "OYpM2RXHEO1/R3jJRhAbjY8JhvjTBbiNJKBStEKu12s=" } } ] diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json index 3f0397f86..2704a0dbf 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/net_info.json @@ -1,5 +1,5 @@ { - "id": "e6cd2152-119e-4349-bf6d-ec8b1e5e077f", + "id": "de1eb555-5788-4ee4-b263-a447ab6de53a", "jsonrpc": "2.0", "result": { "listeners": [ diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/status.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/status.json index 6ad4bfa43..07a144e9f 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/status.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/status.json @@ -1,10 +1,10 @@ { - "id": "cd2af599-b99a-4fdb-a7ed-ee2734e77ebb", + "id": "d517d5b0-22de-4684-89ea-0d822293d7f6", "jsonrpc": "2.0", "result": { "node_info": { "channels": "40202122233038606100", - "id": "56b7224d0a726d7ebeace322ac98c3654673dd4d", + "id": "594d6b74ea5d99705f5cfbd28e20d937bda4c689", "listen_addr": "tcp://0.0.0.0:26656", "moniker": "dockernode", "network": "dockerchain", @@ -22,19 +22,19 @@ "sync_info": { "catching_up": false, "earliest_app_hash": "", - "earliest_block_hash": "BF3827E6A497C55EFCE60AFB641F629DFED0CE4614DD9E7329788DC65E2E97D5", + "earliest_block_hash": "D55CD72165688BE21F2DF8C9AE46FA2BCA423223E99FC665DD2E621066F443C5", "earliest_block_height": "1", - "earliest_block_time": "2023-02-24T15:09:35.386925428Z", + "earliest_block_time": "2023-02-27T07:13:03.391799721Z", "latest_app_hash": "0600000000000000", - "latest_block_hash": "8C6B41DE8CF6A72E435413EDB1FA1AC270B61F75297CEEE4938378E109AD0560", - "latest_block_height": "234", - "latest_block_time": "2023-02-24T15:11:36.508177149Z" + "latest_block_hash": "3CFC71BF78C7520A29378119AA39D0D585C75227E3B8EF8DCF19B4EB5CBF0E9A", + "latest_block_height": "53", + "latest_block_time": "2023-02-27T07:13:30.422625189Z" }, "validator_info": { - "address": "87F74499559B0B60995F57C2224D27E55DD46ACD", + "address": "DD8A65495B6240145764A74E78CF203D51510371", "pub_key": { "type": "tendermint/PubKeyEd25519", - "value": "z/0hzsnbHD6bSLl+2Nmmg0C8vLMo0ZkUHnNCUaXBAgQ=" + "value": "OYpM2RXHEO1/R3jJRhAbjY8JhvjTBbiNJKBStEKu12s=" }, "voting_power": "10" } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json index 1093a9a03..c021fad1f 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_malformed.json @@ -4,6 +4,6 @@ "data": "failed to parse query: \nparse error near PegText (line 1 symbol 2 - line 1 symbol 11):\n\"malformed\"\n", "message": "Internal error" }, - "id": "8c013455-ab08-4b8a-a08f-deb884644319", + "id": "dc2d9ee9-e1f7-401d-b106-ed3b3b1fa24c", "jsonrpc": "2.0" } \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json index 3449a4cfa..9e2f3ac83 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_0.json @@ -1,5 +1,5 @@ { - "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "id": "d7848eb8-b304-435e-b869-0dcb56fdf807", "jsonrpc": "2.0", "result": { "data": { @@ -18,20 +18,20 @@ "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "237", + "height": "56", "last_block_id": { - "hash": "1593E40FB45914C56AB57388EC8F687536D815411F574186A5C1178FC65AEE30", + "hash": "60C0B6596F4F7C591356C5137A6B703C57CF04D9BF9A01845EEE9E1AAF591A4C", "parts": { - "hash": "450C775C1FC4E37B747F45EB9DC99593E4D3A8CB831786ED1A9D80EBE3AF17F1", + "hash": "A80BE8FE1D9C786A8C3ED5DA108D86041B139C381A71F88BA2AD0B4976B2ADAE", "total": 1 } }, - "last_commit_hash": "DF9784413CE9D2D548728192DF9973B7A29ABC8DCB48D6DFB6AEBC519CC8D7DB", + "last_commit_hash": "2B22FC2C9495216758CCE6C2DD4F995E6972E0B106ACF4A03C8551AD4473786E", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:11:38.062402874Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:31.980620894Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -39,20 +39,20 @@ }, "last_commit": { "block_id": { - "hash": "1593E40FB45914C56AB57388EC8F687536D815411F574186A5C1178FC65AEE30", + "hash": "60C0B6596F4F7C591356C5137A6B703C57CF04D9BF9A01845EEE9E1AAF591A4C", "parts": { - "hash": "450C775C1FC4E37B747F45EB9DC99593E4D3A8CB831786ED1A9D80EBE3AF17F1", + "hash": "A80BE8FE1D9C786A8C3ED5DA108D86041B139C381A71F88BA2AD0B4976B2ADAE", "total": 1 } }, - "height": "236", + "height": "55", "round": 0, "signatures": [ { "block_id_flag": 2, - "signature": "7RvLshAh+YLLWVqFtdDP6eQgMdfaE5YyX1uFj/vk30WWjWxa6ChIWtZVlMz4yjIQ7TwFAVua1gKZdcIYI6zcBw==", - "timestamp": "2023-02-24T15:11:38.062402874Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "k0/R5RXKtdQNqb+jO4Zg655dff4armOVI00upV0mlOyvxdo059HHEr6GZcWlwXZjtxntHgDMnR6R2C2YLc/HCw==", + "timestamp": "2023-02-27T07:13:31.980620894Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json index ac271f661..8120f29c3 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json @@ -1,5 +1,5 @@ { - "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "id": "d7848eb8-b304-435e-b869-0dcb56fdf807", "jsonrpc": "2.0", "result": { "data": { @@ -18,20 +18,20 @@ "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "238", + "height": "57", "last_block_id": { - "hash": "CE67E8FAECB5CCBC0ED9CBC33FA4C62E4714F05C115A6FEDBBA7BCA003E0E299", + "hash": "7C88172D141FD038A4320E68F7B089A9669DE2E9A8FA62ED5037C0379437A9CF", "parts": { - "hash": "6BF6AC83B283D927A9C75349350D1F2705D3F8A19F056ECB1E872B6CD178654A", + "hash": "33DE3DBBE54D0CCBE10CC16B63FD95DD737C1D1595FDDA142F8FF5E15E590256", "total": 1 } }, - "last_commit_hash": "839ECB7DA2A777EAA2FC082E77797F839638227976FF58A683A189EA83737B27", + "last_commit_hash": "AD1F18EEC4FAE578CED2CA39C2119A22ED0C528F57F4BE25902A3923AE0722C7", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:11:38.579201448Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:32.50031582Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -39,20 +39,20 @@ }, "last_commit": { "block_id": { - "hash": "CE67E8FAECB5CCBC0ED9CBC33FA4C62E4714F05C115A6FEDBBA7BCA003E0E299", + "hash": "7C88172D141FD038A4320E68F7B089A9669DE2E9A8FA62ED5037C0379437A9CF", "parts": { - "hash": "6BF6AC83B283D927A9C75349350D1F2705D3F8A19F056ECB1E872B6CD178654A", + "hash": "33DE3DBBE54D0CCBE10CC16B63FD95DD737C1D1595FDDA142F8FF5E15E590256", "total": 1 } }, - "height": "237", + "height": "56", "round": 0, "signatures": [ { "block_id_flag": 2, - "signature": "Dn0TS9EVlDC49tUyTvaQSqassCWYWOdqOQ1srEpzT2fdNTM4ovzXCeXsQgIdyGKxi+1GJge90ljVOOPc/lo3Ag==", - "timestamp": "2023-02-24T15:11:38.579201448Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "Gjt0bqP0wyIjCtzVcrQ1yA1OFcZQZUawFCKrBITjtCJeqDN3f5FUITe52Y6St6amM23zr18QObj/DeUAdt3DCA==", + "timestamp": "2023-02-27T07:13:32.50031582Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json index 191af4c0f..d7188e4c4 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_2.json @@ -1,5 +1,5 @@ { - "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "id": "d7848eb8-b304-435e-b869-0dcb56fdf807", "jsonrpc": "2.0", "result": { "data": { @@ -18,20 +18,20 @@ "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "239", + "height": "58", "last_block_id": { - "hash": "562CC9E027599E2E6EF5DBC0F4BFEAE3B0CA2EE419E9181C4F000F4C6937E970", + "hash": "953582B5F928C39F101565321CC67BC234733825A5563C6BD78B5A6F2569CFFD", "parts": { - "hash": "F3434293749106B5861D97EB8C617EAFE66F3A7705CCB53C818ACEDF089FB9B8", + "hash": "8EA4905EB1D92878268729E8B9537611110C12A725FFE132094EA52E87DA188F", "total": 1 } }, - "last_commit_hash": "61B0F7374BA2D42A637B22ADB13AC6877AB3D0F7FADDFF1DBCAF50C3B03A4ECE", + "last_commit_hash": "A69B7992885ED130FED089E2C0D8C4EBD6D6AFE38836F9C6CA531AE3A423E6C1", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:11:39.096768039Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:33.01910569Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -39,20 +39,20 @@ }, "last_commit": { "block_id": { - "hash": "562CC9E027599E2E6EF5DBC0F4BFEAE3B0CA2EE419E9181C4F000F4C6937E970", + "hash": "953582B5F928C39F101565321CC67BC234733825A5563C6BD78B5A6F2569CFFD", "parts": { - "hash": "F3434293749106B5861D97EB8C617EAFE66F3A7705CCB53C818ACEDF089FB9B8", + "hash": "8EA4905EB1D92878268729E8B9537611110C12A725FFE132094EA52E87DA188F", "total": 1 } }, - "height": "238", + "height": "57", "round": 0, "signatures": [ { "block_id_flag": 2, - "signature": "V+17mMoSu+9HLPJ4joKXpd+SflRc0AQXI3kiMXz+zeVGWNLdRrfjWVoMOm9JkvI7Llm4eLzNsOkoUk0OhEAEBA==", - "timestamp": "2023-02-24T15:11:39.096768039Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "a4ujPf5Q8b/bTM2AjRA1/TQC71Xse9kPBIHcITCiyoC24yb5azGGLrga/27+bglz0HJIMtKwumbLsKtG9sJjAA==", + "timestamp": "2023-02-27T07:13:33.01910569Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json index cf4668893..fc0cd8fac 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_3.json @@ -1,5 +1,5 @@ { - "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "id": "d7848eb8-b304-435e-b869-0dcb56fdf807", "jsonrpc": "2.0", "result": { "data": { @@ -18,20 +18,20 @@ "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "240", + "height": "59", "last_block_id": { - "hash": "CD762D6BE3E309711B614B34EB07B9DA517612376051B7ECFC908B7ADC473304", + "hash": "5FEA892A1B3A0A0E8C123AE91EACABF28F6B3674EE00902FEDD24430D56B61BE", "parts": { - "hash": "A1B8CD48BE42269C0858715B757CE75BCD05BA8C86752820D78A386EF8391B92", + "hash": "062F2511A22D89032C67D5ECEB5D99A1E4025581EB087C1F921F4EC6CFF7B103", "total": 1 } }, - "last_commit_hash": "05CAC30F4EE7378FF3EB02C41DD735CAC0AA2D71CBCA6E07FB5E05355190BD16", + "last_commit_hash": "93E03808BBD103ADB03BD7BB511962F254B85FB548B0132FE43771E3A3C8EF48", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:11:39.615658185Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:33.537543698Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -39,20 +39,20 @@ }, "last_commit": { "block_id": { - "hash": "CD762D6BE3E309711B614B34EB07B9DA517612376051B7ECFC908B7ADC473304", + "hash": "5FEA892A1B3A0A0E8C123AE91EACABF28F6B3674EE00902FEDD24430D56B61BE", "parts": { - "hash": "A1B8CD48BE42269C0858715B757CE75BCD05BA8C86752820D78A386EF8391B92", + "hash": "062F2511A22D89032C67D5ECEB5D99A1E4025581EB087C1F921F4EC6CFF7B103", "total": 1 } }, - "height": "239", + "height": "58", "round": 0, "signatures": [ { "block_id_flag": 2, - "signature": "8yW43rI/8kR60jaeb9ccWd32QG5HNGzh5zBtnRuAIZKJfCrezLYqegGHmNE0ufSS3IiiM3Pq2oExbnh2HrbGCA==", - "timestamp": "2023-02-24T15:11:39.615658185Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "lrvMV2Z4GVXhb4E4szfmnwR8rUe6jTXjpDt9JMhvRJZfjTRV/RR3iMoM+4pKC0VJmlzU+fo0MDoRtu6OWBtqCg==", + "timestamp": "2023-02-27T07:13:33.537543698Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json index a7ac2ed39..edcf0c552 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_4.json @@ -1,5 +1,5 @@ { - "id": "0e1ef52e-482f-43d7-b94f-94f1ecdaa8d1", + "id": "d7848eb8-b304-435e-b869-0dcb56fdf807", "jsonrpc": "2.0", "result": { "data": { @@ -18,20 +18,20 @@ "consensus_hash": "048091BC7DDC283F77BFBF91D73C44DA58C3DF8A9CBC867405D8B7F3DAADA22F", "data_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", "evidence_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "height": "241", + "height": "60", "last_block_id": { - "hash": "F60AD9534BDE152760F3F5EE3BAD0063B0D5D50C88E4EF47A6ED724C5B7CDF4A", + "hash": "C3E86C7C298497DF7F36B148F9300F92691D426AEBD749EE25FA34488313EA3A", "parts": { - "hash": "C4BB7FC8E4B586A1C72137B422E577C19871F750A1C5DF0ABD30374F95EA1550", + "hash": "14217342A17F6A14185D85B7E2CFFE44CDC764FA38C5304E88D024E019C547BB", "total": 1 } }, - "last_commit_hash": "92FA36538F6EBD2586A541B9E27D86AE3412FFEC74827059AFB87E5CABEC9972", + "last_commit_hash": "39931C7A54AE3873B4457632A394894966A32A7A21596B7EE67F9EF72EF3022F", "last_results_hash": "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855", - "next_validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", - "proposer_address": "87F74499559B0B60995F57C2224D27E55DD46ACD", - "time": "2023-02-24T15:11:40.133649473Z", - "validators_hash": "D1A8803929B7478B2D459D9113569AFA4037635D8125741F1A9E143FC9C17C55", + "next_validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", + "proposer_address": "DD8A65495B6240145764A74E78CF203D51510371", + "time": "2023-02-27T07:13:34.057389794Z", + "validators_hash": "9815DD28ABEB04863FFC577AF32CF331ADEA96DC1BFD8ECCD1768BA36C15B362", "version": { "app": "1", "block": "11" @@ -39,20 +39,20 @@ }, "last_commit": { "block_id": { - "hash": "F60AD9534BDE152760F3F5EE3BAD0063B0D5D50C88E4EF47A6ED724C5B7CDF4A", + "hash": "C3E86C7C298497DF7F36B148F9300F92691D426AEBD749EE25FA34488313EA3A", "parts": { - "hash": "C4BB7FC8E4B586A1C72137B422E577C19871F750A1C5DF0ABD30374F95EA1550", + "hash": "14217342A17F6A14185D85B7E2CFFE44CDC764FA38C5304E88D024E019C547BB", "total": 1 } }, - "height": "240", + "height": "59", "round": 0, "signatures": [ { "block_id_flag": 2, - "signature": "5eC+jWB2KaTJ7JwR9Ntbf2eJBYfpgfH2Gqq8ehQB9ORoE1SYlU/TmrcMahQnWViaZUm/7bCGtjn7QVJouqS8CQ==", - "timestamp": "2023-02-24T15:11:40.133649473Z", - "validator_address": "87F74499559B0B60995F57C2224D27E55DD46ACD" + "signature": "LvGGliJAHCHtcOhTxRFHokF6s+IXDv3HN9NzeJZP1FLdv+njqIhIBUrkpTF4lHGHNYequJB5VLE0Mim+lHf1BA==", + "timestamp": "2023-02-27T07:13:34.057389794Z", + "validator_address": "DD8A65495B6240145764A74E78CF203D51510371" } ] } diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json index 9b271a28b..d15fc6188 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs.json @@ -1,5 +1,5 @@ { - "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "id": "f04f76fb-73bf-46c5-9151-4e7b089b73ed", "jsonrpc": "2.0", "result": {} } \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json index ce120c42f..16ae10509 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_0.json @@ -1,12 +1,12 @@ { - "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "id": "f04f76fb-73bf-46c5-9151-4e7b089b73ed", "jsonrpc": "2.0", "result": { "data": { "type": "tendermint/event/Tx", "value": { "TxResult": { - "height": "245", + "height": "64", "result": { "events": [ { @@ -89,7 +89,7 @@ "FCB86F71C4EFF43E13C51FA12791F6DD1DDB8600A51131BE2289614D6882F6BE" ], "tx.height": [ - "245" + "64" ] }, "query": "tm.event = 'Tx'" diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json index ac29a6ba5..a90006a5d 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_1.json @@ -1,12 +1,12 @@ { - "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "id": "f04f76fb-73bf-46c5-9151-4e7b089b73ed", "jsonrpc": "2.0", "result": { "data": { "type": "tendermint/event/Tx", "value": { "TxResult": { - "height": "247", + "height": "66", "result": { "events": [ { @@ -89,7 +89,7 @@ "9F424A8E634AAF63CFA61151A306AA788C9CC792F16B370F7867ED0BD972476C" ], "tx.height": [ - "247" + "66" ] }, "query": "tm.event = 'Tx'" diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json index b475e8ce3..ce625ee44 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_2.json @@ -1,12 +1,12 @@ { - "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "id": "f04f76fb-73bf-46c5-9151-4e7b089b73ed", "jsonrpc": "2.0", "result": { "data": { "type": "tendermint/event/Tx", "value": { "TxResult": { - "height": "249", + "height": "68", "result": { "events": [ { @@ -89,7 +89,7 @@ "C9D123E2CF19B9F0EC3CA1F64CD3BF0735397C84778B40B3EB5C49A752D53BF4" ], "tx.height": [ - "249" + "68" ] }, "query": "tm.event = 'Tx'" diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json index 9f4f0b861..84037a904 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_3.json @@ -1,12 +1,12 @@ { - "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "id": "f04f76fb-73bf-46c5-9151-4e7b089b73ed", "jsonrpc": "2.0", "result": { "data": { "type": "tendermint/event/Tx", "value": { "TxResult": { - "height": "251", + "height": "70", "result": { "events": [ { @@ -89,7 +89,7 @@ "73117D6A783E4A37C1D9AD48744AD9FCC0D094C48AB8322FA11CD901C5174CFD" ], "tx.height": [ - "251" + "70" ] }, "query": "tm.event = 'Tx'" diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json index 2bbdbc7e4..20b0b1d6d 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_4.json @@ -1,12 +1,12 @@ { - "id": "5a00f8ae-7178-4d20-b1d2-22de068815a7", + "id": "f04f76fb-73bf-46c5-9151-4e7b089b73ed", "jsonrpc": "2.0", "result": { "data": { "type": "tendermint/event/Tx", "value": { "TxResult": { - "height": "253", + "height": "72", "result": { "events": [ { @@ -89,7 +89,7 @@ "C349F213F04B4E8E749C6656E4C299E3BF22F4FAF141291A5C083336AD1A413B" ], "tx.height": [ - "253" + "72" ] }, "query": "tm.event = 'Tx'" diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json index fddaeb395..4314ab785 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_0.json @@ -1,5 +1,5 @@ { - "id": "7ad4d2b9-0d9b-4ee4-be3f-f602ecf8f5b1", + "id": "cb942a83-32ad-4d23-aa91-86ef642f3816", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json index a1e912b86..4e7cb7d3e 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_1.json @@ -1,5 +1,5 @@ { - "id": "83abc9bc-379d-4a3d-93cd-973393006161", + "id": "c2ea2d7b-c121-4a8c-9bb9-98ff8a2f0a7e", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json index dd0bf32e3..530214878 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_2.json @@ -1,5 +1,5 @@ { - "id": "5a5bbc9c-4b06-4d61-9efc-076d8863aae3", + "id": "e8b3d101-b2e7-4bd1-87d7-ec269a43ac39", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json index 8ed5577bb..3147f574a 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_3.json @@ -1,5 +1,5 @@ { - "id": "07cd909f-796e-448f-a16f-3c120c0d1b5a", + "id": "0877d6b8-2057-4bd1-a67e-8fe5be956598", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json index 283935cb6..40642a38b 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_4.json @@ -1,5 +1,5 @@ { - "id": "0fcbb94c-853b-43fd-bf56-aea2b0156fab", + "id": "66c13051-5981-4485-b5dc-28c59a1059a2", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json index 05e02d37b..1d4e427db 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_txs_broadcast_tx_5.json @@ -1,5 +1,5 @@ { - "id": "cb7ccde0-6d42-47c3-a772-6355f8c7befa", + "id": "d24279ae-fa22-49ab-9e51-c68eab2fb289", "jsonrpc": "2.0", "result": { "code": 0, diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json index 79f8ef376..a0d4892a5 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_no_prove.json @@ -1,12 +1,12 @@ { - "id": "7167bf23-1869-4578-8d37-d6f6387d70a7", + "id": "8254b599-571a-4714-bdad-791d9d125a16", "jsonrpc": "2.0", "result": { "total_count": "9", "txs": [ { "hash": "9F28904F9C0F3AB74A81CBA48E39124DA1C680B47FBFCBA0126870DB722BCC30", - "height": "225", + "height": "44", "index": 0, "tx": "YXN5bmMta2V5PXZhbHVl", "tx_result": { @@ -73,7 +73,7 @@ }, { "hash": "57018296EE0919C9D351F2FFEA82A8D28DE223724D79965FC8D00A7477ED48BC", - "height": "227", + "height": "46", "index": 0, "tx": "c3luYy1rZXk9dmFsdWU=", "tx_result": { @@ -140,7 +140,7 @@ }, { "hash": "D63F9C23791E610410B576D8C27BB5AEAC93CC1A58522428A7B32A1276085860", - "height": "229", + "height": "48", "index": 0, "tx": "Y29tbWl0LWtleT12YWx1ZQ==", "tx_result": { @@ -207,7 +207,7 @@ }, { "hash": "FCB86F71C4EFF43E13C51FA12791F6DD1DDB8600A51131BE2289614D6882F6BE", - "height": "245", + "height": "64", "index": 0, "tx": "dHgwPXZhbHVl", "tx_result": { @@ -274,7 +274,7 @@ }, { "hash": "9F424A8E634AAF63CFA61151A306AA788C9CC792F16B370F7867ED0BD972476C", - "height": "247", + "height": "66", "index": 0, "tx": "dHgxPXZhbHVl", "tx_result": { @@ -341,7 +341,7 @@ }, { "hash": "C9D123E2CF19B9F0EC3CA1F64CD3BF0735397C84778B40B3EB5C49A752D53BF4", - "height": "249", + "height": "68", "index": 0, "tx": "dHgyPXZhbHVl", "tx_result": { @@ -408,7 +408,7 @@ }, { "hash": "73117D6A783E4A37C1D9AD48744AD9FCC0D094C48AB8322FA11CD901C5174CFD", - "height": "251", + "height": "70", "index": 0, "tx": "dHgzPXZhbHVl", "tx_result": { @@ -475,7 +475,7 @@ }, { "hash": "C349F213F04B4E8E749C6656E4C299E3BF22F4FAF141291A5C083336AD1A413B", - "height": "253", + "height": "72", "index": 0, "tx": "dHg0PXZhbHVl", "tx_result": { @@ -542,7 +542,7 @@ }, { "hash": "CC4AC5C231481DD2ED2EA15789483B94565BF41612B6FEDE5BE7694F882CC202", - "height": "255", + "height": "74", "index": 0, "tx": "dHg1PXZhbHVl", "tx_result": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json index 6c45b5623..4843e41de 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/tx_search_with_prove.json @@ -1,12 +1,12 @@ { - "id": "d1b4904e-c0d4-4b37-b6ac-0730c7144e04", + "id": "af0e742a-02d9-41e6-80ad-35d546e01190", "jsonrpc": "2.0", "result": { "total_count": "9", "txs": [ { "hash": "9F28904F9C0F3AB74A81CBA48E39124DA1C680B47FBFCBA0126870DB722BCC30", - "height": "225", + "height": "44", "index": 0, "proof": { "data": "YXN5bmMta2V5PXZhbHVl", @@ -83,7 +83,7 @@ }, { "hash": "57018296EE0919C9D351F2FFEA82A8D28DE223724D79965FC8D00A7477ED48BC", - "height": "227", + "height": "46", "index": 0, "proof": { "data": "c3luYy1rZXk9dmFsdWU=", @@ -160,7 +160,7 @@ }, { "hash": "D63F9C23791E610410B576D8C27BB5AEAC93CC1A58522428A7B32A1276085860", - "height": "229", + "height": "48", "index": 0, "proof": { "data": "Y29tbWl0LWtleT12YWx1ZQ==", @@ -237,7 +237,7 @@ }, { "hash": "FCB86F71C4EFF43E13C51FA12791F6DD1DDB8600A51131BE2289614D6882F6BE", - "height": "245", + "height": "64", "index": 0, "proof": { "data": "dHgwPXZhbHVl", @@ -314,7 +314,7 @@ }, { "hash": "9F424A8E634AAF63CFA61151A306AA788C9CC792F16B370F7867ED0BD972476C", - "height": "247", + "height": "66", "index": 0, "proof": { "data": "dHgxPXZhbHVl", @@ -391,7 +391,7 @@ }, { "hash": "C9D123E2CF19B9F0EC3CA1F64CD3BF0735397C84778B40B3EB5C49A752D53BF4", - "height": "249", + "height": "68", "index": 0, "proof": { "data": "dHgyPXZhbHVl", @@ -468,7 +468,7 @@ }, { "hash": "73117D6A783E4A37C1D9AD48744AD9FCC0D094C48AB8322FA11CD901C5174CFD", - "height": "251", + "height": "70", "index": 0, "proof": { "data": "dHgzPXZhbHVl", @@ -545,7 +545,7 @@ }, { "hash": "C349F213F04B4E8E749C6656E4C299E3BF22F4FAF141291A5C083336AD1A413B", - "height": "253", + "height": "72", "index": 0, "proof": { "data": "dHg0PXZhbHVl", @@ -622,7 +622,7 @@ }, { "hash": "CC4AC5C231481DD2ED2EA15789483B94565BF41612B6FEDE5BE7694F882CC202", - "height": "255", + "height": "74", "index": 0, "proof": { "data": "dHg1PXZhbHVl", diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json index 1c05ffed7..c49d71f05 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_info.json @@ -1,5 +1,5 @@ { - "id": "4cdabace-7cae-4347-9675-e69a71a3b19a", + "id": "4e158c90-577c-4408-b8f6-d3680b84e7e9", "jsonrpc": "2.0", "method": "abci_info", "params": null diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json index 28f01df62..94c2fb2ab 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_existing_key.json @@ -1,5 +1,5 @@ { - "id": "49193475-5bbf-4820-a878-360f8c3c6072", + "id": "4c088a2c-e01c-4d8b-aadc-009753b68d04", "jsonrpc": "2.0", "method": "abci_query", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json index 1d61822f8..d24a8065e 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/abci_query_with_non_existent_key.json @@ -1,5 +1,5 @@ { - "id": "6c6583ab-27ed-44ac-b704-78abe4723da9", + "id": "437f6c65-b4b2-4417-9e03-2b584a75403f", "jsonrpc": "2.0", "method": "abci_query", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json index 9d82f9833..266523e62 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_0.json @@ -1,5 +1,5 @@ { - "id": "2f4bc09e-7e2d-4514-a833-16e86d1af67e", + "id": "c1144ac0-8c4d-46cc-9430-8c14c598a029", "jsonrpc": "2.0", "method": "block", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json index 3b7100391..47f5da6f6 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_1.json @@ -1,5 +1,5 @@ { - "id": "1356e29e-da5d-451a-b42d-cd3931bdb8f6", + "id": "5f66ff6f-8283-4c9a-8437-b120248182d8", "jsonrpc": "2.0", "method": "block", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json index 54542be8c..0f2787c61 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_at_height_10.json @@ -1,5 +1,5 @@ { - "id": "1fa8bed7-d111-484d-abee-902fa1454069", + "id": "a24afd41-dbab-453d-8734-f599f84eb653", "jsonrpc": "2.0", "method": "block", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json index 733bd48c1..d11fb8dd4 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_by_hash.json @@ -1,8 +1,8 @@ { - "id": "abd9f0d1-5b80-424a-8f7d-94b2d854707c", + "id": "56d4851a-1f30-4d73-9f86-c1a084e8aa97", "jsonrpc": "2.0", "method": "block_by_hash", "params": { - "hash": "ABEiM0RVZneImaq7zN3u/wARIjNEVWZ3iJmqu8zd7v8=" + "hash": "/PnCU3/DU0ynEAH+HxTE92kJCUjBpSFoL2EufPc65jk=" } } \ No newline at end of file diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json index e7523f57a..2d8a50195 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_results_at_height_10.json @@ -1,5 +1,5 @@ { - "id": "a5154e64-bf10-4b5f-960a-ed4eec5e261d", + "id": "77cfdbe4-630e-4b73-b30d-90a1236f96a3", "jsonrpc": "2.0", "method": "block_results", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json index 6d63a31a3..63b995b4c 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/block_search.json @@ -1,5 +1,5 @@ { - "id": "35b99dba-c7c1-4229-be9c-23fa795e4432", + "id": "60d0e76b-d645-4b37-adc0-42fc0fa7d394", "jsonrpc": "2.0", "method": "block_search", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json index 0228e6e54..d5fe40e70 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/blockchain_from_1_to_10.json @@ -1,5 +1,5 @@ { - "id": "8b6f991a-4a2c-4dcf-9411-5c706f413235", + "id": "318f73b5-0fe6-43cc-935f-ef76f6c61cd4", "jsonrpc": "2.0", "method": "blockchain", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json index 9a32b2c05..939bc8c1d 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_async.json @@ -1,5 +1,5 @@ { - "id": "37104243-1a80-4b5f-a917-cf38c863171f", + "id": "adb67e95-0d9f-40ed-8e24-6b9b537107b3", "jsonrpc": "2.0", "method": "broadcast_tx_async", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json index ae45fea3b..c1be9b0af 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_commit.json @@ -1,5 +1,5 @@ { - "id": "be2a11c5-e6b3-4803-9f0e-140330c65f43", + "id": "c1b2fe8d-ac41-4c65-aad1-15ff0b156fe1", "jsonrpc": "2.0", "method": "broadcast_tx_commit", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json index fab1c5c51..3a488a2b0 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/broadcast_tx_sync.json @@ -1,5 +1,5 @@ { - "id": "c0bbfd1a-6b75-421e-ba3f-07dec9c1ba98", + "id": "5daaaf5b-d964-4333-9866-9caab5c8efdc", "jsonrpc": "2.0", "method": "broadcast_tx_sync", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json index 347c92f8e..16f63f423 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/commit_at_height_10.json @@ -1,5 +1,5 @@ { - "id": "435978e8-89ed-4128-a94e-1f25dcd46c28", + "id": "9493368d-025d-49b3-a3f8-486e55835e3a", "jsonrpc": "2.0", "method": "commit", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json index 52494a5a3..52b0740e5 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_params.json @@ -1,5 +1,5 @@ { - "id": "abbcacd1-ff31-4725-b5ff-c46e21c02736", + "id": "6713de4d-11cc-4725-9dff-1dad524f2d44", "jsonrpc": "2.0", "method": "consensus_params", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json index c2a7163dd..f82b4261e 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/consensus_state.json @@ -1,5 +1,5 @@ { - "id": "6954460c-8b30-41e9-9752-261e063dda0c", + "id": "d741eb15-a8cf-4b87-ae31-689ee9bcb1e2", "jsonrpc": "2.0", "method": "consensus_state", "params": null diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json index d6abed72a..89ba435aa 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/genesis.json @@ -1,5 +1,5 @@ { - "id": "30777544-c3da-4444-bef1-6035ece3b1c0", + "id": "217c0860-637e-4368-9346-052ffbdee73c", "jsonrpc": "2.0", "method": "genesis", "params": null diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json index bb0e69097..b13f6ea25 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/net_info.json @@ -1,5 +1,5 @@ { - "id": "e6cd2152-119e-4349-bf6d-ec8b1e5e077f", + "id": "de1eb555-5788-4ee4-b263-a447ab6de53a", "jsonrpc": "2.0", "method": "net_info", "params": null diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json index f2dc1be31..a0b375870 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/status.json @@ -1,5 +1,5 @@ { - "id": "cd2af599-b99a-4fdb-a7ed-ee2734e77ebb", + "id": "d517d5b0-22de-4684-89ea-0d822293d7f6", "jsonrpc": "2.0", "method": "status", "params": null diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json index 2a90bfb15..c36834f7e 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_malformed.json @@ -1,5 +1,5 @@ { - "id": "e408a1ef-b634-4c92-864d-e9c5c59345d1", + "id": "505651d8-1cf4-4bdd-b58f-0c66360640b5", "jsonrpc": "2.0", "method": "subscribe", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json index 2fa5f3237..9e713a5f9 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_newblock.json @@ -1,5 +1,5 @@ { - "id": "9d27bbcf-657b-4c6e-8622-b83aa19a74d1", + "id": "c5fff7c8-1aca-40a3-a4d1-a55bb1e62327", "jsonrpc": "2.0", "method": "subscribe", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json index 1260beef9..0b3d2fc9c 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs.json @@ -1,5 +1,5 @@ { - "id": "43fad15f-cac8-4f38-b376-76c658e0b743", + "id": "580dab68-e0de-4a58-85cf-9a56120796d1", "jsonrpc": "2.0", "method": "subscribe", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json index 43666eaa6..95fe89f77 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_0.json @@ -1,5 +1,5 @@ { - "id": "7ad4d2b9-0d9b-4ee4-be3f-f602ecf8f5b1", + "id": "cb942a83-32ad-4d23-aa91-86ef642f3816", "jsonrpc": "2.0", "method": "broadcast_tx_async", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json index 6dee5c11f..b91d73b5b 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_1.json @@ -1,5 +1,5 @@ { - "id": "83abc9bc-379d-4a3d-93cd-973393006161", + "id": "c2ea2d7b-c121-4a8c-9bb9-98ff8a2f0a7e", "jsonrpc": "2.0", "method": "broadcast_tx_async", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json index 4d023a7b0..0d1fd7d30 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_2.json @@ -1,5 +1,5 @@ { - "id": "5a5bbc9c-4b06-4d61-9efc-076d8863aae3", + "id": "e8b3d101-b2e7-4bd1-87d7-ec269a43ac39", "jsonrpc": "2.0", "method": "broadcast_tx_async", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json index f6703d26e..53d18a845 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_3.json @@ -1,5 +1,5 @@ { - "id": "07cd909f-796e-448f-a16f-3c120c0d1b5a", + "id": "0877d6b8-2057-4bd1-a67e-8fe5be956598", "jsonrpc": "2.0", "method": "broadcast_tx_async", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json index 9ca953375..50e86e9c5 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_4.json @@ -1,5 +1,5 @@ { - "id": "0fcbb94c-853b-43fd-bf56-aea2b0156fab", + "id": "66c13051-5981-4485-b5dc-28c59a1059a2", "jsonrpc": "2.0", "method": "broadcast_tx_async", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json index 841d737d1..83c91aece 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/subscribe_txs_broadcast_tx_5.json @@ -1,5 +1,5 @@ { - "id": "cb7ccde0-6d42-47c3-a772-6355f8c7befa", + "id": "d24279ae-fa22-49ab-9e51-c68eab2fb289", "jsonrpc": "2.0", "method": "broadcast_tx_async", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json index 262cff66a..c43385554 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_no_prove.json @@ -1,5 +1,5 @@ { - "id": "7167bf23-1869-4578-8d37-d6f6387d70a7", + "id": "8254b599-571a-4714-bdad-791d9d125a16", "jsonrpc": "2.0", "method": "tx_search", "params": { diff --git a/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json index 5c0408eec..374ec16b7 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json +++ b/rpc/tests/kvstore_fixtures/v0_37/outgoing/tx_search_with_prove.json @@ -1,5 +1,5 @@ { - "id": "d1b4904e-c0d4-4b37-b6ac-0730c7144e04", + "id": "af0e742a-02d9-41e6-80ad-35d546e01190", "jsonrpc": "2.0", "method": "tx_search", "params": { diff --git a/tools/rpc-probe/src/kvstore.rs b/tools/rpc-probe/src/kvstore.rs index 4fac5be26..e8230d849 100644 --- a/tools/rpc-probe/src/kvstore.rs +++ b/tools/rpc-probe/src/kvstore.rs @@ -26,12 +26,9 @@ pub fn quick_probe_plan(output_path: &Path, request_wait: Duration) -> Result 1", 1, 100, "asc").with_name("block_search"), blockchain(1, 10).with_name("blockchain_from_1_to_10"), commit(10).with_name("commit_at_height_10"), From 69468491f2f99b7420a8b7b9297454a14b95988f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 27 Feb 2023 11:28:48 +0200 Subject: [PATCH 68/77] rpc: fudge data in subscribe_newblock_1 Same as was done in the v0_34 fixtures in the past, it lets us test parsing of the struct containing events. --- .../v0_37/incoming/subscribe_newblock_1.json | 30 ++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json index 8120f29c3..a1e86951b 100644 --- a/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json +++ b/rpc/tests/kvstore_fixtures/v0_37/incoming/subscribe_newblock_1.json @@ -57,7 +57,35 @@ ] } }, - "result_begin_block": {}, + "result_begin_block": { + "events": [ + { + "type": "transfer", + "attributes": [ + { + "index": true, + "key": "recipient", + "value": "cosmos17xpfvakm2amg962yls6f84z3kell8c5lserqta" + }, + { + "index": false, + "key": "sender", + "value": "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" + } + ] + }, + { + "type": "message", + "attributes": [ + { + "index": true, + "key": "sender", + "value": "cosmos1m3h30wlvsf8llruxtpukdvsy0km2kum8g38c8q" + } + ] + } + ] + }, "result_end_block": { "validator_updates": null } From 295ef2adb37ed04d42afd6a6a8728ac701f67e7c Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 27 Feb 2023 12:04:38 +0200 Subject: [PATCH 69/77] rpc: adjust kvstore_fixtures tests for v0_37 --- rpc/tests/kvstore_fixtures.rs | 16 --------- rpc/tests/kvstore_fixtures/v0_37.rs | 50 +++++++++++++++++++++++++---- 2 files changed, 43 insertions(+), 23 deletions(-) diff --git a/rpc/tests/kvstore_fixtures.rs b/rpc/tests/kvstore_fixtures.rs index 087f3a053..76a31ea86 100644 --- a/rpc/tests/kvstore_fixtures.rs +++ b/rpc/tests/kvstore_fixtures.rs @@ -48,19 +48,3 @@ fn find_fixtures(ver_folder_name: &str, in_out_folder_name: &str) -> Vec>() } - -fn check_event_attrs(events: &HashMap>, app_key: &str, height: i64) { - for (k, v) in events { - assert_eq!(v.len(), 1); - match k.as_str() { - "app.creator" => assert_eq!(v[0], "Cosmoshi Netowoko"), - "app.index_key" => assert_eq!(v[0], "index is working"), - "app.key" => assert_eq!(v[0], app_key), - "app.noindex_key" => assert_eq!(v[0], "index is working"), - "tm.event" => assert_eq!(v[0], "Tx"), - "tx.hash" => assert_eq!(v[0].len(), 64), - "tx.height" => assert_eq!(v[0], height.to_string()), - _ => panic!("unknown event found {k}"), - } - } -} diff --git a/rpc/tests/kvstore_fixtures/v0_37.rs b/rpc/tests/kvstore_fixtures/v0_37.rs index 55a00bb3c..9d2fa3550 100644 --- a/rpc/tests/kvstore_fixtures/v0_37.rs +++ b/rpc/tests/kvstore_fixtures/v0_37.rs @@ -1109,7 +1109,7 @@ fn incoming_fixtures() { assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events.len(), 2); assert_eq!(tx_result.result.events[0].kind, "app"); for attr in &tx_result.result.events[0].attributes { match attr.key.as_str() { @@ -1142,7 +1142,7 @@ fn incoming_fixtures() { assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events.len(), 2); assert_eq!(tx_result.result.events[0].kind, "app"); for attr in &tx_result.result.events[0].attributes { match attr.key.as_str() { @@ -1176,7 +1176,7 @@ fn incoming_fixtures() { assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events.len(), 2); assert_eq!(tx_result.result.events[0].kind, "app"); for attr in &tx_result.result.events[0].attributes { match attr.key.as_str() { @@ -1209,7 +1209,7 @@ fn incoming_fixtures() { assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events.len(), 2); assert_eq!(tx_result.result.events[0].kind, "app"); for attr in &tx_result.result.events[0].attributes { match attr.key.as_str() { @@ -1242,7 +1242,7 @@ fn incoming_fixtures() { assert!(tx_result.result.log.is_none()); assert!(tx_result.result.gas_wanted.is_none()); assert!(tx_result.result.gas_used.is_none()); - assert_eq!(tx_result.result.events.len(), 1); + assert_eq!(tx_result.result.events.len(), 2); assert_eq!(tx_result.result.events[0].kind, "app"); for attr in &tx_result.result.events[0].attributes { match attr.key.as_str() { @@ -1355,7 +1355,7 @@ fn incoming_fixtures() { for tx in result.txs { assert_ne!(tx.hash.as_bytes(), [0; 32]); assert_eq!(tx.tx_result.code, abci::Code::Ok); - assert_eq!(tx.tx_result.events.len(), 1); + assert_eq!(tx.tx_result.events.len(), 2); assert_eq!(tx.tx_result.events[0].kind, "app"); assert_eq!(tx.tx_result.gas_used, 0); assert_eq!(tx.tx_result.gas_wanted, 0); @@ -1374,7 +1374,7 @@ fn incoming_fixtures() { for tx in result.txs { assert_ne!(tx.hash.as_bytes(), [0; 32]); assert_eq!(tx.tx_result.code, abci::Code::Ok); - assert_eq!(tx.tx_result.events.len(), 1); + assert_eq!(tx.tx_result.events.len(), 2); assert_eq!(tx.tx_result.events[0].kind, "app"); assert_eq!(tx.tx_result.gas_used, 0); assert_eq!(tx.tx_result.gas_wanted, 0); @@ -1393,3 +1393,39 @@ fn incoming_fixtures() { } } } + +fn check_event_attrs(events: &HashMap>, app_key: &str, height: i64) { + for (k, v) in events { + match k.as_str() { + "app.creator" => { + assert_eq!(v.len(), 2); + assert_eq!(v[0], "Cosmoshi Netowoko"); + }, + "app.index_key" => { + assert_eq!(v.len(), 2); + assert_eq!(v[0], "index is working"); + }, + "app.key" => { + assert_eq!(v.len(), 2); + assert_eq!(v[0], app_key); + }, + "app.noindex_key" => { + assert_eq!(v.len(), 2); + assert_eq!(v[0], "index is working"); + }, + "tm.event" => { + assert_eq!(v.len(), 1); + assert_eq!(v[0], "Tx"); + }, + "tx.hash" => { + assert_eq!(v.len(), 1); + assert_eq!(v[0].len(), 64); + }, + "tx.height" => { + assert_eq!(v.len(), 1); + assert_eq!(v[0], height.to_string()); + }, + _ => panic!("unknown event found {k}"), + } + } +} From 7fedc092cf24b3db20ae31be63e242132f72706f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 27 Feb 2023 13:58:31 +0200 Subject: [PATCH 70/77] rpc: fixed and expanded unit tests using fixtures Use the versioned path to the fixture files, and add a copy of tests for v0_37 which was previously not covered. --- rpc/src/client/transport/mock.rs | 65 ++++++-- rpc/src/client/transport/router.rs | 145 ++++++++++++----- rpc/src/client/transport/websocket.rs | 223 ++++++++++++++++++-------- 3 files changed, 314 insertions(+), 119 deletions(-) diff --git a/rpc/src/client/transport/mock.rs b/rpc/src/client/transport/mock.rs index 52edebd2f..987885779 100644 --- a/rpc/src/client/transport/mock.rs +++ b/rpc/src/client/transport/mock.rs @@ -251,9 +251,12 @@ mod test { use super::*; use crate::query::EventType; - async fn read_json_fixture(name: &str) -> String { + async fn read_json_fixture(version: &str, name: &str) -> String { fs::read_to_string( - PathBuf::from("./tests/kvstore_fixtures/incoming/").join(name.to_owned() + ".json"), + PathBuf::from("./tests/kvstore_fixtures") + .join(version) + .join("incoming") + .join(name.to_owned() + ".json"), ) .await .unwrap() @@ -265,14 +268,15 @@ mod test { use crate::event::DialectEvent; async fn read_event(name: &str) -> Event { - let msg = DialectEvent::::from_string(read_json_fixture(name).await).unwrap(); + let msg = DialectEvent::::from_string(read_json_fixture("v0_34", name).await) + .unwrap(); msg.into() } #[tokio::test] async fn mock_client() { - let abci_info_fixture = read_json_fixture("abci_info").await; - let block_fixture = read_json_fixture("block_at_height_10").await; + let abci_info_fixture = read_json_fixture("v0_34", "abci_info").await; + let block_fixture = read_json_fixture("v0_34", "block_at_height_10").await; let matcher = MockRequestMethodMatcher::default() .map(Method::AbciInfo, Ok(abci_info_fixture)) .map(Method::Block, Ok(block_fixture)); @@ -330,11 +334,19 @@ mod test { mod v0_37 { use super::*; + use crate::dialect::v0_37::Event as RpcEvent; + use crate::event::DialectEvent; + + async fn read_event(name: &str) -> Event { + let msg = DialectEvent::::from_string(read_json_fixture("v0_37", name).await) + .unwrap(); + msg.into() + } #[tokio::test] async fn mock_client() { - let abci_info_fixture = read_json_fixture("abci_info").await; - let block_fixture = read_json_fixture("block_at_height_10").await; + let abci_info_fixture = read_json_fixture("v0_37", "abci_info").await; + let block_fixture = read_json_fixture("v0_37", "block_at_height_10").await; let matcher = MockRequestMethodMatcher::default() .map(Method::AbciInfo, Ok(abci_info_fixture)) .map(Method::Block, Ok(block_fixture)); @@ -342,7 +354,7 @@ mod test { let driver_hdl = tokio::spawn(async move { driver.run().await }); let abci_info = client.abci_info().await.unwrap(); - assert_eq!("{\"size\":0}".to_string(), abci_info.data); + assert_eq!("{\"size\":9}".to_string(), abci_info.data); let block = client.block(Height::from(10_u32)).await.unwrap().block; assert_eq!(Height::from(10_u32), block.header.height); @@ -352,6 +364,41 @@ mod test { driver_hdl.await.unwrap().unwrap(); } - // TODO: add mock_subscription_client test for v0_37 + #[tokio::test] + async fn mock_subscription_client() { + let (client, driver) = MockClient::new(MockRequestMethodMatcher::default()); + let driver_hdl = tokio::spawn(async move { driver.run().await }); + + let event1 = read_event("subscribe_newblock_0").await; + let event2 = read_event("subscribe_newblock_1").await; + let event3 = read_event("subscribe_newblock_2").await; + let events = vec![event1, event2, event3]; + + let subs1 = client.subscribe(EventType::NewBlock.into()).await.unwrap(); + let subs2 = client.subscribe(EventType::NewBlock.into()).await.unwrap(); + assert_ne!(subs1.id().to_string(), subs2.id().to_string()); + + // We can do this because the underlying channels can buffer the + // messages as we publish them. + let subs1_events = subs1.take(3); + let subs2_events = subs2.take(3); + for ev in &events { + client.publish(ev); + } + + // Here each subscription's channel is drained. + let subs1_events = subs1_events.collect::>>().await; + let subs2_events = subs2_events.collect::>>().await; + + assert_eq!(3, subs1_events.len()); + assert_eq!(3, subs2_events.len()); + + for i in 0..3 { + assert!(events[i].eq(subs1_events[i].as_ref().unwrap())); + } + + client.close(); + driver_hdl.await.unwrap().unwrap(); + } } } diff --git a/rpc/src/client/transport/router.rs b/rpc/src/client/transport/router.rs index 40542c61b..985492069 100644 --- a/rpc/src/client/transport/router.rs +++ b/rpc/src/client/transport/router.rs @@ -147,25 +147,18 @@ mod test { event::{Event, WrappedEvent}, utils::uuid_str, }; - // TODO: add fixtures for dialect::v0_37 - use crate::dialect::v0_34::Event as RpcEvent; - async fn read_json_fixture(name: &str) -> String { + async fn read_json_fixture(version: &str, name: &str) -> String { fs::read_to_string( - PathBuf::from("./tests/kvstore_fixtures/incoming/").join(name.to_owned() + ".json"), + PathBuf::from("./tests/kvstore_fixtures") + .join(version) + .join("incoming") + .join(name.to_owned() + ".json"), ) .await .unwrap() } - async fn read_event(name: &str) -> Event { - serde_json::from_str::>(read_json_fixture(name).await.as_str()) - .unwrap() - .into_result() - .unwrap() - .into() - } - async fn must_recv(ch: &mut ChannelRx, timeout_ms: u64) -> T { let delay = time::sleep(Duration::from_millis(timeout_ms)); tokio::select! { @@ -185,37 +178,101 @@ mod test { } } - #[tokio::test] - async fn router_basic_pub_sub() { - let mut router = SubscriptionRouter::default(); - - let (subs1_id, subs2_id, subs3_id) = (uuid_str(), uuid_str(), uuid_str()); - let (subs1_event_tx, mut subs1_event_rx) = unbounded(); - let (subs2_event_tx, mut subs2_event_rx) = unbounded(); - let (subs3_event_tx, mut subs3_event_rx) = unbounded(); - - // Two subscriptions with the same query - router.add(subs1_id, "query1", subs1_event_tx); - router.add(subs2_id, "query1", subs2_event_tx); - // Another subscription with a different query - router.add(subs3_id, "query2", subs3_event_tx); - - let mut ev = read_event("subscribe_newblock_0").await; - ev.query = "query1".into(); - router.publish_event(ev.clone()); - - let subs1_ev = must_recv(&mut subs1_event_rx, 500).await.unwrap(); - let subs2_ev = must_recv(&mut subs2_event_rx, 500).await.unwrap(); - must_not_recv(&mut subs3_event_rx, 50).await; - assert_eq!(ev, subs1_ev); - assert_eq!(ev, subs2_ev); - - ev.query = "query2".into(); - router.publish_event(ev.clone()); - - must_not_recv(&mut subs1_event_rx, 50).await; - must_not_recv(&mut subs2_event_rx, 50).await; - let subs3_ev = must_recv(&mut subs3_event_rx, 500).await.unwrap(); - assert_eq!(ev, subs3_ev); + mod v0_34 { + use super::*; + use crate::dialect::v0_34::Event as RpcEvent; + + async fn read_event(name: &str) -> Event { + serde_json::from_str::>( + read_json_fixture("v0_34", name).await.as_str(), + ) + .unwrap() + .into_result() + .unwrap() + .into() + } + + #[tokio::test] + async fn router_basic_pub_sub() { + let mut router = SubscriptionRouter::default(); + + let (subs1_id, subs2_id, subs3_id) = (uuid_str(), uuid_str(), uuid_str()); + let (subs1_event_tx, mut subs1_event_rx) = unbounded(); + let (subs2_event_tx, mut subs2_event_rx) = unbounded(); + let (subs3_event_tx, mut subs3_event_rx) = unbounded(); + + // Two subscriptions with the same query + router.add(subs1_id, "query1", subs1_event_tx); + router.add(subs2_id, "query1", subs2_event_tx); + // Another subscription with a different query + router.add(subs3_id, "query2", subs3_event_tx); + + let mut ev = read_event("subscribe_newblock_0").await; + ev.query = "query1".into(); + router.publish_event(ev.clone()); + + let subs1_ev = must_recv(&mut subs1_event_rx, 500).await.unwrap(); + let subs2_ev = must_recv(&mut subs2_event_rx, 500).await.unwrap(); + must_not_recv(&mut subs3_event_rx, 50).await; + assert_eq!(ev, subs1_ev); + assert_eq!(ev, subs2_ev); + + ev.query = "query2".into(); + router.publish_event(ev.clone()); + + must_not_recv(&mut subs1_event_rx, 50).await; + must_not_recv(&mut subs2_event_rx, 50).await; + let subs3_ev = must_recv(&mut subs3_event_rx, 500).await.unwrap(); + assert_eq!(ev, subs3_ev); + } + } + + mod v0_37 { + use super::*; + use crate::dialect::v0_37::Event as RpcEvent; + + async fn read_event(name: &str) -> Event { + serde_json::from_str::>( + read_json_fixture("v0_37", name).await.as_str(), + ) + .unwrap() + .into_result() + .unwrap() + .into() + } + + #[tokio::test] + async fn router_basic_pub_sub() { + let mut router = SubscriptionRouter::default(); + + let (subs1_id, subs2_id, subs3_id) = (uuid_str(), uuid_str(), uuid_str()); + let (subs1_event_tx, mut subs1_event_rx) = unbounded(); + let (subs2_event_tx, mut subs2_event_rx) = unbounded(); + let (subs3_event_tx, mut subs3_event_rx) = unbounded(); + + // Two subscriptions with the same query + router.add(subs1_id, "query1", subs1_event_tx); + router.add(subs2_id, "query1", subs2_event_tx); + // Another subscription with a different query + router.add(subs3_id, "query2", subs3_event_tx); + + let mut ev = read_event("subscribe_newblock_0").await; + ev.query = "query1".into(); + router.publish_event(ev.clone()); + + let subs1_ev = must_recv(&mut subs1_event_rx, 500).await.unwrap(); + let subs2_ev = must_recv(&mut subs2_event_rx, 500).await.unwrap(); + must_not_recv(&mut subs3_event_rx, 50).await; + assert_eq!(ev, subs1_ev); + assert_eq!(ev, subs2_ev); + + ev.query = "query2".into(); + router.publish_event(ev.clone()); + + must_not_recv(&mut subs1_event_rx, 50).await; + must_not_recv(&mut subs2_event_rx, 50).await; + let subs3_ev = must_recv(&mut subs3_event_rx, 500).await.unwrap(); + assert_eq!(ev, subs3_ev); + } } } diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 8c3665c7b..25731d88e 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -974,9 +974,7 @@ mod test { }; use super::*; - use crate::{client::sync::unbounded, query::EventType, request, Id, Method}; - // TODO: test with dialect::v0_37 as well - use crate::dialect::v0_34::Event as RpcEvent; + use crate::{client::sync::unbounded, dialect, query::EventType, request, Id, Method}; // Interface to a driver that manages all incoming WebSocket connections. struct TestServer { @@ -987,7 +985,7 @@ mod test { } impl TestServer { - async fn new(addr: &str) -> Self { + async fn new(addr: &str, compat: CompatMode) -> Self { let listener = TcpListener::bind(addr).await.unwrap(); let local_addr = listener.local_addr().unwrap(); let node_addr = net::Address::Tcp { @@ -997,7 +995,7 @@ mod test { }; let (terminate_tx, terminate_rx) = unbounded(); let (event_tx, event_rx) = unbounded(); - let driver = TestServerDriver::new(listener, event_rx, terminate_rx); + let driver = TestServerDriver::new(listener, compat, event_rx, terminate_rx); let driver_hdl = tokio::spawn(async move { driver.run().await }); Self { node_addr, @@ -1020,6 +1018,7 @@ mod test { // Manages all incoming WebSocket connections. struct TestServerDriver { listener: TcpListener, + compat: CompatMode, event_rx: ChannelRx, terminate_rx: ChannelRx>, handlers: Vec, @@ -1028,11 +1027,13 @@ mod test { impl TestServerDriver { fn new( listener: TcpListener, + compat: CompatMode, event_rx: ChannelRx, terminate_rx: ChannelRx>, ) -> Self { Self { listener, + compat, event_rx, terminate_rx, handlers: Vec::new(), @@ -1064,7 +1065,8 @@ mod test { } async fn handle_incoming(&mut self, stream: TcpStream) { - self.handlers.push(TestServerHandler::new(stream).await); + self.handlers + .push(TestServerHandler::new(stream, self.compat).await); } async fn terminate(&mut self) { @@ -1087,12 +1089,12 @@ mod test { } impl TestServerHandler { - async fn new(stream: TcpStream) -> Self { + async fn new(stream: TcpStream, compat: CompatMode) -> Self { let conn: WebSocketStream> = accept_async(stream).await.unwrap(); let (terminate_tx, terminate_rx) = unbounded(); let (event_tx, event_rx) = unbounded(); - let driver = TestServerHandlerDriver::new(conn, event_rx, terminate_rx); + let driver = TestServerHandlerDriver::new(conn, compat, event_rx, terminate_rx); let driver_hdl = tokio::spawn(async move { driver.run().await }); Self { driver_hdl, @@ -1114,6 +1116,7 @@ mod test { // Manages interaction with a single incoming WebSocket connection. struct TestServerHandlerDriver { conn: WebSocketStream>, + compat: CompatMode, event_rx: ChannelRx, terminate_rx: ChannelRx>, // A mapping of subscription queries to subscription IDs for this @@ -1124,11 +1127,13 @@ mod test { impl TestServerHandlerDriver { fn new( conn: WebSocketStream>, + compat: CompatMode, event_rx: ChannelRx, terminate_rx: ChannelRx>, ) -> Self { Self { conn, + compat, event_rx, terminate_rx, subscriptions: HashMap::new(), @@ -1157,8 +1162,16 @@ mod test { Some(id) => id.clone(), None => return, }; - let ev: DialectEvent = ev.into(); - self.send(Id::Str(subs_id), ev).await; + match self.compat { + CompatMode::Latest => { + let ev: DialectEvent = ev.into(); + self.send(Id::Str(subs_id), ev).await; + }, + CompatMode::V0_34 => { + let ev: DialectEvent = ev.into(); + self.send(Id::Str(subs_id), ev).await; + }, + } } async fn handle_incoming_msg(&mut self, msg: Message) -> Option> { @@ -1257,76 +1270,154 @@ mod test { } } - async fn read_json_fixture(name: &str) -> String { + async fn read_json_fixture(version: &str, name: &str) -> String { fs::read_to_string( - PathBuf::from("./tests/kvstore_fixtures/incoming/").join(name.to_owned() + ".json"), + PathBuf::from("./tests/kvstore_fixtures") + .join(version) + .join("incoming") + .join(name.to_owned() + ".json"), ) .await .unwrap() } - async fn read_event(name: &str) -> Event { - DialectEvent::::from_string(read_json_fixture(name).await) - .unwrap() - .into() - } + mod v0_34 { + use super::*; + use crate::dialect::v0_34::Event as RpcEvent; - #[tokio::test] - async fn websocket_client_happy_path() { - let event1 = read_event("subscribe_newblock_0").await; - let event2 = read_event("subscribe_newblock_1").await; - let event3 = read_event("subscribe_newblock_2").await; - let test_events = vec![event1, event2, event3]; - - println!("Starting WebSocket server..."); - let mut server = TestServer::new("127.0.0.1:0").await; - println!("Creating client RPC WebSocket connection..."); - let (client, driver) = WebSocketClient::new_with_config( - server.node_addr.clone(), - WebSocketConfig { - compat: CompatMode::V0_34, - ..Default::default() - }, - ) - .await - .unwrap(); - let driver_handle = tokio::spawn(async move { driver.run().await }); - - println!("Initiating subscription for new blocks..."); - let mut subs = client.subscribe(EventType::NewBlock.into()).await.unwrap(); - - // Collect all the events from the subscription. - let subs_collector_hdl = tokio::spawn(async move { - let mut results = Vec::new(); - while let Some(res) = subs.next().await { - results.push(res); - if results.len() == 3 { - break; + async fn read_event(name: &str) -> Event { + DialectEvent::::from_string(read_json_fixture("v0_34", name).await) + .unwrap() + .into() + } + + #[tokio::test] + async fn websocket_client_happy_path() { + let event1 = read_event("subscribe_newblock_0").await; + let event2 = read_event("subscribe_newblock_1").await; + let event3 = read_event("subscribe_newblock_2").await; + let test_events = vec![event1, event2, event3]; + + println!("Starting WebSocket server..."); + let mut server = TestServer::new("127.0.0.1:0", CompatMode::V0_34).await; + println!("Creating client RPC WebSocket connection..."); + let (client, driver) = WebSocketClient::new_with_config( + server.node_addr.clone(), + WebSocketConfig { + compat: CompatMode::V0_34, + ..Default::default() + }, + ) + .await + .unwrap(); + let driver_handle = tokio::spawn(async move { driver.run().await }); + + println!("Initiating subscription for new blocks..."); + let mut subs = client.subscribe(EventType::NewBlock.into()).await.unwrap(); + + // Collect all the events from the subscription. + let subs_collector_hdl = tokio::spawn(async move { + let mut results = Vec::new(); + while let Some(res) = subs.next().await { + results.push(res); + if results.len() == 3 { + break; + } } + results + }); + + println!("Publishing events"); + // Publish the events from this context + for ev in &test_events { + server.publish_event(ev.clone()).unwrap(); } - results - }); - println!("Publishing events"); - // Publish the events from this context - for ev in &test_events { - server.publish_event(ev.clone()).unwrap(); + println!("Collecting results from subscription..."); + let collected_results = subs_collector_hdl.await.unwrap(); + + client.close().unwrap(); + server.terminate().await.unwrap(); + let _ = driver_handle.await.unwrap(); + println!("Closed client and terminated server"); + + assert_eq!(3, collected_results.len()); + for i in 0..3 { + assert_eq!( + test_events[i], + collected_results[i].as_ref().unwrap().clone() + ); + } } + } - println!("Collecting results from subscription..."); - let collected_results = subs_collector_hdl.await.unwrap(); + mod v0_37 { + use super::*; + use crate::dialect::v0_37::Event as RpcEvent; - client.close().unwrap(); - server.terminate().await.unwrap(); - let _ = driver_handle.await.unwrap(); - println!("Closed client and terminated server"); + async fn read_event(name: &str) -> Event { + DialectEvent::::from_string(read_json_fixture("v0_37", name).await) + .unwrap() + .into() + } - assert_eq!(3, collected_results.len()); - for i in 0..3 { - assert_eq!( - test_events[i], - collected_results[i].as_ref().unwrap().clone() - ); + #[tokio::test] + async fn websocket_client_happy_path() { + let event1 = read_event("subscribe_newblock_0").await; + let event2 = read_event("subscribe_newblock_1").await; + let event3 = read_event("subscribe_newblock_2").await; + let test_events = vec![event1, event2, event3]; + + println!("Starting WebSocket server..."); + let mut server = TestServer::new("127.0.0.1:0", CompatMode::Latest).await; + println!("Creating client RPC WebSocket connection..."); + let (client, driver) = WebSocketClient::new_with_config( + server.node_addr.clone(), + WebSocketConfig { + compat: CompatMode::Latest, + ..Default::default() + }, + ) + .await + .unwrap(); + let driver_handle = tokio::spawn(async move { driver.run().await }); + + println!("Initiating subscription for new blocks..."); + let mut subs = client.subscribe(EventType::NewBlock.into()).await.unwrap(); + + // Collect all the events from the subscription. + let subs_collector_hdl = tokio::spawn(async move { + let mut results = Vec::new(); + while let Some(res) = subs.next().await { + results.push(res); + if results.len() == 3 { + break; + } + } + results + }); + + println!("Publishing events"); + // Publish the events from this context + for ev in &test_events { + server.publish_event(ev.clone()).unwrap(); + } + + println!("Collecting results from subscription..."); + let collected_results = subs_collector_hdl.await.unwrap(); + + client.close().unwrap(); + server.terminate().await.unwrap(); + let _ = driver_handle.await.unwrap(); + println!("Closed client and terminated server"); + + assert_eq!(3, collected_results.len()); + for i in 0..3 { + assert_eq!( + test_events[i], + collected_results[i].as_ref().unwrap().clone() + ); + } } } From 7e79039558b50fcdd3ca47512b4e58ed6624132f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 27 Feb 2023 16:17:38 +0200 Subject: [PATCH 71/77] abci: more sensible default impl of ABCI++ methods Returning blank responses does not make a good migration path for applications that are yet unaware of the ABCI++ proposal handling phases. Implement the simplest sensible behaviors by default for Application::prepare_proposal and Application::process_proposal to fulfill the specification. --- abci/src/application.rs | 58 ++++++++++++++++++++++++++++++++++------- 1 file changed, 48 insertions(+), 10 deletions(-) diff --git a/abci/src/application.rs b/abci/src/application.rs index 2f4e8f503..b6086041b 100644 --- a/abci/src/application.rs +++ b/abci/src/application.rs @@ -6,13 +6,14 @@ pub mod echo; pub mod kvstore; use tendermint_proto::v0_37::abci::{ - request::Value, response, Request, RequestApplySnapshotChunk, RequestBeginBlock, - RequestCheckTx, RequestDeliverTx, RequestEcho, RequestEndBlock, RequestInfo, RequestInitChain, - RequestLoadSnapshotChunk, RequestOfferSnapshot, RequestPrepareProposal, RequestProcessProposal, - RequestQuery, Response, ResponseApplySnapshotChunk, ResponseBeginBlock, ResponseCheckTx, - ResponseCommit, ResponseDeliverTx, ResponseEcho, ResponseEndBlock, ResponseFlush, ResponseInfo, - ResponseInitChain, ResponseListSnapshots, ResponseLoadSnapshotChunk, ResponseOfferSnapshot, - ResponsePrepareProposal, ResponseProcessProposal, ResponseQuery, + request::Value, response, response_process_proposal, Request, RequestApplySnapshotChunk, + RequestBeginBlock, RequestCheckTx, RequestDeliverTx, RequestEcho, RequestEndBlock, RequestInfo, + RequestInitChain, RequestLoadSnapshotChunk, RequestOfferSnapshot, RequestPrepareProposal, + RequestProcessProposal, RequestQuery, Response, ResponseApplySnapshotChunk, ResponseBeginBlock, + ResponseCheckTx, ResponseCommit, ResponseDeliverTx, ResponseEcho, ResponseEndBlock, + ResponseFlush, ResponseInfo, ResponseInitChain, ResponseListSnapshots, + ResponseLoadSnapshotChunk, ResponseOfferSnapshot, ResponsePrepareProposal, + ResponseProcessProposal, ResponseQuery, }; /// An ABCI application. @@ -99,12 +100,49 @@ pub trait Application: Send + Clone + 'static { Default::default() } - fn prepare_proposal(&self, _request: RequestPrepareProposal) -> ResponsePrepareProposal { - Default::default() + /// A stage where the application can modify the list of transactions + /// in the preliminary proposal. + /// + /// The default implementation implements the required behavior in a + /// very naive way, removing transactions off the end of the list + /// until the limit on the total size of the transaction is met as + /// specified in the `max_tx_bytes` field of the request, or there are + /// no more transactions. It's up to the application to implement + /// more elaborate removal strategies. + /// + /// This method is introduced in ABCI++. + fn prepare_proposal(&self, request: RequestPrepareProposal) -> ResponsePrepareProposal { + // Per the ABCI++ spec: if the size of RequestPrepareProposal.txs is + // greater than RequestPrepareProposal.max_tx_bytes, the Application + // MUST remove transactions to ensure that the + // RequestPrepareProposal.max_tx_bytes limit is respected by those + // transactions returned in ResponsePrepareProposal.txs. + let RequestPrepareProposal { + mut txs, + max_tx_bytes, + .. + } = request; + let max_tx_bytes: usize = max_tx_bytes.try_into().unwrap_or(0); + let mut total_tx_bytes: usize = txs.iter().map(|tx| tx.len()).sum(); + while total_tx_bytes > max_tx_bytes { + if let Some(tx) = txs.pop() { + total_tx_bytes -= tx.len(); + } else { + break; + } + } + ResponsePrepareProposal { txs } } + /// A stage where the application can accept or reject the proposed block. + /// + /// The default implementation returns the status value of `ACCEPT`. + /// + /// This method is introduced in ABCI++. fn process_proposal(&self, _request: RequestProcessProposal) -> ResponseProcessProposal { - Default::default() + ResponseProcessProposal { + status: response_process_proposal::ProposalStatus::Accept as i32, + } } } From 0fe73a10e97d8b8c37885e21e3e92bac5b9cb45f Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 27 Feb 2023 16:23:01 +0200 Subject: [PATCH 72/77] abci: overflow-proof impl of prepare_proposal --- abci/src/application.rs | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/abci/src/application.rs b/abci/src/application.rs index b6086041b..6fd532b7c 100644 --- a/abci/src/application.rs +++ b/abci/src/application.rs @@ -123,10 +123,13 @@ pub trait Application: Send + Clone + 'static { .. } = request; let max_tx_bytes: usize = max_tx_bytes.try_into().unwrap_or(0); - let mut total_tx_bytes: usize = txs.iter().map(|tx| tx.len()).sum(); + let mut total_tx_bytes: usize = txs + .iter() + .map(|tx| tx.len()) + .fold(0, |acc, len| acc.saturating_add(len)); while total_tx_bytes > max_tx_bytes { if let Some(tx) = txs.pop() { - total_tx_bytes -= tx.len(); + total_tx_bytes = total_tx_bytes.saturating_sub(tx.len()); } else { break; } From 9e25f3fadedcc9cbef177b618ec1832cecaa6936 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Mon, 27 Feb 2023 16:58:12 +0200 Subject: [PATCH 73/77] Update #1193 changelog for tendermint-rpc changes --- .../1193-multi-version-tendermint.md | 4 ++++ .../enhancements/1193-multi-version-tendermint.md | 12 +++++++----- 2 files changed, 11 insertions(+), 5 deletions(-) diff --git a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md index 95639322d..1b7342341 100644 --- a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md +++ b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md @@ -9,3 +9,7 @@ to unsigned varint, to correspond to the changes in Tendermint Core 0.37. No compatibility with 0.34 is provided at the moment. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). +- [`tendermint-rpc`] Changed the signature of `WebSocketClient::new_with_config` + and the public `WebSocketConfig` type of its parameter: instead of being + a re-export from tungstenite, it's a struct defined in this crate and + featuring a compatibility mode parameter. diff --git a/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md b/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md index 42ea183e1..dd45fe91d 100644 --- a/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md +++ b/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md @@ -8,11 +8,13 @@ - [`tendermint`] Protobuf conversions provided for both `v0_34` and `v0_37` versions of the generated [`tendermint-proto`] structs, where applicable. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). -- [`tendermint-rpc`] Provide separate `Client` traits for Tendermint Core 0.34 - and 0.37, placed under the `v0_34::client` and `v0_37::client` modules. - The latest version is re-exported as `crate::Client`. - The websocket and HTTP client implement both traits, it's up to the - application which one to import for use. +- [`tendermint-rpc`] Introduce protocol compatibility modes specifying the + RPC data encoding used by the client. An `HttpClient` can be created with + a selected mode specified as a field in `HttpConfig`, or have the mode + changed afterwards (usually after version discovery) by the added + `set_compat_mode` method. + `WebSocketClient` can only be created with `CompatMode` specified in the added + `new_with_config` constructor, accepting a new `WebSocketConfig` struct. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) - [`tendermint-abci`] Port ABCI application support to 0.37 Tendermint Core API. No legacy support for 0.34 is provided at the moment. From 74b87931d3c5d5c032c1c76098d8bb79c082ab79 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 28 Feb 2023 10:51:06 +0200 Subject: [PATCH 74/77] Fill out .changelog entry for #1193 --- .../breaking-changes/1193-multi-version-tendermint.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md index 1b7342341..494000a07 100644 --- a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md +++ b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md @@ -8,8 +8,11 @@ - [`tendermint-abci`] Change the frame length encoding in the ABCI wire protocol to unsigned varint, to correspond to the changes in Tendermint Core 0.37. No compatibility with 0.34 is provided at the moment. - ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) - [`tendermint-rpc`] Changed the signature of `WebSocketClient::new_with_config` and the public `WebSocketConfig` type of its parameter: instead of being a re-export from tungstenite, it's a struct defined in this crate and featuring a compatibility mode parameter. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) +- [`tendermint-proto`] The `serializers::evidence` module has been made private. + ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) From f3e161e02b4bc42a9c60a369a4b0b7ecd779da99 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Tue, 28 Feb 2023 18:40:24 +0200 Subject: [PATCH 75/77] rpc: improve CompatMode enum Instead of Latest as a variant, have only the explicit list of supported protocol versions as the enum variants. Make LATEST an associated const. --- rpc/src/client.rs | 8 +++++--- rpc/src/client/compat.rs | 17 ++++++++++------- rpc/src/client/transport.rs | 2 +- rpc/src/client/transport/http.rs | 8 ++++---- rpc/src/client/transport/websocket.rs | 20 ++++++++++---------- 5 files changed, 30 insertions(+), 25 deletions(-) diff --git a/rpc/src/client.rs b/rpc/src/client.rs index c4081ddd0..2deb73649 100644 --- a/rpc/src/client.rs +++ b/rpc/src/client.rs @@ -24,7 +24,6 @@ use tendermint::{abci, block::Height, evidence::Evidence, Genesis, Hash}; use tokio::time; use crate::{ - dialect::v0_37::Dialect, endpoint::{validators::DEFAULT_VALIDATORS_PER_PAGE, *}, paging::Paging, prelude::*, @@ -320,8 +319,11 @@ pub trait Client { Ok(()) } - /// Perform a request against the RPC endpoint + /// Perform a request against the RPC endpoint. + /// + /// This method is used by the default implementations of specific + /// endpoint methods. The latest protocol dialect is assumed to be invoked. async fn perform(&self, request: R) -> Result where - R: SimpleRequest; + R: SimpleRequest; } diff --git a/rpc/src/client/compat.rs b/rpc/src/client/compat.rs index 778b20832..55a5c6ec5 100644 --- a/rpc/src/client/compat.rs +++ b/rpc/src/client/compat.rs @@ -8,19 +8,22 @@ use crate::Error; /// Protocol compatibility mode for a Tendermint RPC client. #[derive(Copy, Clone, Debug, PartialEq, Eq)] pub enum CompatMode { - /// Use the latest version of the protocol (v0.37 in this release). - Latest, - /// Use v0.34 version of the protocol. + /// Use version 0.34 of the protocol. V0_34, + /// Use version 0.37 of the protocol. + V0_37, } impl Default for CompatMode { fn default() -> Self { - CompatMode::Latest + CompatMode::LATEST } } impl CompatMode { + /// The latest supported version, selected by default. + pub const LATEST: Self = CompatMode::V0_37; + /// Parse the Tendermint version string to determine /// the compatibility mode. /// @@ -40,7 +43,7 @@ impl CompatMode { .map_err(|_| Error::invalid_tendermint_version(raw_version))?; match (version.major, version.minor) { (0, 34) => Ok(CompatMode::V0_34), - (0, 37) => Ok(CompatMode::Latest), + (0, 37) => Ok(CompatMode::V0_37), _ => Err(Error::unsupported_tendermint_version(version.to_string())), } } @@ -65,11 +68,11 @@ mod tests { ); assert_eq!( CompatMode::from_version(parse_version("v0.37.0-pre1")).unwrap(), - CompatMode::Latest + CompatMode::V0_37 ); assert_eq!( CompatMode::from_version(parse_version("v0.37.0")).unwrap(), - CompatMode::Latest + CompatMode::V0_37 ); let res = CompatMode::from_version(parse_version("v0.38.0")); assert!(res.is_err()); diff --git a/rpc/src/client/transport.rs b/rpc/src/client/transport.rs index c0f9f0c5c..f8859696b 100644 --- a/rpc/src/client/transport.rs +++ b/rpc/src/client/transport.rs @@ -8,7 +8,7 @@ macro_rules! perform_with_compat { ($self:expr, $request:expr) => {{ let request = $request; match $self.compat { - CompatMode::Latest => $self.perform(request).await, + CompatMode::V0_37 => $self.perform(request).await, CompatMode::V0_34 => $self.perform_v0_34(request).await, } }}; diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index 13df4299c..d75a52770 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -10,7 +10,7 @@ use async_trait::async_trait; use tendermint::{block::Height, Hash}; use tendermint_config::net; -use crate::dialect::{v0_34, v0_37}; +use crate::dialect::v0_34; use crate::prelude::*; use crate::{ client::{Client, CompatMode}, @@ -151,7 +151,7 @@ impl HttpClient { impl Client for HttpClient { async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, { self.inner.perform(request).await } @@ -169,7 +169,7 @@ impl Client for HttpClient { { let height = height.into(); match self.compat { - CompatMode::Latest => self.perform(endpoint::header::Request::new(height)).await, + CompatMode::V0_37 => self.perform(endpoint::header::Request::new(height)).await, CompatMode::V0_34 => { // Back-fill with a request to /block endpoint and // taking just the header from the response. @@ -186,7 +186,7 @@ impl Client for HttpClient { hash: Hash, ) -> Result { match self.compat { - CompatMode::Latest => { + CompatMode::V0_37 => { self.perform(endpoint::header_by_hash::Request::new(hash)) .await }, diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index 25731d88e..de8b4c0a6 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -196,7 +196,7 @@ impl WebSocketClient { impl Client for WebSocketClient { async fn perform(&self, request: R) -> Result where - R: SimpleRequest, + R: SimpleRequest, { self.inner.perform(request).await } @@ -214,7 +214,7 @@ impl Client for WebSocketClient { { let height = height.into(); match self.compat { - CompatMode::Latest => self.perform(endpoint::header::Request::new(height)).await, + CompatMode::V0_37 => self.perform(endpoint::header::Request::new(height)).await, CompatMode::V0_34 => { // Back-fill with a request to /block endpoint and // taking just the header from the response. @@ -231,7 +231,7 @@ impl Client for WebSocketClient { hash: Hash, ) -> Result { match self.compat { - CompatMode::Latest => { + CompatMode::V0_37 => { self.perform(endpoint::header_by_hash::Request::new(hash)) .await }, @@ -833,7 +833,7 @@ impl WebSocketClientDriver { async fn handle_text_msg(&mut self, msg: String) -> Result<(), Error> { let parse_res = match self.compat { - CompatMode::Latest => DialectEvent::::from_string(&msg).map(Into::into), + CompatMode::V0_37 => DialectEvent::::from_string(&msg).map(Into::into), CompatMode::V0_34 => DialectEvent::::from_string(&msg).map(Into::into), }; if let Ok(ev) = parse_res { @@ -1159,17 +1159,17 @@ mod test { async fn publish_event(&mut self, ev: Event) { let subs_id = match self.subscriptions.get(&ev.query) { - Some(id) => id.clone(), + Some(id) => Id::Str(id.clone()), None => return, }; match self.compat { - CompatMode::Latest => { + CompatMode::V0_37 => { let ev: DialectEvent = ev.into(); - self.send(Id::Str(subs_id), ev).await; + self.send(subs_id, ev).await; }, CompatMode::V0_34 => { let ev: DialectEvent = ev.into(); - self.send(Id::Str(subs_id), ev).await; + self.send(subs_id, ev).await; }, } } @@ -1369,12 +1369,12 @@ mod test { let test_events = vec![event1, event2, event3]; println!("Starting WebSocket server..."); - let mut server = TestServer::new("127.0.0.1:0", CompatMode::Latest).await; + let mut server = TestServer::new("127.0.0.1:0", CompatMode::V0_37).await; println!("Creating client RPC WebSocket connection..."); let (client, driver) = WebSocketClient::new_with_config( server.node_addr.clone(), WebSocketConfig { - compat: CompatMode::Latest, + compat: CompatMode::V0_37, ..Default::default() }, ) From 84d9cad8c8e41e9e0343633a06ae8288101b0ad3 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 1 Mar 2023 02:06:22 +0200 Subject: [PATCH 76/77] rpc: builder API for clients Replace the *Config structs with a proper builder API for better extensibility. --- rpc/src/client.rs | 2 +- rpc/src/client/transport/http.rs | 106 +++++++++++++--------- rpc/src/client/transport/websocket.rs | 125 +++++++++++++++++--------- 3 files changed, 146 insertions(+), 87 deletions(-) diff --git a/rpc/src/client.rs b/rpc/src/client.rs index 2deb73649..9194b190d 100644 --- a/rpc/src/client.rs +++ b/rpc/src/client.rs @@ -9,7 +9,7 @@ pub mod sync; mod transport; #[cfg(feature = "http-client")] -pub use transport::http::{HttpClient, HttpClientUrl, HttpConfig}; +pub use transport::http::{HttpClient, HttpClientUrl}; pub use transport::mock::{MockClient, MockRequestMatcher, MockRequestMethodMatcher}; #[cfg(feature = "websocket-client")] pub use transport::websocket::{ diff --git a/rpc/src/client/transport/http.rs b/rpc/src/client/transport/http.rs index d75a52770..7fa254ffb 100644 --- a/rpc/src/client/transport/http.rs +++ b/rpc/src/client/transport/http.rs @@ -51,11 +51,60 @@ pub struct HttpClient { compat: CompatMode, } -#[derive(Debug, Clone, Default)] -pub struct HttpConfig { - /// Compatibility mode for Tendermint RPC protocol. - pub compat: CompatMode, - pub proxy_url: Option, +/// The builder pattern constructor for [`HttpClient`]. +pub struct Builder { + url: HttpClientUrl, + compat: CompatMode, + proxy_url: Option, +} + +impl Builder { + /// Use the specified compatibility mode for the Tendermint RPC protocol. + /// + /// The default is the latest protocol version supported by this crate. + pub fn compat_mode(&mut self, mode: CompatMode) -> &mut Self { + self.compat = mode; + self + } + + /// Specify the URL of a proxy server for the client to connect through. + /// + /// If the RPC endpoint is secured (HTTPS), the proxy will automatically + /// attempt to connect using the [HTTP CONNECT] method. + /// + /// [HTTP CONNECT]: https://en.wikipedia.org/wiki/HTTP_tunnel + pub fn proxy_url(&mut self, url: HttpClientUrl) -> &mut Self { + self.proxy_url = Some(url); + self + } + + /// Try to create a client with the options specified for this builder. + pub fn build(&self) -> Result { + match &self.proxy_url { + None => Ok(HttpClient { + inner: if self.url.0.is_secure() { + sealed::HttpClient::new_https(self.url.clone().try_into()?) + } else { + sealed::HttpClient::new_http(self.url.clone().try_into()?) + }, + compat: self.compat, + }), + Some(proxy_url) => Ok(HttpClient { + inner: if proxy_url.0.is_secure() { + sealed::HttpClient::new_https_proxy( + self.url.clone().try_into()?, + proxy_url.clone().try_into()?, + )? + } else { + sealed::HttpClient::new_http_proxy( + self.url.clone().try_into()?, + proxy_url.clone().try_into()?, + )? + }, + compat: self.compat, + }), + } + } } impl HttpClient { @@ -88,45 +137,18 @@ impl HttpClient { U: TryInto, P: TryInto, { - Self::new_with_config( - url, - HttpConfig { - proxy_url: Some(proxy_url.try_into()?), - ..Default::default() - }, - ) + let url = url.try_into()?; + Self::builder(url).proxy_url(proxy_url.try_into()?).build() } - /// Construct a new Tendermint RPC HTTP/S client connecting to the given - /// URL with specified configuration options. - /// - /// If the `proxy_url` member of the [`HttpConfig`] parameter is not `None` - /// and the RPC endpoint is secured (HTTPS), the proxy will automatically - /// attempt to connect using the [HTTP CONNECT] method. - /// - /// [HTTP CONNECT]: https://en.wikipedia.org/wiki/HTTP_tunnel - pub fn new_with_config(url: U, config: HttpConfig) -> Result - where - U: TryInto, - { - let url = url.try_into()?; - match config.proxy_url { - None => Ok(Self { - inner: if url.0.is_secure() { - sealed::HttpClient::new_https(url.try_into()?) - } else { - sealed::HttpClient::new_http(url.try_into()?) - }, - compat: config.compat, - }), - Some(proxy_url) => Ok(Self { - inner: if proxy_url.0.is_secure() { - sealed::HttpClient::new_https_proxy(url.try_into()?, proxy_url.try_into()?)? - } else { - sealed::HttpClient::new_http_proxy(url.try_into()?, proxy_url.try_into()?)? - }, - compat: config.compat, - }), + /// Initiate a builder for a Tendermint RPC HTTP/S client connecting + /// to the given URL, so that more configuration options can be specified + /// with the builder. + pub fn builder(url: HttpClientUrl) -> Builder { + Builder { + url, + compat: Default::default(), + proxy_url: None, } } diff --git a/rpc/src/client/transport/websocket.rs b/rpc/src/client/transport/websocket.rs index de8b4c0a6..025942a0e 100644 --- a/rpc/src/client/transport/websocket.rs +++ b/rpc/src/client/transport/websocket.rs @@ -56,13 +56,8 @@ const RECV_TIMEOUT: Duration = Duration::from_secs(RECV_TIMEOUT_SECONDS); // Taken from https://github.com/tendermint/tendermint/blob/309e29c245a01825fc9630103311fd04de99fa5e/rpc/jsonrpc/server/ws_handler.go#L28 const PING_INTERVAL: Duration = Duration::from_secs((RECV_TIMEOUT_SECONDS * 9) / 10); -#[derive(Default, Debug)] -/// WebSocket client configuration -pub struct WebSocketConfig { - pub compat: CompatMode, - /// Low-level protocol configuration - pub transport: Option, -} +/// Low-level WebSocket configuration +pub use async_tungstenite::tungstenite::protocol::WebSocketConfig; /// Tendermint RPC client that provides access to all RPC functionality /// (including [`Event`] subscription) over a WebSocket connection. @@ -149,6 +144,42 @@ pub struct WebSocketClient { compat: CompatMode, } +/// The builder pattern constructor for [`WebSocketClient`]. +pub struct Builder { + url: WebSocketClientUrl, + compat: CompatMode, + transport_config: Option, +} + +impl Builder { + /// Use the specified compatibility mode for the Tendermint RPC protocol. + /// + /// The default is the latest protocol version supported by this crate. + pub fn compat_mode(&mut self, mode: CompatMode) -> &mut Self { + self.compat = mode; + self + } + + /// Use the specfied low-level WebSocket configuration options. + pub fn config(&mut self, config: WebSocketConfig) -> &mut Self { + self.transport_config = Some(config); + self + } + + /// Try to create a client with the options specified for this builder. + pub async fn build(&self) -> Result<(WebSocketClient, WebSocketClientDriver), Error> { + let url = self.url.0.clone(); + let compat = self.compat; + let (inner, driver) = if url.is_secure() { + sealed::WebSocketClient::new_secure(url, compat, self.transport_config).await? + } else { + sealed::WebSocketClient::new_unsecure(url, compat, self.transport_config).await? + }; + + Ok((WebSocketClient { inner, compat }, driver)) + } +} + impl WebSocketClient { /// Construct a new WebSocket-based client connecting to the given /// Tendermint node's RPC endpoint. @@ -158,7 +189,8 @@ impl WebSocketClient { where U: TryInto, { - Self::new_with_config(url, Default::default()).await + let url = url.try_into()?; + Self::builder(url).build().await } /// Construct a new WebSocket-based client connecting to the given @@ -173,15 +205,19 @@ impl WebSocketClient { U: TryInto, { let url = url.try_into()?; - let compat = config.compat; - - let (inner, driver) = if url.0.is_secure() { - sealed::WebSocketClient::new_secure(url.0, config).await? - } else { - sealed::WebSocketClient::new_unsecure(url.0, config).await? - }; + Self::builder(url).config(config).build().await + } - Ok((Self { inner, compat }, driver)) + /// Initiate a builder for a WebSocket-based client connecting to the given + /// Tendermint node's RPC endpoint. + /// + /// Supports both `ws://` and `wss://` protocols. + pub fn builder(url: WebSocketClientUrl) -> Builder { + Builder { + url, + compat: Default::default(), + transport_config: Default::default(), + } } async fn perform_v0_34(&self, request: R) -> Result @@ -364,6 +400,7 @@ mod sealed { client::{ sync::{unbounded, ChannelTx}, transport::auth::authorize, + CompatMode, }, dialect::Dialect, prelude::*, @@ -406,16 +443,17 @@ mod sealed { /// doesn't block the client. pub async fn new( url: Url, - config: WebSocketConfig, + compat: CompatMode, + config: Option, ) -> Result<(Self, WebSocketClientDriver), Error> { debug!("Connecting to unsecure WebSocket endpoint: {}", url); - let (stream, _response) = connect_async_with_config(url, config.transport) + let (stream, _response) = connect_async_with_config(url, config) .await .map_err(Error::tungstenite)?; let (cmd_tx, cmd_rx) = unbounded(); - let driver = WebSocketClientDriver::new(stream, cmd_rx, config.compat); + let driver = WebSocketClientDriver::new(stream, cmd_rx, compat); let client = Self { cmd_tx, _client_type: Default::default(), @@ -437,19 +475,20 @@ mod sealed { /// doesn't block the client. pub async fn new( url: Url, - config: WebSocketConfig, + compat: CompatMode, + config: Option, ) -> Result<(Self, WebSocketClientDriver), Error> { debug!("Connecting to secure WebSocket endpoint: {}", url); // Not supplying a connector means async_tungstenite will create the // connector for us. let (stream, _response) = - connect_async_with_tls_connector_and_config(url, None, config.transport) + connect_async_with_tls_connector_and_config(url, None, config) .await .map_err(Error::tungstenite)?; let (cmd_tx, cmd_rx) = unbounded(); - let driver = WebSocketClientDriver::new(stream, cmd_rx, config.compat); + let driver = WebSocketClientDriver::new(stream, cmd_rx, compat); let client = Self { cmd_tx, _client_type: Default::default(), @@ -541,17 +580,21 @@ mod sealed { impl WebSocketClient { pub async fn new_unsecure( url: Url, - config: WebSocketConfig, + compat: CompatMode, + config: Option, ) -> Result<(Self, WebSocketClientDriver), Error> { - let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; + let (client, driver) = + AsyncTungsteniteClient::::new(url, compat, config).await?; Ok((Self::Unsecure(client), driver)) } pub async fn new_secure( url: Url, - config: WebSocketConfig, + compat: CompatMode, + config: Option, ) -> Result<(Self, WebSocketClientDriver), Error> { - let (client, driver) = AsyncTungsteniteClient::::new(url, config).await?; + let (client, driver) = + AsyncTungsteniteClient::::new(url, compat, config).await?; Ok((Self::Secure(client), driver)) } @@ -1301,15 +1344,12 @@ mod test { println!("Starting WebSocket server..."); let mut server = TestServer::new("127.0.0.1:0", CompatMode::V0_34).await; println!("Creating client RPC WebSocket connection..."); - let (client, driver) = WebSocketClient::new_with_config( - server.node_addr.clone(), - WebSocketConfig { - compat: CompatMode::V0_34, - ..Default::default() - }, - ) - .await - .unwrap(); + let url = server.node_addr.clone().try_into().unwrap(); + let (client, driver) = WebSocketClient::builder(url) + .compat_mode(CompatMode::V0_34) + .build() + .await + .unwrap(); let driver_handle = tokio::spawn(async move { driver.run().await }); println!("Initiating subscription for new blocks..."); @@ -1371,15 +1411,12 @@ mod test { println!("Starting WebSocket server..."); let mut server = TestServer::new("127.0.0.1:0", CompatMode::V0_37).await; println!("Creating client RPC WebSocket connection..."); - let (client, driver) = WebSocketClient::new_with_config( - server.node_addr.clone(), - WebSocketConfig { - compat: CompatMode::V0_37, - ..Default::default() - }, - ) - .await - .unwrap(); + let url = server.node_addr.clone().try_into().unwrap(); + let (client, driver) = WebSocketClient::builder(url) + .compat_mode(CompatMode::V0_37) + .build() + .await + .unwrap(); let driver_handle = tokio::spawn(async move { driver.run().await }); println!("Initiating subscription for new blocks..."); From 7d9572c11443db85b47e0af32c36e73aa0f4bb38 Mon Sep 17 00:00:00 2001 From: Mikhail Zabaluev Date: Wed, 1 Mar 2023 02:13:34 +0200 Subject: [PATCH 77/77] Update #1193 changelog about RPC client builders --- .../1193-multi-version-tendermint.md | 4 +--- .../enhancements/1193-multi-version-tendermint.md | 14 +++++++------- 2 files changed, 8 insertions(+), 10 deletions(-) diff --git a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md index 494000a07..cda523977 100644 --- a/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md +++ b/.changelog/unreleased/breaking-changes/1193-multi-version-tendermint.md @@ -10,9 +10,7 @@ No compatibility with 0.34 is provided at the moment. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) - [`tendermint-rpc`] Changed the signature of `WebSocketClient::new_with_config` - and the public `WebSocketConfig` type of its parameter: instead of being - a re-export from tungstenite, it's a struct defined in this crate and - featuring a compatibility mode parameter. + to accept a `WebSocketConfig` struct value rather than an `Option`. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) - [`tendermint-proto`] The `serializers::evidence` module has been made private. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) diff --git a/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md b/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md index dd45fe91d..617491b14 100644 --- a/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md +++ b/.changelog/unreleased/enhancements/1193-multi-version-tendermint.md @@ -8,13 +8,13 @@ - [`tendermint`] Protobuf conversions provided for both `v0_34` and `v0_37` versions of the generated [`tendermint-proto`] structs, where applicable. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)). -- [`tendermint-rpc`] Introduce protocol compatibility modes specifying the - RPC data encoding used by the client. An `HttpClient` can be created with - a selected mode specified as a field in `HttpConfig`, or have the mode - changed afterwards (usually after version discovery) by the added - `set_compat_mode` method. - `WebSocketClient` can only be created with `CompatMode` specified in the added - `new_with_config` constructor, accepting a new `WebSocketConfig` struct. +- [`tendermint-rpc`] Introduce `client::CompatMode`, enumerating protocol + compatibility modes specifying the RPC data encoding used by the client. + An `HttpClient` can be created with a selected mode specified in the new + `builder` API, or have the mode changed afterwards (usually after + version discovery) by the added `set_compat_mode` method. + For `WebSocketClient`, the mode can only be specified at creation via the new + `builder` API. ([#1193](https://github.com/informalsystems/tendermint-rs/pull/1193)) - [`tendermint-abci`] Port ABCI application support to 0.37 Tendermint Core API. No legacy support for 0.34 is provided at the moment.