I'm trying to restrict access to my site to allow only specific IPs and I've got the following problem: when I access www.example.com deny works perfectly, but when I try to access www.example.com/index.php it returns "Access denied" page AND php file is downloaded directly in browser without processing.
I do want to deny access to all the files on the website for all IPs but mine. How should I do that?
Here's the config I have:
server {
listen 80;
server_name example.com;
root /var/www/example;
location / {
index index.html index.php; ## Allow a static html file to be shown first
try_files $uri $uri/ #handler; ## If missing pass the URI to front handler
expires 30d; ## Assume all files are cachable
allow my.public.ip;
deny all;
}
location #handler { ## Common front handler
rewrite / /index.php;
}
location ~ .php/ { ## Forward paths like /js/index.php/x.js to relevant handler
rewrite ^(.*.php)/ $1 last;
}
location ~ .php$ { ## Execute PHP scripts
if (!-e $request_filename) { rewrite / /index.php last; } ## Catch 404s that try_files miss
expires off; ## Do not cache dynamic content
fastcgi_pass 127.0.0.1:9001;
fastcgi_param HTTPS $fastcgi_https;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params; ## See /etc/nginx/fastcgi_params
}
}
That is because your deny/allow rule applies to just one location.
Remove that and try:
server {
listen 80;
server_name example.com;
root /var/www/example;
if ($remote_addr != "YOUR.PUBLIC.IP") {return 403;}
...
}
As the test is outside any specific locationblock, it will apply to all cases.
Note also that IF is not evil here since it just "returns".
OK, so I've found the solution. Nginx processes the most exact regex which in this case is the regex for php files. To make the config work all further locations must be defined within / location rule except for #handler (you cannot put under any rule - only as root)
server {
listen 80;
server_name example.com;
root /var/www/example;
location / {
index index.html index.php; ## Allow a static html file to be shown first
try_files $uri $uri/ #handler; ## If missing pass the URI to front handler
expires 30d; ## Assume all files are cachable
allow my.public.ip;
deny all;
location ~ .php/ { ## Forward paths like /js/index.php/x.js to relevant handler
rewrite ^(.*.php)/ $1 last;
}
location ~ .php$ { ## Execute PHP scripts
if (!-e $request_filename) { rewrite / /index.php last; } ## Catch 404s that try_files miss
expires off; ## Do not cache dynamic content
fastcgi_pass 127.0.0.1:9001;
fastcgi_param HTTPS $fastcgi_https;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params; ## See /etc/nginx/fastcgi_params
}
}
location #handler { ## Common front handler
rewrite / /index.php;
}
}
Related
i need your help with setting location allow,
location /route {
deny [my-ip];
}
So this works, it doesn't let me access the route
Throws this error
403 Forbidden
nginx/1.10.0 (Ubuntu)
And this...
location /route {
allow [my-ip];
deny all;
}
Doesn't let me access but it's supposed to let me access the route, can't understand why, it shows this error
404 Not Found
nginx/1.10.0 (Ubuntu)
Config file (with two examples on routes):
# Add index.php to the list if you are using PHP
index index.php index.html index.htm;
server_name [my-domain];
location / {
# First attempt to serve request as file, then
# as directory, then fall back to displaying a 404.
try_files $uri $uri/ /index.php?$query_string;
}
# pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
#
location ~ \.php$ {
include snippets/fastcgi-php.conf;
#
# # With php7.0-cgi alone:
# fastcgi_pass 127.0.0.1:9000;
# # With php7.0-fpm:
fastcgi_pass unix:/run/php/php7.0-fpm.sock;
}
# deny access to .htaccess files, if Apache's document root
# concurs with nginx's one
#
location ~ /\.ht {
deny all;
}
# Phpmyadmin Configurations
location /phpmyadmin {
root /usr/share/;
index index.php index.html index.htm;
location ~ ^/phpmyadmin/(.+\.php)$ {
try_files $uri =404;
root /usr/share/;
#fastcgi_pass 127.0.0.1:9000;
#fastcgi_param HTTPS on; # <-- add this line
fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params;
}
location ~* ^/phpmyadmin/(.+\.
(jpg|jpeg|gif|css|png|js|ico|html|xml|txt))$ {
root /usr/share/;
}
}
# Dealing with the uppercased letters
location /phpMyAdmin {
rewrite ^/* /phpmyadmin last;
}
location /logs {
deny [myip];
}
location /admin {
allow [myip];
deny all;
}
for anybody else who is searching for the solution. This did it for me after long try and error:
location = /phpmyadmin/index.php {
allow 1.2.3.4;
deny all;
....
}
Make sure you use the "=" sign or else it won't work.
So your problem is not the allow and deny. It is root /usr/share/; Since you have placed it into a location block location /phpmyadmin, it can not be found by location \admin therefore, it returns 404. Try to place the root /usr/share/ to the server block instead of a location block.
I have a configuration file like this one below:
server {
listen 80;
server_name localhost;
#charset utf-8;
root html/laravel/public;
index index.html index.php;
#browse folders if no index file
autoindex on;
# enforce NO www
if ($host ~* ^www\.(.*))
{
set $host_without_www $1;
rewrite ^/(.*)$ $scheme://$host_without_www/$1 permanent;
}
# serve static files directly
location ~* \.(jpg|jpeg|gif|css|png|js|ico|html)$ {
access_log off;
#expires max;
}
# removes trailing slashes (prevents SEO duplicate content issues)
if (!-d $request_filename)
{
rewrite ^/(.+)/$ /$1 permanent;
}
# canonicalize codeigniter url end points
# if your default controller is something other than "welcome" you should change the following
# if ($request_uri ~* ^(/lobby(/index)?|/index(.php)?)/?$)
# {
# rewrite ^(.*)$ / permanent;
# }
# removes trailing "index" from all controllers
if ($request_uri ~* index/?$)
{
rewrite ^/(.*)/index/?$ /$1 permanent;
}
# unless the request is for a valid file (image, js, css, etc.), send to bootstrap
if (!-e $request_filename)
{
rewrite ^/(.*)$ /index.php?/$1 last;
break;
}
# redirect server error pages to the static page /50x.html
#
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
location /backend/ {
root /html/frontend;
}
location ~ \.php$ {
include fastcgi.conf;
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
include fastcgi_params;
}
location ~ /\.ht {
deny all;
}
# catch all
# error_page 404 /index.php;
# location ~ \.php$ {
# try_files $uri =404;
# fastcgi_pass unix:/tmp/php.socket;
# fastcgi_index index.php;
# #include fastcgi_params;
# include /home/tamer/code/nginx/fastcgi_params;
# }
# access_log /home/tamer/code/laravel/storage/logs.access.log;
# error_log /home/tamer/code/laravel/storage/logs.error.log;
}
I have to change root folder to html/backend for any url with $host/backend/. All rules for load pages have to be the same, only root folder have to change.
How can I do that?
server {
location / {
root /data/www;
}
location /images/ {
root /data;
rewrite ^/images/(.+?)$ $1 break; #following is the explation
}
}
use break to continue; the root in location will take effect
use last to internal simulate request; the root in location will not take effect
use permanent to 301 redirect;
use redirect to 302 redirect;
adding 127.0.0.1 to server_name to be able to use the link you provided in the comment 127.0.0.1
server_name localhost 127.0.0.1;
also you still need to have the backend location with root inside it.
location /backend/ {
root /html/backend;
}
I'll take a wild guess here:
location /backend/ {
root /html/backend;
try_files $uri $uri/ /index.php?_url=$uri&$args;
}
This means: all requests to .../backend/* will be redirected to the location block of php followed after:
location ~ \.php${ ... }
and php will handle those requests as backend scripts
Nginx Beginner's Guide has this example:
server {
location / {
root /data/www;
}
location /images/ {
root /data;
}
}
So in theory this should work for you:
server {
listen 80;
server_name localhost;
location / {
root html/laravel/public;
}
location /backend/ {
root html/backend;
}
# common config goes here
}
If I understood the question correctly you can use alias to change just the OS search path for a specific location:
Defines a replacement for the specified location. For example, with the following configuration on request of “/i/top.gif”, the file /data/w3/images/top.gif will be sent.
location /i/ {
alias /data/w3/images/;
}
You need to define new location and use alias instead of root or else the behaviour would be funky. Also you need to define location for .php to use $request_filename.
location /backend {
alias /html/backend;
try_files $uri $uri/ /index.php$is_args$args;
location ~ \.php$ {
fastcgi_param SCRIPT_FILENAME $request_filename;
}
}
My problem is following: I use Wordpress on Nginx with "pretty links". I also run 2 other services on ports 88 and 1234 and I want to make a subdomains bugs.mydomain and mail.mydomain. I did the proxypass on location / but it's working only for the main directory, anything that is after the domain/ is falling into Wordpress "pretty links" mechanism. Do you have any idea how to solve this? My config files below:
The server config:
server {
listen <IP>:80;
root /usr/share/nginx/www/domain;
index index.html index.htm index.php;
server_name domain www.domain;
location / {
try_files $uri $uri/ /index.html;
if ( $host ~ "bugs.domain" ) {
proxy_pass http://domain:88;
}
if ( $host ~ "mail.domain" ) {
proxy_pass http://domain:1234;
}
}
location /doc/ {
alias /usr/share/doc/;
autoindex on;
allow 127.0.0.1;
deny all;
}
location ~ \.php$ {
try_files $uri =404;
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass unix:/var/run/php5-fpm.sock;
fastcgi_index index.php;
include fastcgi_params;
}
location ~ /\.ht {
deny all;
}
include /home/domain/public_html/nginx.conf;
}
the config for specified domain (with Wordpress):
#First there is many rewrites for the W3TC plugin, like minification, caches etc
if ($host ~* ^www\.(.*))
{
set $host_without_www $1;
rewrite ^/(.*)$ $scheme://$host_without_www/$1 permanent;
}
#
# unless the request is for a valid file, send to bootstrap
if (!-e $request_filename)
{
rewrite ^(.+)$ /index.php?q=$1 last;
}
Now, when I enter domain:88 or domain:1234 it works. When I enter bugs.domain the website loads, but no CSS or images works as the url is bugs.domain/somapath and this falls into the Wordpress bootstrap. I run out of the ideas.
why create only 1 server with if's in it, separate the servers
server {
listen 80;
server_name bugs.example.com;
proxy_pass http://example.com:88;
}
server {
listen 80;
server_name mail.example.com;
proxy_pass http://example.com:1234;
}
server {
listen 80;
# the rest of your main server
#
}
So the problem was completely different then I thought. it was failing on this line:
try_files $uri $uri/ /index.html;
The problem was, that file index.html didn't exist, I only had index.php. Changing it solved the problem.
I have a location which simply for some reason isn't triggering. I've tried the routes in all sorts of different orders, and still it doesn't work. When a user comes along and requests /_hostmanager/ it should trigger, but instead it gets the index.php page from the route.
The server config file is:
server {
index index.php index.html;
root /var/www/html;
server_name _;
listen 80;
# Logging
error_log /var/log/httpd/elasticbeanstalk-error_log;
# Route standard requests
location / {
try_files $uri $uri/ /index.php;
}
# Proxy Hostmanager
location /_hostmanager/ {
proxy_pass http://127.0.0.1:8999/;
}
# Include PHP
location ~ \.php {
# CGI Configuration
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include /etc/nginx/fastcgi_params;
fastcgi_index index.php;
# Zero-day exploit defense
try_files $uri $uri/ /index.php =404;
# Use socket for connection
fastcgi_pass unix:/tmp/php5-fpm.sock;
}
# Cache control
location ~* \.(jpg|jpeg|gif|png|css|js|ico|xml)$ {
log_not_found off;
expires 360d;
}
# Disable hidden files
location ~ /\. {
deny all;
}
}
Can anyone spot what my (probably stupid!) error is?
Thanks in advance! :)
Nevermind, I worked it out! For some reason using the reload command on nginx wasn't working. stopped and started and voila!
My nginx version is :
root#v-enterprise15:/etc/nginx/conf.d# nginx -v
nginx: nginx version: nginx/1.0.5
My application is installed at
/usr/share/nginx/www/magento/current
When I access
http://{my_server}:81/magento/current/index.php
it works fine. This is because the server root is set to /usr/share/nginx/www;
Now I want to acces the app using http://{myserver}:81/index.php.
When I change the server root to /usr/share/nginx/www/magento/current and type the above URL, it REDIRECTS with http 302 to
http://{my_server}:81/magento/current
What might be the reason for this?
It then applies other rules from my .conf and gives a 404.
I see this in the access log:
[31/Jul/2012:11:19:23 +0530] "GET /index.php HTTP/1.1" 302 5 "-" "Opera/9.80 (Windows NT 6.1; U; en) Presto/2.10.229 Version/11.64"
My .conf file is:
server {
listen 81 default;
## SSL directives might go here
server_name {my_server};
#root /usr/share/nginx/www;
root /usr/share/nginx/www/magento/current;
error_log /var/log/nginx.error.log notice;
access_log /var/log/nginx.access.log ;
rewrite_log on;
location / {
auth_basic "Restricted"; ## Message shown in login window
auth_basic_user_file htpasswd; ## See /etc/nginx/htpassword
index index.html index.php; ## Allow a static html file to be shown first
try_files $uri $uri/ #magehandler; ## If missing pass the URI to Magento's front handler
#try_files $uri $uri/ ; ## If missing pass the URI to Magento's front handler
#expires 30d; ## Assume all files are cachable
}
location ^~ /. { ## Disable .htaccess and other hidden files
return 404;
}
location #magehandler { ## Magento uses a common front handler
#rewrite / /index.php;
rewrite ^(.*) index.php$1 last;
}
#The more-specific regex are at the top.
#The regex's are evaluated in the order in which they appear.
location ~ .php$ { ## Execute PHP scripts
#if (!-e $request_filename) { rewrite / /index.php last; } ## Catch 404s that try_files miss
proxy_read_timeout 120;
proxy_connect_timeout 120;
expires off; ## Do not cache dynamic content
fastcgi_pass 127.0.0.1:9000;
#fastcgi_param HTTPS $fastcgi_https;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param MAGE_RUN_CODE default; ## Store code is defined in administration > Configuration > Manage Stores
fastcgi_param MAGE_RUN_TYPE store;
include fastcgi_params; ## See /etc/nginx/fastcgi_params
}
location ~ /(media|skin|js)/ { }
location ~ /(tag|admin|customer|wishlist|checkout|catalog|app).*$ { #store URL
rewrite /(.*)$ /index.php/$1 last;
}
location ~ /[a-zA-Z]+$ { #store URL
rewrite ^/([a-zA-Z]+) ?store=$1 last;
}
location ~ /[a-zA-Z]+/ { #store URL
rewrite ^/([a-zA-Z]+)(.*) /$2?store=$1 last;
}
Since you have not any redirects in your nginx config, then it is most likely that redirect caused by your application.