diff --git a/Cargo.lock b/Cargo.lock index b1ff864..7e3eda9 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -411,6 +411,7 @@ dependencies = [ "serde_json", "serde_json5", "toml", + "winreg", ] [[package]] @@ -1221,6 +1222,16 @@ version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "09dac053f1cd375980747450bfc7250c264eaae0583872e845c0c7cd578872b5" +[[package]] +name = "winreg" +version = "0.56.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d6f32a0ff4a9f6f01231eb2059cc85479330739333e0e58cadf03b6af2cca10" +dependencies = [ + "cfg-if", + "windows-sys 0.61.2", +] + [[package]] name = "wit-bindgen" version = "0.51.0" diff --git a/Cargo.toml b/Cargo.toml index f7b943e..c441036 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -27,3 +27,6 @@ clap_complete = { version = "4.5", features = ["unstable-dynamic"] } serde_json = "1.0.149" indicatif = "0.17" console = "0.15.8" + +[target."cfg(windows)".dependencies] +winreg = "0.56.0" diff --git a/src/config.rs b/src/config.rs index 2aa9e98..fa5fd14 100644 --- a/src/config.rs +++ b/src/config.rs @@ -77,8 +77,69 @@ impl Config { #[cfg(target_os = "windows")] { - let default_paths = vec![PathBuf::from("C:\\Program Files\\Huawei\\DevEco Studio")]; - for path in default_paths { + let mut paths = Vec::new(); + + // 1. 通过注册表获取 DevEco Studio (基于 JetBrains 系列的注册表特征) + // 常见的卸载列表路径 + let uninstall_keys = [ + ( + winreg::enums::HKEY_LOCAL_MACHINE, + "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall", + ), + ( + winreg::enums::HKEY_CURRENT_USER, + "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall", + ), + ( + winreg::enums::HKEY_LOCAL_MACHINE, + "SOFTWARE\\WOW6432Node\\Microsoft\\Windows\\CurrentVersion\\Uninstall", + ), + ( + winreg::enums::HKEY_CURRENT_USER, + "SOFTWARE\\WOW6432Node\\Microsoft\\Windows\\CurrentVersion\\Uninstall", + ), + ]; + + for (hkey, subkey) in uninstall_keys { + let hk = winreg::RegKey::predef(hkey); + if let Ok(uninstall_key) = hk.open_subkey(subkey) { + for name in uninstall_key.enum_keys().filter_map(|k| k.ok()) { + if name.starts_with("DevEco Studio") { + if let Ok(app_key) = uninstall_key.open_subkey(&name) { + if let Ok(install_location) = + app_key.get_value::("InstallLocation") + { + let path = PathBuf::from(install_location); + if path.exists() { + paths.push(path); + } + } else if let Ok(uninstall_string) = + app_key.get_value::("UninstallString") + { + // UninstallString 通常类似于 "C:\Program Files\Huawei\DevEco Studio\bin\uninstall.exe" + let clean_str = uninstall_string.trim_matches('"'); + let uninstall_path = PathBuf::from(clean_str); + if let Some(bin_dir) = uninstall_path.parent() { + if let Some(root_dir) = bin_dir.parent() { + if root_dir.exists() { + paths.push(root_dir.to_path_buf()); + } + } + } + } + } + } + } + } + } + + // 2. 兜底方案:常见的默认安装路径 + let default_path = PathBuf::from("C:\\Program Files\\Huawei\\DevEco Studio"); + if default_path.exists() { + paths.push(default_path); + } + + for path in paths { if path.exists() { return Some(path); }