diff --git a/implementations/rust/ockam/ockam_app_lib/src/api/functions.rs b/implementations/rust/ockam/ockam_app_lib/src/api/functions.rs index e7a3264854b..77fd037362f 100644 --- a/implementations/rust/ockam/ockam_app_lib/src/api/functions.rs +++ b/implementations/rust/ockam/ockam_app_lib/src/api/functions.rs @@ -75,7 +75,6 @@ extern "C" fn initialize_application( #[cfg(target_os = "macos")] crate::cli::add_homebrew_to_path(); - crate::cli::set_no_automatic_reset(); if let Err(err) = check_ockam_executable() { error!(?err, "Couldn't find the ockam executable"); diff --git a/implementations/rust/ockam/ockam_app_lib/src/cli/mod.rs b/implementations/rust/ockam/ockam_app_lib/src/cli/mod.rs index 51e0a8812c5..c5e4306add4 100644 --- a/implementations/rust/ockam/ockam_app_lib/src/cli/mod.rs +++ b/implementations/rust/ockam/ockam_app_lib/src/cli/mod.rs @@ -43,13 +43,6 @@ pub(crate) fn add_homebrew_to_path() { } } -/// Set the OCKAM_NO_AUTOMATIC_RESET environment variable to avoid -/// automatically resetting the node when the application find an incoherent state -/// this may happen if a command is launched during a write operation -pub(crate) fn set_no_automatic_reset() { - std::env::set_var("OCKAM_NO_AUTOMATIC_RESET", "true"); -} - /// Check that the OCKAM environment variable defines an absolute path /// Otherwise we might fail to run the ockam command when starting the desktop application from an unexpected path /// Check that the ockam command can at least be called with the `--version` option and log diff --git a/implementations/rust/ockam/ockam_command/Cargo.toml b/implementations/rust/ockam/ockam_command/Cargo.toml index 9e2c4710e91..e03063cdd10 100644 --- a/implementations/rust/ockam/ockam_command/Cargo.toml +++ b/implementations/rust/ockam/ockam_command/Cargo.toml @@ -88,7 +88,7 @@ r3bl_rs_utils_core = "0.9.7" r3bl_tuify = "0.1.21" rand = "0.8" regex = "1.10.2" -reqwest = { version = "0.11", default-features = false, features = ["json", "rustls-tls-native-roots"] } +reqwest = { version = "0.11", default-features = false, features = ["json", "rustls-tls-native-roots", "blocking"] } rustls = "0.22.1" rustls-native-certs = "0.7.0" rustls-pki-types = "1.0.1" diff --git a/implementations/rust/ockam/ockam_command/src/lib.rs b/implementations/rust/ockam/ockam_command/src/lib.rs index 62664ecb1b9..0a652267983 100644 --- a/implementations/rust/ockam/ockam_command/src/lib.rs +++ b/implementations/rust/ockam/ockam_command/src/lib.rs @@ -17,6 +17,7 @@ //! cd implementations/rust/ockam/ockam_command && cargo install --path . //! ``` +use std::process::exit; use std::{path::PathBuf, sync::Mutex}; use clap::{ArgAction, Args, Parser, Subcommand}; @@ -70,7 +71,7 @@ use crate::kafka::direct::KafkaDirectCommand; use crate::kafka::outlet::KafkaOutletCommand; use crate::logs::setup_logging; use crate::node::NodeSubcommand; -use crate::output::{Output, OutputFormat}; +use crate::output::OutputFormat; use crate::run::RunCommand; use crate::sidecar::SidecarCommand; use crate::subscription::SubscriptionCommand; @@ -242,30 +243,22 @@ pub struct CommandGlobalOpts { impl CommandGlobalOpts { pub fn new(global_args: GlobalArgs) -> Self { + let terminal = Terminal::from(&global_args); let state = match CliState::with_default_dir() { Ok(state) => state, - Err(err) => { - eprintln!("Failed to initialize state: {}", err); - if std::env::var("OCKAM_NO_AUTOMATIC_RESET").is_ok() { - std::process::exit(exitcode::CONFIG); - } - let state = CliState::backup_and_reset().expect( - "Failed to initialize CliState. Try to manually remove the '~/.ockam' directory", - ); - let dir = state.dir(); - let backup_dir = CliState::backup_default_dir().unwrap(); - eprintln!( - "The {dir:?} directory has been reset and has been backed up to {backup_dir:?}" - ); - state + Err(_) => { + terminal + .write_line(fmt_err!("Failed to initialize local state")) + .unwrap(); + terminal + .write_line(fmt_log!( + "Consider upgrading to the latest version of Ockam Command, \ + or try removing the local state directory at ~/.ockam" + )) + .unwrap(); + exit(exitcode::SOFTWARE); } }; - let terminal = Terminal::new( - global_args.quiet, - global_args.no_color, - global_args.no_input, - global_args.output_format.clone(), - ); Self { global_args, state, @@ -279,15 +272,6 @@ impl CommandGlobalOpts { clone.terminal = clone.terminal.set_quiet(); clone } - - /// Print a value on the console. - /// TODO: replace this implementation with a call to the terminal instead - pub fn println(&self, t: &T) -> Result<()> - where - T: Output + serde::Serialize, - { - self.global_args.output_format.println_value(t) - } } #[cfg(test)] @@ -374,10 +358,7 @@ pub fn run() { match OckamCommand::try_parse_from(input) { Ok(command) => { - if !command.global_args.test_argument_parser { - check_if_an_upgrade_is_available(); - } - + check_if_an_upgrade_is_available(&command.global_args); command.run(); } Err(help) => pager::render_help(help), diff --git a/implementations/rust/ockam/ockam_command/src/project/create.rs b/implementations/rust/ockam/ockam_command/src/project/create.rs index dd5db60cd17..8b6f7e24155 100644 --- a/implementations/rust/ockam/ockam_command/src/project/create.rs +++ b/implementations/rust/ockam/ockam_command/src/project/create.rs @@ -6,6 +6,7 @@ use ockam_api::cloud::project::Projects; use ockam_api::nodes::InMemoryNode; use crate::operation::util::check_for_project_completion; +use crate::output::Output; use crate::project::util::check_project_readiness; use crate::util::api::CloudOpts; use crate::util::node_rpc; @@ -56,6 +57,10 @@ async fn run_impl( .await?; let project = check_for_project_completion(&opts, ctx, &node, project).await?; let project = check_project_readiness(&opts, ctx, &node, project).await?; - opts.println(&project)?; + opts.terminal + .stdout() + .plain(project.output()?) + .json(serde_json::json!(&project)) + .write_line()?; Ok(()) } diff --git a/implementations/rust/ockam/ockam_command/src/terminal/mod.rs b/implementations/rust/ockam/ockam_command/src/terminal/mod.rs index f825435bacd..b6a6cf62522 100644 --- a/implementations/rust/ockam/ockam_command/src/terminal/mod.rs +++ b/implementations/rust/ockam/ockam_command/src/terminal/mod.rs @@ -4,6 +4,7 @@ use std::io::Write; use std::time::Duration; use colorful::Colorful; +use console::Term; use indicatif::{ProgressBar, ProgressDrawTarget, ProgressStyle}; use miette::Context as _; use miette::{miette, IntoDiagnostic}; @@ -19,7 +20,7 @@ use r3bl_rs_utils_core::*; use r3bl_tuify::*; use crate::error::Error; -use crate::{fmt_list, fmt_log, fmt_warn, OutputFormat, Result}; +use crate::{fmt_list, fmt_log, fmt_warn, GlobalArgs, OutputFormat, Result}; pub mod colors; pub mod fmt; @@ -45,9 +46,14 @@ impl Terminal { } } -impl Default for Terminal { - fn default() -> Self { - Terminal::new(false, false, false, OutputFormat::Plain) +impl From<&GlobalArgs> for Terminal> { + fn from(global_args: &GlobalArgs) -> Self { + Terminal::new( + global_args.quiet, + global_args.no_color, + global_args.no_input, + global_args.output_format.clone(), + ) } } diff --git a/implementations/rust/ockam/ockam_command/src/upgrade.rs b/implementations/rust/ockam/ockam_command/src/upgrade.rs index 878922a5314..21f4186124a 100644 --- a/implementations/rust/ockam/ockam_command/src/upgrade.rs +++ b/implementations/rust/ockam/ockam_command/src/upgrade.rs @@ -1,46 +1,45 @@ +use crate::{fmt_info, GlobalArgs, Terminal}; use clap::crate_version; use colorful::Colorful; use ockam_core::env::get_env_with_default; use serde::Deserialize; use std::env; -use tokio::runtime::Builder; #[derive(Deserialize)] -struct UpgradeFile { - upgrade_message: Option, - upgrade_message_macos: Option, +pub struct UpgradeFile { + #[serde(default = "default_upgrade_message")] + pub upgrade_message: String, + #[serde(default = "default_upgrade_message_macos")] + pub upgrade_message_macos: String, } -pub fn check_if_an_upgrade_is_available() { - if !upgrade_check_is_disabled() { - // check if a new version has been released - Builder::new_current_thread() - .enable_all() - .build() - .unwrap() - .block_on(check()); - } +fn default_upgrade_message() -> String { + "Check out the latest release at https://github.com/build-trust/ockam/releases".to_string() +} + +fn default_upgrade_message_macos() -> String { + "Run the following command to upgrade the Ockam Command: 'brew install build-trust/ockam/ockam'" + .to_string() } -async fn check() { +pub fn check_if_an_upgrade_is_available(global_args: &GlobalArgs) { + if upgrade_check_is_disabled() || global_args.test_argument_parser { + return; + } let url = format!( "https://github.com/build-trust/ockam/releases/download/ockam_v{}/upgrade.json", crate_version!() ); - let resp = reqwest::get(url).await; - - if let Ok(r) = resp { - if let Ok(upgrade) = r.json::().await { - if let Some(message) = upgrade.upgrade_message { - eprintln!("\n{}", message.yellow()); - - if cfg!(target_os = "macos") { - if let Some(message) = upgrade.upgrade_message_macos { - eprintln!("\n{}", message.yellow()); - } - } - - eprintln!(); + if let Ok(r) = reqwest::blocking::get(url) { + if let Ok(f) = r.json::() { + let terminal = Terminal::from(global_args); + terminal + .write_line(fmt_info!("{}", f.upgrade_message)) + .unwrap(); + if cfg!(target_os = "macos") { + terminal + .write_line(fmt_info!("{}", f.upgrade_message_macos)) + .unwrap(); } } }