我的文件 .pl
中有这行代码
system("./read_image http://echopaw.fr/wp-content/uploads/2015/09/animals-41.jpg");
read_image
是一个 C 可执行文件,它在命令行中运行良好,但是当我在网络服务器中运行我的 .pl
文件时,这一行不起作用,它的功能是将一些数据写入文件,所以我可以看看它是否有效
我也试过``,还是不行
有人有想法吗?
最佳答案
我认为这是因为当您的网络服务器运行您的 CGI 时,它会从某个奇怪的目录(/var/www/htdocs
或 /
或其他目录)运行。那么你的 read_image
也应该在那个目录中,因为 ./read_image
.
./
表示当前目录,不一定是你的.cgi所在的目录。
我建议使用 Perl 模块 FindBin :
您的 cgi:
...
use strict;
use warnings;
use FindBin;
...
system("$FindBin::Bin/read_image http://echopaw.fr/wp-content/uploads/2015/09/animals-41.jpg");
$FindBin::Bin
解析为您的 .cgi 所在的路径——无论您从何处调用它。这是一个非常方便的模块,也可以用来修改@INC 路径以找到您自己的模块:
use lib "$FindBin::Bin/../lib";
use MyModule;
这样 MyModule.pm
应该在 $current_script_path/../lib
中。非常方便。
附录
随着讨论的深入,这显然不仅是 apache 能否找到 read_image
命令的问题,而且还是 read_image
能否找到 命令的问题>wget
它试图执行的命令。
正如@CDahn 已经在评论中指出的那样,出于安全原因,apache 在有限环境 中运行CGI 脚本等。如果你从你的 shell 运行 read_image
,那么你就有了一个完整的工作环境,比如说,PATH 包括 15 个不同的目录(比如 /usr/bin:/opt/bin:/usr/share/bin:/usr/local/bin:...
,随便)。当 apache 运行你的脚本时,PATH 可能只包含 2 或 3 个绝对必要的目录,例如/usr/bin:/usr/local/bin
。其他环境变量也是如此。
你可以用一个简单地回应当前环境的小.cgi脚本来验证这一点,比如
while (my ($key,$value) = each %ENV) {
print "$key=$value\n";
}
(摘自http://perldoc.perl.org/functions/each.html)
从您的浏览器调用此 .cgi,您将看到不同之处。
当您的 read_image
找不到 wget
命令时,可能是因为 wget
位于 apache 不知道的 PATH 中。我不会教 apache 关于附加目录(坏主意),而是在你的 read_image
程序中给出 wget
命令的完整路径。从您的终端窗口运行
$ which wget
/usr/bin/wget
并在从您的 read_image
调用 wget
时使用该路径。
关于无法在cgi中执行外部命令,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36101900/