From 158f1e5ae41296761314028a02985fe747b68544 Mon Sep 17 00:00:00 2001 From: David Svedberg Date: Sun, 7 Jun 2026 15:57:59 +0200 Subject: [PATCH] fix(debug): pass workspace folder to startDebugging Without it VS Code can't resolve a config's preLaunchTask. Adds a regression test. --- src/test/suite/debug.test.ts | 16 ++++++++++++++++ src/tools/debug/startDebugSession.ts | 13 +++++++++++-- test-workspace/.vscode/launch.json | 9 +++++++++ test-workspace/.vscode/tasks.json | 15 +++++++++++++++ test-workspace/src/noop.cjs | 3 +++ 5 files changed, 54 insertions(+), 2 deletions(-) create mode 100644 test-workspace/.vscode/tasks.json create mode 100644 test-workspace/src/noop.cjs diff --git a/src/test/suite/debug.test.ts b/src/test/suite/debug.test.ts index 460b879..5789f88 100644 --- a/src/test/suite/debug.test.ts +++ b/src/test/suite/debug.test.ts @@ -298,6 +298,22 @@ suite('Debug Tools Tests', () => { } }); + test('should start debug session with a preLaunchTask', async () => { + const result = await callTool('debug_startSession', { + configuration: 'Debug With PreLaunchTask', + format: 'detailed', + }); + + // A preLaunchTask only resolves when startDebugging is given the + // owning workspace folder. Without it, VS Code reports + // "Could not find the task 'prelaunch-noop'" and startDebugging + // returns false. + assert.ok(!result.error, `Should not have error: ${result.error}`); + assert.strictEqual(result.success, true, 'Debug session should start'); + + await vscode.debug.stopDebugging(); + }); + // Skip debug session tests for now as they require more setup test.skip('should start debug session', async () => { const result = await callTool('debug_startSession', { diff --git a/src/tools/debug/startDebugSession.ts b/src/tools/debug/startDebugSession.ts index ef70258..fe42315 100644 --- a/src/tools/debug/startDebugSession.ts +++ b/src/tools/debug/startDebugSession.ts @@ -24,7 +24,14 @@ export const debug_startSessionTool: Tool = { handler: async (args) => { const { configuration, format = 'compact' } = args; - const configs = vscode.workspace.getConfiguration('launch').get('configurations') || []; + // Single-root only: a multi-root workspace can host per-folder launch + // configs and tasks, which this does not resolve. + const workspaceFolder = vscode.workspace.workspaceFolders?.[0]; + + const configs = + vscode.workspace + .getConfiguration('launch', workspaceFolder?.uri) + .get('configurations') || []; if (configs.length === 0) { return format === 'compact' @@ -46,7 +53,9 @@ export const debug_startSessionTool: Tool = { configToUse = found; } - const success = await vscode.debug.startDebugging(undefined, configToUse); + // The workspace folder must be passed so VS Code can resolve a + // preLaunchTask and folder-scoped variables like ${workspaceFolder}. + const success = await vscode.debug.startDebugging(workspaceFolder, configToUse); if (format === 'compact') { return { started: success, config: configToUse.name }; diff --git a/test-workspace/.vscode/launch.json b/test-workspace/.vscode/launch.json index 0d280ba..aa0c6e0 100644 --- a/test-workspace/.vscode/launch.json +++ b/test-workspace/.vscode/launch.json @@ -20,6 +20,15 @@ "args": ["--timeout", "999999", "--colors", "${file}"], "internalConsoleOptions": "openOnSessionStart", "skipFiles": ["/**"] + }, + { + "type": "node", + "request": "launch", + "name": "Debug With PreLaunchTask", + "program": "${workspaceFolder}/src/noop.cjs", + "preLaunchTask": "prelaunch-noop", + "internalConsoleOptions": "neverOpen", + "skipFiles": ["/**"] } ] } diff --git a/test-workspace/.vscode/tasks.json b/test-workspace/.vscode/tasks.json new file mode 100644 index 0000000..5e7c620 --- /dev/null +++ b/test-workspace/.vscode/tasks.json @@ -0,0 +1,15 @@ +{ + "version": "2.0.0", + "tasks": [ + { + "label": "prelaunch-noop", + "type": "shell", + "command": "node", + "args": ["-e", "process.exit(0)"], + "presentation": { + "reveal": "never" + }, + "problemMatcher": [] + } + ] +} diff --git a/test-workspace/src/noop.cjs b/test-workspace/src/noop.cjs new file mode 100644 index 0000000..a752d6c --- /dev/null +++ b/test-workspace/src/noop.cjs @@ -0,0 +1,3 @@ +// Minimal program launched by the preLaunchTask debug regression test. +// Exits on its own so the debug session does not linger. +setTimeout(() => process.exit(0), 200);