Skip to content

feat(workspaces): add list and launch CLI - #51114

Open
Boliang Zhang (LegendaryBlair) wants to merge 3 commits into
microsoft:mainfrom
LegendaryBlair:prototype/workspaces-cli
Open

Boliang Zhang (LegendaryBlair) wants to merge 3 commits into
microsoft:mainfrom
LegendaryBlair:prototype/workspaces-cli

Conversation

@LegendaryBlair

@LegendaryBlair Boliang Zhang (LegendaryBlair) commented Oct 8, 2026 •

Copy link
Copy Markdown
Contributor

Summary of the Pull Request

Add a supported Workspaces CLI for discovering saved workspaces and synchronously launching one through the existing Workspaces engine.

Related to #49900. This implements the agreed list and launch subset; capture/create and other workspace CRUD operations are out of scope, so this PR does not automatically close the broader proposal.

PowerToys.Workspaces.CLI.exe list --json
PowerToys.Workspaces.CLI.exe list --id "{workspace-guid}" --details --json
PowerToys.Workspaces.CLI.exe launch --name "Development" --json
PowerToys.Workspaces.CLI.exe launch --id "{workspace-guid}" --timeout 120 --json

This is a draft for implementation review. Local x64 Debug validation is complete for the scenarios below; outstanding release/installer checks are explicitly listed rather than represented as passing.

PR Checklist

  • Related to [Workspaces] Add supported list, launch, and capture CLI #49900; automatic issue closure is N/A because capture/create are not included.
  • Communication: Confirm the narrowed scope and implementation with core contributors.
  • Tests: Added/updated; executed local test slices pass. Full CI and the remaining release matrix are not claimed as complete.
  • Localization: CLI help, prompts and user-facing error messages use resources; editor save failures have a localized message.
  • Dev docs: Added doc/devdocs/modules/workspaces-cli.md and the local build/testing README.
  • New binaries: Register the CLI in PowerToys.slnx, tools/CliShim/CliShimManifest.props, .pipelines/ESRPSigning_core.json and installer/PowerToysSetupVNext/CliShims.wxs; include payload and wrapper in installer process shutdown.
  • CI/release YAML: No separate new pipeline is introduced. The existing solution build, unit-test discovery, shared shim and signing infrastructure are reused. Interactive fixture tests remain explicitly opt-in.
  • Documentation updated: Public user documentation in the separate docs repository remains follow-up work; developer documentation is included here.

Detailed Description of the Pull Request / Additional comments

Command and output contract

  • list reads saved data without launching applications or modifying the workspace. Select by GUID or exact case-insensitive name; ambiguous names fail. Braced/unbraced GUIDs and either hex case are accepted, while output preserves stored IDs.
  • Successful list --json returns only top-level view and workspaces. Summary entries reuse id, name and applications[].application; detail uses the existing native serializer. Arrays, saved application order and duplicates are preserved.
  • Public JSON is one indented UTF-8 document. Errors remain structured with nonzero exit codes. launch retains its status/result/warnings envelope, distinguishing complete, partial and failed outcomes.
  • Launch waits for the final arrangement result and metadata outcome using one immutable workspace snapshot. The deadline is configurable from 1 to 600 seconds, defaulting to 120. Cancellation does not kill already-started applications or undo window moves.
  • Effective user/GPO-disabled Workspaces is rejected. The CLI does not enable the module, require a running Runner, create a daemon, or replace the saved configuration.

Reuse, PATH integration and privilege boundaries

  • src/modules/Workspaces/WorkspacesCLI links shared Workspaces logic and reuses the launcher/arranger rather than introducing another application-launch engine.
  • The existing native wrapper at bin\PowerToys.Workspaces.CLI.exe forwards to the real PowerToys.WorkspacesCLI.exe payload. Only bin belongs on PATH; self-contained application/DLL directories are not added.
  • Workspaces-owned progress/editor/error UI is suppressed, but normal Windows UAC remains. The existing unverified-elevated-EXE trust gate is retained.
  • When confirmation is required, the foreground terminal offers Allow once or Skip (default). Prompts use stderr and a separate bounded request/reply channel; stdout JSON stays separate. EOF, redirected/unavailable input, timeout or cancellation never implicitly approve a target.
  • Same-user administrator terminals keep their original console while WorkerHandoff creates and verifies a Medium-integrity worker through the normal Explorer context. It transfers only restricted operation handles, never a token or general administrator-process capability. Failure to obtain the correct user/session/context fails closed.
  • Operation IPC validates peer identity, image/version and session, requiring Microsoft-signed peers in Release. src/common/interop/pipe_caller_auth.* adds server verification using the existing client policy implementation without weakening Runner policies.

