From 0b65cea021781d818e47cf44b4971c27b3f68008 Mon Sep 17 00:00:00 2001 From: Boyu Yang Date: Wed, 21 Jul 2021 12:12:08 +0800 Subject: [PATCH] feat: better tips for "migrate" subcomamnd --- ckb-bin/src/lib.rs | 4 ++-- ckb-bin/src/subcommand/export.rs | 8 +++++++- ckb-bin/src/subcommand/import.rs | 8 +++++++- ckb-bin/src/subcommand/replay.rs | 16 ++++++++++++++-- ckb-bin/src/subcommand/stats.rs | 8 +++++++- util/app-config/src/app_config.rs | 25 +++++++++++++++++++++++++ util/app-config/src/cli.rs | 24 +++++++++++++++--------- util/app-config/src/legacy/mod.rs | 6 ++++++ util/app-config/src/lib.rs | 5 +++-- util/launcher/src/lib.rs | 2 ++ util/launcher/src/shared_builder.rs | 17 +++++++++++++---- 11 files changed, 101 insertions(+), 22 deletions(-) diff --git a/ckb-bin/src/lib.rs b/ckb-bin/src/lib.rs index 52b3c07b718..0f09e1cc743 100644 --- a/ckb-bin/src/lib.rs +++ b/ckb-bin/src/lib.rs @@ -27,7 +27,7 @@ pub fn run_app(version: Version) -> Result<(), ExitCode> { // Always print backtrace on panic. ::std::env::set_var("RUST_BACKTRACE", "full"); - let app_matches = cli::get_matches(&version); + let (bin_name, app_matches) = cli::get_bin_name_and_matches(&version); match app_matches.subcommand() { (cli::CMD_INIT, Some(matches)) => { return subcommand::init(Setup::init(&matches)?); @@ -48,7 +48,7 @@ pub fn run_app(version: Version) -> Result<(), ExitCode> { } let (handle, _stop) = new_global_runtime(); - let setup = Setup::from_matches(&app_matches)?; + let setup = Setup::from_matches(bin_name, &app_matches)?; let _guard = SetupGuard::from_setup(&setup, &version, handle.clone())?; raise_fd_limit(); diff --git a/ckb-bin/src/subcommand/export.rs b/ckb-bin/src/subcommand/export.rs index cfd76d8ecd4..660a518f3b0 100644 --- a/ckb-bin/src/subcommand/export.rs +++ b/ckb-bin/src/subcommand/export.rs @@ -4,7 +4,13 @@ use ckb_instrument::Export; use ckb_launcher::SharedBuilder; pub fn export(args: ExportArgs, async_handle: Handle) -> Result<(), ExitCode> { - let builder = SharedBuilder::new(&args.config.db, None, async_handle)?; + let builder = SharedBuilder::new( + &args.config.bin_name, + args.config.root_dir.as_path(), + &args.config.db, + None, + async_handle, + )?; let (shared, _) = builder.consensus(args.consensus).build()?; Export::new(shared, args.target).execute().map_err(|err| { eprintln!("Export error: {:?}", err); diff --git a/ckb-bin/src/subcommand/import.rs b/ckb-bin/src/subcommand/import.rs index 10f53d6fc20..ef5ae6213e7 100644 --- a/ckb-bin/src/subcommand/import.rs +++ b/ckb-bin/src/subcommand/import.rs @@ -5,7 +5,13 @@ use ckb_instrument::Import; use ckb_launcher::SharedBuilder; pub fn import(args: ImportArgs, async_handle: Handle) -> Result<(), ExitCode> { - let builder = SharedBuilder::new(&args.config.db, None, async_handle)?; + let builder = SharedBuilder::new( + &args.config.bin_name, + args.config.root_dir.as_path(), + &args.config.db, + None, + async_handle, + )?; let (shared, mut pack) = builder.consensus(args.consensus).build()?; let chain_service = ChainService::new(shared, pack.take_proposal_table()); diff --git a/ckb-bin/src/subcommand/replay.rs b/ckb-bin/src/subcommand/replay.rs index 2fc74d5aebd..42bc0080deb 100644 --- a/ckb-bin/src/subcommand/replay.rs +++ b/ckb-bin/src/subcommand/replay.rs @@ -10,7 +10,13 @@ use ckb_verification_traits::Switch; use std::sync::Arc; pub fn replay(args: ReplayArgs, async_handle: Handle) -> Result<(), ExitCode> { - let shared_builder = SharedBuilder::new(&args.config.db, None, async_handle.clone())?; + let shared_builder = SharedBuilder::new( + &args.config.bin_name, + args.config.root_dir.as_path(), + &args.config.db, + None, + async_handle.clone(), + )?; let (shared, _) = shared_builder .consensus(args.consensus.clone()) .tx_pool_config(args.config.tx_pool) @@ -31,7 +37,13 @@ pub fn replay(args: ReplayArgs, async_handle: Handle) -> Result<(), ExitCode> { let mut tmp_db_config = args.config.db.clone(); tmp_db_config.path = tmp_db_dir.path().to_path_buf(); - let shared_builder = SharedBuilder::new(&tmp_db_config, None, async_handle)?; + let shared_builder = SharedBuilder::new( + &args.config.bin_name, + args.config.root_dir.as_path(), + &tmp_db_config, + None, + async_handle, + )?; let (tmp_shared, mut pack) = shared_builder .consensus(args.consensus) .tx_pool_config(args.config.tx_pool) diff --git a/ckb-bin/src/subcommand/stats.rs b/ckb-bin/src/subcommand/stats.rs index 75931ce0928..7a912229ef8 100644 --- a/ckb-bin/src/subcommand/stats.rs +++ b/ckb-bin/src/subcommand/stats.rs @@ -19,7 +19,13 @@ struct Statics { impl Statics { pub fn build(args: StatsArgs, async_handle: Handle) -> Result { - let shared_builder = SharedBuilder::new(&args.config.db, None, async_handle)?; + let shared_builder = SharedBuilder::new( + &args.config.bin_name, + args.config.root_dir.as_path(), + &args.config.db, + None, + async_handle, + )?; let (shared, _) = shared_builder.consensus(args.consensus).build()?; let tip_number = shared.snapshot().tip_number(); diff --git a/util/app-config/src/app_config.rs b/util/app-config/src/app_config.rs index a2b4605f63f..741e6edf2a7 100644 --- a/util/app-config/src/app_config.rs +++ b/util/app-config/src/app_config.rs @@ -37,6 +37,12 @@ pub enum AppConfig { #[derive(Clone, Debug, Serialize)] #[serde(deny_unknown_fields)] pub struct CKBAppConfig { + /// The binary name. + #[serde(skip)] + pub bin_name: String, + /// The root directory. + #[serde(skip)] + pub root_dir: PathBuf, /// The data directory. pub data_dir: PathBuf, /// freezer files path @@ -91,6 +97,12 @@ pub struct CKBAppConfig { #[derive(Clone, Debug, Serialize)] #[serde(deny_unknown_fields)] pub struct MinerAppConfig { + /// The binary name. + #[serde(skip)] + pub bin_name: String, + /// The root directory. + #[serde(skip)] + pub root_dir: PathBuf, /// The data directory. pub data_dir: PathBuf, /// Chain config options. @@ -144,6 +156,7 @@ impl AppConfig { _ => { let resource = ensure_ckb_dir(Resource::ckb_config(root_dir.as_ref()))?; let config = CKBAppConfig::load_from_slice(&resource.get()?)?; + Ok(AppConfig::with_ckb( config.derive_options(root_dir.as_ref(), subcommand_name)?, )) @@ -221,6 +234,14 @@ impl AppConfig { } } } + + /// Set the binary name with full path. + pub fn set_bin_name(&mut self, bin_name: String) { + match self { + AppConfig::CKB(config) => config.bin_name = bin_name, + AppConfig::Miner(config) => config.bin_name = bin_name, + } + } } impl AppConfig { @@ -246,6 +267,8 @@ impl CKBAppConfig { } fn derive_options(mut self, root_dir: &Path, subcommand_name: &str) -> Result { + self.root_dir = root_dir.to_path_buf(); + self.data_dir = canonicalize_data_dir(self.data_dir, root_dir); self.db.adjust(root_dir, &self.data_dir, "db"); @@ -297,6 +320,8 @@ impl MinerAppConfig { } fn derive_options(mut self, root_dir: &Path) -> Result { + self.root_dir = root_dir.to_path_buf(); + self.data_dir = mkdir(canonicalize_data_dir(self.data_dir, root_dir))?; self.logger.log_dir = self.data_dir.join("logs"); self.logger.file = self.logger.log_dir.join("miner.log"); diff --git a/util/app-config/src/cli.rs b/util/app-config/src/cli.rs index a07bfc8f63d..3ee7a966973 100644 --- a/util/app-config/src/cli.rs +++ b/util/app-config/src/cli.rs @@ -3,6 +3,8 @@ use ckb_build_info::Version; use ckb_resource::{DEFAULT_P2P_PORT, DEFAULT_RPC_PORT, DEFAULT_SPEC}; use clap::{App, AppSettings, Arg, ArgGroup, ArgMatches, SubCommand}; +pub(crate) const BIN_NAME: &str = "ckb"; + /// Subcommand `run`. pub const CMD_RUN: &str = "run"; /// Subcommand `miner`. @@ -113,7 +115,7 @@ pub const ARG_MIGRATE_CHECK: &str = "check"; const GROUP_BA: &str = "ba"; fn basic_app<'b>() -> App<'static, 'b> { - App::new("ckb") + App::new(BIN_NAME) .author("Nervos Core Dev ") .about("Nervos CKB - The Common Knowledge Base") .setting(AppSettings::SubcommandRequiredElseHelp) @@ -144,11 +146,15 @@ fn basic_app<'b>() -> App<'static, 'b> { /// Parse the command line arguments by supplying the version information. /// /// The version is used to generate the help message and output for `--version`. -pub fn get_matches(version: &Version) -> ArgMatches<'static> { - basic_app() +pub fn get_bin_name_and_matches(version: &Version) -> (String, ArgMatches<'static>) { + let bin_name = std::env::args() + .next() + .unwrap_or_else(|| BIN_NAME.to_owned()); + let matches = basic_app() .version(version.short().as_str()) .long_version(version.long().as_str()) - .get_matches() + .get_matches(); + (bin_name, matches) } fn run() -> App<'static, 'static> { @@ -544,7 +550,7 @@ mod tests { #[test] fn ba_message_requires_ba_arg_or_ba_code_hash() { let ok_ba_arg = basic_app().get_matches_from_safe(&[ - "ckb", + BIN_NAME, "init", "--ba-message", "0x00", @@ -552,14 +558,14 @@ mod tests { "0x00", ]); let ok_ba_code_hash = basic_app().get_matches_from_safe(&[ - "ckb", + BIN_NAME, "init", "--ba-message", "0x00", "--ba-code-hash", "0x00", ]); - let err = basic_app().get_matches_from_safe(&["ckb", "init", "--ba-message", "0x00"]); + let err = basic_app().get_matches_from_safe(&[BIN_NAME, "init", "--ba-message", "0x00"]); assert!( ok_ba_arg.is_ok(), @@ -588,7 +594,7 @@ mod tests { #[test] fn ba_arg_and_ba_code_hash() { let ok_matches = basic_app().get_matches_from_safe(&[ - "ckb", + BIN_NAME, "init", "--ba-code-hash", "0x00", @@ -605,7 +611,7 @@ mod tests { #[test] fn ba_advanced() { let matches = basic_app() - .get_matches_from_safe(&["ckb", "run", "--ba-advanced"]) + .get_matches_from_safe(&[BIN_NAME, "run", "--ba-advanced"]) .unwrap(); let sub_matches = matches.subcommand().1.unwrap(); diff --git a/util/app-config/src/legacy/mod.rs b/util/app-config/src/legacy/mod.rs index c00ffde7e11..446b22c95e1 100644 --- a/util/app-config/src/legacy/mod.rs +++ b/util/app-config/src/legacy/mod.rs @@ -3,6 +3,8 @@ use serde::Deserialize; use std::path::PathBuf; +use crate::cli; + mod store; mod tx_pool; @@ -105,6 +107,8 @@ impl From for crate::CKBAppConfig { #[cfg(not(feature = "with_sentry"))] let _ = sentry; Self { + bin_name: cli::BIN_NAME.to_owned(), + root_dir: Default::default(), data_dir, ancient, tmp_dir, @@ -140,6 +144,8 @@ impl From for crate::MinerAppConfig { #[cfg(not(feature = "with_sentry"))] let _ = sentry; Self { + bin_name: cli::BIN_NAME.to_owned(), + root_dir: Default::default(), data_dir, chain, logger, diff --git a/util/app-config/src/lib.rs b/util/app-config/src/lib.rs index de935aa04f0..ee385a0b32e 100644 --- a/util/app-config/src/lib.rs +++ b/util/app-config/src/lib.rs @@ -44,7 +44,7 @@ pub struct Setup { impl Setup { /// Boots the ckb process by parsing the command line arguments and loading the config file. - pub fn from_matches(matches: &ArgMatches<'_>) -> Result { + pub fn from_matches(bin_name: String, matches: &ArgMatches<'_>) -> Result { let subcommand_name = match matches.subcommand_name() { Some(subcommand_name) => subcommand_name, None => { @@ -54,7 +54,8 @@ impl Setup { }; let root_dir = Self::root_dir_from_matches(matches)?; - let config = AppConfig::load_for_subcommand(&root_dir, subcommand_name)?; + let mut config = AppConfig::load_for_subcommand(&root_dir, subcommand_name)?; + config.set_bin_name(bin_name); #[cfg(feature = "with_sentry")] let is_sentry_enabled = is_daemon(&subcommand_name) && config.sentry().is_enabled(); diff --git a/util/launcher/src/lib.rs b/util/launcher/src/lib.rs index aaabfa82706..407565a18f0 100644 --- a/util/launcher/src/lib.rs +++ b/util/launcher/src/lib.rs @@ -188,6 +188,8 @@ impl Launcher { block_assembler_config: Option, ) -> Result<(Shared, SharedPackage), ExitCode> { let shared_builder = SharedBuilder::new( + &self.args.config.bin_name, + self.args.config.root_dir.as_path(), &self.args.config.db, Some(self.args.config.ancient.clone()), self.async_handle.clone(), diff --git a/util/launcher/src/shared_builder.rs b/util/launcher/src/shared_builder.rs index 1c8e6429575..5daf08bf41f 100644 --- a/util/launcher/src/shared_builder.rs +++ b/util/launcher/src/shared_builder.rs @@ -28,7 +28,7 @@ use ckb_types::packed::Byte32; use ckb_verification::cache::init_cache; use p2p::SessionId as PeerIndex; use std::collections::HashSet; -use std::path::PathBuf; +use std::path::{Path, PathBuf}; use std::sync::atomic::AtomicBool; use std::sync::Arc; @@ -44,7 +44,11 @@ pub struct SharedBuilder { async_handle: Handle, } -pub fn open_or_create_db(config: &DBConfig) -> Result { +pub fn open_or_create_db( + bin_name: &str, + root_dir: &Path, + config: &DBConfig, +) -> Result { let migrate = Migrate::new(&config.path); let mut db_exist = false; @@ -65,7 +69,10 @@ pub fn open_or_create_db(config: &DBConfig) -> Result { You can use the old version CKB if you don't want to do the migration.\n\ We strongly recommended you to use the latest stable version of CKB, \ since the old versions may have unfixed vulnerabilities.\n\ - Run `ckb migrate --help` for more information about migration." + Run `\"{}\" migrate -C \"{}\"` to migrate the data.\n\ + We strongly recommend that you backup the data directory before migration.", + bin_name, + root_dir.display() ); return Err(ExitCode::Failure); } @@ -86,11 +93,13 @@ pub fn open_or_create_db(config: &DBConfig) -> Result { impl SharedBuilder { /// Generates the base SharedBuilder with ancient path and async_handle pub fn new( + bin_name: &str, + root_dir: &Path, db_config: &DBConfig, ancient: Option, async_handle: Handle, ) -> Result { - let db = open_or_create_db(db_config)?; + let db = open_or_create_db(bin_name, root_dir, db_config)?; Ok(SharedBuilder { db,