/usr/bin/env: php: No such file or directory

40,210

Solution 1

Make sure that line endings and/or invisible spaces aren't causing the problem.

Remove the spaces in the first line of the script and insert new ones, making sure not to hold CTRL while pressing space.

Also, make sure you don't have DOS line endings (CR+LF). See https://stackoverflow.com/questions/82726/convert-dos-line-endings-to-linux-line-endings-in-vim for details.

Solution 2

The env command will look through a user's $PATH to find the first executable of the given name. So, /usr/bin/env php will look for an executable file called php in any of the directories in the $PATH of the user running it.

In your case, that's almost certainly because when running a command over ssh, you don't start a full shell and don't actually read your shell's initialization files. You can check this by running this command (note the single quotes):

ssh [email protected] 'echo $PATH'

And comparing the output to what you get if you ssh [email protected] and then run echo $PATH. On my system. for example:

$ echo $PATH
/usr/bin:/usr/local/sbin:/usr/local/bin:/usr/lib/jvm/default/bin:/usr/bin/site_perl:/usr/bin/vendor_perl:/usr/bin/core_perl:

$ ssh localhost 'echo $PATH'
/usr/bin:/bin:/usr/sbin:/sbin

Therefore, the $PATH that your script has access to when run with ssh [email protected] is not the same as when you log in to test it.

In any case, the simple solution is to use the full path to the interpreter instead of env. Both env and full paths have their benefits and drawbacks but, in this case, the path is safer:

#!/usr/bin/php

Solution 3

Easiest way.... change the user's shell as the script.

/etc/passwd

Before:
deploy:x:0:0:,,,:/root:/bin/bash

After:
deploy:x:0:0:,,,:/root:/scripts/deploy.sh

Example script (make sure execute bit is set chmod +x)

/scripts/deploy.sh

#!/bin/bash 
PATH=$PATH:/moo etc...
moo.sh

Sample Works everytime! You should even be able to use the script to troubleshoot/debug any env variables which you may feel are unset etc ... also the handling arguments being passed into ssh will work as well..

Note: Its Best Practice to always FULLY QUALIFY the paths for any scripts, executables, etc.. Above is just an example which allows the default path to be set to call moo.sh within the moo folder ;)

That was easy.. Thanks for posting..

Reference: /etc/passwd format

Solution 4

Is it possible that bash needs a reset to its hash table?

If so, you might try adding hash -r somewhere in your script, which forces the shell to look through $PATH again rather than relying on (possibly outdated) info from the hash table.

When needed, hash can also enable the shell to remember paths to executables installed in non-standard locations using the -p option, or forget paths with the -d option.

Sources:

https://unix.stackexchange.com/a/86017/121251
https://stackoverflow.com/a/22543353/2146843

Solution 5

Looks like maybe you need to add php to your path. Try:

vim ~/.bashrc
PATH=$PATH:/usr/local/bin/php
export PATH

You might also want to check where your php lives to be sure that the path there is correct. Try:

which php
Share:
40,210

Related videos on Youtube

Tomáš Blatný
Author by

Tomáš Blatný

Updated on September 18, 2022

