From cc5df17ee57ec9f9de554bd3ce21017cd67d71ed Mon Sep 17 00:00:00 2001 From: karlligamesvc-spec Date: Mon, 13 Jul 2026 05:56:09 -0700 Subject: [PATCH] test(desktop): make windows-child-process needles whitespace-tolerant MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The "desktop background child processes opt into hidden Windows consoles" contract test has been silently broken since 2026-06-12 (d62979a6f, an unrelated feature commit that reformatted 5 spawn/ execFileSync call sites from single-line to multi-line). node --test only ever reported 1 failure because assert throws on the first failing needle and aborts the rest of that test() body — in reality 5 of 9 needles no longer matched. Root cause is test brittleness, not a wiring regression: every affected call site (pyExe python-version probe, git spawn, the two backend.command/args spawns, the uninstall spawn) still correctly wraps its options with hiddenWindowsChildOptions(...), so windowsHide:true is still applied on Windows. No user-visible console-flash regression. Fix: match needles against whitespace-collapsed source/needle text instead of exact substrings, so the assertion tracks call-site shape (identifier adjacency) rather than incidental line-wrapping. Verified the new matcher still catches a real regression (temporarily strayed the pyExe call's hiddenWindowsChildOptions wrapping locally -> test failed as expected; reverted). Co-Authored-By: Claude Fable 5 --- .../electron/windows-child-process.test.cjs | 20 ++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) diff --git a/apps/desktop/electron/windows-child-process.test.cjs b/apps/desktop/electron/windows-child-process.test.cjs index 4239da56e2343..9c9728576cfda 100644 --- a/apps/desktop/electron/windows-child-process.test.cjs +++ b/apps/desktop/electron/windows-child-process.test.cjs @@ -11,10 +11,24 @@ function readElectronFile(name) { return fs.readFileSync(path.join(ELECTRON_DIR, name), 'utf8').replace(/\r\n/g, '\n') } +// Prettier is free to re-wrap a long call's argument list across lines any +// time a nearby edit nudges it over the print width (this is exactly what +// happened in d62979a6f, which reformatted 5 of these call sites from +// single-line to multi-line in an otherwise unrelated feature commit and +// broke every needle below that assumed single-line layout). Matching on +// whitespace-collapsed text makes the assertion track the call site's +// *shape* (identifier order, adjacency) instead of its incidental line +// breaks, so a future reformat can't silently defeat this guard again. +function collapseWhitespace(str) { + return str.replace(/\s+/g, '') +} + function requireHiddenChildOptions(source, needle) { - const index = source.indexOf(needle) + const collapsedSource = collapseWhitespace(source) + const collapsedNeedle = collapseWhitespace(needle) + const index = collapsedSource.indexOf(collapsedNeedle) assert.notEqual(index, -1, `missing call site: ${needle}`) - const snippet = source.slice(index, index + 700) + const snippet = collapsedSource.slice(index, index + 700) assert.match( snippet, /hiddenWindowsChildOptions\(/, @@ -27,7 +41,7 @@ test('desktop background child processes opt into hidden Windows consoles', () = assert.match(source, /function hiddenWindowsChildOptions\(options = \{\}\)/) - requireHiddenChildOptions(source, "execFileSync(\n 'reg'") + requireHiddenChildOptions(source, "execFileSync('reg'") requireHiddenChildOptions(source, 'execFileSync(pyExe') requireHiddenChildOptions(source, 'spawn(resolveGitBinary()') requireHiddenChildOptions(source, "execFileSync('taskkill'")