You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
hooks: last-resort python3 probe launches the Microsoft Store redirector on Windows (visible console flash, exit 9009) #4563
Where: graphify/hooks.py, _PYTHON_DETECT, the "Last resort" block — python3 -c "$_GFY_PROBE" is tried before python -c … (0.9.92: L131–135; same order back to 0.8.36 L64–68).
What happens on Windows: with the Microsoft Store app-execution alias enabled (the Windows 10/11 default) and no Store Python installed, command -v python3 in Git Bash resolves to /c/Users/<me>/AppData/Local/Microsoft/WindowsApps/python3 — the AppInstallerPythonRedirector.exe stub. Running it opens a visible console window for ~1.1 s, then exits 9009. So on any machine where the pinned interpreter, .graphify_python, the launcher shebang and the uv-tools scan all miss (removed venv, graphify moved to another env, GUI git client with a minimal PATH), every commit flashes a terminal window before the hook falls through to python.
Environment: Windows 11 Home 23H2 (build 22631), Git for Windows, Windows Terminal 1.24 as default terminal, CPython 3.11.9 (per-user install under %LOCALAPPDATA%\Programs\Python, not the Store build), graphifyy 0.8.36 (probe block unchanged in 0.9.92).
Measured three times from a hidden launcher: ~1.1 s each, one AppInstallerPythonRedirector.exe + OpenConsole.exe per call.
Caveat: on my machine the hook never reached this branch (the pinned interpreter has graphify), so this is measured on the alias directly, not through a hook run.
Suggested fix (either):
on Windows (uname -s = MINGW*/MSYS*/CYGWIN*) probe python before python3; or
skip a python3 whose resolved path contains /WindowsApps/ (case "$(command -v python3)" in */WindowsApps/*) ;; esac).
Related: #287 noted the WindowsApps stub's exit code for the AGENTS.md command; #1416 touches the python3 fallback in skill-claw.md. Neither covers the hook probe or the window flash. The console-window burst from DETACHED_PROCESS is #2253 (fixed in 0.9.29) and is a different mechanism.
Thanks for the precise report. I checked it against v8 (86c57be). The last-resort block in _PYTHON_DETECT (hooks.py:131) tries python3 before python on every platform, so on a machine with the Store alias and python.org's CPython, the hook runs the stub first every time probes 1 to 4 miss.
I don't have a Windows machine, so I reproduced the probe order on Linux instead. I put a fake WindowsApps/python3 at the front of PATH that logs its call, sleeps 1 s and exits 9009, with a real python behind it. Then I ran the v8 probe block. The stub was called first and python was chosen after it, 1.07 s in total.
I have a fix on a branch. It follows your first suggestion: when WINDIR or MSYSTEM is set, the last resort tries python before python3. That's the same Windows check hooks.py already uses for its pipe-handle handling. Everywhere else the order stays python3, then python. Probes 1 to 4, the probe itself, and the "could not locate a Python" message are unchanged. I didn't take the /WindowsApps/ skip, because a real Store Python also lives in WindowsApps, and skipping it there would leave those users with no fallback.
Tests, with sh-script fakes and only the fake interpreters on PATH:
MSYSTEM=MINGW64 or WINDIR set: the stub is neen. Both fail on v8.
Neither set: python3 is still tried first.
On Windows, if python lacks graphify, the hoo
If nothing works, the warning and exit 0 are unchanged.
I also ran the block under dash and BusyBox ash, and both behave the same.
Limits:
None of this ran on Windows. If you can try the branch on your machine once the PR is up, that would close the 2. Installed hooks keep the old order until grain.
If python is itself a Store stub (no real Python on PATH), it still runs once before the warning.
Activity
github-actions commentedon Oct 19, 2026
Thanks for opening this issue, @leonjeng. A maintainer will take a look soon.
If you would like to discuss it in real time, come say hi on our Discord server. For longer-form questions and ideas there is also GitHub Discussions.
To help us triage, please make sure the report includes what you expected, what actually happened, and the steps (and a small sample) to reproduce it.
Deepjyoti-Sarmah commentedon Oct 19, 2026
Thanks for the precise report. I checked it against v8 (86c57be). The last-resort block in _PYTHON_DETECT (hooks.py:131) tries python3 before python on every platform, so on a machine with the Store alias and python.org's CPython, the hook runs the stub first every time probes 1 to 4 miss.
I don't have a Windows machine, so I reproduced the probe order on Linux instead. I put a fake WindowsApps/python3 at the front of PATH that logs its call, sleeps 1 s and exits 9009, with a real python behind it. Then I ran the v8 probe block. The stub was called first and python was chosen after it, 1.07 s in total.
I have a fix on a branch. It follows your first suggestion: when WINDIR or MSYSTEM is set, the last resort tries python before python3. That's the same Windows check hooks.py already uses for its pipe-handle handling. Everywhere else the order stays python3, then python. Probes 1 to 4, the probe itself, and the "could not locate a Python" message are unchanged. I didn't take the /WindowsApps/ skip, because a real Store Python also lives in WindowsApps, and skipping it there would leave those users with no fallback.
Tests, with sh-script fakes and only the fake interpreters on PATH:
I also ran the block under dash and BusyBox ash, and both behave the same.
Limits:
fix: hooks try python before python3 under Git for Windows (Graphify-…
test: hooks try python before python3 under Git for Windows (Graphify…