I'm using Nginx with PHP-FPM, and I want to restrict access to a subdirectory of PHP files on my site so that only traffic from my IP address is allowed.
Here is what I have tried, assuming my IP is 1.1.1.1:
location ^~ /blocktest/
{
if ($remote_addr != "1.1.1.1")
{
return 503;
}
}
This blocks the public, but PHP scripts are no longer executed for me, and I'm just prompted to download the raw file. So, I tried including my PHP configuration file in the block, like this:
location ^~ /blocktest/
{
if ($remote_addr != "1.1.1.1")
{
return 503;
}
include /usr/local/nginx/conf/php.conf;
}
…but then the public could access the PHP files again. Ugh. Any idea on how I could get this to work? Thanks!
For reference, here's my php.conf file:
location ~ \.php$ {
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
try_files $uri =404;
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_connect_timeout 60;
#fastcgi_send_timeout 180;
#fastcgi_read_timeout 180;
fastcgi_send_timeout 2000;
fastcgi_read_timeout 2000;
fastcgi_buffer_size 256k;
fastcgi_buffers 4 256k;
fastcgi_busy_buffers_size 256k;
fastcgi_temp_file_write_size 256k;
fastcgi_intercept_errors on;
fastcgi_param PATH_INFO $fastcgi_path_info;
fastcgi_param PATH_TRANSLATED $document_root$fastcgi_path_info;
fastcgi_param QUERY_STRING $query_string;
fastcgi_param REQUEST_METHOD $request_method;
fastcgi_param CONTENT_TYPE $content_type;
fastcgi_param CONTENT_LENGTH $content_length;
fastcgi_param SCRIPT_NAME $fastcgi_script_name;
fastcgi_param REQUEST_URI $request_uri;
fastcgi_param DOCUMENT_URI $document_uri;
fastcgi_param DOCUMENT_ROOT $document_root;
fastcgi_param SERVER_PROTOCOL $server_protocol;
fastcgi_param GATEWAY_INTERFACE CGI/1.1;
fastcgi_param SERVER_SOFTWARE nginx/$nginx_version;
fastcgi_param REMOTE_ADDR $remote_addr;
fastcgi_param REMOTE_PORT $remote_port;
fastcgi_param SERVER_ADDR $server_addr;
fastcgi_param SERVER_PORT $server_port;
fastcgi_param SERVER_NAME $server_name;
# PHP only, required if PHP was built with --enable-force-cgi-redirect
fastcgi_param REDIRECT_STATUS 200;
}
Best Answer
I've figured this out. Apparently, the only way to actually prevent the PHP files from being processed by PHP-FPM is to use HttpAccessModule's "deny all", you can't just "return 503".
Here is a Nginx configuration snippet which defines a custom 503 error page and lets you block all public access to a subdirectory, including PHP files generated by PHP-FPM. You can define which IPs have access to the blocked subdirectory using the rules defined by the Nginx HttpAccessModule documentation.