Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Version numbers not supported for shebang line virtual command /usr/bin/env python on windows #119070

Closed
jacacthomas opened this issue May 15, 2024 · 11 comments
Assignees
Labels
docs Documentation in the Doc dir OS-windows

Comments

@jacacthomas
Copy link

jacacthomas commented May 15, 2024

Documentation

In section 4.8.2 of the docs (Shebang Lines), it is stated that: "Any of the above virtual commands can be suffixed with an explicit version (either just the major version, or the major and minor version)."

This sentence refers to the 4 virtual commands: /usr/bin/env, /usr/bin/python, /usr/local/bin/python, python.

This is correct for the last 3 virtual commands (e.g. /usr/bin/python3.12 works), but not for /usr/bin/env.

Specifically, using either the major version (e.g. "/usr/bin/env python3") or the major and minor version (e.g. "/usr/bin/env python3.12") in the shebang line of a .py file, then calling the .py with the windows launcher, results in the following error: "Python was not found; run without arguments to install from the Microsoft Store, or disable this shortcut from Settings > Manage App Execution Aliases."

Simple solution: change the relevant sentence in the docs to exclude /usr/bin/env: "Any of the above virtual commands (apart from /usr/bin/env) can be suffixed with an explicit version (either just the major version, or the major and minor version)."

Linked PRs

@jacacthomas jacacthomas added the docs Documentation in the Doc dir label May 15, 2024
@zooba
Copy link
Member

zooba commented May 15, 2024

It looks like it decided to launch the launcher stub rather than a regular Python install, which probably means you haven't got the latest version of the launcher (which will avoid doing this).

Disabling the stub from Settings > Manage App Execution Aliases should work, as then the /usr/bin/env python... format won't find a python3.exe on your PATH, or if you install Python 3.12.3 or 3.13.0b1 you will also get the newest launcher that deliberately ignores the one that Windows includes by default.

@eryksun
Copy link
Contributor

eryksun commented May 15, 2024

In the original implementation of the launcher, "python*" commands in "/usr/bin/env" shebangs were special cased to only search registered Python installations. The new implementation of the launcher always searches PATH first, even for "python*" commands.

Generally that's the right behavior, but it does need to skip Microsoft's generic "python*" app links that run "Microsoft.DesktopAppInstaller". This was fixed back in February for Python 3.11.8+ and 3.12.2+. In PowerShell, you can check the version of the launcher using (py --help)[0]. In CMD, use py --help | more and check the first line of the output.

@jacacthomas
Copy link
Author

Update: this problem no longer occurs on my machine (i.e. it works as the docs described).

However I'm confused as to why, since I didn't disable the stub as @zooba suggests, and the launcher version is 3.12.1. All I've done since posting earlier is clone the Python repo and install Visual Studio (I was intending to implement the doc change). It's a mystery.

Thanks both for your comments - I'm happy for this issue to be closed now.

@eryksun
Copy link
Contributor

eryksun commented May 15, 2024

Specifically, using either the major version (e.g. "/usr/bin/env python3") or the major and minor version (e.g. "/usr/bin/env python3.12")

There is no "python3.12" appexec link for the app installer. Microsoft only creates links by default for "python.exe" and "python3.exe". The reason it's finding "python3.exe" is a bug in the launcher's searchPath() function that handles the ".12" file 'extension' in the shebang command. It gets the base name "python3"; compares the ".12" extension to ".exe"; and since it's not ".exe", appends ".exe" to the base name to search for "python3.exe". If the extension isn't ".exe", it should append ".exe" to the original name, not the base name, in order to search for "python3.12.exe".

@zooba
Copy link
Member

zooba commented May 15, 2024

The reason it's finding "python3.exe" is a bug in the launcher's searchPath() function that handles the ".12" file 'extension' in the shebang command.

