Skip to content

Commit

Permalink
fix(updater): cross-platform compatibility, robustness enhancements (#…
Browse files Browse the repository at this point in the history
  • Loading branch information
mistydemeo authored Apr 30, 2024
1 parent 6a4428c commit d5963ce
Show file tree
Hide file tree
Showing 3 changed files with 57 additions and 43 deletions.
16 changes: 16 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion crates/cli/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,8 @@ serde_json = { version = "1.0.96" }
uuid = { version = "1.1", features = ["v4", "serde"] }
tokio = { version = "1", features = ["full"] }
chrono = { version = "0.4.26", features = ["serde"] }
reqwest = { version = "0.11", features = ["json"] }
reqwest = { version = "0.11", features = ["json", "stream"] }
futures-util = "0.3.30"
lazy_static = { version = "1.4.0" }
indicatif-log-bridge = { version = "0.2.1" }
colored = { version = "2.0.4" }
Expand Down
81 changes: 39 additions & 42 deletions crates/cli/src/updater.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ use anyhow::bail;
use anyhow::{Context, Result};
use chrono::{DateTime, NaiveDateTime, Utc};
use colored::Colorize;
use futures_util::StreamExt;
use log::info;
use marzano_auth::info::AuthInfo;
use marzano_gritmodule::config::REPO_CONFIG_DIR_NAME;
Expand Down Expand Up @@ -359,7 +360,10 @@ impl Updater {
let (downloaded, manifest) = tokio::try_join!(downloader, manifest_fetcher)?;

// Unzip the artifact
self.unpack_artifact(app, downloaded).await?;
self.unpack_artifact(app, downloaded.to_owned()).await?;

// Clean up the temp artifact
async_fs::remove_file(&downloaded).await?;

self.set_app_version(app, manifest.version.unwrap(), manifest.release.unwrap())?;
self.dump().await?;
Expand Down Expand Up @@ -444,17 +448,17 @@ impl Updater {
async fn download_artifact(&self, app: SupportedApp, artifact_url: String) -> Result<PathBuf> {
let target_path = self.bin_path.join(format!("{}-temp", app.get_bin_name()));

// Download via curl
let cmd = AsyncCommand::new("curl")
.arg("-L")
.arg("-o")
.arg(&target_path)
.arg(&artifact_url)
.output()
.await?;

if !cmd.status.success() {
bail!("Failed to download artifact: {:?}", cmd);
match reqwest::get(&artifact_url).await {
Ok(response) => {
let mut file = async_fs::File::create(&target_path).await?;
let mut bytes_stream = response.bytes_stream();
while let Some(chunk) = bytes_stream.next().await {
tokio::io::copy(&mut chunk?.as_ref(), &mut file).await?;
}
}
Err(e) => {
bail!("Failed to download artifact: {:?}", e);
}
}

Ok(target_path)
Expand Down Expand Up @@ -484,42 +488,35 @@ impl Updater {
}

let target_path = self.get_app_bin(&app)?;
let output = AsyncCommand::new("mv")
.arg(format!("{}/{}", unpacked_dir.display(), app.get_bin_name()))
.arg(&target_path)
.output()
.await?;

if !output.status.success() {
let fallback_output = AsyncCommand::new("mv")
.arg(format!(
"{}/{}",
unpacked_dir.display(),
app.get_fallback_bin_name()
))
.arg(&target_path)
.output()
.await?;
if !fallback_output.status.success() {
bail!("Failed to move files: {:?}", output);
if async_fs::rename(unpacked_dir.join(app.get_bin_name()), &target_path)
.await
.is_err()
{
if let Err(e) =
async_fs::rename(unpacked_dir.join(app.get_fallback_bin_name()), &target_path).await
{
bail!("Failed to move files: {:?}", e);
}
}

// Make the file executable
let output = AsyncCommand::new("chmod")
.arg("+x")
.arg(&target_path)
.output()
.await?;
#[cfg(unix)]
{
use std::os::unix::fs::PermissionsExt;

let target_file = std::fs::File::open(&target_path)?;
let mut perms = target_file.metadata()?.permissions();
perms.set_mode(0o744);
if let Err(e) = target_file.set_permissions(perms) {
bail!(
"Failed to make {} executable: {:?}",
target_path.display(),
e
);
}

if !output.status.success() {
bail!(
"Failed to make {} executable: {:?}",
target_path.display(),
output
);
info!("Successfully made {} executable", target_path.display());
}
info!("Successfully made {} executable", target_path.display());

async_fs::remove_dir_all(&unpacked_dir).await?;

Expand Down

0 comments on commit d5963ce

Please sign in to comment.