Persistence and review focus

  • Native and managed writers coordinate history updates through a shared lock and fresh-read/atomic-replace logic. A successful layout with a nonessential history-save failure returns a warning; unverified replacement remains a failure.
  • WorkspacesCsharpLibrary/Utils/IOUtils.cs and editor save handling preserve newer history and retain edits when saving fails. This is directly coupled to avoiding lost updates when CLI launches and the editor share the same workspace store.
  • Please pay particular attention to administrator-to-Medium handoff/capabilities, confirmation lifetime, bidirectional IPC identity validation, writer coordination, and installer/signing integration.
  • No new third-party dependency or CLI telemetry is added. Local builds intentionally share the current user's installed Workspaces data.

User-provided screenshots

1. Saved-workspace discovery (list --json). The terminal output shows the simplified top-level view: "summary" and workspaces array, without a schemaVersion/command/state/result wrapper. Each entry preserves the saved braced GUID, workspace name and minimal application names.

Workspaces CLI list JSON with top-level view and workspaces, saved GUIDs and minimal application names

2. Terminal confirmation and partial launch (launch --id ... --json). The unbraced GUID is accepted. The shared trust gate reports invalid-signature (0x80096010) for the configured elevated TamperedSignature.exe; the user explicitly selects A (Allow once). The final response reports two applications as arranged, Terminal as arrangeFailed, aggregate state: "partial", persistenceStatus: "updated" and an empty warnings array.

The second screenshot demonstrates the confirmation and partial-result contract, not an all-apps-successful launch or a Windows UAC test. A read-only investigation separately reproduced an existing shared Workspaces matching limitation: a running older Terminal package can no longer match the refreshed package path/display name. That shared-engine issue is not fixed or hidden by this CLI PR; the CLI correctly does not report complete success.

Workspaces CLI launch with explicit Allow once confirmation, two arranged applications, Terminal arrangeFailed and updated persistence

Validation Steps Performed

Current local x64 Debug evidence

  • Rebuilt the CLI, matching window arranger and native test project after simplifying list output.
  • 33/33 focused tests passed after the final list change: CliContractTests, CliJsonOutputTests and CliApprovalTests. Coverage includes the exact flat list shape, empty arrays, existing payload fields, errors, unchanged launch results and JSON formatting.
  • Read-only executable checks compare summary/detail payload and human-readable output hashes against the prior build. GUID/name selectors, clean redirected JSON stdout, invalid arguments and missing-workspace error exits retain their behavior.
  • Before publication, moved only the new Workspaces shim registration blocks to avoid textual insertion conflicts with main's new Settings CLI entries; XML registration contents are unchanged. Rebuilt the shim/tests and CLI, passed 8/8 shim tests, and checked wrapper/payload equivalence against the current saved workspace data.
  • 131/131 selected regression tests passed before the final list-only change, covering the integrated approval/de-elevation implementation and related Workspaces behavior. This is not presented as a full repository test run or as 131 tests rerun after the last change.
  • A controlled real administrator-frontend fixture verified a same-user/session Medium worker, read-only snapshot, wait-only cancellation/owner handles, and Allow/Skip/cancel round-trips. That fixture did not launch workspace applications.
  • The author manually verified the local version and supplied the two screenshots described above.
  • git diff --check passed.

Earlier supporting evidence and remaining gates

Earlier implementation stages also built the editor/managed tests, x64 Release and ARM64 Debug CLI/arranger, and installer custom actions, and exercised shim/peer-identity/persistence tests. Those earlier Release/ARM64 builds do not cover the latest confirmation, de-elevation and list-output changes.

Still required before release/merge sign-off:

  • Fresh final-source Release/ARM64 builds and CI results.
  • Signed per-user/per-machine installer install/upgrade, custom paths, PATH layout and running-process shutdown.
  • Positive signed Release IPC and ARM64 runtime checks.
  • Full real-app UAC accept/deny/pending-timeout cases from normal and administrator terminals, without bypassing the Windows consent UI.
  • Multi-monitor/mixed-DPI/topology and broader packaged/PWA/existing-window scenarios.
  • Interactive editor save-failure/concurrent-history checks and different-user/missing-shell rejection scenarios.

Reproduction/build instructions and compatibility boundaries are in doc/devdocs/modules/workspaces-cli.md and src/modules/Workspaces/WorkspacesCLI/README.md.

Add the PATH-visible shim, saved-workspace discovery and synchronous launch with terminal trust confirmation, verified non-elevated workers and coordinated launch-history persistence.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 664ee900-ce2d-4112-ac57-395314d818dc
Move only the new Workspaces entries so current main can retain its Settings CLI additions. Registration contents and installed mappings are unchanged.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 664ee900-ce2d-4112-ac57-395314d818dc
@github-actions

github-actions Bot commented Oct 8, 2026

Copy link
Copy Markdown

