Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ keywords = ["core blockchain", "xcb", "cli"]
license = "MIT OR Apache-2.0"
homepage = "https://github.com/core-coin/core-cli"
repository = "https://github.com/core-coin/core-cli"
version = "0.0.3"
version = "0.0.4"

[workspace.dependencies]
# Workspace members
Expand Down
1 change: 1 addition & 0 deletions crates/console/src/base.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ fn list() {
println!(" 'get_block(<hash>|<number>|'latest')' - get block information by hash or number. Use 'latest' to get the latest block");
println!(" 'get_energy_price()' - get the current energy price to allow a timely execution of a transaction");
println!(" 'get_network_id()' - get the nework ID of the current network");
println!(" 'syncing()' - get the syncing status of the node");

println!("'xcbkey' - XCB Key module commands:");
println!(" 'list()' - list all accounts");
Expand Down
3 changes: 3 additions & 0 deletions crates/modules/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -31,3 +31,6 @@ atoms-rpc-types.workspace = true
xcb-keystore.workspace = true

rpassword = "5.0"

[dev-dependencies]
base-primitives.workspace = true
9 changes: 9 additions & 0 deletions crates/modules/src/xcb.rs
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,14 @@ impl XcbModule {
Err(e) => Err(e),
}
}

async fn syncing(&self) -> Result<Response, CliError> {
let syncing = self.client().await.lock().await.syncing().await;
match syncing {
Ok(syncing) => Ok(Response::SyncStatus(syncing)),
Err(e) => Err(e),
}
}
}

#[async_trait::async_trait]
Expand All @@ -96,6 +104,7 @@ impl Module for XcbModule {
"get_block" => self.block(args).await,
"get_energy_price" => self.get_energy_price().await,
"get_network_id" => self.get_network_id().await,
"syncing" => self.syncing().await,
_ => Err(CliError::UnknownCommand),
}
}
Expand Down
53 changes: 52 additions & 1 deletion crates/modules/tests/xcb_tests.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
#[cfg(test)]
mod tests {
use atoms_rpc_types::Block;
use atoms_rpc_types::{Block, SyncInfo};
use base_primitives::U256;
use cli_error::CliError;
use modules::{Module, XcbModule};
use rpc::MockRpcClient;
Expand All @@ -23,6 +24,11 @@ mod tests {
XcbModule::new(client)
}

fn get_module_with_rpc_client(client: MockRpcClient) -> XcbModule {
let client = Arc::new(Mutex::new(client));
XcbModule::new(client)
}

#[tokio::test]
async fn test_execute_get_block_height() {
let mut module = get_module();
Expand Down Expand Up @@ -139,4 +145,49 @@ mod tests {
Err(CliError::InvalidNumberOfArguments(_))
));
}

#[tokio::test]
async fn test_syncing() {
let mut module = get_module();
let response = module.execute("syncing".to_string(), vec![]).await.unwrap();
assert_eq!(
response,
Response::SyncStatus(atoms_rpc_types::SyncStatus::None)
);

assert_eq!(
response.format(types::ResponseView::Human),
"RPC node is synced and data is up to date"
);
}

#[tokio::test]
async fn test_syncing_active() {
let mut module = get_module_with_rpc_client(MockRpcClient::new().with_syncing(
atoms_rpc_types::SyncStatus::Info(SyncInfo {
starting_block: U256::from(0),
current_block: U256::from(100),
highest_block: U256::from(1000),
warp_chunks_amount: None,
warp_chunks_processed: None,
}),
));

let response = module.execute("syncing".to_string(), vec![]).await.unwrap();
assert_eq!(
response,
Response::SyncStatus(atoms_rpc_types::SyncStatus::Info(SyncInfo {
starting_block: U256::from(0),
current_block: U256::from(100),
highest_block: U256::from(1000),
warp_chunks_amount: None,
warp_chunks_processed: None,
}))
);

assert_eq!(
response.format(types::ResponseView::Human),
"RPC node is syncing now. Current block: 100, highest block: 1000, starting block: 0"
);
}
}
11 changes: 10 additions & 1 deletion crates/rpc/src/go_core.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ use crate::RpcClient;
use async_trait::async_trait;
use atoms_provider::{network::Ethereum, Provider, RootProvider};
use atoms_rpc_client::RpcClient as AtomsRpcClient;
use atoms_rpc_types::{Block, BlockId, BlockNumberOrTag, RpcBlockHash};
use atoms_rpc_types::{Block, BlockId, BlockNumberOrTag, RpcBlockHash, SyncStatus};
use atoms_transport_http::{Client, Http};
use base_primitives::{hex::FromHex, FixedBytes};
use cli_error::CliError;
Expand Down Expand Up @@ -90,4 +90,13 @@ impl RpcClient for GoCoreClient {
.map_err(|e| CliError::RpcError(e.to_string()))?;
Ok(response)
}

