Apache mod_proxy_fcgi and PHP-FPM (php-cgi.exe) is

2020-07-03 07:56发布

The following is PHP-FPM (PHP 5.5)

php-cgi.exe -b 127.0.0.1:9000

The following is mod_proxy_fcgi (Apache 2.4)

The first way

<Files ~ "\.(php|phtml)$">
    SetHandler "proxy:fcgi://127.0.0.1:9000/"
</Files>

The second way

<LocationMatch ^(.*\.(php|phtml))$>
    ProxyPass fcgi://127.0.0.1:9000/$1
</LocationMatch>

The third way

<IfModule mod_rewrite.c>
    RewriteCond %{REQUEST_FILENAME} -f
    RewriteRule ^([^\.]+\.(php|phtml))$ fcgi://127.0.0.1:9000/$1 [P,L]
</IfModule>

The above three ways will get an error "No input file specified." Anybody know why? How should I do to solve this problem?

标签: php apache
4条回答
ゆ 、 Hurt°
2楼-- · 2020-07-03 08:06

Inexplicably, simply changing the trailing / to a # seems to fix the problem:

<Files ~ "\.(php|phtml)$">
    SetHandler "proxy:fcgi://127.0.0.1:9000#"
</Files>

In trying to understand this I set Apache to LogLevel debug (timestamp/module/process details removed for brevity):

  • Using / gives:

    mod_proxy_fcgi.c(911): [client ::1:60730] AH01076: url: fcgi://127.0.0.1:9000/E:/test/webroot/test.php proxyname: (null) proxyport: 0
    mod_proxy_fcgi.c(920): [client ::1:60730] AH01078: serving URL fcgi://127.0.0.1:9000/E:/test/webroot/test.php
    proxy_util.c(2154): AH00942: FCGI: has acquired connection for (*)
    proxy_util.c(2208): [client ::1:60730] AH00944: connecting fcgi://127.0.0.1:9000/E:/test/webroot/test.php to 127.0.0.1:9000
    proxy_util.c(2417): [client ::1:60730] AH00947: connected /E:/test/webroot/test.php to 127.0.0.1:9000
    
  • Using # gives:

    mod_proxy_fcgi.c(911): [client ::1:60738] AH01076: url: fcgi://127.0.0.1:9000#E:/test/webroot/test.php proxyname: (null) proxyport: 0
    mod_proxy_fcgi.c(920): [client ::1:60738] AH01078: serving URL fcgi://127.0.0.1:9000#E:/test/webroot/test.php
    proxy_util.c(2154): AH00942: FCGI: has acquired connection for (*)
    proxy_util.c(2208): [client ::1:60738] AH00944: connecting fcgi://127.0.0.1:9000#E:/test/webroot/test.php to 127.0.0.1:9000
    proxy_util.c(2417): [client ::1:60738] AH00947: connected  to 127.0.0.1:9000
    

The crucial difference appears to be in the last line, where the second (working) method doesn't appear to log anything as the value passed to the PHP process.

I'm at a loss to explain this and can't find mention of it anywhere. (Perhaps a braver soul than I would be willing to delve into the Apache and/or PHP source to investigate.)

Note that I haven't tested this beyond running phpinfo() so wouldn't recommend it for a production server.


Edit

This works for PHP 7.0, but with PHP 5.6 I still get the 'No input file specified' error.

Edit 2

And working with Apache 2.4.25, but not the recently released 2.4.26!

This seems to be an incompatibility minefield that is explicitly mentioned in the CHANGES_2.4.26 file:

mod_proxy_fcgi: Return to 2.4.20-and-earlier behavior of leaving a "proxy:fcgi://" prefix in the SCRIPT_FILENAME environment variable by default. Add ProxyFCGIBackendType to allow the type of backend to be specified so these kinds of fixups can be restored without impacting FPM. PR60576 [Eric Covener, Jim Jagielski]

The documentation has been updated to reflect this:

One example of values that change based on the setting of this directive is SCRIPT_FILENAME. When using mod_proxy_fcgi historically, SCRIPT_FILENAME was prefixed with the string "proxy:fcgi://". This variable is what some generic FastCGI applications would read as their script input, but PHP-FPM would strip the prefix then remember it was talking to Apache. In 2.4.21 through 2.4.25, this prefix was automatically stripped by the server, breaking the ability of PHP-FPM to detect and interoperate with Apache in some scenarios.

查看更多
家丑人穷心不美
3楼-- · 2020-07-03 08:13

I think this is a bug in mod_proxy_fcgi, connected to an issue resolved in Apache 2.4.12 onwards:

mod_proxy_fcgi: Remove proxy:balancer:// prefix from SCRIPT_FILENAME passed to fastcgi backends. [Eric Covener]

Here is a link

Unfortunatelly it was not good enough as Apache is sending the SCRIPT_FILENAME with a starting slash, similar to \c:\fileName.php, which is not resolved as a local file name and is never executed. You may verify this using a network sniffer(Wireshark) listening on your FastCGI port.

I will be more than happy to see this issue resolved officially since I am not confident in recompiling Apache by myself and so I am using distributions from apachelounge.

查看更多
太酷不给撩
4楼-- · 2020-07-03 08:29

Maybe you didn't get me right.

Before the fix it was: proxy:balancer://\c:\fileName.php

After the fix it is: \c:\fileName.php

Which are both invalid file names in Windows, while thinking Linux there is no drive letter there so it becomes \fileName.php which is valid. The fix would be to remove the starting slash and recompile.

查看更多
【Aperson】
5楼-- · 2020-07-03 08:29

I was getting this error when following the steps indicated here to run PHP under Apache on Windows via FastCGI:

https://www.orbitale.io/2017/11/11/apache-and-php-fpm-in-windows.html

After setting up php-cgi.exe as a service on port 9000 (using NSSM) and setting httpd.conf to handle php files as such:

<IfModule dir_module>
    DirectoryIndex index.php index.html
</IfModule>

<Files ~ "\.php$">
    SetHandler "proxy:fcgi://127.0.0.1:9000#"
</Files>

I was getting this same error when navigating to localhost (which contained an index.php with a simple <?php phpinfo(); ?> .

I was getting worried until I tried editing my php.ini where I defined the doc_root directive:

doc_root = C:\Apache24\htdocs

Having done that and having restarted my Apache service, voilà I got the php info page! I'm using PHP 7.3.5 NTS x64 with Apache 2.4 x64.

查看更多
登录 后发表回答