🧭 PR intake

Visual evidence: Not needed — The changed files do not indicate a visible UI change. Visual evidence was detected in the PR description.

Recommendation

Link the issue this PR fixes using a closing keyword such as Closes #123.

✅ Ready for review

This PR passed the automated intake checks and is ready for maintainer review.

Automated PR intake; PowerToys maintainers make final decisions.

Copilot AI left a comment

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.

🟡 Changes recommended

A failed new-workspace save currently removes excluded applications from the retained editor model before persistence succeeds.

1 open finding
What changed in this PR

Adds a supported Workspaces CLI for listing saved workspaces and synchronously launching them through the existing engine.

Changes:

  • Adds CLI parsing, JSON output, localization, shim, signing, and installer integration.
  • Adds authenticated worker/arranger IPC, administrator de-elevation, confirmation, cancellation, and result handling.
  • Coordinates native and managed workspace persistence and adds focused tests and documentation.
File Description
tools/​CliShim/​CliShimManifest.props Registers the CLI shim target.
src/​modules/​Workspaces/​WorkspacesWindowArranger/​WindowArranger.h Adds CLI IPC state.
src/​modules/​Workspaces/​WorkspacesWindowArranger/​WindowArranger.cpp Returns final arranger results.
src/​modules/​Workspaces/​WorkspacesWindowArranger/​main.cpp Adds CLI arranger mode.
src/​modules/​Workspaces/​WorkspacesLib/​WorkspaceStore.h Defines coordinated persistence API.
src/​modules/​Workspaces/​WorkspacesLib/​WorkspaceStore.cpp Implements locked atomic writes.
src/​modules/​Workspaces/​WorkspacesLib/​WorkspacesLib.vcxproj.filters Registers new library sources.
src/​modules/​Workspaces/​WorkspacesLib/​WorkspacesLib.vcxproj Builds CLI and authentication support.
src/​modules/​Workspaces/​WorkspacesLib/​two_way_pipe_message_ipc.cpp Adds peer authentication and limits.
src/​modules/​Workspaces/​WorkspacesLib/​OperationLifetime.h Bounds worker lifetime.
src/​modules/​Workspaces/​WorkspacesLib/​JsonUtils.cpp Routes writes through the store.
src/​modules/​Workspaces/​WorkspacesLib/​IPCHelper.h Extends authenticated IPC API.
src/​modules/​Workspaces/​WorkspacesLib/​IPCHelper.cpp Implements peer policy and callback replacement.
src/​modules/​Workspaces/​WorkspacesLib/​CliCommands.h Defines CLI contracts.
src/​modules/​Workspaces/​WorkspacesLib/​CliCommands.cpp Implements parsing, selection, and results.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​WorkspaceStoreTests.cpp Tests coordinated persistence.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​WorkspacesLibUnitTests.vcxproj.filters Registers new tests.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​WorkspacesLibUnitTests.vcxproj Builds CLI test slices.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​CliWorkerTests.cpp Tests worker launch behavior.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​CliJsonOutputTests.cpp Tests JSON formatting.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​CliHandoffTests.cpp Tests de-elevation handoff.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​CliContractTests.cpp Tests public CLI contracts.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​CliApprovalTests.cpp Tests approval protocol behavior.
src/​modules/​Workspaces/​WorkspacesLib.UnitTests/​CliApprovalConsoleTests.cpp Tests isolated console prompts.
src/​modules/​Workspaces/​WorkspacesLauncher/​WindowArrangerHelper.h Extends arranger launch API.
src/​modules/​Workspaces/​WorkspacesLauncher/​WindowArrangerHelper.cpp Launches operation-scoped arrangers.
src/​modules/​Workspaces/​WorkspacesLauncher/​main.cpp Uses coordinated metadata writes.
src/​modules/​Workspaces/​WorkspacesLauncher/​Launcher.h Exposes synchronous CLI results.
src/​modules/​Workspaces/​WorkspacesLauncher/​Launcher.cpp Integrates CLI cancellation and results.
src/​modules/​Workspaces/​WorkspacesLauncher/​AppLauncher.h Exposes native launch errors.
src/​modules/​Workspaces/​WorkspacesLauncher/​AppLauncher.cpp Captures per-application errors.
src/​modules/​Workspaces/​WorkspacesEditor/​WorkspacesEditorPage.xaml.cs Keeps the editor open after failed saves.
src/​modules/​Workspaces/​WorkspacesEditor/​ViewModels/​MainViewModel.cs Makes editor updates transactional.
src/​modules/​Workspaces/​WorkspacesEditor/​Utils/​WorkspacesEditorIO.cs Reports save success and failure.
src/​modules/​Workspaces/​WorkspacesEditor/​Properties/​Resources.resx Adds localized save failure text.
src/​modules/​Workspaces/​WorkspacesEditor/​Properties/​Resources.Designer.cs Exposes the new resource.
src/​modules/​Workspaces/​WorkspacesEditor/​Models/​Project.cs Preserves project timestamps when copying.
src/​modules/​Workspaces/​WorkspacesCsharpLibrary/​Utils/​IOUtils.cs Adds managed locking and atomic replacement.
src/​modules/​Workspaces/​WorkspacesCsharpLibrary.UnitTests/​WorkspaceWriteTests.cs Tests managed persistence.
src/​modules/​Workspaces/​WorkspacesCsharpLibrary.UnitTests/​WorkspacesCsharpLibrary.UnitTests.csproj Adds the managed test project.
src/​modules/​Workspaces/​WorkspacesCLI/​WorkspacesCLI.vcxproj Defines and stages the CLI executable.
src/​modules/​Workspaces/​WorkspacesCLI/​WorkspacesCLI.base.rc Adds executable version metadata.
src/​modules/​Workspaces/​WorkspacesCLI/​WorkerHandoff.h Defines restricted worker capabilities.
src/​modules/​Workspaces/​WorkspacesCLI/​Tests/​WindowFixture/​WindowFixture.vcxproj Builds the window fixture.
src/​modules/​Workspaces/​WorkspacesCLI/​Tests/​WindowFixture/​main.cpp Implements the disposable test window.
src/​modules/​Workspaces/​WorkspacesCLI/​Tests/​HandoffFixture/​version.rc Versions the handoff fixture.
src/​modules/​Workspaces/​WorkspacesCLI/​Tests/​HandoffFixture/​main.cpp Exercises restricted handoff behavior.
src/​modules/​Workspaces/​WorkspacesCLI/​Tests/​HandoffFixture/​HandoffFixture.vcxproj Builds the handoff fixture.
src/​modules/​Workspaces/​WorkspacesCLI/​Tests/​ApprovalConsoleFixture/​main.cpp Exercises terminal approval scenarios.
src/​modules/​Workspaces/​WorkspacesCLI/​Tests/​ApprovalConsoleFixture/​ApprovalConsoleFixture.vcxproj Builds the approval fixture.
src/​modules/​Workspaces/​WorkspacesCLI/​Resources.h Maps localized CLI resources.
src/​modules/​Workspaces/​WorkspacesCLI/​Resource.resx Defines CLI-facing strings.
src/​modules/​Workspaces/​WorkspacesCLI/​resource.base.h Provides the resource header base.
src/​modules/​Workspaces/​WorkspacesCLI/​README.md Documents development and testing.
src/​modules/​Workspaces/​WorkspacesCLI/​JsonOutput.h Formats indented JSON output.
src/​modules/​Workspaces/​WorkspacesCLI/​ConsoleApproval.h Defines console confirmation handling.
src/​modules/​Workspaces/​WorkspacesCLI/​ConsoleApproval.cpp Implements fail-closed terminal prompts.
src/​modules/​Workspaces/​WorkspacesCLI/​CommandLogging.h Sanitizes CLI diagnostics.
src/​modules/​Workspaces/​WorkspacesCLI/​ApprovalChannel.h Defines framed approval IPC.
src/​modules/​Workspaces/​WorkspacesCLI/​ApprovalChannel.cpp Implements approval request/reply handling.
src/​common/​UnitTests-CommonUtils/​PipeCallerAuth.Tests.cpp Tests server identity validation.
src/​common/​interop/​pipe_caller_auth.h Adds server authentication API.
src/​common/​interop/​pipe_caller_auth.cpp Reuses process authentication for servers.
PowerToys.slnx Registers the CLI and managed tests.
installer/​PowerToysSetupVNext/​CliShims.wxs Installs the Workspaces shim.
installer/​PowerToysSetupCustomActionsVNext/​CustomAction.cpp Stops CLI processes during servicing.
doc/​devdocs/​modules/​workspaces-cli.md Documents the public CLI contract.
.pipelines/​ESRPSigning_core.json Adds the CLI payload to signing.
Files not reviewed (1)
  • src/modules/Workspaces/WorkspacesEditor/Properties/Resources.Designer.cs: Generated file

🧠 Review effort: Balanced


Give feedback about Copilot approvals in this survey to enter a drawing for a $150 gift card.

Comment thread src/modules/Workspaces/WorkspacesEditor/ViewModels/MainViewModel.cs
Defer excluded-application removal and preview initialization until persistence succeeds. Exercise failure preservation, re-inclusion and retry, and post-save filtering through a small internal persistence seam without touching real settings or editor UI.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 664ee900-ce2d-4112-ac57-395314d818dc

This branch has not been deployed

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

Labels

0.102 Product-Workspaces Refers to the Workspaces utility Ready for review

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants