Repository navigation
Releases: drliuhuan/dsh-plugin-pwsh7
Release list
v0.3.4
Changed
-
The manifest now declares which DSH it is built for (
engines.dsh: ^0.2.0-rc.2) instead of
onlyengines.node. Without that declaration neither the plugin manager nor the market could
answer the host-version question — this plugin showedunknown. -
Verified against DSH desktop 0.2.1-rc.3. Re-checked the integration points before widening
the claim:SandboxPwshExecutorand itsexecute(spec)seam, thePwshLocalExecutor.pwshPath
getter this executor overrides,defineTool, the sandbox'smatchesSignature/
classifyRunnerFailure, and thepwsh-sandboxrow id the bundle patch disables — all still
present and unchanged.
v0.3.3
Changed
- System installs and updates raise the UAC prompt themselves. When the host is not elevated,
the portable installer downloads and extracts the verified archive into the user-writable router
temp directory, then spawns an elevated helper (Start-Process -Verb RunAs) that copies the tree
into the system location and updates the machine PATH. The settings page and setup dialog no
longer stop with "run DSH as administrator"; the job showswaiting for administrator approval (UAC)while the prompt is open, and cancelling it fails the job with a clear message while
leaving the per-user copy untouched. A caller that injects its own administrator check keeps the
strict preflight behavior. - System installs use a versioned side-by-side directory and prepend PATH. A machine-wide
install now lands in…\PowerShell\7\<version>instead of overwriting the existing installation,
so upgrading cannot collide with a runningpwsh.exeor with an official install's files. The
new directory is moved to the front of the machine PATH (and user PATH for user-scope
installs), so other software resolves the upgradedpwsh; the older directory stays behind it.
The elevated helper also records the real PowerShell error in its result file instead of only
an exit code. Relocation/upgrade notices no longer say "moving to system scope" for an install
that was already system-wide.
Fixed
- Settings showed
Version: Unknownwhile the update row named the version. The install
description can only infer a version from a versioned directory orinstalled.pwsh.version, so a
system-level install at…\PowerShell\7\pwsh.exehad none; the update row probespwsh -vand
knew it. The probe result is now cached and used forinstall.version(and the top-level
version) in every snapshot.
Changed
- Settings: one
Updateaction. The maintenance card no longer shows separate update in
user folder / update system-wide buttons; it always offers the single labelUpdate
(升级). A user-folder installation then chooses between Update in place (keeps the user copy
and its PATH entry) and Update and move to system (elevated relocate, removes the user copy and
PATH entry); a system installation updates system-wide. The setup dialog keeps its two explicit
update labels.
v0.3.2
Changed
- Host-side hot paths no longer hit the filesystem in steady state:
readRouterConfigis cached by configmtimeMs/size and invalidated by every in-process
writeRouterConfig(which now also bumps a monotonic generation counter);readDialectis memoized against that generation, so model-prompt assembly does no filesystem
access at all (measured ~0.028 ms → ~0.002 ms per assembly);getRouterStatekeeps its cached detection for 10 s (was 1.5 s) and invalidates on a generation
bump;discoveredPortablePwshPathscaches itsreaddirfor 2 s;/pwsh7/statesnapshots reuse the generation-memoized config values (~0.39 ms → ~0.29 ms).
- Client surfaces poll only when useful: the setup dialog polls only while it is open (SSE
still drives re-opening), both dialog and settings pause polling/SSE while the page is hidden,
and the composer chip polls every 60 s instead of 15 s and skips hidden tabs.
v0.3.1
Added
- Opt-in prompt injection with two levels (
dialectinconfig.json, default off):- Common PowerShell 7 guidance (1,337 chars ≈ 335 tokens/request): states that
pwshis
PowerShell 7 (not bash, not cmd) and lists the bash-only forms that fail with their PowerShell
equivalents (export/NAME=value,[[ ]], heredoc,source,$(...),for … do,
POSIX tools → cmdlets,/dev/null→$null), plus the rewrite-after-a-parser-error rule. - Force PowerShell 7 mode (1,442 chars ≈ 361 tokens/request): additionally substitutes the
PowerShell equivalent when the request names a POSIX tool. Checking it also checks the common
level; the level is normalized soforcecannot be set withoutcommon.
Both are selectable in the setup dialog and on the Settings → PowerShell 7 page, which
disclose the token cost and the measured lift. The prompt section reads the stored level on every
assembly, so a change applies to the next model step with no restart.
- Common PowerShell 7 guidance (1,337 chars ≈ 335 tokens/request): states that
POST /pwsh7/dialect({"common": boolean, "force"?: boolean}) persists the level additively
and returns a fresh state snapshot; the install route accepts the samedialectobject so the
setup dialog can record the choice while it installs.shell_router statusreports the active
level, and the self-check verifies the exact routes.- One-time initial setup dialog even when PowerShell 7 is already present: the overlay now opens
on first load regardless offound, shows the detected version, executable, source
(automatic detection /DSH_PWSH_PATH/ router config) and system-vs-user scope, and lets the
user confirm the prompt-injection level.POST /pwsh7/onboardingstores
onboarding.completed, so later launches stay quiet; a missing executable still reopens it on
every failed run. Confirming after an install records the same flag. - Latest-release check and update actions (
POST /pwsh7/latest): the host resolves the newest
PowerShell 7 release, probes the installed executable and reports
{version, current, updateAvailable, error}in the snapshot (cached five minutes, failures stay
non-fatal). The setup dialog and the settings page show a compact fact list (version, executable,
scope, source); with a user-folder copy they offer Update in user folder and Install
system-wide (elevated, removes the user copy and its PATH entry), and with a system copy they
offer Update system-wide. Dialog copy was shortened to labels instead of paragraphs. - Composer quick toggle (
conversation.input.right, beside the model selector): a compact
pwsh7chip whose text and rounded border follow the level — green for forced, blue for common,
grey for off. Clicking it opens a menu (Off / Common / Force, like the model selector's own
menu); choosing a level asks for confirmation first (Cancel/Switch) because switching
mid-session alters the request prefix and may drop the prompt cache; onlySwitchposts
POST /pwsh7/dialect. The chip polls/pwsh7/stateevery 15 s and hides itself when the host has
no setup routes. - A/B evidence for the contract (
docs/dialect-ab.md): on twelve bash-inviting tasks with
5 samples each, the contract raised the correct-command rate from 38–42% to 98% (the earlier,
shorter draft reached 67–90%); on ordinary phrasing both arms scored 100% (ceiling). - Failure-time dialect hint (
lib/dialect.mjs): a failed command's stderr gets one
[pwsh7]line appended when PowerShell reports a parser error (English and zh-CN) or
"command not recognized", mapping common POSIX names to their PowerShell 7 replacements
(grep→Select-String,cat→Get-Content, …). Delivered by the executor'sexecute
hook; it never changes the exit code or the command itself.
Fixed
- First-run dialog flashed and closed before it could be read: the dialog opened on the first
snapshot, then the next SSE/poll frame (found: true, phaseidle) took the "installed outside
the dialog" branch and closed it. That branch now closes only whenonboarding.completedis
true, so the dialog stays open until the user confirms (or dismisses it). Covered by a client
test that replays the first load plus two state frames.
Tests
test/dialect.test.mjs: prompt levels and normalization, hint selection (parse error / unknown
command / mapped POSIX name / non-parser failure), single-append memoization, success passthrough.test/dialect-config.test.mjs: defaults,forceimpliescommon, key preservation,
prompt-size disclosure, the HTTP route (persist / validate / 405), and the install-route path.test/client.test.mjs: the settings page renders both levels with their disclosed cost, the
setup dialog offers them while the force level stays disabled until common is checked, the
detected-PowerShell state renders the compact fact list, and a user-folder copy with an available
update renders both update buttons plus the system-removal hint.test/setup.test.mjs: the latest-release route (update detected / offline check keeps the
installed state).test/client.test.mjs(composer chip): registration inconversation.input.right, the chip
colour per level, the menu contents, and the confirmation path that posts the chosendialect
only afterSwitch.test/onboarding.test.mjs: default flag, key preservation, snapshot field, and the HTTP route
(persist / validate / 405).
v0.3.0 — PowerShell 7 settings page
dsh-plugin-pwsh7 0.3.0
Highlights
- New PowerShell 7 settings page (settings.section): install status, executable/version, install directory, scope/method, config path, managed/removable flags.
- Self-check (11 checks: executable, version, route, config, install, PATH, shipped packages, sandbox, install job, registered routes, plugin version).
- Route switch between the plugin-managed PowerShell 7 and the system default (falls back to Windows PowerShell 5.1 when no system PS7 exists).
- Uninstall of the plugin-managed per-user portable install (files, temp dir, managed PATH entry; reparse points are never followed).
- Migrate to system scope from the settings page (elevated DSH required; removes the per-user copy afterwards).
- Installation is user-initiated only: the setup dialog and Settings page are the only install surfaces. The model-facing shell_router tool never starts installs or relocation; install/
elocate return guidance. No automatic installation.
Fixes/hardening
- Uninstall/relocation cleanup is confined to the real router root and refuses to follow junctions.
- Install and maintenance operations share one busy slot (HTTP 409); JSON bodies over 4 KiB return 413.
- Self-check reports actually-registered routes and warns instead of "ok" when the sandbox policy probe fails.
- CLIXML stderr from Windows PowerShell is decoded to readable errors (friendly elevation message).
Full test suite: 141 tests, 137 pass, 0 fail, 4 environment-gated skips.
v0.2.2 — User and system installation with PATH support
Supports user and system installation scopes in the Web dialog, setup API, and shell_router tool.
- User installs remain under LOCALAPPDATA; system installs use Program Files and require an elevated DSH host.
- Both persist the executable directory in the matching Windows PATH, preserve existing registry entries and value types, avoid duplicates, refresh the host PATH, and broadcast the environment change.
- Existing installations and winget fallback respect the selected scope. PATH write failures report an installation failure.
Validation: Windows GitHub Actions tests and npm package build passed, including real user/system registry PATH persistence and idempotency checks.
v0.2.1
Fixed
- The bundle patch now disables the stock
pwsh-sandboxrow and inserts the router executor under its own id (pwsh7-executor). DSH treats a patch entry'snameas an assertion against the targeted row, not a replacement, so 0.2.0's id-targeted change was skipped and thepwshtool kept running Windows PowerShell 5.1. test/client.test.mjsnow asserts the disable-and-insert shape of the bundle patch.
v0.2.0
Web setup dialog with live download progress
- The dialog opens when PowerShell 7 is missing — on load and again on every failed
pwshrun. - Download, cancel, retry, and done actions with live bytes, percent, and phase (
downloading → extracting → verifying). - The dialog and
shell_router installshare one install job, so they never race. - New same-origin routes:
/pwsh7/state,/pwsh7/events(SSE + polling fallback),/pwsh7/install,/pwsh7/cancel. - Installer phase callbacks, English/Chinese copy, and 23 new tests for the coordinator, routes, packaging, and render path.
Full changelog: https://github.com/drliuhuan/dsh-plugin-pwsh7/blob/main/CHANGELOG.md
dsh-plugin-pwsh7 0.1.1
0.1.1 - first release published through npm Trusted Publishing (OIDC).
- GitHub Actions (
.github/workflows/publish.yml) publishes on a GitHub Release with provenance; no npm token or OTP secret is used. - Tag/version validation and the full test suite run before publishing.
- README cross-links are now absolute so they render correctly on npm.
- Added
CHANGELOG.mdand enabledpublishConfig.provenance. 0.1.0was the first public release.
dsh-plugin-pwsh7 0.1.0
First public release: a Windows DSH bundle that routes the model-facing pwsh tool to PowerShell 7.
- Replaces the
pwsh-sandboxexecutor row with a PowerShell 7 resolver, keeping the stock sandbox/escalation/job/rendering behavior. - Model-facing
shell_routertool:status/diagnose/install. - Automatic per-user PowerShell 7 installation (official portable zip from GitHub releases; winget fallback; no admin rights).
- Works in
workspace-write,read-onlyanddanger-full-access. - Bilingual README (English/Chinese) and bilingual plugin-manager metadata.
- 49 unit tests (48 pass, 1 network-gated skip).
Install with DSH: plugin_manager action=install_bundle target=dsh-plugin-pwsh7@0.1.0
npm: https://www.npmjs.com/package/dsh-plugin-pwsh7