async fn syncing(&self) -> Result<SyncStatus, CliError> {
let response = self
.provider
.syncing()
.await
.map_err(|e| CliError::RpcError(e.to_string()))?;
Ok(response)
}
}
4 changes: 3 additions & 1 deletion crates/rpc/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
use async_trait::async_trait;
use atoms_rpc_types::Block;
use atoms_rpc_types::{Block, SyncStatus};
use cli_error::CliError;

pub mod go_core;
Expand All @@ -17,4 +17,6 @@ pub trait RpcClient {

async fn get_energy_price(&self) -> Result<u128, CliError>;
async fn get_network_id(&self) -> Result<u64, CliError>;

async fn syncing(&self) -> Result<SyncStatus, CliError>;
}
11 changes: 11 additions & 0 deletions crates/rpc/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ pub struct MockRpcClient {
pub block_latest: Block,
pub energy_price: u128,
pub network_id: u64,
pub syncing: atoms_rpc_types::SyncStatus,
}

impl MockRpcClient {
Expand All @@ -20,6 +21,7 @@ impl MockRpcClient {
block_latest: Block::default(),
energy_price: 0,
network_id: 0,
syncing: atoms_rpc_types::SyncStatus::None,
}
}

Expand Down Expand Up @@ -52,6 +54,11 @@ impl MockRpcClient {
self.network_id = network_id;
self
}

pub fn with_syncing(mut self, syncing: atoms_rpc_types::SyncStatus) -> Self {
self.syncing = syncing;
self
}
}

impl Default for MockRpcClient {
Expand Down Expand Up @@ -85,4 +92,8 @@ impl RpcClient for MockRpcClient {
async fn get_network_id(&self) -> Result<u64, CliError> {
Ok(self.network_id)
}

async fn syncing(&self) -> Result<atoms_rpc_types::SyncStatus, CliError> {
Ok(self.syncing)
}
}
9 changes: 9 additions & 0 deletions crates/rpc/tests/go_core_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

#[cfg(test)]
mod tests {
use atoms_rpc_types::SyncStatus;
use cli_error::CliError;
use rpc::{GoCoreClient, RpcClient};
use types::DEFAULT_BACKEND;
Expand Down Expand Up @@ -92,4 +93,12 @@ mod tests {
let response = go_core_client.get_block_by_number(999999999).await;
assert!(matches!(response, Err(CliError::RpcError(_))));
}

#[tokio::test]
async fn test_syncing() {
let go_core_client = gocore_client().await;

let response = go_core_client.syncing().await.unwrap();
assert_eq!(response, SyncStatus::None);
}
}
12 changes: 12 additions & 0 deletions crates/types/src/response.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,9 @@ use atoms_rpc_types::Block;
use serde::Serialize;

use crate::{account::KeyFile, Account};
use atoms_rpc_types::SyncStatus;
use std::str::FromStr;

/// ResponseView decided if response of call will be returned as a string, json object or human readable format
#[derive(Debug, Clone, PartialEq, Default)]
pub enum ResponseView {
Expand Down Expand Up @@ -38,6 +40,7 @@ pub enum Response {

Block(Block),
Struct(serde_json::Value), // Use serde_json::Value for custom structs
SyncStatus(SyncStatus),

Accounts(Vec<Account>),
Keyfile(KeyFile),
Expand Down Expand Up @@ -71,6 +74,14 @@ impl std::fmt::Display for Response {
}
Ok(())
}
Response::SyncStatus(sync_info) => {
if let SyncStatus::Info(sync_info) = sync_info {
write!(f, "RPC node is syncing now. Current block: {}, highest block: {}, starting block: {}", sync_info.current_block, sync_info.highest_block, sync_info.starting_block)
} else {
write!(f, "RPC node is synced and data is up to date")
}
}

Response::Keyfile(keyfile) => write!(f, "{}", keyfile),
}
}
Expand All @@ -96,6 +107,7 @@ impl Response {
Response::Struct(val) => format!("Struct value: {:#?}", val),
Response::Accounts(_) => self.to_string(),
Response::Keyfile(_) => self.to_string(),
Response::SyncStatus(_) => self.to_string(),
}
}
}
Loading