Skip to content

Commit c5e09e7

Browse files
authored
fix: route Windows .cmd shims through PowerShell to fix Ctrl+C terminal corruption (#1414)
## Summary Running a `node_modules/.bin/*.cmd` shim on Windows — what `vp run <script>` does when resolving `vite`, `tsc`, etc. — triggers `cmd.exe`'s *"Terminate batch job (Y/N)?"* prompt on Ctrl+C. That prompt leaves the terminal in a corrupt state: backspace prints `^H`, Ctrl+C prints `^C`, input becomes sluggish. Pulls in voidzero-dev/vite-task#345 (merged as `c45e5e72`), which teaches the plan layer to rewrite the invocation at plan time: ``` program_path: <abs path to pwsh.exe or powershell.exe> args: [-NoProfile, -NoLogo, -ExecutionPolicy, Bypass, -File, <.ps1 path relative to task cwd>, ...original_args] ``` PowerShell resolves `-File <relative>` against its own working directory (= the task's cwd) and lands on the correct `.ps1`, so Ctrl+C propagates cleanly without the `cmd.exe` hop. The `.ps1` path is **cwd-relative** so `SpawnFingerprint.args` stays portable — no absolute paths leak into cache keys. The rewrite only fires when **all** of these hold: extension is `.cmd`, path lives inside the workspace root, the two last path components are `.bin` / `node_modules` (case-insensitive), a sibling `.ps1` exists, and `pwsh.exe` / `powershell.exe` is on PATH. Any miss keeps the original `.cmd` path — behavior matches pre-merge. Also includes a previously-pushed CI fix: the musl test job disables `crt-static` so `fspy_preload_unix`'s cdylib build doesn't fail after voidzero-dev/vite-task#344 made that crate an unconditional build-dep. Closes #1176 ## Test plan - [x] `cargo check --workspace` clean on macOS - [x] vite-task CI green on the merged PR (includes new Windows-only plan snapshot verifying the rewrite end-to-end across `cwd` and `--filter` invocations) - [ ] vite-plus CI green - [ ] Manual on Windows: reproduce with https://github.com/Curtion/report-vite-plus-1; Ctrl+C during `vp run dev` should leave the terminal clean - [ ] Manual: confirm `.cmd` fallback on a Windows box with PATH stripped of PowerShell - [ ] Manual: confirm a globally installed `.cmd` outside the workspace is *not* rewritten
1 parent 562365d commit c5e09e7

File tree

6 files changed

+73
-49
lines changed

6 files changed

+73
-49
lines changed

.github/workflows/ci.yml

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,13 @@ jobs:
121121
# Pin Rust tooling paths to avoid $HOME mismatch issues.
122122
CARGO_HOME: /root/.cargo
123123
RUSTUP_HOME: /root/.rustup
124+
# `-crt-static`: vite-task's `fspy_preload_unix` cdylib (unconditional
125+
# build-dep since voidzero-dev/vite-task#344) can't link against a
126+
# static musl libc. vite+ ships as a NAPI module that links musl libc
127+
# dynamically anyway, so matching here is correct.
128+
# Must mirror `.cargo/config.toml` rustflags — RUSTFLAGS env overrides
129+
# both [build] and [target.*] levels.
130+
RUSTFLAGS: --cfg tokio_unstable -C link-args=-Wl,--warn-unresolved-symbols -C target-feature=-crt-static
124131
steps:
125132
- name: Install Alpine dependencies
126133
shell: sh {0}

Cargo.lock

Lines changed: 40 additions & 38 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -89,7 +89,7 @@ dunce = "1.0.5"
8989
fast-glob = "1.0.0"
9090
flate2 = { version = "=1.1.9", features = ["zlib-rs"] }
9191
form_urlencoded = "1.2.1"
92-
fspy = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "954cd3bead71be4ddc1e3183110d713bbe26286b" }
92+
fspy = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "c45e5e72d3a17b850310128480e92d3e332c2d5a" }
9393
futures = "0.3.31"
9494
futures-util = "0.3.31"
9595
glob = "0.3.2"
@@ -194,16 +194,16 @@ vfs = "0.13.0"
194194
vite_command = { path = "crates/vite_command" }
195195
vite_error = { path = "crates/vite_error" }
196196
vite_js_runtime = { path = "crates/vite_js_runtime" }
197-
vite_glob = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "954cd3bead71be4ddc1e3183110d713bbe26286b" }
197+
vite_glob = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "c45e5e72d3a17b850310128480e92d3e332c2d5a" }
198198
vite_install = { path = "crates/vite_install" }
199199
vite_migration = { path = "crates/vite_migration" }
200200
vite_setup = { path = "crates/vite_setup" }
201201
vite_shared = { path = "crates/vite_shared" }
202202
vite_static_config = { path = "crates/vite_static_config" }
203-
vite_path = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "954cd3bead71be4ddc1e3183110d713bbe26286b" }
204-
vite_str = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "954cd3bead71be4ddc1e3183110d713bbe26286b" }
205-
vite_task = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "954cd3bead71be4ddc1e3183110d713bbe26286b" }
206-
vite_workspace = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "954cd3bead71be4ddc1e3183110d713bbe26286b" }
203+
vite_path = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "c45e5e72d3a17b850310128480e92d3e332c2d5a" }
204+
vite_str = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "c45e5e72d3a17b850310128480e92d3e332c2d5a" }
205+
vite_task = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "c45e5e72d3a17b850310128480e92d3e332c2d5a" }
206+
vite_workspace = { git = "https://github.com/voidzero-dev/vite-task.git", rev = "c45e5e72d3a17b850310128480e92d3e332c2d5a" }
207207
walkdir = "2.5.0"
208208
wax = "0.6.0"
209209
which = "8.0.0"