Comments

  • Tomáš Blatný
    Tomáš Blatný over 1 year

    I want to use .sh script for deployment of my app. That script is on my home server (Ubuntu 15.10 Server), marked as executable. Access to this script is done through ssh, using this tutorial, I have set up ssh login, that runs that script. So basically I just call ssh [email protected] someArguments and it runs my script with someArguments as parameters. The user deployer has uid=0, so its basically root (this will be changed in the future, I have set it only to eliminate permissions problems until it works fine).

    And here is where the things get tricky. The script reports /usr/bin/env: php: No such file or directory at command /bin/composer install (using Composer). Things are more weird the more I look on that script. Before this line, there is also called /bin/composer self-update and /bin/composer -V, which both runs correctly and displays correct output.

    I have checked following things:

    • /usr/bin/env php -v displays correct PHP version (same as /usr/bin/php -v)
    • whereis php displays php: /usr/bin/php /usr/local/bin/php /usr/share/man/man1/php.1.gz
    • php5-cli package is installed and newest version
    • $PATH contains /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games
    • which env displays /usr/bin/env

    I have also tried following things:

    • running the script directly as bash deploy.sh under root (since it is same as that user) - works perfectly without errors
    • running failing commands directly - also perfectly without errors

    So this seems to me as very specific case, why this command does not work. I spent 12 hours of debugging it and I am out of ideas here.

    P.S.: Similar error (/usr/bin/env: node: No such file or directory) occurs when there is bower install (using Bower), but not when running npm install (using NPM).

    • Giacomo Catenazzi
      Giacomo Catenazzi about 8 years
      Run sh deploy instead of bash deploy (maybe some bashism). How did you check the "following things"? I recommend to check them in the script, so that you can discover eventual overrides and sanitations of envs.
    • Tomáš Blatný
      Tomáš Blatný about 8 years
      regarding "following things": I added them to start of deploy.sh script and they output these things I put down to question. Same output is when I run them alone, though.
    • Tomáš Blatný
      Tomáš Blatný about 8 years
      sh deploy and bash deploy both gives same results
    • Oleg Bolden
      Oleg Bolden about 8 years
      Show that line here, please. I recommend you to replace your php command at this line in your script with output to file to examine environment variables at the moment of calling /usr/bin/env: /usr/bin/env > environment.txt
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    Nice answer, but I actually never use the user on server directly, I always ssh to server, and by lane in authorized_keys, the script gets called and then connection ends. How shall I modify authorized_keys to keep this working?
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    I am using IDE, which automatically checks (and converts) CR+LF to LF only, removes BOM and cares about white characters, but I double-checked it, and it appears ok (still not working though). Thanks anyway
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    Well this is not the problem, since php -v outputs correct PHP version and composer --version outputs composer version. As I said, problem is in one command only.
  • NotAdmin Dave
    NotAdmin Dave about 8 years
    It should work the same. You would be authenticating via key and as long as the shell is set to the script for the remote account in question within the remote server's /etc/passwd file the script will execute. I'll add a screenshot to my post shortly.
  • Burgi
    Burgi about 8 years
    @Dave can't wait for your book
  • dave_thompson_085
    dave_thompson_085 about 8 years
    ITYM "note the single quotes" not "not".
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    I am actually using full paths everywhere, as I mentioned in my question, the error is reported inside composer install command, which i obviously cannot modify. Also $PATH is ok, as I mentioned in my question too, I checked all the things by adding them into the script and running remotely via ssh login. Also I can not check the ssh [email protected] 'echo $PATH' as you stated, since my ssh login is limited to one script only, but I hovever did check it when I add $PATH to that script (stated above) Anyway, thank you for your answer, and accept +1 for explaining me the env thing
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    Regarding Without knowing exactly how you have setup your deploy script to run: in my question at the begining, there is a link, how I set it up (using ~/.ssh/authorized_keys. Thanks for the tip with updating command, I tried it, but unfortunatelly with no difference. I will however futher investigate this and try different shells. Please accept a +1 for that idea.
  • terdon
    terdon about 8 years
    @TomášBlatný well, you're using env somewhere, or you wouldn't be seeing that error. I don't know composer but you will probably have to copy or link the php executable to a directory in its path. This sort of thing is hard to debug since there are so many things each depending on the other.
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    Thats true, env is actually called inside composer. But this does not solve the problem, why some composer calls pass, and some not. However I will futher investigate this by looking into its code. Thanks for your time
  • terdon
    terdon about 8 years
    @TomášBlatný I am guessing that those that pass are calling binaries that are in a directory that is in whatever limited PATH composer uses. Try linking the ones that don't work into the directory holding the ones that do. Good luck!
  • mattpr
    mattpr about 8 years
    Did you try updating your deploy script to print out the current $PATH? Could you post the result? If it doesn't match what you expect, then you can just try setting the PATH explicitly as I suggested at the beginning of your deploy script.
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    This did not solved the problem for me, however its a good knowledge, so I added you a +1
  • Tomáš Blatný
    Tomáš Blatný about 8 years
    Thanks for your answer, it did not solve my problem, but was for me the most interesting and actually solved other problems I had. Gave you the bounty, thanks again