如何使用 PHP-FPM 和 Apache 的 mod_fastcgi 修复 SCRIPT_NAME?

如何使用 PHP-FPM 和 Apache 的 mod_fastcgi 修复 SCRIPT_NAME?

为了使 PHP-FPM 正常工作,我在 Apache 配置中包含了以下内容:

FastCgiExternalServer /srv/www/fast-cgi-fake-handler -host 127.0.0.1:9000
AddHandler php-fastcgi .php
AddType text/html .php
Action php-fastcgi /var/www/cgi-bin
Alias /var/www/cgi-bin /srv/www/fast-cgi-fake-handler
DirectoryIndex index.php

除了 SCRIPT_NAME 始终存在/var/www/cgi-bin并且某些脚本使用 SCRIPT_NAME 来找出当前脚本 (vBulletin) 的位置之外,这种方法工作正常。

Google 为 Nginx 提供了大量解决方案,但却没有针对 Apache 的解决方案。

答案1

如果你使用 RewriteRule 代替“Action”方法,效果会很好

下面给出了我在 Apache 中用于连接 FCGI::Daemon 外部 fastcgi 守护进程的一个例子。此守护进程可以视为 php-fpm 的 perl 版本。

<VirtualHost 127.0.0.1:80>
    ServerAdmin [email protected]
    DocumentRoot "/var/www/example"
    ServerName www.example.com

    <IfModule mod_fastcgi.c>
    FastCGIExternalServer /var/www/fcgi-daemon/perl.fcgi -socket /var/run/fcgi-daemon.sock
    ScriptAlias /perl.fcgi /var/www/fcgi-daemon/perl.fcgi
    </IfModule>
</VirtualHost>

<Directory /var/www/example/cgi-bin>
    Options ExecCGI
    RewriteRule ^(.*)$ /perl.fcgi [L]
</Directory>

注意:“/var/www/fcgi-daemon/”必须存在!作为空白目录。实际上,您用于 php 的方法对于 perl 守护进程不起作用。SCRIPT_FILENAME 始终是 /var/www/fcgi-daemon/perl.fcgi,它从未存在过,从而导致错误。使用 RewriteRule 将所有必需的环境变量保留在原位并将它们传递给 perl fastcgi 守护进程。

答案2

我发现,当设置FastCgiExternalServer为存在的目录(可能也适用于文件)/srv/www时,所有 PHP 变量都正确设置。但是,所有非 PHP 内容都会充当text/html或,text/plain这不是很好。也DirectoryIndex停止了效果,这让我想起StackOverflow 上的这个问题但是我无法通过他混合使用绝对路径和相对路径的解决方案取得任何进展。

与 PHP-FPM、Apache 和 SCRIPT_NAME 相关的唯一 Google 搜索结果是名为 Dimas 的人发表的评论谁说的这个方法帮他解决了这个问题,但我没有那么幸运。

我已将auto_prepend_filephp.ini 中的设置改为包含以下内容的文件:

<?php
$_SERVER['SCRIPT_FILENAME'] = $_SERVER['PATH_TRANSLATED'];
unset($_SERVER['PATH_TRANSLATED']);
$_SERVER['SCRIPT_NAME'] = $_SERVER['PATH_INFO'];
unset($_SERVER['PATH_INFO']);

虽然不是最好的解决方案,但至少我不必手动编辑 vBulletin、Wordpress 等。

答案3

您可以通过确保以下方法解决此问题:cgi.fix-pathinfo在您的 php.ini 中设置为 1。这会导致 PHP 填充 $_SERVER 数组,正如您在 Apache 上将 PHP 作为 CGI/FastCGI 执行时所期望的那样。

答案4

https://serverfault.com/a/423965/118969上面由 ColtonCat 提供的答案是最好的答案。我尝试使用 nginx (ssl-reverse-proxy) -> apache -> php53-fpm。

如果使用 nginx (ssl-reverse-proxy) ->Apache + mod_php, 您可以使用cgi.fix_pathinfo=0

相关内容