Skip to content

fix: run a .cmd or .bat gortex shim through cmd.exe for the hook - #40

Merged
vitaliyslion merged 1 commit into
mainfrom
fix/windows-cmd-shim
Oct 24, 2026
Merged

vitaliyslion merged 1 commit into
mainfrom
fix/windows-cmd-shim

Conversation

@vitaliyslion

@vitaliyslion vitaliyslion commented Oct 24, 2026 •

Copy link
Copy Markdown
Collaborator

Summary

With gortex installed as a .cmd or .bat shim on Windows (npm's global install), the hook bridge never ran. Node refuses to spawn batch files directly (EINVAL), and callHook swallowed the error. Pi's MCP spawns through cross-spawn, so the graph tools connected and the session looked healthy, but there was no briefing, no read discipline and no version check, and nothing reported it.

  • src/runtime.ts: when a command resolves to a .cmd or .bat on Windows, the process seam runs it through cmd.exe with cross-spawn's escaping. The command is passed as written, so cmd.exe searches PATH the same way it does for Pi's MCP.
  • Resolution on Windows follows cross-spawn too: PATHEXT extensions, and the bare name only when it already carries one. Before, the extensionless sh script npm puts beside gortex.cmd matched first, and Windows cannot spawn it. binaryResolves now uses this shared resolver.

Reproduction

Reproduced end to end under Windows Node 24 running in Wine in a Podman container. The extension ran under Pi's runner with its real process seam, and gortex was installed with npm's .cmd shim template and the sh script beside it, in a directory with spaces and parentheses.

before after
binaryResolves("gortex") true true
MCP tools connect (cross-spawn) yes yes
Briefing on first turn no yes
Pi read blocked by the hook no yes
Hook calls reaching gortex none session_start, tool_call Read

Closes #37

Testing

  • npm run check passes
  • New behaviour has a suite that drives it through Pi's ExtensionRunner (see docs/tests.md): test/runtime.test.ts tests the process seam directly, since the hook double replaces exactly this seam in the runner suites. The Wine repro above covered the runner path.
  • Tried by hand in Pi (pi -e /path/to/checkout), if user-visible: not on a real Windows machine.

test/runtime.test.ts tests resolution and escaping as pure functions on every OS, and spawns real batch files on Windows only. Under Wine, the test that runs a .bat by a path with spaces fails. cross-spawn fails on the same path under Wine too, and the test passes on the windows-latest CI job, so the failure was Wine's cmd.exe.

Checklist

  • No runtime dependencies added
  • README configuration table updated, if config changed (no config change)
  • docs/architecture.md updated briefly, only if a design decision changed (no design decision changed)
  • Works on Windows paths and process spawning, if touching either: Wine repro, and the batch file spawn tests pass on windows-latest

Node refuses to spawn batch files directly, so with gortex installed as
an npm shim the hook bridge failed silently: no briefing, no read
discipline, no version check, while Pi's MCP connected the tools through
cross-spawn. The process seam now runs such a command through cmd.exe
with cross-spawn's escaping.

Resolution on Windows also follows cross-spawn: PATHEXT extensions, and
the bare name only when it already carries one, so the sh script npm
puts beside its .cmd shim no longer passes the binary check.

Closes #37
@vitaliyslion
vitaliyslion merged commit 781f20c into main Oct 24, 2026
3 checks passed
@vitaliyslion
vitaliyslion deleted the fix/windows-cmd-shim branch October 24, 2026 19:13
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

On Windows, a .cmd or .bat gortex shim passes the binary check but the hook cannot run it

1 participant