pypa / pipx

Install and Run Python Applications in Isolated Environments
https://pipx.pypa.io
MIT License
10.07k stars 406 forks source link

pipx ensurepath fails on last Alpine (3.20): "No such file or directory: 'bash'" #1486

Open deronnax opened 1 month ago

deronnax commented 1 month ago

Describe the bug

pipx ensurepath fails with a cryptic error on the last Alpine in docker with default shell and user (ash shell, root user). Not sure it has ever worked before. The same does work on debian:

$ docker run -it --rm debian:bookworm-slim sh -c "apt-get update && apt-get install -y pipx && pipx ensurepath"
Success! Added /root/.local/bin to the PATH environment variable.
Consider adding shell completions for pipx. Run 'pipx completions' for instructions.
You will need to open a new terminal or re-login for the PATH changes to take effect.

How to reproduce

$ docker run -it --rm alpine:3.20 sh -c 'apk add pipx && pipx ensurepath'
[ apk installing pipx...]
pipx >(setup:1083): pipx version is 1.6.0
pipx >(setup:1084): Default python interpreter is '/usr/bin/python3.12'
pipx >(mkdir:76): creating directory /root/.local/share/pipx/venvs
pipx >(mkdir:76): creating directory /root/.local/bin
pipx >(mkdir:76): creating directory /root/.local/share/man
pipx >(mkdir:76): creating directory /root/.cache/pipx
pipx >(mkdir:76): creating directory /root/.local/share/pipx/py
[Errno 2] No such file or directory: 'bash'

sh is ash, alpine default shell. You can reproduce just the same it with a real docker session and not the oneliner docker run [...] -c sh [...]. The oneliner was for this ticket concision purpose.

Expected behavior

I guess it should work? Or maybe have a gotcha section in https://pipx.pypa.io/stable/troubleshooting/ ?

chrysle commented 1 month ago

This sounds like an issue with userpath (which we use internally) shell detection to me; I don't have time to try to reproduce that right now, though, probably soon-ish.

deronnax commented 1 month ago

Looks like a userpath problem, indeed:

$ docker run -it --rm alpine:3.20 sh -c "apk add py3-pip && pip install --break-system-package userpath && userpath append '~/.local/bin'"
[...]
Traceback (most recent call last):
  File "/usr/bin/userpath", line 8, in <module>
    sys.exit(userpath())
             ^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/click/core.py", line 1157, in __call__
    return self.main(*args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/click/core.py", line 1078, in main
    rv = self.invoke(ctx)
         ^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/click/core.py", line 1688, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
                           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/click/core.py", line 1434, in invoke
    return ctx.invoke(self.callback, **ctx.params)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/click/core.py", line 783, in invoke
    return __callback(*args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/userpath/cli.py", line 122, in append
    elif up.in_new_path(location, shells=shells, all_shells=all_shells, home=home):
         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/userpath/core.py", line 17, in in_new_path
    return interface.location_in_new_path(location, check=check)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/userpath/interface.py", line 116, in location_in_new_path
    new_path = get_flat_output(show_path_command)
               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/site-packages/userpath/utils.py", line 33, in get_flat_output
    process = subprocess.Popen(command, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE, **kwargs)
              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/subprocess.py", line 1026, in __init__
    self._execute_child(args, executable, preexec_fn, close_fds,
  File "/usr/lib/python3.12/subprocess.py", line 1955, in _execute_child
    raise child_exception_type(errno_num, err_msg, err_filename)
FileNotFoundError: [Errno 2] No such file or directory: 'bash'

Do you want me to open an issue in userpath's Github?

dukecat0 commented 1 month ago

Do you want me to open an issue in userpath's Github?

Yes, and I believe that should be the correct place for this issue.

deronnax commented 1 month ago

Here you go https://github.com/ofek/userpath/issues/60