From f0141c0385de0d793c0a024d29743c5303084c56 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Fri, 9 Aug 2024 21:12:58 +0200 Subject: [PATCH 1/2] Add test for `GlobalContext::get_env_list` method --- src/cargo/util/context/mod.rs | 39 +++++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) diff --git a/src/cargo/util/context/mod.rs b/src/cargo/util/context/mod.rs index a8fee94d5e4..4ed24440b47 100644 --- a/src/cargo/util/context/mod.rs +++ b/src/cargo/util/context/mod.rs @@ -2971,9 +2971,13 @@ fn disables_multiplexing_for_bad_curl( mod tests { use super::disables_multiplexing_for_bad_curl; use super::CargoHttpConfig; + use super::ConfigKey; + use super::Definition; use super::GlobalContext; use super::Shell; + use std::collections::HashMap; + #[test] fn disables_multiplexing() { let mut gctx = GlobalContext::new(Shell::new(), "".into(), "".into()); @@ -3010,4 +3014,39 @@ mod tests { assert_eq!(http.multiplexing, result); } } + + #[test] + fn env_argument_parsing() { + let mut gctx = GlobalContext::new(Shell::new(), "".into(), "".into()); + gctx.set_search_stop_path(std::path::PathBuf::new()); + + let values: &[(&str, &[&str])] = &[ + ("VAL1", &["--path"]), + // FIXME: this one is parsed as `["--path=\"y", "z\""]`. + // ("VAL2", &["--path=\"y z\""]), + // FIXME: this one is parsed as `["--path", "\"y", "z\""]`. + // ("VAL3", &["--path", "\"y z\""]), + ]; + + let mut env = HashMap::new(); + for (key, value) in values { + env.insert(format!("CARGO_{key}"), value.join(" ")); + } + gctx.set_env(env); + + for (key, value) in values { + let mut args = Vec::new(); + gctx.get_env_list(&ConfigKey::from_str(key), &mut args) + .unwrap(); + + let mut expected = Vec::new(); + for sub in *value { + expected.push(( + sub.replace("\"", ""), + Definition::Environment(format!("CARGO_{key}")), + )); + } + assert_eq!(args, expected, "failed for key {}", key); + } + } } From 4b152ec5d6e3d4f339f2e3ba4f4f4fdc346fdd42 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Fri, 9 Aug 2024 12:06:04 +0200 Subject: [PATCH 2/2] Correctly parse arguments from environment variables --- Cargo.lock | 9 ++++++++- Cargo.toml | 2 ++ src/cargo/util/context/mod.rs | 11 +++++------ 3 files changed, 15 insertions(+), 7 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index a5b3703ba09..7cd37318959 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -324,6 +324,7 @@ dependencies = [ "serde_json", "sha1", "shell-escape", + "shlex", "snapbox", "supports-hyperlinks", "supports-unicode", @@ -2169,7 +2170,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4979f22fdb869068da03c9f7528f8297c6fd2606bc3a4affe42e6a823fdb8da4" dependencies = [ "cfg-if", - "windows-targets 0.48.5", + "windows-targets 0.52.6", ] [[package]] @@ -3182,6 +3183,12 @@ version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "24188a676b6ae68c3b2cb3a01be17fbf7240ce009799bb56d5b1409051e78fde" +[[package]] +name = "shlex" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" + [[package]] name = "signature" version = "2.2.0" diff --git a/Cargo.toml b/Cargo.toml index 9dc40f90a8e..99a6a07da0e 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -90,6 +90,7 @@ serde_json = "1.0.120" sha1 = "0.10.6" sha2 = "0.10.8" shell-escape = "0.1.5" +shlex = "1.3.0" similar = "2.6.0" supports-hyperlinks = "3.0.0" snapbox = { version = "0.6.16", features = ["diff", "dir", "term-svg", "regex", "json"] } @@ -192,6 +193,7 @@ serde_ignored.workspace = true serde_json = { workspace = true, features = ["raw_value"] } sha1.workspace = true shell-escape.workspace = true +shlex.workspace = true supports-hyperlinks.workspace = true tar.workspace = true tempfile.workspace = true diff --git a/src/cargo/util/context/mod.rs b/src/cargo/util/context/mod.rs index 4ed24440b47..996483c0899 100644 --- a/src/cargo/util/context/mod.rs +++ b/src/cargo/util/context/mod.rs @@ -89,6 +89,7 @@ use lazycell::LazyCell; use serde::de::IntoDeserializer as _; use serde::Deserialize; use serde_untagged::UntaggedEnumVisitor; +use shlex::Shlex; use time::OffsetDateTime; use toml_edit::Item; use url::Url; @@ -973,8 +974,8 @@ impl GlobalContext { } } else { output.extend( - env_val - .split_whitespace() + Shlex::new(env_val) + .into_iter() .map(|s| (s.to_string(), def.clone())), ); } @@ -3022,10 +3023,8 @@ mod tests { let values: &[(&str, &[&str])] = &[ ("VAL1", &["--path"]), - // FIXME: this one is parsed as `["--path=\"y", "z\""]`. - // ("VAL2", &["--path=\"y z\""]), - // FIXME: this one is parsed as `["--path", "\"y", "z\""]`. - // ("VAL3", &["--path", "\"y z\""]), + ("VAL2", &["--path=\"y z\""]), + ("VAL3", &["--path", "\"y z\""]), ]; let mut env = HashMap::new();