Skip to content
This repository has been archived by the owner on Jan 22, 2025. It is now read-only.

Commit

Permalink
Cli: add cluster-date subcommand, and make block-time slot optional (#…
Browse files Browse the repository at this point in the history
…9878) (#9883)

automerge
  • Loading branch information
mergify[bot] authored May 5, 2020
1 parent d8e885f commit 8cb3953
Show file tree
Hide file tree
Showing 3 changed files with 82 additions and 19 deletions.
10 changes: 8 additions & 2 deletions cli/src/cli.rs
Original file line number Diff line number Diff line change
Expand Up @@ -179,6 +179,7 @@ pub enum CliCommand {
commitment_config: CommitmentConfig,
follow: bool,
},
ClusterDate,
ClusterVersion,
CreateAddressWithSeed {
from_pubkey: Option<Pubkey>,
Expand All @@ -187,7 +188,7 @@ pub enum CliCommand {
},
Fees,
GetBlockTime {
slot: Slot,
slot: Option<Slot>,
},
GetEpochInfo {
commitment_config: CommitmentConfig,
Expand Down Expand Up @@ -587,6 +588,10 @@ pub fn parse_command(
let response = match matches.subcommand() {
// Cluster Query Commands
("catchup", Some(matches)) => parse_catchup(matches, wallet_manager),
("cluster-date", Some(_matches)) => Ok(CliCommandInfo {
command: CliCommand::ClusterDate,
signers: vec![],
}),
("cluster-version", Some(_matches)) => Ok(CliCommandInfo {
command: CliCommand::ClusterVersion,
signers: vec![],
Expand Down Expand Up @@ -1680,14 +1685,15 @@ pub fn process_command(config: &CliConfig) -> ProcessResult {
*commitment_config,
*follow,
),
CliCommand::ClusterDate => process_cluster_date(&rpc_client, config),
CliCommand::ClusterVersion => process_cluster_version(&rpc_client),
CliCommand::CreateAddressWithSeed {
from_pubkey,
seed,
program_id,
} => process_create_address_with_seed(config, from_pubkey.as_ref(), &seed, &program_id),
CliCommand::Fees => process_fees(&rpc_client),
CliCommand::GetBlockTime { slot } => process_get_block_time(&rpc_client, *slot),
CliCommand::GetBlockTime { slot } => process_get_block_time(&rpc_client, config, *slot),
CliCommand::GetGenesisHash => process_get_genesis_hash(&rpc_client),
CliCommand::GetEpochInfo { commitment_config } => {
process_get_epoch_info(&rpc_client, config, *commitment_config)
Expand Down
23 changes: 23 additions & 0 deletions cli/src/cli_output.rs
Original file line number Diff line number Diff line change
Expand Up @@ -839,3 +839,26 @@ impl From<&Lockout> for CliLockout {
}
}
}

#[derive(Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct CliBlockTime {
pub slot: Slot,
pub timestamp: UnixTimestamp,
}

impl fmt::Display for CliBlockTime {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
writeln_name_value(f, "Block:", &self.slot.to_string())?;
writeln_name_value(
f,
"Date:",
&format!(
"{} (UnixTimestamp: {})",
DateTime::<Utc>::from_utc(NaiveDateTime::from_timestamp(self.timestamp, 0), Utc)
.to_rfc3339_opts(SecondsFormat::Secs, true),
self.timestamp
),
)
}
}
68 changes: 51 additions & 17 deletions cli/src/cluster_query.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,8 @@
use crate::{
cli::{check_account_for_fee, CliCommand, CliCommandInfo, CliConfig, CliError, ProcessResult},
cli_output::{
CliBlockProduction, CliBlockProductionEntry, CliEpochInfo, CliKeyedStakeState,
CliSlotStatus, CliStakeVec, CliValidator, CliValidators,
},
cli_output::*,
display::println_name_value,
};
use chrono::{DateTime, NaiveDateTime, SecondsFormat, Utc};
use clap::{value_t, value_t_or_exit, App, Arg, ArgMatches, SubCommand};
use console::{style, Emoji};
use indicatif::{ProgressBar, ProgressStyle};
Expand All @@ -24,7 +20,7 @@ use solana_client::{
use solana_remote_wallet::remote_wallet::RemoteWalletManager;
use solana_sdk::{
account_utils::StateMut,
clock::{self, Slot},
clock::{self, Clock, Slot},
commitment_config::CommitmentConfig,
epoch_schedule::Epoch,
hash::Hash,
Expand All @@ -33,6 +29,7 @@ use solana_sdk::{
pubkey::Pubkey,
signature::{Keypair, Signer},
system_instruction,
sysvar::{self, Sysvar},
transaction::Transaction,
};
use std::{
Expand Down Expand Up @@ -83,6 +80,10 @@ impl ClusterQuerySubCommands for App<'_, '_> {
)
.arg(commitment_arg()),
)
.subcommand(
SubCommand::with_name("cluster-date")
.about("Get current cluster date, computed from genesis creation time and network time")
)
.subcommand(
SubCommand::with_name("cluster-version")
.about("Get the version of the cluster entrypoint"),
Expand All @@ -96,7 +97,6 @@ impl ClusterQuerySubCommands for App<'_, '_> {
.index(1)
.takes_value(true)
.value_name("SLOT")
.required(true)
.help("Slot number of the block to query")
)
)
Expand Down Expand Up @@ -315,7 +315,7 @@ pub fn parse_cluster_ping(
}

pub fn parse_get_block_time(matches: &ArgMatches<'_>) -> Result<CliCommandInfo, CliError> {
let slot = value_t_or_exit!(matches, "slot", u64);
let slot = value_of(matches, "slot");
Ok(CliCommandInfo {
command: CliCommand::GetBlockTime { slot },
signers: vec![],
Expand Down Expand Up @@ -523,6 +523,24 @@ pub fn process_catchup(
}
}

pub fn process_cluster_date(rpc_client: &RpcClient, config: &CliConfig) -> ProcessResult {
let result = rpc_client
.get_account_with_commitment(&sysvar::clock::id(), CommitmentConfig::default())?;
if let Some(clock_account) = result.value {
let clock: Clock = Sysvar::from_account(&clock_account).ok_or_else(|| {
CliError::RpcRequestError("Failed to deserialize clock sysvar".to_string())
})?;
let block_time = CliBlockTime {
slot: result.context.slot,
timestamp: clock.unix_timestamp,
};
config.output_format.formatted_print(&block_time);
Ok("".to_string())
} else {
Err(format!("AccountNotFound: pubkey={}", sysvar::clock::id()).into())
}
}

pub fn process_cluster_version(rpc_client: &RpcClient) -> ProcessResult {
let remote_version = rpc_client.get_version()?;
Ok(remote_version.solana_core)
Expand Down Expand Up @@ -572,15 +590,20 @@ pub fn process_leader_schedule(rpc_client: &RpcClient) -> ProcessResult {
Ok("".to_string())
}

pub fn process_get_block_time(rpc_client: &RpcClient, slot: Slot) -> ProcessResult {
pub fn process_get_block_time(
rpc_client: &RpcClient,
config: &CliConfig,
slot: Option<Slot>,
) -> ProcessResult {
let slot = if let Some(slot) = slot {
slot
} else {
rpc_client.get_slot()?
};
let timestamp = rpc_client.get_block_time(slot)?;
let result = format!(
"{} (UnixTimestamp: {})",
DateTime::<Utc>::from_utc(NaiveDateTime::from_timestamp(timestamp, 0), Utc)
.to_rfc3339_opts(SecondsFormat::Secs, true),
timestamp
);
Ok(result)
let block_time = CliBlockTime { slot, timestamp };
config.output_format.formatted_print(&block_time);
Ok("".to_string())
}

pub fn process_get_epoch_info(
Expand Down Expand Up @@ -1201,6 +1224,17 @@ mod tests {
let (default_keypair_file, mut tmp_file) = make_tmp_file();
write_keypair(&default_keypair, tmp_file.as_file_mut()).unwrap();

let test_cluster_version = test_commands
.clone()
.get_matches_from(vec!["test", "cluster-date"]);
assert_eq!(
parse_command(&test_cluster_version, &default_keypair_file, &mut None).unwrap(),
CliCommandInfo {
command: CliCommand::ClusterDate,
signers: vec![],
}
);

let test_cluster_version = test_commands
.clone()
.get_matches_from(vec!["test", "cluster-version"]);
Expand Down Expand Up @@ -1229,7 +1263,7 @@ mod tests {
assert_eq!(
parse_command(&test_get_block_time, &default_keypair_file, &mut None).unwrap(),
CliCommandInfo {
command: CliCommand::GetBlockTime { slot },
command: CliCommand::GetBlockTime { slot: Some(slot) },
signers: vec![],
}
);
Expand Down

0 comments on commit 8cb3953

Please sign in to comment.