From d5ede56e6242bb34c098d3577623df22b0660fb1 Mon Sep 17 00:00:00 2001 From: yiliang114 <1204183885@qq.com> Date: Fri, 28 Nov 2025 00:57:33 +0800 Subject: [PATCH] =?UTF-8?q?Revert=20"fix(vscode-ide-companion):=20?= =?UTF-8?q?=E8=A7=A3=E5=86=B3=20mac=20=E7=8E=AF=E5=A2=83=E5=A4=9A=E4=B8=AA?= =?UTF-8?q?=20node=20=E7=89=88=E6=9C=AC=E7=9A=84=E5=AE=89=E8=A3=85?= =?UTF-8?q?=E9=97=AE=E9=A2=98"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 530039c517a2f6b00f6161fa9d24f17049176ae4. --- .../src/acp/acpConnection.ts | 90 +------------------ .../src/agents/qwenAgentManager.ts | 7 +- .../src/agents/qwenConnectionHandler.ts | 16 ++-- .../src/utils/CliInstaller.ts | 35 +------- .../src/utils/cliDetector.ts | 66 ++------------ .../src/webview/WebViewProvider.ts | 7 +- 6 files changed, 20 insertions(+), 201 deletions(-) diff --git a/packages/vscode-ide-companion/src/acp/acpConnection.ts b/packages/vscode-ide-companion/src/acp/acpConnection.ts index cc62a7aa..13639d4d 100644 --- a/packages/vscode-ide-companion/src/acp/acpConnection.ts +++ b/packages/vscode-ide-companion/src/acp/acpConnection.ts @@ -20,7 +20,6 @@ import type { } from './connectionTypes.js'; import { AcpMessageHandler } from './acpMessageHandler.js'; import { AcpSessionManager } from './acpSessionManager.js'; -import { statSync } from 'fs'; /** * ACP Connection Handler for VSCode Extension @@ -70,75 +69,7 @@ export class AcpConnection { } /** - * Determine the correct Node.js executable path for a given CLI installation - * Handles various Node.js version managers (nvm, n, manual installations) - * - * @param cliPath - Path to the CLI executable - * @returns Path to the Node.js executable, or null if not found - */ - private determineNodePathForCli(cliPath: string): string | null { - // Common patterns for Node.js installations - const nodePathPatterns = [ - // NVM pattern: /Users/user/.nvm/versions/node/vXX.XX.X/bin/qwen -> /Users/user/.nvm/versions/node/vXX.XX.X/bin/node - cliPath.replace(/\/bin\/qwen$/, '/bin/node'), - - // N pattern: /Users/user/n/bin/qwen -> /Users/user/n/bin/node - cliPath.replace(/\/bin\/qwen$/, '/bin/node'), - - // Manual installation pattern: /usr/local/bin/qwen -> /usr/local/bin/node - cliPath.replace(/\/qwen$/, '/node'), - - // Alternative pattern: /opt/nodejs/bin/qwen -> /opt/nodejs/bin/node - cliPath.replace(/\/bin\/qwen$/, '/bin/node'), - ]; - - // Check each pattern - for (const nodePath of nodePathPatterns) { - try { - if (statSync(nodePath).isFile()) { - // Verify it's executable - const stats = statSync(nodePath); - if (stats.mode & 0o111) { - // Check if executable - console.log( - `[ACP] Found Node.js executable for CLI at: ${nodePath}`, - ); - return nodePath; - } - } - } catch (_error) { - // File doesn't exist or other error, continue to next pattern - continue; - } - } - - // Try to find node in the same directory as the CLI - const cliDir = cliPath.substring(0, cliPath.lastIndexOf('/')); - const potentialNodePaths = [`${cliDir}/node`, `${cliDir}/bin/node`]; - - for (const nodePath of potentialNodePaths) { - try { - if (statSync(nodePath).isFile()) { - const stats = statSync(nodePath); - if (stats.mode & 0o111) { - console.log( - `[ACP] Found Node.js executable in CLI directory at: ${nodePath}`, - ); - return nodePath; - } - } - } catch (_error) { - // File doesn't exist, continue - continue; - } - } - - console.log(`[ACP] Could not determine Node.js path for CLI: ${cliPath}`); - return null; - } - - /** - * 连接到ACP后端 + * Connect to ACP backend * * @param backend - Backend type * @param cliPath - CLI path @@ -184,23 +115,8 @@ export class AcpConnection { spawnCommand = isWindows ? 'npx.cmd' : 'npx'; spawnArgs = [...parts.slice(1), '--experimental-acp', ...extraArgs]; } else { - // For qwen CLI, ensure we use the correct Node.js version - // Handle various Node.js version managers (nvm, n, manual installations) - if (cliPath.includes('/qwen') && !isWindows) { - // Try to determine the correct node executable for this qwen installation - const nodePath = this.determineNodePathForCli(cliPath); - if (nodePath) { - spawnCommand = nodePath; - spawnArgs = [cliPath, '--experimental-acp', ...extraArgs]; - } else { - // Fallback to direct execution - spawnCommand = cliPath; - spawnArgs = ['--experimental-acp', ...extraArgs]; - } - } else { - spawnCommand = cliPath; - spawnArgs = ['--experimental-acp', ...extraArgs]; - } + spawnCommand = cliPath; + spawnArgs = ['--experimental-acp', ...extraArgs]; } console.log('[ACP] Spawning command:', spawnCommand, spawnArgs.join(' ')); diff --git a/packages/vscode-ide-companion/src/agents/qwenAgentManager.ts b/packages/vscode-ide-companion/src/agents/qwenAgentManager.ts index 125749c8..13328b51 100644 --- a/packages/vscode-ide-companion/src/agents/qwenAgentManager.ts +++ b/packages/vscode-ide-companion/src/agents/qwenAgentManager.ts @@ -72,14 +72,12 @@ export class QwenAgentManager { /** * Connect to Qwen service * - * @param workingDir - 工作目录 - * @param authStateManager - 认证状态管理器(可选) - * @param cliPath - CLI路径(可选,如果提供将覆盖配置中的路径) + * @param workingDir - Working directory + * @param authStateManager - Auth state manager (optional) */ async connect( workingDir: string, authStateManager?: AuthStateManager, - cliPath?: string, ): Promise { this.currentWorkingDir = workingDir; await this.connectionHandler.connect( @@ -87,7 +85,6 @@ export class QwenAgentManager { this.sessionReader, workingDir, authStateManager, - cliPath, ); } diff --git a/packages/vscode-ide-companion/src/agents/qwenConnectionHandler.ts b/packages/vscode-ide-companion/src/agents/qwenConnectionHandler.ts index 49e3eb4c..fce12e16 100644 --- a/packages/vscode-ide-companion/src/agents/qwenConnectionHandler.ts +++ b/packages/vscode-ide-companion/src/agents/qwenConnectionHandler.ts @@ -23,18 +23,16 @@ export class QwenConnectionHandler { /** * Connect to Qwen service and establish session * - * @param connection - ACP连接实例 - * @param sessionReader - 会话读取器实例 - * @param workingDir - 工作目录 - * @param authStateManager - 认证状态管理器(可选) - * @param cliPath - CLI路径(可选,如果提供将覆盖配置中的路径) + * @param connection - ACP connection instance + * @param sessionReader - Session reader instance + * @param workingDir - Working directory + * @param authStateManager - Auth state manager (optional) */ async connect( connection: AcpConnection, sessionReader: QwenSessionReader, workingDir: string, authStateManager?: AuthStateManager, - cliPath?: string, ): Promise { const connectId = Date.now(); console.log(`\n========================================`); @@ -43,9 +41,7 @@ export class QwenConnectionHandler { console.log(`========================================\n`); const config = vscode.workspace.getConfiguration('qwenCode'); - // Use the provided CLI path if available, otherwise use the configured path - const effectiveCliPath = - cliPath || config.get('qwen.cliPath', 'qwen'); + const cliPath = config.get('qwen.cliPath', 'qwen'); const openaiApiKey = config.get('qwen.openaiApiKey', ''); const openaiBaseUrl = config.get('qwen.openaiBaseUrl', ''); const model = config.get('qwen.model', ''); @@ -67,7 +63,7 @@ export class QwenConnectionHandler { console.log('[QwenAgentManager] Using proxy:', proxy); } - await connection.connect('qwen', effectiveCliPath, workingDir, extraArgs); + await connection.connect('qwen', cliPath, workingDir, extraArgs); // Determine authentication method const authMethod = openaiApiKey ? 'openai' : 'qwen-oauth'; diff --git a/packages/vscode-ide-companion/src/utils/CliInstaller.ts b/packages/vscode-ide-companion/src/utils/CliInstaller.ts index 4a7da08e..b9aeb748 100644 --- a/packages/vscode-ide-companion/src/utils/CliInstaller.ts +++ b/packages/vscode-ide-companion/src/utils/CliInstaller.ts @@ -93,39 +93,9 @@ export class CliInstaller { const execAsync = promisify(exec); try { - // Use NVM environment to ensure we get the same Node.js version - // as when they run 'node -v' in terminal - // Fallback chain: default alias -> node alias -> current version - const installCommand = - process.platform === 'win32' - ? 'npm install -g @qwen-code/qwen-code@latest' - : 'source ~/.nvm/nvm.sh 2>/dev/null && (nvm use default 2>/dev/null || nvm use node 2>/dev/null || nvm use 2>/dev/null); npm install -g @qwen-code/qwen-code@latest'; - - console.log( - '[CliInstaller] Installing with command:', - installCommand, - ); - console.log( - '[CliInstaller] Current process PATH:', - process.env.PATH, - ); - - // Also log Node.js version being used by VS Code - console.log( - '[CliInstaller] VS Code Node.js version:', - process.version, - ); - console.log( - '[CliInstaller] VS Code Node.js execPath:', - process.execPath, - ); - const { stdout, stderr } = await execAsync( - installCommand, - { - timeout: 120000, - shell: '/bin/bash', - }, // 2 minutes timeout + 'npm install -g @qwen-code/qwen-code@latest', + { timeout: 120000 }, // 2 minutes timeout ); console.log('[CliInstaller] Installation output:', stdout); @@ -159,7 +129,6 @@ export class CliInstaller { const errorMessage = error instanceof Error ? error.message : String(error); console.error('[CliInstaller] Installation failed:', errorMessage); - console.error('[CliInstaller] Error stack:', error); vscode.window .showErrorMessage( diff --git a/packages/vscode-ide-companion/src/utils/cliDetector.ts b/packages/vscode-ide-companion/src/utils/cliDetector.ts index b88755dd..c09ed250 100644 --- a/packages/vscode-ide-companion/src/utils/cliDetector.ts +++ b/packages/vscode-ide-companion/src/utils/cliDetector.ts @@ -40,77 +40,28 @@ export class CliDetector { this.cachedResult && now - this.lastCheckTime < this.CACHE_DURATION_MS ) { - console.log('[CliDetector] Returning cached result'); return this.cachedResult; } - console.log( - '[CliDetector] Starting CLI detection, current PATH:', - process.env.PATH, - ); - try { const isWindows = process.platform === 'win32'; const whichCommand = isWindows ? 'where' : 'which'; // Check if qwen command exists try { - // Use NVM environment for consistent detection - // Fallback chain: default alias -> node alias -> current version - const detectionCommand = - process.platform === 'win32' - ? `${whichCommand} qwen` - : 'source ~/.nvm/nvm.sh 2>/dev/null && (nvm use default 2>/dev/null || nvm use node 2>/dev/null || nvm use 2>/dev/null); which qwen'; - - console.log( - '[CliDetector] Detecting CLI with command:', - detectionCommand, - ); - - const { stdout } = await execAsync(detectionCommand, { + const { stdout } = await execAsync(`${whichCommand} qwen`, { timeout: 5000, - shell: '/bin/bash', }); - // The output may contain multiple lines, with NVM activation messages - // We want the last line which should be the actual path - const lines = stdout - .trim() - .split('\n') - .filter((line) => line.trim()); - const cliPath = lines[lines.length - 1]; - - console.log('[CliDetector] Found CLI at:', cliPath); + const cliPath = stdout.trim().split('\n')[0]; // Try to get version let version: string | undefined; try { - // Use NVM environment for version check - // Fallback chain: default alias -> node alias -> current version - // Also ensure we use the correct Node.js version that matches the CLI installation - const versionCommand = - process.platform === 'win32' - ? 'qwen --version' - : 'source ~/.nvm/nvm.sh 2>/dev/null && (nvm use default 2>/dev/null || nvm use node 2>/dev/null || nvm use 2>/dev/null); qwen --version'; - - console.log( - '[CliDetector] Getting version with command:', - versionCommand, - ); - - const { stdout: versionOutput } = await execAsync(versionCommand, { + const { stdout: versionOutput } = await execAsync('qwen --version', { timeout: 5000, - shell: '/bin/bash', }); - // The output may contain multiple lines, with NVM activation messages - // We want the last line which should be the actual version - const versionLines = versionOutput - .trim() - .split('\n') - .filter((line) => line.trim()); - version = versionLines[versionLines.length - 1]; - console.log('[CliDetector] CLI version:', version); - } catch (versionError) { - console.log('[CliDetector] Failed to get CLI version:', versionError); + version = versionOutput.trim(); + } catch { // Version check failed, but CLI is installed } @@ -121,8 +72,7 @@ export class CliDetector { }; this.lastCheckTime = now; return this.cachedResult; - } catch (detectionError) { - console.log('[CliDetector] CLI not found, error:', detectionError); + } catch (_error) { // CLI not found this.cachedResult = { isInstalled: false, @@ -132,7 +82,6 @@ export class CliDetector { return this.cachedResult; } } catch (error) { - console.log('[CliDetector] General detection error:', error); const errorMessage = error instanceof Error ? error.message : String(error); this.cachedResult = { @@ -166,9 +115,6 @@ export class CliDetector { 'Install via npm:', ' npm install -g @qwen-code/qwen-code@latest', '', - 'If you are using nvm (automatically handled by the plugin):', - ' The plugin will automatically use your default nvm version', - '', 'Or install from source:', ' git clone https://github.com/QwenLM/qwen-code.git', ' cd qwen-code', diff --git a/packages/vscode-ide-companion/src/webview/WebViewProvider.ts b/packages/vscode-ide-companion/src/webview/WebViewProvider.ts index df6c77cd..6e924763 100644 --- a/packages/vscode-ide-companion/src/webview/WebViewProvider.ts +++ b/packages/vscode-ide-companion/src/webview/WebViewProvider.ts @@ -399,12 +399,7 @@ export class WebViewProvider { const authInfo = await this.authStateManager.getAuthInfo(); console.log('[WebViewProvider] Auth cache status:', authInfo); - // Pass the detected CLI path to ensure we use the correct installation - await this.agentManager.connect( - workingDir, - this.authStateManager, - cliDetection.cliPath, - ); + await this.agentManager.connect(workingDir, this.authStateManager); console.log('[WebViewProvider] Agent connected successfully'); this.agentInitialized = true;