【问题标题】:How do I change the shell for php's exec()如何更改 php 的 exec() 的 shell
【发布时间】:2010-12-20 01:01:27
【问题描述】:

我想在 ubuntu 服务器上使用 php 的 exec() 函数。 问题是,我总是收到一个错误,即找不到该命令。例如使用

exec("echo 123");

打印

sh: /echo: 未找到

对我来说,当我想使用 bash 时,看起来 php 正在使用 sh shell。 我尝试在 /etc/passwd 中更改 www-data 的 shell,但也没有帮助。

有没有人知道问题可能出在哪里,或者我可以如何更改 php 的 ubuntu 用户的 shell。

谢谢,蒂莫


[编辑]

也许这会有所帮助:

我从 ssh 调用一个 bash 脚本作为 timo,这个脚本调用一个使用 exec 的 php 脚本。我知道,这听起来很奇怪,但它是更大开发环境的一部分……

关键是,我不确定执行 exec 中的脚本是由哪个用户执行的。


[编辑]

到现在为止,我发现肯定涉及另一个权利问题。 即使我尝试从 exec 中调用 bash 脚本 test.sh(通过它的完整路径!),php test.php 也会说。

sh: /test.sh: 未找到

【问题讨论】:

    标签: php bash shell ubuntu exec


    【解决方案1】:

    改用 shell_exec()。 exec 不应调用任何 shell 来执行您的程序。或者,您可以使用 exec 调用 bash,例如

    exec("/bin/bash -c \"echo $foo > bar.txt'\"")
    

    【讨论】:

    • 这只会说“sh: /bash: not found”。看起来 php 搜索 / 中的所有二进制文件。在 php.ini 中,safe_mode_exec_dir 设置为空,所以我想这意味着,没有限制!? (改变它似乎没有帮助)
    • 我没有使用安全模式的经验,所以这可能是你的问题。试试关掉?无论如何你都不应该使用它,它已经消失并且从一开始就是一个坏主意(列出大多数 PHP 语言“功能”)php.net/manual/en/features.safe-mode.php
    • 没有注意到有人已经提到了这一点 - 同意的安全模式被认为是有害的。关于safe_mode_exec_dir,如果安全模式已打开并且设置为空,那么这将解释它(如果你想运行任何需要设置为/的东西)。我建议您尝试将其设置为有意义的内容并在该路径中调用某些内容。
    【解决方案2】:

    我认为问题在于没有 $PATH 设置。尝试使用二进制文件的完整路径,即 /bin/echo

    【讨论】:

    • 感谢您的超级快速回复。不幸的是,这并没有解决问题。 /bin/echo 也不起作用。我真正想做的是这个 /usr/bin/mysql --user=asdf --password=asdf mydb
    【解决方案3】:

    如果你想做的是:

    /usr/bin/mysql --user=asdf --password=asdf mydb < ./dump.sql

    然后我想这会起作用(无论外壳如何):

    /usr/bin/mysql --user=asdf --password=asdf mydb < /full/path/to/dir/dump.sql

    【讨论】:

    • 哦,我不确定如何在 PHP 中实际设置 shell,但如果你真的在第一行,你可以使用 "#!/bin/bash" 从 sh 调用脚本确实需要 bash(并且找不到其他方法)。
    • 问题不在于找不到我的dump,而是找不到mysql...
    • 如果确实在 /usr/bin/mysql 上安装了二进制文件,那么 sh 会找到它,问题出在其他问题上 - 比如可能启用了安全模式(查看文档以了解安全模式 - exec-dir 和类似的)。要检查的另一件事是 open_basedir,它也可以限制 exec 的访问权限。
    【解决方案4】:

    我认为 PHP 会在内部调用 /bin/sh(或在 Windows 上调用 cmd.exe),无论您使用哪个函数。

    在 Linux 系统的终端中运行 ls -l /proc/$$/exe | sed 's%.*/%%' 应该会告诉您正在使用的 shell,默认情况下在我的 Ubuntu 终端中是 bash。如果您在 Ubuntu 中运行以下命令:

    <?php
    
    exec('ls -l /proc/$$/exe | sed \'s%.*/%%\'', $res);
    // or:
    //$res = shell_exec('ls -l /proc/$$/exe | sed \'s%.*/%%\'');
    echo(json_encode($res));
    

    无论您使用哪个函数,您都会得到 ["dash"] 作为结果。如果将 /bin/sh 更改为指向 bash 而不是 dash,则 PHP 的结果会更改为 bash,但我不建议明显这样做。

    长话短说,如果不修改整个服务器的默认 shell 或从源代码编译 PHP,可能无法更改此设置。

    如果你想进一步解开这个谜,它可能与PHP源码中的ext/standard/proc_open.c和ext/standard/exec.c(所有这些函数都在那里,系统,passthru等)有关,但说实话,它打败了我。

    【讨论】:

      【解决方案5】:

      我在使用 Debian Docker PHP 映像时遇到了问题,这对我有帮助:

      https://www.reliableembeddedsystems.com/wiki/index.php?title=Make_bash_default_shell

      /bin/sh 是 dash 的符号链接,这可能更好,但不适用于我的脚本。

              echo "dash dash/sh boolean false" | debconf-set-selections
              dpkg-reconfigure -f noninteractive dash
      

      【讨论】:

        猜你喜欢
        • 2010-09-18
        • 2012-12-07
        • 1970-01-01
        • 2015-10-02
        • 2019-01-04
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多