packages/cli/snap-tests/npm-install-with-options/snap.txt

Lines changed: 17 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -23,15 +23,28 @@ Run "npm help install" for more info
2323
> vp run install # https://docs.npmjs.com/cli/v10/commands/npm-install
2424
$ vp install --production --silent
2525

26-
---
27-
vp run: npm-install-with-options#install not cached because it modified its input. (Run `vp run --last-details` for full details)
2826

2927
> ls node_modules
3028
@oxlint
3129
tslib
3230

3331
> vp run install # install again hit cache
34-
$ vp install --production --silent
32+
$ vp install --production --silent ◉ cache hit, replaying
3533

3634
---
37-
vp run: npm-install-with-options#install not cached because it modified its input. (Run `vp run --last-details` for full details)
35+
vp run: cache hit, <variable>ms saved.
36+
37+
> vp run --last-details
38+
39+
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
40+
Vite+ Task Runner • Execution Summary
41+
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
42+
43+
Statistics: 1 tasks • 1 cache hits • 0 cache misses
44+
Performance: 100% cache hit rate, <variable>ms saved in total
45+
46+
Task Details:
47+
────────────────────────────────────────────────
48+
[1] npm-install-with-options#install: $ vp install --production --silent ✓
49+
→ Cache hit - output replayed - <variable>ms saved
50+
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

packages/cli/snap-tests/npm-install-with-options/steps.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
"vp install --help # print help message",
44
"vp run install # https://docs.npmjs.com/cli/v10/commands/npm-install",
55
"ls node_modules",
6-
"vp run install # install again hit cache"
6+
"vp run install # install again hit cache",
7+
"vp run --last-details"
78
]
89
}

packages/cli/snap-tests/npm-install-with-options/vite.config.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ export default {
44
tasks: {
55
install: {
66
command: 'vp install --production --silent',
7+
input: [{ auto: true }, '!node_modules/**', '!package-lock.json'],
78
},
89
},
910
},

0 commit comments

Comments
 (0)