diff --git a/Cargo.lock b/Cargo.lock index 256c3f3d1e..bc7b8c44a1 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -162,6 +162,7 @@ dependencies = [ "serde_derive 1.0.98 (registry+https://github.com/rust-lang/crates.io-index)", "serde_json 1.0.40 (registry+https://github.com/rust-lang/crates.io-index)", "structopt 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)", + "subprocess 0.1.18 (registry+https://github.com/rust-lang/crates.io-index)", "tempdir 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", "termcolor 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)", "toml 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)", @@ -342,6 +343,11 @@ dependencies = [ "crossbeam-utils 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "crossbeam-utils" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + [[package]] name = "crossbeam-utils" version = "0.6.6" @@ -1421,6 +1427,16 @@ dependencies = [ "syn 0.15.43 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "subprocess" +version = "0.1.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "crossbeam-utils 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.60 (registry+https://github.com/rust-lang/crates.io-index)", + "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "syn" version = "0.15.43" @@ -1873,6 +1889,7 @@ dependencies = [ "checksum crossbeam-deque 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b18cd2e169ad86297e6bc0ad9aa679aee9daa4f19e8163860faf7c164e4f5a71" "checksum crossbeam-epoch 0.7.2 (registry+https://github.com/rust-lang/crates.io-index)" = "fedcd6772e37f3da2a9af9bf12ebe046c0dfe657992377b4df982a2b54cd37a9" "checksum crossbeam-queue 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7c979cd6cfe72335896575c6b5688da489e420d36a27a0b9eb0c73db574b4a4b" +"checksum crossbeam-utils 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "677d453a17e8bd2b913fa38e8b9cf04bcdbb5be790aa294f2389661d72036015" "checksum crossbeam-utils 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)" = "04973fa96e96579258a5091af6003abde64af786b860f18622b82e026cca60e6" "checksum ctor 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "3b4c17619643c1252b5f690084b82639dd7fac141c57c8e77a00e0148132092c" "checksum difference 2.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "524cbf6897b527295dff137cec09ecf3a05f4fddffd7dfcd1585403449e74198" @@ -1996,6 +2013,7 @@ dependencies = [ "checksum strsim 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "8ea5119cdb4c55b55d432abb513a0429384878c15dde60cc77b1c99de1a95a6a" "checksum structopt 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)" = "16c2cdbf9cc375f15d1b4141bc48aeef444806655cd0e904207edc8d68d86ed7" "checksum structopt-derive 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)" = "53010261a84b37689f9ed7d395165029f9cc7abb9f56bbfe86bee2597ed25107" +"checksum subprocess 0.1.18 (registry+https://github.com/rust-lang/crates.io-index)" = "28fc0f40f0c0da73339d347aa7d6d2b90341a95683a47722bc4eebed71ff3c00" "checksum syn 0.15.43 (registry+https://github.com/rust-lang/crates.io-index)" = "ee06ea4b620ab59a2267c6b48be16244a3389f8bfa0986bdd15c35b890b00af3" "checksum synstructure 0.10.2 (registry+https://github.com/rust-lang/crates.io-index)" = "02353edf96d6e4dc81aea2d8490a7e9db177bf8acb0e951c24940bf866cb313f" "checksum tempdir 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)" = "15f2b5fb00ccdf689e0149d1b1b3c03fead81c2b37735d812fa8bddbbf41b6d8" diff --git a/Cargo.toml b/Cargo.toml index a9295974fb..2b7c552e95 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -59,6 +59,7 @@ reqwest = "0.9.19" serde = "1.0.98" serde_derive = "1.0.98" serde_json = "1.0.40" +subprocess = "0.1.18" termcolor = "1.0.5" toml_edit = "0.1.5" atty = "0.2.13" diff --git a/src/fetch.rs b/src/fetch.rs index 57f7e5d846..79d2ce4b79 100644 --- a/src/fetch.rs +++ b/src/fetch.rs @@ -2,7 +2,6 @@ use crate::errors::*; use crate::registry::{registry_path, registry_url}; use crate::{Dependency, Manifest}; use env_proxy; -use git2::Repository; use regex::Regex; use reqwest; use semver; @@ -98,15 +97,45 @@ pub fn update_registry_index(manifest_path: &Path) -> Result<()> { output.reset()?; writeln!(output, " '{}' index", registry_url)?; - repo.remote_anonymous(registry_url.as_str())?.fetch( - &["refs/heads/master:refs/remotes/origin/master"], - None, - None, - )?; + let refspec = "refs/heads/master:refs/remotes/origin/master"; + fetch_with_cli(&repo, registry_url.as_str(), refspec)?; Ok(()) } +// https://github.com/rust-lang/cargo/blob/57986eac7157261c33f0123bade7ccd20f15200f/src/cargo/sources/git/utils.rs#L758 +fn fetch_with_cli( + repo: &git2::Repository, + url: &str, + refspec: &str, +) -> Result<()> { + let cmd = subprocess::Exec::shell("git").arg("fetch") + .arg("--tags") // fetch all tags + .arg("--force") // handle force pushes + .arg("--update-head-ok") // see discussion in rust-lang/cargo#2078 + .arg(url) + .arg(refspec) + // If cargo is run by git (for example, the `exec` command in `git + // rebase`), the GIT_DIR is set by git and will point to the wrong + // location (this takes precedence over the cwd). Make sure this is + // unset so git will look at cwd for the repo. + .env_remove("GIT_DIR") + // The reset of these may not be necessary, but I'm including them + // just to be extra paranoid and avoid any issues. + .env_remove("GIT_WORK_TREE") + .env_remove("GIT_INDEX_FILE") + .env_remove("GIT_OBJECT_DIRECTORY") + .env_remove("GIT_ALTERNATE_OBJECT_DIRECTORIES") + .cwd(repo.path()); + + let _ = cmd.capture().map_err(|e| match e { + subprocess::PopenError::IoError(io) => ErrorKind::Io(io), + subprocess::PopenError::LogicError(_) | + subprocess::PopenError::Utf8Error(_) => unreachable!("expected only io error"), + })?; + Ok(()) +} + #[test] fn get_latest_stable_version_from_json() { let versions: Vec = serde_json::from_str( @@ -215,7 +244,7 @@ fn fuzzy_query_registry_index( registry_path: impl AsRef, ) -> Result> { let crate_name = crate_name.into(); - let repo = Repository::open(registry_path)?; + let repo = git2::Repository::open(registry_path)?; let tree = repo .find_reference("refs/remotes/origin/master")? .peel_to_tree()?;