From 43973d7e86444c1a5b32a4c79d8e8d41babacf23 Mon Sep 17 00:00:00 2001 From: Jiahao XU Date: Fri, 18 Aug 2023 11:59:48 +1000 Subject: [PATCH] Refactor `cargo-binstall` (#1302) - Move implementation of `main` into the library part of `cargo-binstall` to speedup codegen. - Move `manifests.rs` into `binstalk-manifests` Signed-off-by: Jiahao XU --- Cargo.lock | 1 - crates/bin/Cargo.toml | 1 - crates/bin/src/entry.rs | 6 +- crates/bin/src/lib.rs | 12 ++-- crates/bin/src/main.rs | 65 ++--------------- crates/bin/src/main_impl.rs | 64 +++++++++++++++++ .../src/crates_manifests.rs} | 72 ++++++++++--------- crates/binstalk-manifests/src/lib.rs | 2 + 8 files changed, 120 insertions(+), 103 deletions(-) create mode 100644 crates/bin/src/main_impl.rs rename crates/{bin/src/manifests.rs => binstalk-manifests/src/crates_manifests.rs} (51%) diff --git a/Cargo.lock b/Cargo.lock index 47aea5ea..8d43afb0 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -530,7 +530,6 @@ dependencies = [ "dirs", "embed-resource", "file-format", - "fs-lock", "gh-token", "home", "log", diff --git a/crates/bin/Cargo.toml b/crates/bin/Cargo.toml index 03e6e4fe..2c2d09ad 100644 --- a/crates/bin/Cargo.toml +++ b/crates/bin/Cargo.toml @@ -28,7 +28,6 @@ clap = { version = "4.3.0", features = ["derive", "env"] } compact_str = "0.7.0" dirs = "5.0.1" file-format = { version = "0.18.0", default-features = false } -fs-lock = { version = "0.1.0", path = "../fs-lock" } gh-token = "0.1.2" home = "0.5.5" log = { version = "0.4.18", features = ["std"] } diff --git a/crates/bin/src/entry.rs b/crates/bin/src/entry.rs index 6aec09f5..8c265285 100644 --- a/crates/bin/src/entry.rs +++ b/crates/bin/src/entry.rs @@ -21,8 +21,9 @@ use binstalk::{ CargoTomlFetchOverride, Options, Resolver, }, }; -use binstalk_manifests::cargo_config::Config; -use binstalk_manifests::cargo_toml_binstall::PkgOverride; +use binstalk_manifests::{ + cargo_config::Config, cargo_toml_binstall::PkgOverride, crates_manifests::Manifests, +}; use file_format::FileFormat; use home::cargo_home; use log::LevelFilter; @@ -33,7 +34,6 @@ use tracing::{debug, error, info, warn}; use crate::{ args::{Args, Strategy}, install_path, - manifests::Manifests, ui::confirm, }; diff --git a/crates/bin/src/lib.rs b/crates/bin/src/lib.rs index 2f9e9057..4475363a 100644 --- a/crates/bin/src/lib.rs +++ b/crates/bin/src/lib.rs @@ -1,11 +1,13 @@ #![cfg_attr(docsrs, feature(doc_auto_cfg))] -pub mod args; -pub mod bin_util; -pub mod entry; +mod args; +mod bin_util; +mod entry; mod git_credentials; mod install_path; -pub mod logging; -mod manifests; +mod logging; +mod main_impl; mod signal; mod ui; + +pub use main_impl::do_main; diff --git a/crates/bin/src/main.rs b/crates/bin/src/main.rs index 2fa221df..7733f5df 100644 --- a/crates/bin/src/main.rs +++ b/crates/bin/src/main.rs @@ -1,68 +1,11 @@ -use std::time::Instant; +use std::process::Termination; -use binstalk::{helpers::jobserver_client::LazyJobserverClient, TARGET}; -use log::LevelFilter; -use tracing::debug; - -use cargo_binstall::{ - args, - bin_util::{run_tokio_main, MainExit}, - entry, - logging::logging, -}; +use cargo_binstall::do_main; #[cfg(feature = "mimalloc")] #[global_allocator] static GLOBAL: mimalloc::MiMalloc = mimalloc::MiMalloc; -fn main() -> MainExit { - // This must be the very first thing to happen - let jobserver_client = LazyJobserverClient::new(); - - let args = args::parse(); - - if args.version { - let cargo_binstall_version = env!("CARGO_PKG_VERSION"); - if args.verbose { - let build_date = env!("VERGEN_BUILD_DATE"); - - let features = env!("VERGEN_CARGO_FEATURES"); - - let git_sha = option_env!("VERGEN_GIT_SHA").unwrap_or("UNKNOWN"); - let git_commit_date = option_env!("VERGEN_GIT_COMMIT_DATE").unwrap_or("UNKNOWN"); - - let rustc_semver = env!("VERGEN_RUSTC_SEMVER"); - let rustc_commit_hash = env!("VERGEN_RUSTC_COMMIT_HASH"); - let rustc_llvm_version = env!("VERGEN_RUSTC_LLVM_VERSION"); - - println!( - r#"cargo-binstall: {cargo_binstall_version} -build-date: {build_date} -build-target: {TARGET} -build-features: {features} -build-commit-hash: {git_sha} -build-commit-date: {git_commit_date} -rustc-version: {rustc_semver} -rustc-commit-hash: {rustc_commit_hash} -rustc-llvm-version: {rustc_llvm_version}"# - ); - } else { - println!("{cargo_binstall_version}"); - } - MainExit::Success(None) - } else { - logging( - args.log_level.unwrap_or(LevelFilter::Info), - args.json_output, - ); - - let start = Instant::now(); - - let result = run_tokio_main(|| entry::install_crates(args, jobserver_client)); - - let done = start.elapsed(); - debug!("run time: {done:?}"); - - MainExit::new(result, done) - } +fn main() -> impl Termination { + do_main() } diff --git a/crates/bin/src/main_impl.rs b/crates/bin/src/main_impl.rs new file mode 100644 index 00000000..14a3dbd8 --- /dev/null +++ b/crates/bin/src/main_impl.rs @@ -0,0 +1,64 @@ +use std::{process::Termination, time::Instant}; + +use binstalk::{helpers::jobserver_client::LazyJobserverClient, TARGET}; +use log::LevelFilter; +use tracing::debug; + +use crate::{ + args, + bin_util::{run_tokio_main, MainExit}, + entry, + logging::logging, +}; + +pub fn do_main() -> impl Termination { + // This must be the very first thing to happen + let jobserver_client = LazyJobserverClient::new(); + + let args = args::parse(); + + if args.version { + let cargo_binstall_version = env!("CARGO_PKG_VERSION"); + if args.verbose { + let build_date = env!("VERGEN_BUILD_DATE"); + + let features = env!("VERGEN_CARGO_FEATURES"); + + let git_sha = option_env!("VERGEN_GIT_SHA").unwrap_or("UNKNOWN"); + let git_commit_date = option_env!("VERGEN_GIT_COMMIT_DATE").unwrap_or("UNKNOWN"); + + let rustc_semver = env!("VERGEN_RUSTC_SEMVER"); + let rustc_commit_hash = env!("VERGEN_RUSTC_COMMIT_HASH"); + let rustc_llvm_version = env!("VERGEN_RUSTC_LLVM_VERSION"); + + println!( + r#"cargo-binstall: {cargo_binstall_version} +build-date: {build_date} +build-target: {TARGET} +build-features: {features} +build-commit-hash: {git_sha} +build-commit-date: {git_commit_date} +rustc-version: {rustc_semver} +rustc-commit-hash: {rustc_commit_hash} +rustc-llvm-version: {rustc_llvm_version}"# + ); + } else { + println!("{cargo_binstall_version}"); + } + MainExit::Success(None) + } else { + logging( + args.log_level.unwrap_or(LevelFilter::Info), + args.json_output, + ); + + let start = Instant::now(); + + let result = run_tokio_main(|| entry::install_crates(args, jobserver_client)); + + let done = start.elapsed(); + debug!("run time: {done:?}"); + + MainExit::new(result, done) + } +} diff --git a/crates/bin/src/manifests.rs b/crates/binstalk-manifests/src/crates_manifests.rs similarity index 51% rename from crates/bin/src/manifests.rs rename to crates/binstalk-manifests/src/crates_manifests.rs index 609fa250..dc5636a1 100644 --- a/crates/bin/src/manifests.rs +++ b/crates/binstalk-manifests/src/crates_manifests.rs @@ -1,13 +1,35 @@ -use std::{collections::BTreeMap, fs, io::Seek, path::Path}; - -use binstalk::errors::BinstallError; -use binstalk_manifests::{ - binstall_crates_v1::Records as BinstallCratesV1Records, cargo_crates_v1::CratesToml, - crate_info::CrateInfo, CompactString, Version, +use std::{ + collections::BTreeMap, + fs, + io::{self, Seek}, + path::Path, }; + use fs_lock::FileLock; -use miette::{Error, Result}; -use tracing::debug; +use miette::Diagnostic; +use thiserror::Error as ThisError; + +use crate::{ + binstall_crates_v1::{Error as BinstallCratesV1Error, Records as BinstallCratesV1Records}, + cargo_crates_v1::{CratesToml, CratesTomlParseError}, + crate_info::CrateInfo, + CompactString, Version, +}; + +#[derive(Debug, Diagnostic, ThisError)] +#[non_exhaustive] +pub enum ManifestsError { + #[error("failed to parse binstall crates-v1 manifest: {0}")] + #[diagnostic(transparent)] + BinstallCratesV1(#[from] BinstallCratesV1Error), + + #[error("failed to parse cargo v1 manifest: {0}")] + #[diagnostic(transparent)] + CargoManifestV1(#[from] CratesTomlParseError), + + #[error("I/O error: {0}")] + Io(#[from] io::Error), +} pub struct Manifests { binstall: BinstallCratesV1Records, @@ -15,33 +37,22 @@ pub struct Manifests { } impl Manifests { - pub fn open_exclusive(cargo_roots: &Path) -> Result { + pub fn open_exclusive(cargo_roots: &Path) -> Result { // Read cargo_binstall_metadata let metadata_path = cargo_roots.join("binstall/crates-v1.json"); - fs::create_dir_all(metadata_path.parent().unwrap()).map_err(BinstallError::Io)?; - - debug!( - "Reading binstall metadata from {} and obtaining exclusive lock", - metadata_path.display() - ); + fs::create_dir_all(metadata_path.parent().unwrap())?; let binstall = BinstallCratesV1Records::load_from_path(&metadata_path)?; // Read cargo_install_v1_metadata let manifest_path = cargo_roots.join(".crates.toml"); - debug!( - "Obtaining exclusive lock of cargo install v1 metadata in path {}", - manifest_path.display() - ); - let cargo_crates_v1 = fs::File::options() .read(true) .write(true) .create(true) .open(manifest_path) - .and_then(FileLock::new_exclusive) - .map_err(BinstallError::Io)?; + .and_then(FileLock::new_exclusive)?; Ok(Self { binstall, @@ -49,32 +60,29 @@ impl Manifests { }) } - fn rewind_cargo_crates_v1(&mut self) -> Result<()> { - self.cargo_crates_v1 - .rewind() - .map_err(BinstallError::Io) - .map_err(Error::from) + fn rewind_cargo_crates_v1(&mut self) -> Result<(), ManifestsError> { + self.cargo_crates_v1.rewind().map_err(ManifestsError::from) } /// `cargo-uninstall` can be called to uninstall crates, /// but it only updates .crates.toml. /// /// So here we will honour .crates.toml only. - pub fn load_installed_crates(&mut self) -> Result> { + pub fn load_installed_crates( + &mut self, + ) -> Result, ManifestsError> { self.rewind_cargo_crates_v1()?; CratesToml::load_from_reader(&mut self.cargo_crates_v1) .and_then(CratesToml::collect_into_crates_versions) - .map_err(Error::from) + .map_err(ManifestsError::from) } - pub fn update(mut self, metadata_vec: Vec) -> Result<()> { + pub fn update(mut self, metadata_vec: Vec) -> Result<(), ManifestsError> { self.rewind_cargo_crates_v1()?; - debug!("Writing .crates.toml"); CratesToml::append_to_file(&mut self.cargo_crates_v1, &metadata_vec)?; - debug!("Writing binstall/crates-v1.json"); for metadata in metadata_vec { self.binstall.replace(metadata); } diff --git a/crates/binstalk-manifests/src/lib.rs b/crates/binstalk-manifests/src/lib.rs index f3befa80..c61b5181 100644 --- a/crates/binstalk-manifests/src/lib.rs +++ b/crates/binstalk-manifests/src/lib.rs @@ -13,6 +13,8 @@ mod helpers; pub mod binstall_crates_v1; pub mod cargo_config; pub mod cargo_crates_v1; +/// Contains both [`binstall_crates_v1`] and [`cargo_crates_v1`]. +pub mod crates_manifests; pub use binstalk_types::{cargo_toml_binstall, crate_info}; pub use compact_str::CompactString;