Not us:

    const wchar_t *ext = L".exe";
    // If the command already has an extension, we do not want to add it again
    if (!lastDot || _comparePath(&filename[lastDot], -1, ext, -1)) {
        if (wcscat_s(filename, MAXLEN, L".exe")) {
            ....

I could imagine SearchPathW doing this though, but we should have already added .exe to the end.

My guess is that it's working now with /usr/bin/env python3.12, which has no stub to be distracted by, and if that one failed earlier it was a different reason from /usr/bin/env python3 (which will have been distracted by the stub).

@zooba zooba closed this as completed May 15, 2024
@eryksun
Copy link
Contributor

eryksun commented May 15, 2024

I just stepped through the code in the debugger before writing that post. It's a bug in the launcher. The contents of filename are set by wcsncpy_s(filename, MAXLEN, command, lastDot), where lastDot is the count up to the last dot in the command. So filename does not include the ".12" extension when _comparePath() is called, and filename[lastDot] is the null character. It ends up appending ".exe" to the base name "python3".

@zooba
Copy link
Member

zooba commented May 15, 2024

The contents of filename are set by wcsncpy_s(filename, MAXLEN, command, lastDot), where lastDot is the count up to the last dot in the command.

Okay, yeah, that's a bug. That means the _comparePath() call has never done anything useful.

Have I ever mentioned how much I wish we didn't try to support these shebang templates 🙃

@zooba zooba reopened this May 15, 2024
@zooba zooba self-assigned this May 22, 2024
zooba added a commit to zooba/cpython that referenced this issue May 22, 2024
zooba added a commit to zooba/cpython that referenced this issue May 22, 2024
zooba added a commit to zooba/cpython that referenced this issue May 22, 2024
miss-islington pushed a commit to miss-islington/cpython that referenced this issue May 29, 2024
… extension (pythonGH-119426)

(cherry picked from commit df93f5d)

Co-authored-by: Steve Dower <steve.dower@python.org>
zooba added a commit to zooba/cpython that referenced this issue May 29, 2024
zooba added a commit that referenced this issue May 29, 2024
…sion (GH-119426)

(cherry picked from commit df93f5d)

Co-authored-by: Steve Dower <steve.dower@python.org>
@encukou
Copy link
Member

encukou commented May 31, 2024

test_launcher now fails on Windows buildbots, e.g. here & here:

======================================================================
FAIL: test_shebang_executable_extension (test.test_launcher.TestLauncher.test_shebang_executable_extension)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "D:\buildarea\3.x.bolen-windows10\build\Lib\test\test_launcher.py", line 770, in test_shebang_executable_extension
    data = self.run_py([script])
  File "D:\buildarea\3.x.bolen-windows10\build\Lib\test\test_launcher.py", line 254, in run_py
    self.assertEqual(expect_returncode, p.returncode)
    ~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
AssertionError: 0 != 103
Stdout:
++ COMMAND ++
[WindowsPath('D:/buildarea/3.x.bolen-windows10/build/PCbuild/amd64/py_d.exe'), WindowsPath('D:/buildarea/3.x.bolen-windows10/build/build/test_python_1300�/tmpn00o3m8y.py')]
++ STDOUT ++
++ STDERR ++
argv0: D:\buildarea\3.x.bolen-windows10\build\PCbuild\amd64\py_d.exe
version: 3.14.0a0
# Read 26 bytes from D:\buildarea\3.x.bolen-windows10\build\build\test_python_1300?\tmpn00o3m8y.py to find shebang line
Shebang: /usr/bin/env python3.12
# Search PATH for python3.12.exe
# Did not find python3.12.exe on PATH
# Reading from C:\Users\db3l\AppData\Local\py.ini for commands/python3.12
# Did not find file C:\Users\db3l\AppData\Local\py.ini
# Reading from D:\buildarea\3.x.bolen-windows10\build\PCbuild\amd64\py.ini for commands/python3.12
# Did not find file D:\buildarea\3.x.bolen-windows10\build\PCbuild\amd64\py.ini
# Treating shebang command '3.12' as 'py -3.12'
# Cannot select defaults for tag '3.12'
SearchInfo.originalCmdLine: D:\buildarea\3.x.bolen-windows10\build\PCbuild\amd64\py_d.exe D:\buildarea\3.x.bolen-windows10\build\build\test_python_1300?\tmpn00o3m8y.py
SearchInfo.restOfCmdLine:  D:\buildarea\3.x.bolen-windows10\build\build\test_python_1300?\tmpn00o3m8y.py
SearchInfo.executablePath: (null)
SearchInfo.scriptFile: D:\buildarea\3.x.bolen-windows10\build\build\test_python_1300?\tmpn00o3m8y.py
SearchInfo.executable: python_d.exe
SearchInfo.executableArgs: 
SearchInfo.company: (null)
SearchInfo.tag: 3.12
SearchInfo.oldStyleTag: True
SearchInfo.lowPriorityTag: True
SearchInfo.allowDefaults: True
SearchInfo.allowExecutableOverride: True
SearchInfo.windowed: False
SearchInfo.list: False
SearchInfo.listPaths: False
SearchInfo.help: False
SearchInfo.limitToCompany: (null)
# PythonTestSuite/ignored has no executable path
 -V:3.11          C:\Python\3.11\python.exe
 -V:2.7           C:\Python\2.7\python_d.exe
 -V:PythonTestSuite/3.100 X.Y.exe
 -V:PythonTestSuite/3.100-32 X.Y-32.exe
 -V:PythonTestSuite/3.100-arm64 X.Y-arm64.exe -X fake_arg_for_test
 -V:PythonTestSuite1/3.100 D:\buildarea\3.x.bolen-windows10\build\PCbuild\amd64\python_d.exe
No suitable Python runtime found
Pass --list (-0) to see all detected environments on your machine
or set environment variable PYLAUNCHER_ALLOW_INSTALL to use winget
or open the Microsoft Store to the requested version.

@zooba
Copy link
Member

zooba commented May 31, 2024

On it. We should ignore the exit code for this test - there's a single debug message we're looking for.

zooba added a commit to zooba/cpython that referenced this issue May 31, 2024
@zooba
Copy link
Member

zooba commented May 31, 2024

See #119846

encukou pushed a commit that referenced this issue Jun 4, 2024
miss-islington pushed a commit to miss-islington/cpython that referenced this issue Jun 4, 2024
…se non-installed version (pythonGH-119846)

(cherry picked from commit 5c48eb0)

Co-authored-by: Steve Dower <steve.dower@python.org>
miss-islington pushed a commit to miss-islington/cpython that referenced this issue Jun 4, 2024
…se non-installed version (pythonGH-119846)

(cherry picked from commit 5c48eb0)

Co-authored-by: Steve Dower <steve.dower@python.org>
encukou pushed a commit that referenced this issue Jun 4, 2024
…use non-installed version (GH-119846) (#GH-120015)

gh-119070: Update test_shebang_executable_extension to always use non-installed version (GH-119846)
(cherry picked from commit 5c48eb0)

Co-authored-by: Steve Dower <steve.dower@python.org>
encukou pushed a commit that referenced this issue Jun 4, 2024
…use non-installed version (GH-119846) (GH-120016)

gh-119070: Update test_shebang_executable_extension to always use non-installed version (GH-119846)
(cherry picked from commit 5c48eb0)
@encukou
Copy link
Member

encukou commented Jun 4, 2024

Thanks for the fix!

@encukou encukou closed this as completed Jun 4, 2024
barneygale pushed a commit to barneygale/cpython that referenced this issue Jun 5, 2024
noahbkim pushed a commit to hudson-trading/cpython that referenced this issue Jul 11, 2024
noahbkim pushed a commit to hudson-trading/cpython that referenced this issue Jul 11, 2024
estyxx pushed a commit to estyxx/cpython that referenced this issue Jul 17, 2024
estyxx pushed a commit to estyxx/cpython that referenced this issue Jul 17, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
docs Documentation in the Doc dir OS-windows
Projects
None yet
Development

No branches or pull requests

4 participants