I have the following config on 0.7.26:
server {
...
location / {
error_page 404 = @cms;
}
location @cms {
fastcgi_pass 127.0.0.1:1234;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME /www_root/index.php;
fastcgi_param SCRIPT_NAME /index.php;
}
location ~ \.php$ {
fastcgi_pass 127.0.0.1:1234;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME /www_root$fastcgi_script_name;
fastcgi_param SCRIPT_NAME $fastcgi_script_name;
fastcgi_intercept_errors on;
error_page 404 = @cms;
}
...
}
This should pass all requests to non-existent paths to /index.php so "clean
URLs" will work and the CMS will display the corresponding pages. Indeed it
works if I try to access a URI that is first handled by the "location /" block,
such as http://my.com/2008/12/my-blog-post.
However, when I access a URI that is first handled by the "location ~ \.php$"
block, such as http://my.com/non-existent.php, theoretically nginx will first
pass this request to FastCGI, then PHP sends back 404 because it can't find the
non-existent.php file, then nginx should honor the error_page directive and send
the request to @cms. In reality it results in a 502 Bad Gateway. The error log
says "upstream sent invalid header while reading response header from upstream".
But if I used the following:
location ~ \.php$ {
error_page 404 = /index.php;
}
Then it will work as intended.
Why can't I use a named location for error_page if the location block contains a
fastcgi_pass directive? (I assume this is the case for proxy_pass too, but I
didn't test that one.)