Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

RA doesn't properly resolve _relative_ env vars from .cargo/config.toml #18143

Open
devjgm opened this issue Sep 18, 2024 · 2 comments
Open

RA doesn't properly resolve _relative_ env vars from .cargo/config.toml #18143

devjgm opened this issue Sep 18, 2024 · 2 comments
Labels
C-bug Category: bug

Comments

@devjgm
Copy link

devjgm commented Sep 18, 2024

rust-analyzer version: rust-analyzer version: 0.3.2112-standalone (94b526fc8 2024-09-15) [/Users/greg/.vscode/extensions/rust-lang.rust-analyzer-0.3.2112-darwin-arm64/server/rust-analyzer]

rustc version: rustc 1.81.0 (eeb90cda1 2024-09-04)

editor or extension: vscode v0.3.2112

relevant settings:

Any .cargo/config.toml setting a relative env var. For example:

[env]
CARGO_WORKSPACE_DIR = { value = "", relative = true }

repository link (if public, optional):

code snippet to reproduce:

The [env] table in .cargo/config.toml allows for values to specified as relative paths, in which case they should be resolved to absolute paths that are relative to the .cargo dir. See https://doc.rust-lang.org/cargo/reference/config.html#env. An example is:

[env]
FOO = { value = ".", relative = true }

Rust-Analyzer does not convert this to a proper absolute path.

The relevant code is here:

pub(crate) fn cargo_config_env(
manifest: &ManifestPath,
extra_env: &FxHashMap<String, String>,
sysroot: &Sysroot,
) -> FxHashMap<String, String> {
let mut cargo_config = sysroot.tool(Tool::Cargo);
cargo_config.envs(extra_env);
cargo_config
.current_dir(manifest.parent())
.args(["-Z", "unstable-options", "config", "get", "env"])
.env("RUSTC_BOOTSTRAP", "1");
if manifest.is_rust_manifest() {
cargo_config.arg("-Zscript");
}
// if successful we receive `env.key.value = "value" per entry
tracing::debug!("Discovering cargo config env by {:?}", cargo_config);
utf8_stdout(cargo_config)
.map(parse_output_cargo_config_env)
.inspect(|env| {
tracing::debug!("Discovered cargo config env: {:?}", env);
})
.inspect_err(|err| {
tracing::debug!("Failed to discover cargo config env: {:?}", err);
})
.unwrap_or_default()
}
fn parse_output_cargo_config_env(stdout: String) -> FxHashMap<String, String> {
stdout
.lines()
.filter_map(|l| l.strip_prefix("env."))
.filter_map(|l| l.split_once(" = "))
.filter_map(|(k, v)| {
if k.contains('.') {
k.strip_suffix(".value").zip(Some(v))
} else {
Some((k, v))
}
})
.map(|(key, value)| (key.to_owned(), value.trim_matches('"').to_owned()))
.collect()
}

We an see that RA runs a command like: cargo -Zunstable-options config get env, which will output something like the following, assuming the example toml snippet above:

env.FOO.relative = true
env.FOO.value = "."

We can see that RA strips the .value suffix

k.strip_suffix(".value").zip(Some(v))

and ignores the .relative field.

A Fix

One way to fix this would be to compute the absolute path by joining the relative path with the config file's path.

@devjgm devjgm added the C-bug Category: bug label Sep 18, 2024
@devjgm
Copy link
Author

devjgm commented Sep 18, 2024

One way to fix this would be to compute the absolute path by joining the relative path with the config file's path.

Actually, it looks like RA doesn't know where the .cargo/config.toml file was, so it may not be trivial to compute the correct absolute path.

@Veykril
Copy link
Member

Veykril commented Sep 19, 2024

Yes we don't know where the source is, we'd need cargo to somehow inform us about this

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
C-bug Category: bug
Projects
None yet
Development

No branches or pull requests

2 participants