fix(run): match environment variable names by platform rules - #747
Merged
Merged
Conversation
wan9chi
added this pull request to stack #748
September 22, 2026 15:38
wan9chi
force-pushed
the
fix/windows-env-name-comparison
branch
from
September 22, 2026 15:40
666eba1 to
32ae3e1
Compare
fspy benchmarklinuxmacoswindows |
wan9chi
removed this pull request from stack #748
September 23, 2026 06:58
Environment variable names ignore ASCII case on Windows, but env maps compare names exactly, so each lookup and override has to handle case by hand. Add `Folded<S, R>`, generic over string storage and case rule, with an `EnvName` alias that follows the platform's rule. `S` may be unsized, so `Folded<OsStr, R>` serves as the borrowed form for map lookups. An optional `serde` feature encodes a value as its storage. Nothing uses the crate yet. Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
Environment variable names ignore ASCII case on Windows, but the env maps used to plan, spawn, and serve tasks compared names exactly. For task command assignments such as `Foo=a FOO=b`, map iteration order decided which value a task saw, and an assignment could fail to replace an inherited variable spelled differently. The `FORCE_COLOR` fallback added a second entry next to a differently spelled parent value, and `VP_RUN_CONCURRENCY_LIMIT` and runner `getEnv` lookups missed differently spelled variables. PATH lookups and prefix queries handled case by hand. Key the env maps in `vt_shell`, `vt_plan`, `vt`, `vt_server`, and `fspy::Command` by `EnvName`, which drops the manual case handling. When an assignment overrides a variable spelled differently, the task gets the assignment's spelling, and its fingerprint entry replaces the one recorded under the other spelling. Cache keys and fingerprints still store plain strings. `TaskParsedCommand` drops its unused wincode and `Diff` derives, which don't support `EnvName` keys. Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
wan9chi
force-pushed
the
fix/windows-env-name-comparison
branch
from
September 24, 2026 02:33
32ae3e1 to
39c1af6
Compare
wan9chi
marked this pull request as ready for review
September 24, 2026 02:49
wan9chi
added a commit
to voidzero-dev/vite-plus
that referenced
this pull request
Sep 25, 2026
Bumps vite-task from `790b152` to `7d69d65`. Changelog: voidzero-dev/vite-task@790b152...7d69d65#diff-06572a96a58dc510037d5efa622f9bec8519bc1beab13c9f251e97e657a9d4ed ## Changes from vite-task - **Changed** A task's cache settings now go inside `cache`, e.g. `cache: { env: ["NODE_ENV"], input: ["src/**"] }`. `cache: true` is the same as `cache: {}`. Top-level `env`, `untrackedEnv`, `input`, and `output` are rejected with an error that points to `vp migrate` ([voidzero-dev/vite-task#749](voidzero-dev/vite-task#749)). - **Fixed** On Windows, environment variable names used by `vp run` match regardless of ASCII letter case ([voidzero-dev/vite-task#747](voidzero-dev/vite-task#747)). - **Fixed** Cached tasks on macOS no longer intermittently fail with `oils I/O error (main): No such process` ([voidzero-dev/vite-task#703](voidzero-dev/vite-task#703)). ## Changes in this PR - `Session::init_with`, `ScriptCommand::envs`, and `SyntheticPlanRequest::envs` now key environment variables by `vt_casefold::EnvName`. The `vite-plus-cli` env maps use the same key type (`EnvMap`), so PATH lookup and env merging follow the platform rules. The hand-written case-insensitive PATH lookups are replaced by `vt::get_path_env`. - Adds `vt_casefold` as a workspace dependency, including the commented local `[patch]` entry. - Regenerates `packages/cli/src/run-config.ts`. - Moves top-level task cache fields under `cache` in CLI snapshot fixtures and a `vp_static_config` test. - Keeps `docs/vite.config.ts` in the old format. Docs deploys build it with the released `vp` from `setup-vp`, and that version rejects a `cache` object. #2814 pins that `vp` version for docs builds, so the first release with this vite-task doesn't break them. - Documents the `cache` object in `docs/config/run.md`. `env`, `untrackedEnv`, `input`, and `output` become `cache.env`, `cache.untrackedEnv`, `cache.input`, and `cache.output`. Updates the examples and links in the cache, run, and automatic data tracking guides and the READMEs. The docs describe only the `cache` object and don't mention the old top-level fields. `vp migrate` support for moving these fields comes in the next PR in this stack.
wan9chi
added a commit
to voidzero-dev/vite-plus
that referenced
this pull request
Sep 26, 2026
Task cache settings now live under `cache`, and `vp migrate` moves existing task settings for you. `vp lint` and `vp fmt` run from a package directory now pick the same config as your editor, and piped `vp` output exits cleanly. ### Breaking Changes Task cache settings in `run.tasks` now go inside `cache` ([#2813](#2813), [#2814](#2814), [#2823](#2823), [vite-task#749](voidzero-dev/vite-task#749)), by @wan9chi. | Old (top level of a task) | New | | --- | --- | | `env` | `cache.env` | | `untrackedEnv` | `cache.untrackedEnv` | | `input` | `cache.input` | | `output` | `cache.output` | `cache: true` is the same as `cache: {}`. After upgrading, a task that still uses the old top-level fields fails with an error that points to `vp migrate`. Run `vp migrate` to move the fields in `vite.config.*` for the workspace root and every package. It warns about tasks in `vite.config.*` that it cannot rewrite safely. Tasks created in other modules, such as by a shared helper function, are not detected, so move their fields by hand; the error lists every task that still needs it. Projects whose tasks do not use these fields need no changes. See the [task cache migration rules](https://viteplus.dev/guide/migrate-rules#task-cache-configuration) and the [`cache` reference](https://viteplus.dev/config/run#cache). ### Highlights - `vp lint` and `vp fmt` run from a package directory now use the same config as Oxlint, Oxfmt, and the language server, so results match your editor. `vp check` still applies the workspace-root settings ([#2807](#2807)), by @fengmk2. - Global `vp` commands now exit cleanly when piped into a command that closes early, such as `vp --version | head -n 1`, instead of aborting with exit code 134 ([#2785](#2785), [#2793](#2793)), by @naokihaba. - Cached tasks on macOS no longer intermittently fail with `oils I/O error (main): No such process` ([vite-task#703](voidzero-dev/vite-task#703)), by @lifeiscontent. ### Features - The bundled tools update `vite@8.3.0` -> `vite@8.3.1`, `rolldown@1.2.9` -> `rolldown@1.2.11`, and `oxlint-tsgolint@7.0.2002` -> `oxlint-tsgolint@7.0.2003` ([#2805](#2805), [#2812](#2812)), by @voidzero-guard[bot]. ### Fixes & Enhancements - Async `defineConfig` callbacks now type-check lint and format options, such as `'warn'` rule severities, the same way as synchronous callbacks, so configs updated by `vp migrate` no longer fail with `TS2769` ([#2803](#2803)), by @TheAlexLichter. - `vp test --help` now lists the Vitest 5 options `--repeats`, `--injectCjsGlobals`, `--fsModuleCache`, `--fsModuleCachePath`, and `--sharedViteServer` ([#2809](#2809)), by @Marve10s. - On Windows, `vp run` now matches environment variable names regardless of letter case ([vite-task#747](voidzero-dev/vite-task#747)), by @wan9chi. ### Docs - The copy prompt dialog no longer nests scroll areas and shows clearer copy feedback ([#2794](#2794), [#2799](#2799)), by @liangmiQwQ and @Boshen. ### Chore - Snapshot tests share prepared packages and one Chromium process, run faster on every platform, and no longer read the live npm registry in the standalone npm fallback case ([#2771](#2771), [#2786](#2786), [#2797](#2797)), by @fengmk2 and @voidzero-guard[bot]. - The snapshot setup check links the local `vite-plus` package into its reference home instead of installing the version under release from npm, so it passes before that version is published ([#2819](#2819)), by @wan9chi. - The preview migration harness installs a project's committed dependencies before running `vp migrate`, so the Vitest 5 migration can read the original Vitest version ([#2822](#2822)), by @wan9chi. - The standalone install workflow loads the generated environment before running `vp env doctor` ([#2790](#2790)), by @naokihaba. ### Bundled Versions | Tool | Version | Source | | --- | --- | --- | | vite | `8.3.1` | [`39ddf7c`](vitejs/vite@39ddf7c) | | rolldown | `1.2.11` | [`8df4219`](rolldown/rolldown@8df4219) | | tsdown | `0.23.0` | [npm](https://npmx.dev/package/tsdown/v/0.23.0) | | vitest | `5.0.1` | [npm](https://npmx.dev/package/vitest/v/5.0.1) | | oxlint | `1.85.0` | [npm](https://npmx.dev/package/oxlint/v/1.85.0) | | oxlint-tsgolint | `7.0.2003` | [npm](https://npmx.dev/package/oxlint-tsgolint/v/7.0.2003) | | oxfmt | `0.70.0` | [npm](https://npmx.dev/package/oxfmt/v/0.70.0) | ### Upgrade ```bash vp upgrade ``` ### New Contributors @Marve10s **Full Changelog**: v1.0.0-rc.0...v1.0.0-rc.1 --- Merging this PR will trigger the release workflow. --------- Co-authored-by: voidzero-guard[bot] <278573678+voidzero-guard[bot]@users.noreply.github.com> Co-authored-by: wan9chi <me@wan9chi.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Motivation
Environment variable names ignore ASCII case on Windows, but the env maps used to plan, spawn, and serve tasks compared names exactly:
Foo=a FOO=b, map iteration order decided which value a task saw, and an assignment could fail to replace an inherited variable spelled differently.FORCE_COLORfallback added a second entry next to a differently spelled parent value.VP_RUN_CONCURRENCY_LIMITand runnergetEnvlookups missed differently spelled variables.Summary
vt_casefold.Folded<S, R>compares a string by the case ruleRwhile keeping its original spelling.EnvName<S>uses the platform's rule (ASCII letters ignore case on Windows; exact elsewhere), andEnvName<OsStr>is the borrowed form for map lookups.vt_shell,vt_plan,vt,vt_server, andfspy::CommandbyEnvName, replacing the manual case handling.TaskParsedCommanddrops its unused wincode andDiffderives, which don't supportEnvNamekeys.Session::init_with,ScriptCommand.envs,SyntheticPlanRequest.envs,SpawnCommand.spawn_envs, andget_path_envnow useEnvNamekeys; callers depend onvt_casefolddirectly.Non-ASCII letters still compare exactly, as documented on
EnvNameCaseRule.