Skip to content

Commit 789b7da

Browse files
committed
refactor: replace canonicalization in search path retrieval with dedicated normalization function
1 parent d94564d commit 789b7da

File tree

1 file changed

+26
-2
lines changed
  • crates/pet-env-var-path/src

1 file changed

+26
-2
lines changed

crates/pet-env-var-path/src/lib.rs

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@
33

44
use pet_core::os_environment::Environment;
55
use std::collections::HashSet;
6-
use std::fs;
76
use std::path::PathBuf;
87

98
pub fn get_search_paths_from_env_variables(environment: &dyn Environment) -> Vec<PathBuf> {
@@ -19,7 +18,7 @@ pub fn get_search_paths_from_env_variables(environment: &dyn Environment) -> Vec
1918
environment
2019
.get_know_global_search_locations()
2120
.into_iter()
22-
.map(|p| fs::canonicalize(&p).unwrap_or(p))
21+
.map(normalize_search_path)
2322
.collect::<HashSet<PathBuf>>()
2423
.into_iter()
2524
.filter(|p| !p.starts_with(apps_path.clone()))
@@ -28,3 +27,28 @@ pub fn get_search_paths_from_env_variables(environment: &dyn Environment) -> Vec
2827
Vec::new()
2928
}
3029
}
30+
31+
/// Normalizes a search path for deduplication purposes.
32+
///
33+
/// On Unix: Uses fs::canonicalize to resolve symlinks. This is important for merged-usr
34+
/// systems where /bin, /sbin, /usr/sbin are symlinks to /usr/bin - we don't want to
35+
/// report the same Python installation multiple times.
36+
/// See: https://github.com/microsoft/python-environment-tools/pull/200
37+
///
38+
/// On Windows: Uses norm_case (GetLongPathNameW) to normalize case WITHOUT resolving
39+
/// directory junctions. This is important for tools like Scoop that use junctions
40+
/// (e.g., python\current -> python\3.13.3). Using fs::canonicalize would resolve
41+
/// the junction, causing symlink tracking to fail when the shim points to the
42+
/// junction path but executables are discovered from the resolved path.
43+
/// See: https://github.com/microsoft/python-environment-tools/issues/187
44+
fn normalize_search_path(path: PathBuf) -> PathBuf {
45+
#[cfg(unix)]
46+
{
47+
std::fs::canonicalize(&path).unwrap_or(path)
48+
}
49+
50+
#[cfg(windows)]
51+
{
52+
pet_fs::path::norm_case(&path)
53+
}
54+
}

0 commit comments

Comments
 (0)