From 00825f2a3998d647571fae33098d296557ecb970 Mon Sep 17 00:00:00 2001 From: xintaofei Date: Wed, 18 Mar 2026 23:13:58 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E5=A4=8Dnpx=E7=B1=BB=E5=9E=8B?= =?UTF-8?q?=E7=9A=84agent=E7=9A=84=E6=9C=AC=E5=9C=B0=E7=89=88=E6=9C=AC?= =?UTF-8?q?=E6=A3=80=E6=B5=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src-tauri/src/commands/acp.rs | 38 +++++++++++++++++++++++++++++++---- 1 file changed, 34 insertions(+), 4 deletions(-) diff --git a/src-tauri/src/commands/acp.rs b/src-tauri/src/commands/acp.rs index ae6231e..145b9d9 100644 --- a/src-tauri/src/commands/acp.rs +++ b/src-tauri/src/commands/acp.rs @@ -85,15 +85,45 @@ fn is_cmd_available(cmd: &str) -> bool { which::which(cmd).is_ok() } +/// Detect the actual installed version of an npm global package by running +/// `npm list -g --json` and parsing the JSON output. +async fn detect_npm_global_version(package_name: &str) -> Option { + let npm_path = which::which("npm").ok()?; + let output = crate::process::tokio_command(npm_path) + .arg("list") + .arg("-g") + .arg(package_name) + .arg("--json") + .arg("--depth=0") + .output() + .await + .ok()?; + // npm list --json may exit non-zero when package is missing, but still + // outputs valid JSON with an empty dependencies object. + let stdout = String::from_utf8_lossy(&output.stdout); + let json: serde_json::Value = serde_json::from_str(&stdout).ok()?; + let version = json + .get("dependencies")? + .get(package_name)? + .get("version")? + .as_str()?; + normalize_version_candidate(version) +} + async fn detect_local_version(agent_type: AgentType) -> Option { let meta = registry::get_agent_meta(agent_type); match meta.distribution { registry::AgentDistribution::Npx { cmd, package, .. } => { - if is_cmd_available(cmd) { - version_from_package_spec(package) - } else { - None + if !is_cmd_available(cmd) { + return None; } + // Try `npm list -g --json` to get the real installed version. + let pkg_name = package_name_from_spec(package); + if let Some(v) = detect_npm_global_version(&pkg_name).await { + return Some(v); + } + // Fallback: parse version from registry package spec + version_from_package_spec(package) } registry::AgentDistribution::Binary { cmd, .. } => { binary_cache::detect_installed_version(agent_type, cmd)