简体   繁体   中英

virtctl works when executed via command line but not from php exec()

I am trying to run kubectl virt commands to manage my virtual machine via PHP. First, I log in to my server with phpseclib with the following code:

$ssh = new SSH2('localhost');
if (!$ssh->login('root', 'rootPassword')) {
    throw new \Exception('Login failed');
}

This part works fine, and when I try to run $ssh->exec('whoami && echo $PATH') , I get the following output:

root
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin

But, whenever I try to run kubectl virt via PHP, I get the following output:

error: unknown command "virt" for "kubectl"

kubectl and kubectl virt work perfectly fine when I run them via terminal but somehow do not work with PHP exec(). I also tried to check the $PATH via terminal and I get a different output:

/root/.krew/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin

I thought that it may be because of $PATH but the interesting part is when I try to run sudo kubectl virt via terminal I also get the same error:

error: unknown command "virt" for "kubectl"

At that point, I am completely lost and don't even know where to look for a problem. I am thankful for all the answers.

When you are issuing ad-hoc ssh commands, you are not using interactive shell, and depending on your default shell behavior it may or may not load your .bashrc file . See https://serverfault.com/questions/936746/bashrc-is-not-sourced-on-ssh-command and Running command via ssh also runs .bashrc? for more details.

So by default, krew modifies your PATH variable, and appends it's bin path to it, ie my config contains export PATH="${KREW_ROOT:-$HOME/.krew}/bin:$PATH" . But what exactly is kubectl plugin? Usually it's just a single binary, with kubectl- plugin_name name. So by invoking which kubectl-virt you can easily know where is your virt binary located and invoke it directly, so something like

$ssh->exec('~/.krew/bin/kubectl-virt')

should work

The other way is to modify PATH all by yourself, setting PATH=$PATH:~/.krew/bin should make it work, at least in my case

ssh localhost 'PATH=$PATH:~/.krew/bin kubectl virt'

worked nicely.

You can try to force loading of .bashrc in your shell configuration, but personally i think it's a bad practice, and ssh commands are not usually loading rc files for a reason, command execution speed and consistency between systems are the first things that come to mind.

Regarding sudo, it's actually not that surprising, because without -E or -i flags it won't load your current environment / won't start interactive shell. See https://unix.stackexchange.com/questions/228314/sudo-command-doesnt-source-root-bashrc for more info

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM