Skip to content

fix: make ClaudeCliBackend work on Windows (.cmd shim resolution + argv length) - #98

Merged
Yifan Yang (Yif-Yang) merged 2 commits into
microsoft:mainfrom
codeL1985:fix/windows-claude-cli
Jul 12, 2026
Merged

Yifan Yang (Yif-Yang) merged 2 commits into
microsoft:mainfrom
codeL1985:fix/windows-claude-cli

Conversation

@codeL1985

Copy link
Copy Markdown
Contributor

Problem

On Windows, claude installed via npm is a .cmd shim. subprocess.run(["claude", ...]) raises FileNotFoundError (WinError 2) because CreateProcess does not resolve .cmd files by bare name. The bare except Exception: return "" in ClaudeCliBackend._call swallows this, so every backend call silently returns an empty string — real-backend cycles report held-out 0.000 -> 0.000 => reject with zero edits, which is indistinguishable from "nothing to optimize" (same user-facing symptom as #68, different cause).

Fix

  • Resolve claude_path via shutil.which() in __init__ — it honors PATHEXT and returns the full claude.CMD path.
  • Pass the prompt via stdin instead of argv, in both _call and attempt_with_tools. The .cmd shim routes through cmd.exe, whose command line caps at ~8K chars; reflect/judge prompts routinely exceed that. claude -p with no positional prompt reads stdin, so behavior is unchanged on POSIX.

Verification (Windows 11, Python 3.14, claude CLI 2.1.170)

  • Before: reflect() on a synthetic max_chars failure returned [] (raw _call output was "").
  • After: same call returns a concrete bounded edit through the real CLI; a 12KB stdin prompt round-trips cleanly (rc 0).

🤖 Generated with Claude Code

codeL1985 and others added 2 commits July 3, 2026 10:19
… limit)

Every claude call failed with WinError 2 and was swallowed by the bare
except -> return '', so real-backend cycles silently scored 0.000/0.000
and produced zero edits.

- resolve claude_path via shutil.which: the npm-installed claude is a
  .cmd shim that CreateProcess cannot resolve by bare name
- pass the prompt via stdin instead of argv: the .cmd shim routes
  through cmd.exe whose command line caps at ~8K chars, which
  reflect/judge prompts exceed

Verified: reflect() on a synthetic max_chars failure now returns a
concrete bounded edit via the real CLI (was [] before).

Co-Authored-By: Claude Fable 5 <[email protected]>
…INDOW)

Every CLI subprocess (claude/codex/copilot) spawned from a console-less
parent allocates a visible console window on Windows. A cycle making
hundreds of calls strobes cmd windows and steals focus, making the
machine unusable while the engine runs. Pass CREATE_NO_WINDOW on all
CLI call sites; no-op on POSIX.

Co-Authored-By: Claude Fable 5 <[email protected]>
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.

2 participants