I have two directories which I need to serve static assets out of:
/srv/web
: Static assets which include images, JavaScript, HTML, etc./srv/php
: Dynamic PHP scripts alongside some static assets.
I'm using NGINX and have configured it like so:
server {
listen 80;
server_name _;
# root /;
index index.php index.html index.htm;
try_files /srv/web/$uri /srv/php/$uri =404;
location ~ \.php$ {
root /srv/php;
try_files $uri =404;
fastcgi_pass unix:/var/run/php5-fpm.sock;
fastcgi_index index.php;
# fastcgi_param SCRIPT_FILENAME /srv/php$fastcgi_script_name;
include fastcgi_params;
}
}
I'm on Ubuntu 14.04, PHP FPM package version is 5.5.9, NGINX package version is 1.4.6.
The simple goal here is to serve static files out of /srv/web
first, failing that /srv/php
, failing that, return 404. All files ending in \.php$
will be requested from PHP FPM over the Unix socket, and this is working.
The problem I'm currently having is that the index
directive on the server
isn't working as planned. I have an index.html
file in /srv/web
, and when I do
curl -is http://localhost/
I get a 404.
Is this the most ideal way of setting up an NGINX site with multiple filesystem folders to serve from alongside PHP? Any ideas as to why my static index isn't working?
Update
As per AD7six's answer below, I've updated my configuration to look like this:
server {
listen 80;
server_name _; # listen at all host names
# serve static files first from /srv/web, then from /srv/php, and any dynamic PHP files from
# FastCGI/FPM at the Unix socket.
location / {
root /srv/web;
index index.html index.htm;
try_files $uri $uri/ @php;
}
location @php {
root /srv/php;
index index.php;
try_files $uri $uri/ =404;
}
location ~ \.php$ {
root /srv/php;
fastcgi_pass unix:/var/run/php5-fpm.sock;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME /srv/php/$fastcgi_script_name;
include fastcgi_params;
}
}
My directory listing looks like this:
/srv/
|-- php
| |-- demo.php
| |-- index.php
| `-- phpstatic.txt
`-- web
|-- static.html
`-- subdir
`-- index.html
3 directories, 5 files
Getting static files and PHP files works as planned and getting /subdir/
with its index works fine, but if I GET /
, I get a 403 forbidden, and nginx complains of directory listing:
2015/08/24 21:50:59 [error] 9159#0: *7 directory index of "/srv/web/" is forbidden, client: 127.0.0.1, server: _, request: "GET / HTTP/1.1", host: "localhost"
Not sure why this is failing, but it smells like progress at least.
Multiple roots won't work like that
With this config:
There is no request processing that would use the index directive, as written the request must match a file. Using the debug log confirms this:
Using a
try_files
directive that does look for directories like this:also doesn't work:
Note that the "root" is confused,
try_files
expects a url not a file path. I suggest not to continue trying to use a solution of this kind - especially not setting the root as/
and potentially allowing access to any file on the server.Use two location blocks
Instead keep things simple. This config will serve all the static content:
This config serves all php content:
Just put them together:
One gotcha is that with this kind of setup a request which matches a folder under
/srv/web
which doesn't have anindex.html
file will throw a 403 error (as the request is for a directory, and there is no directory index file). To allow these requests to also be handled by php - it's necessary to redirect 403 errors to the php handler.