1

I'm using Alpine Linux in a container. I have ENV PATH="~/.local/bin:$PATH" \ in my Dockerfile

When logging into the shell I can successfully ls ~/.local/bin which is the same as ls /root/.local/bin, the target binary is there.

However which I call the binary directly or which mybin it won't work. After explicitly add /root/.local/bin, then it works.

I'm not sure why is this happening, since ~/.local/bin and /root/.local/bin are the same.

Any ideas? Thanks!

Edit:

The dup link gave me some idea of what was happening, but I found that wasn't the main cause. Removing quotes won't work still, as the Dockerfile ENV directive does not do any shell expansion.

It seems the only viable way to do this is to use export && in a CMD directive.

Nor does $HOME work in ENV directive.

dz902
  • 403

1 Answers1

0

While I am not sure which shell you are using, assuming bash, you will need to specify $HOME rather than ~ as apart from the interactive command line it is not safe to use ~ anywhere else.

Some locations as in inside scripts, ~ will also work, but defining them inside a variable may have unexpected results, as you have experienced.

You can also echo back $PATH to see what the contents are.

echo $PATH

You will see that with your current implementation, it will include the path ~/.local/bin instead of the self-expanded /root/.local/bin as ~ was taken literally.

Phoenix
  • 286
  • "it is not safe to use ~ anywhere else" What's unsafe about it? On the contrary, ~ is safer than $HOME, since it does not undergo filename expansion: HOME='*'; echo $HOME; echo ~. – muru Oct 21 '19 at 04:58
  • @muru, what you describe is exactly what is unsafe about using ~. On the command line the unescaped ~ will expand to your home directory. However, when placed inside a variable, like PATH, it will be taken literally. So, the behavior changes (unexpectedly to the untrained eye). The result is that PATH will include a directory which most-likely does not exist. In order to get proper expansion to your home directory inside variables, one wants to use $HOME as it expands to the user home directory (even on the command-line). – Phoenix Oct 21 '19 at 06:52
  • 1
    I think you and I have rather different interpretations of "unsafe." – muru Oct 21 '19 at 07:15
  • This appears to be. In regards to variables or auto-expansion objects (like ~) my understanding of “safe” is that while using them unescaped behaves the same way no matter where they are implemented. If the behavior changes under some methods, it may result in surprises on the result (like the one the OP voiced). Hence, I regard its use unsafe. I am not at all talking about data safety, where with a variable (any variable really) one can delete an unintended file due lack of knowledge of its contents. They are two different books for me. – Phoenix Oct 22 '19 at 04:47