diff --git a/CHANGELOG.md b/CHANGELOG.md index 5d6d57cd6b..ef9c535d9f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -17,6 +17,7 @@ Post 1.0.0 release, the changelog format is based on [Keep a Changelog](https:// - clients,validator-api: take coconut signers from the chain instead of specifying them via CLI ([#1747]) - multisig contract: add DKG contract to the list of addresses that can create proposals ([#1747]) - socks5-client: wait closing inbound connection until data is sent, and throttle incoming data in general ([#1783]) +- nym-cli: improve error reporting/handling and changed `vesting-schedule` queries to use query client instead of signing client ### Fixed diff --git a/Cargo.lock b/Cargo.lock index 4303004d95..3c177de6a5 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -3139,6 +3139,7 @@ dependencies = [ "pretty_env_logger", "serde", "serde_json", + "tap", "tokio", "validator-client", ] @@ -3164,6 +3165,7 @@ dependencies = [ "rand 0.6.5", "serde", "serde_json", + "tap", "thiserror", "time 0.3.14", "toml", diff --git a/common/commands/Cargo.toml b/common/commands/Cargo.toml index 35b38512fa..ce0195cce4 100644 --- a/common/commands/Cargo.toml +++ b/common/commands/Cargo.toml @@ -22,6 +22,7 @@ thiserror = "1" time = { version = "0.3.6", features = ["parsing", "formatting"] } toml = "0.5.6" url = "2.2" +tap = "1" cosmrs = { git = "https://github.com/neacsu/cosmos-rust", branch = "neacsu/feegrant_support" } cosmwasm-std = { version = "1.0.0" } diff --git a/common/commands/src/context/errors.rs b/common/commands/src/context/errors.rs index 5c3d24a2bb..44a99f49ed 100644 --- a/common/commands/src/context/errors.rs +++ b/common/commands/src/context/errors.rs @@ -15,4 +15,10 @@ pub enum ContextError { // TODO: improve this to return known errors #[error("failed to create client - {0}")] NymdError(String), + + #[error("{0}")] + NymdErrorPassthrough(#[from] validator_client::nymd::error::NymdError), + + #[error("{0}")] + ValidatorClientError(#[from] validator_client::ValidatorClientError), } diff --git a/common/commands/src/context/mod.rs b/common/commands/src/context/mod.rs index 856a03e62a..4f55aa1847 100644 --- a/common/commands/src/context/mod.rs +++ b/common/commands/src/context/mod.rs @@ -6,6 +6,7 @@ use network_defaults::{ var_names::{API_VALIDATOR, MIXNET_CONTRACT_ADDRESS, NYMD_VALIDATOR, VESTING_CONTRACT_ADDRESS}, NymNetworkDetails, }; +use tap::prelude::*; use validator_client::nymd::{self, AccountId, NymdClient, QueryNymdClient, SigningNymdClient}; pub use validator_client::validator_api::Client as ValidatorApiClient; @@ -58,7 +59,7 @@ pub fn create_signing_client( network_details: &NymNetworkDetails, ) -> Result { let client_config = nymd::Config::try_from_nym_network_details(network_details) - .expect("failed to construct valid validator client config with the provided network"); + .tap_err(|e| log::error!("Failed to get client config - {:?}", e))?; // get mnemonic let mnemonic = match std::env::var("MNEMONIC") { @@ -87,7 +88,7 @@ pub fn create_query_client( network_details: &NymNetworkDetails, ) -> Result { let client_config = nymd::Config::try_from_nym_network_details(network_details) - .expect("failed to construct valid validator client config with the provided network"); + .tap_err(|e| log::error!("Failed to get client config - {:?}", e))?; let nymd_url = network_details .endpoints @@ -107,7 +108,7 @@ pub fn create_signing_client_with_validator_api( network_details: &NymNetworkDetails, ) -> Result { let client_config = validator_client::Config::try_from_nym_network_details(network_details) - .expect("failed to construct valid validator client config with the provided network"); + .tap_err(|e| log::error!("Failed to get client config - {:?}", e))?; // get mnemonic let mnemonic = match std::env::var("MNEMONIC") { @@ -129,7 +130,7 @@ pub fn create_query_client_with_validator_api( network_details: &NymNetworkDetails, ) -> Result { let client_config = validator_client::Config::try_from_nym_network_details(network_details) - .expect("failed to construct valid validator client config with the provided network"); + .tap_err(|e| log::error!("Failed to get client config - {:?}", e))?; match validator_client::client::Client::new_query(client_config) { Ok(client) => Ok(client), diff --git a/common/commands/src/validator/vesting/balance.rs b/common/commands/src/validator/vesting/balance.rs index 45b2f7866d..0dff560b9f 100644 --- a/common/commands/src/validator/vesting/balance.rs +++ b/common/commands/src/validator/vesting/balance.rs @@ -3,11 +3,11 @@ use clap::Parser; use cosmrs::AccountId; -use log::info; +use log::{error, info}; use validator_client::nymd::{Coin, VestingQueryClient}; -use crate::context::SigningClient; +use crate::context::QueryClient; use crate::utils::show_error; use crate::utils::{pretty_coin, pretty_cosmwasm_coin}; @@ -18,8 +18,16 @@ pub struct Args { pub address: Option, } -pub async fn balance(args: Args, client: SigningClient) { - let account_id = args.address.unwrap_or_else(|| client.address().clone()); +pub async fn balance(args: Args, client: QueryClient, address_from_mnemonic: Option) { + if args.address.is_none() && address_from_mnemonic.is_none() { + error!("Please specify an account address or a mnemonic to get the balance for"); + return; + } + + let account_id = args + .address + .unwrap_or_else(|| address_from_mnemonic.expect("please provide a mnemonic")); + let vesting_address = account_id.to_string(); let denom = client.current_chain_details().mix_denom.base.as_str(); diff --git a/common/commands/src/validator/vesting/query_vesting_schedule.rs b/common/commands/src/validator/vesting/query_vesting_schedule.rs index 23118c1bf5..10a4dc41d3 100644 --- a/common/commands/src/validator/vesting/query_vesting_schedule.rs +++ b/common/commands/src/validator/vesting/query_vesting_schedule.rs @@ -4,11 +4,11 @@ use clap::Parser; use cosmrs::AccountId; use cosmwasm_std::Coin as CosmWasmCoin; -use log::info; +use log::{error, info}; use validator_client::nymd::{Coin, VestingQueryClient}; -use crate::context::SigningClient; +use crate::context::QueryClient; use crate::utils::show_error; use crate::utils::{pretty_coin, pretty_cosmwasm_coin}; @@ -19,8 +19,18 @@ pub struct Args { pub address: Option, } -pub async fn query(args: Args, client: SigningClient) { - let account_id = args.address.unwrap_or_else(|| client.address().clone()); +pub async fn query(args: Args, client: QueryClient, address_from_mnemonic: Option) { + if args.address.is_none() && address_from_mnemonic.is_none() { + error!("Please specify an account address or a mnemonic to get the balance for"); + return; + } + + let account_id = args + .address + .unwrap_or_else(|| address_from_mnemonic.expect("please provide a mnemonic")); + + info!("Checking account {} for a vesting schedule...", account_id); + let vesting_address = account_id.to_string(); let denom = client.current_chain_details().mix_denom.base.as_str(); diff --git a/tools/nym-cli/Cargo.toml b/tools/nym-cli/Cargo.toml index 2ec5af6404..67c3bda09a 100644 --- a/tools/nym-cli/Cargo.toml +++ b/tools/nym-cli/Cargo.toml @@ -18,6 +18,7 @@ serde_json = "1" tokio = { version = "1.11", features = [ "net", "rt-multi-thread", "macros", "signal"] } bip39 = "1.0.1" anyhow = "1" +tap = "1" nym-cli-commands = { path = "../../common/commands" } logging = { path = "../../common/logging"} diff --git a/tools/nym-cli/src/validator/vesting.rs b/tools/nym-cli/src/validator/vesting.rs index d87ca2c9ff..202011bc3c 100644 --- a/tools/nym-cli/src/validator/vesting.rs +++ b/tools/nym-cli/src/validator/vesting.rs @@ -2,7 +2,7 @@ // SPDX-License-Identifier: Apache-2.0 use network_defaults::NymNetworkDetails; -use nym_cli_commands::context::{create_signing_client, ClientArgs}; +use nym_cli_commands::context::{create_query_client, create_signing_client, ClientArgs}; pub(crate) async fn execute( global_args: ClientArgs, @@ -19,18 +19,22 @@ pub(crate) async fn execute( .await } Some(nym_cli_commands::validator::vesting::VestingScheduleCommands::Query(args)) => { + let address_from_args = args.address.clone(); nym_cli_commands::validator::vesting::query_vesting_schedule::query( args, - create_signing_client(global_args, network_details)?, + create_query_client(network_details)?, + address_from_args, ) .await } Some(nym_cli_commands::validator::vesting::VestingScheduleCommands::VestedBalance( args, )) => { + let address_from_args = args.address.clone(); nym_cli_commands::validator::vesting::balance::balance( args, - create_signing_client(global_args, network_details)?, + create_query_client(network_details)?, + address_from_args, ) .await }