Skip to content

Due to wmic has been deprecated. Use @vscode/windows-process-tree for Windows process listing with WMIC fallback#991

Open
ZA139 wants to merge 4 commits intomicrosoft:mainfrom
ZA139:trunk
Open

Due to wmic has been deprecated. Use @vscode/windows-process-tree for Windows process listing with WMIC fallback#991
ZA139 wants to merge 4 commits intomicrosoft:mainfrom
ZA139:trunk

Conversation

@ZA139
Copy link
Copy Markdown

@ZA139 ZA139 commented Mar 30, 2026

Following up on #858, which replaced WMIC with PowerShell for process listing, this PR takes a different approach by using the native @vscode/windows-process-tree module (getAllProcesses) to enumerate processes on Windows. This avoids spawning external commands entirely and provides better performance.

Changes:

  • Use @vscode/windows-process-tree (getAllProcesses with ProcessDataFlag.CommandLine) as the primary method for listing processes on Windows.
  • When windows-process-tree is unavailable or fails (e.g. native module load failure), fall back to the existing WMIC parser to maintain backward compatibility on older Windows versions.
  • Wrap getAllProcesses in a manual Promise instead of util.promisify, since the library's callback signature (callback, flags?) does not follow the Node.js (err, result) convention.
  • Add @vscode/windows-process-tree as a dependency and configure it as a webpack external (native module).
  • macOS/Linux process listing remains unchanged (ps-based).

Test changes:

  • Add unit tests for the getAllProcesses happy path on Windows.
  • Add unit tests for the WMIC fallback when getAllProcesses throws.
  • Add getAttachItems sorting and Python-process-priority tests for both paths.

No feature changed. This is an internal improvement to process enumeration reliability on Windows.

ZA139 and others added 4 commits March 24, 2026 19:58
Add @vscode/windows-process-tree as a dependency and use it on Windows to enumerate processes (via promisified getAllProcesses). Fall back to the existing WMIC parser when windows-process-tree is unavailable. Update provider logic to return parsed process items from the native API on Windows and keep PS-based listing for macOS/Linux. Update unit tests to stub and exercise the new getAllProcesses flow and the WMIC fallback, and add webpack externals entry for the new native module.
Adjust Windows process provider unit tests to match the updated getAllProcesses API that accepts a flag parameter and uses an error-first callback. Stubs now use signatures like (_flag, callback) and call callback(null, processList); throwing stubs were updated to accept two arguments. These are test-only updates to align with the new function signature.
Replace use of util.promisify with an explicit Promise wrapper around wpc.getAllProcesses, removing the promisify import and adapting the call site to resolve with the process list. Update unit tests to match the changed callback shape (stubs now call callback(processList) and throw without an error-first parameter). This keeps Windows process enumeration working while aligning with the windows-process-tree callback behavior.
Integrate windows-process-tree for Windows process enumeration
@ZA139
Copy link
Copy Markdown
Author

ZA139 commented Mar 30, 2026

Hi,@eleanorjboyd @Tyriar Sorry for the delay!
Due to the merge of microsoft/vscode-windows-process-tree#84 and some delays from my regular work, progress on this PR was postponed for a while. The new implementation is now ready and available for review. Could someone please be assigned to review it? Thank you!

Best Regards
Charles

'@opentelemetry/instrumentation': 'commonjs @opentelemetry/instrumentation', // ignored because we don't ship instrumentation
'@azure/opentelemetry-instrumentation-azure-sdk': 'commonjs @azure/opentelemetry-instrumentation-azure-sdk', // ignored because we don't ship instrumentation
'@azure/functions-core': '@azure/functions-core', // ignored because we don't ship instrumentation
'@vscode/windows-process-tree': 'commonjs @vscode/windows-process-tree',
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think this is correct. It's not an external. We need to have it as part of the webpack. Otherwise VS code would have to provide it?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the review — I dug into this a bit more, and I think there are really two separate constraints here.

1. Why external is still required

@vscode/windows-process-tree is a native Node addon and includes a compiled .node binary (build/Release/windows_process_tree.node).

If we remove it from externals, webpack tries to parse that binary and the build fails immediately with:

ERROR in ./node_modules/@vscode/windows-process-tree/build/Release/windows_process_tree.node 1:2
Module parse failed: Unexpected character '�' (1:2)
You may need an appropriate loader to handle this file type

So marking it as external is a hard requirement for native addons.

2. Runtime issue with VS Code's built-in version

The other issue is runtime resolution.

VS Code already ships @vscode/windows-process-tree in resources/app/node_modules, but the bundled version is currently 0.6.3 (from VS Code's ^0.6.0 dependency). That version does not expose getAllProcesses — that API was added in 0.7.0.

So with the current setup:

  • webpack externalizes the module
  • .vscodeignore excludes our node_modules
  • at runtime Node resolves to VS Code's built-in 0.6.3
  • getAllProcesses is unavailable
  • we fall back to WMIC

That means the native path is effectively not used yet.

Possible ways forward

Option A: Ship 0.7.0 in the VSIX

Whitelist this dependency in .vscodeignore so the extension ships its own native module.

node_modules/**
!node_modules/@vscode/windows-process-tree/lib/**
!node_modules/@vscode/windows-process-tree/build/Release/windows_process_tree.node
!node_modules/@vscode/windows-process-tree/package.json

This gives us immediate self-contained support. The existing target-specific packaging should already handle the platform-specific native artifact.— but I haven't verified this end-to-end yet. Could you confirm whether the current packaging pipeline supports shipping a native addon this way, or if additional build steps would be needed?

Option B: Use node-loader

Handle the .node binary through webpack so it gets copied into dist/ and required from there.

This would also make the extension self-contained, but is a bit more webpack-specific than Option A.

Option C: Update VS Code's dependency

Longer term, we could update VS Code itself to depend on @vscode/windows-process-tree >= 0.7.0. Once that version is broadly available in supported VS Code builds, this extension could rely on the built-in module and stop shipping its own copy.

That said, this does not solve the immediate problem for current users, and older VS Code versions would still fall back to WMIC.

Recommendation

I think Option A is the most practical short-term fix:

  • keeps external (required for build)
  • makes runtime resolution deterministic
  • avoids depending on VS Code’s release timeline

Option C still makes sense as a longer-term cleanup once the built-in version catches up.
Sorry for the long reply, but I wanted to make sure I understood the constraints correctly and ask the concrete packaging/runtime question here.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Option C is my preferred solution. The problem I see with Option A (unless I'm remembering incorrectly), .node files are tied to specific versions of node and may not load in VS code, especially if VS code changes their node version.

As far as shipping it, I believe if running vsce package causes the file to end up in the vsix for you locally, it will also work when the real build is generated.

So maybe Option A works for the short term as long VS code's current node version matches. I'm wondering what happens when it doesn't. Is that error catchable so that it falls back to WMIC?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah our internal automated review tools are flagging the static import at the top as having this exact problem. if the node file doesn't match the node version, the static import will fail. It suggests this instead:

let wpcModule: typeof import('@vscode/windows-process-tree');
try {
    wpcModule = require('@vscode/windows-process-tree');
} catch {
    // fall through to WMIC
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants