Repository navigation
test(web): isolate startup fixtures from inherited npm_execpath casing - #186
Merged
Merged
Conversation
pnpm script invocations on Windows expose npm_execpath as NPM_EXECPATH. The fixture's exact-case delete left the inherited key in the child environment, so the launcher used the real pnpm instead of the fixture shim/entry: migrations exited 0 without writing the marker and the exit-7 gate served anyway. Remove every case variant before the runner is selected and cover both runner modes with a regression that restores the inherited value.
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.
Problem
The final-verification full suite (
pnpm --filter @macro-tracker/web test, Windows,work/final-verification/web-vitest-rerun.log) failed exactly 3 tests inapps/web/tests/unit/startup-process.test.ts:runs migrations then serves and terminates on kill on Windows—ENOENT ...\macro-startup-*\migrationruns the package manager entry provided through npm_execpath— same migration marker missingfails startup without serving when migrations fail—readyresolved instead of rejectingDirect
vitestruns of the same file passed, so the failure depended on how the suite was launched. It reproduced with no backend listening (no PORT/BACKEND_URL involvement).Root cause
pnpm runon Windows exposes the package manager entry asNPM_EXECPATH(uppercase) alongsideNPM_NODE_EXECPATH;pnpm exec/direct vitest do not. The fixture's exact-casedelete env.npm_execpathleft the inherited uppercase key in the child environment, so the copied launcher preferred the realpnpm.cjsover the fixture shim/entry. Migrations then exited 0 without writing themigrationmarker, and the exit-7 fixture never failed.Evidence from the instrumented reproduction:
npm_execpath=C:\...\corepack\v1\pnpm\10.28.2\bin\pnpm.cjs, withhasKey:falsefor the lowercase name andkeys:["NPM_EXECPATH","NPM_NODE_EXECPATH"]at spawn time.getPackageManagerCommandresolvednode ...pnpm.cjs --filter @macro-tracker/db db:migratefor both runner modes.pnpm test(script) vspnpm exec vitest(uppercase vs none) — seework/startup-final/logs referenced below.Fix (test-only, no application code)
removeCaseInsensitiveEnvKey(env, "npm_execpath")so every case variant of the inherited variable is removed before the runner is selected; thenode-entrybranch then sets its own entry, thepath-shimbranch falls back to PATH.npm_execpath(decoy.cjsentry that exits 0 without recording migrations) for both runner modes, restoring the inherited value afterwards.Verification (Windows, Node 24.20.0 / pnpm 10.28.2)
pnpm --filter @macro-tracker/web test -- tests/unit/startup-process.test.tstest-faults)pnpm --filter @macro-tracker/web typecheck/lintLogs:
C:/Users/lnieu/Documents/macro-tracker-audit-20260917/work/startup-final/(prefix-targeted2.log,postfix-targeted.log,postfix-verifierenv-targeted.log,postfix-full-suite2.log).Linux CI still runs the POSIX signal cases; the fixture regression is meaningful on Windows and harmless on POSIX, where environment names are case-sensitive.