nginx + php in a user's public_html
location ~ ^/~(.+?)(/.*)?$ {
alias /home/$1/public_html/$2;
autoindex on;
}
Here is for the main site's php:
location ~ \.php$ {
include /etc/nginx/fastcgi_params;
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME /srv/www/youdolinux.com/html$fastcgi_script_name;
}
I have tried doing a copy of the publichtml config and including ".php" and ".php$" in every conceivable part of the location line, but nothing works when I restart nginx. There's no error when restarting nginx, but it still thinks php files loaded from my user's publichtml are BIN files.
(BTW, I'm the only user on my Linode who actually uses php in my public_html dir, though I trust the other two users enough to let them if they want to)
8 Replies
You can use PHP with arbitrary subdomains: see here
@Eamonn:
Check what user php-fpm is running as and can that user read files in the users public_html.
I didn't think of permissions
I'm going to set the group instead, though: since /home/piki/public_html rightfully belongs to user piki and need to be read by php-fpm, it makes more sense to leave user ownership to piki so he can still modify the files and set group ownership to www-data for reading by php-fpm
When there are multiple "location" directives with regular expressions in them, nginx will stop looking after it finds the first match. This probably means that your PHP-specific "location" directive is never being evaluated in the first place.
You can use PHP with arbitrary subdomains: see here. But I don't think it will work with your tilde-is-userdir scheme.
Just at a quick glance, that looks more like it's for configuring several subdomains under the same server block. Just to avoid being redundant, I don't want the userdir load for each subdomain, just for the main one.
That does give me an idea on what to do with my location drectives to make it work.
Seems like a common enough problem, but no one has the answer. Hmm.
server {
listen 80;
server_name yoursite.com;
root /srv/http/yoursite.com/public_html;
index index.php index.html index.htm;
# Not really needed, but in my experience it seems to help performance
try_files $uri $uri/ /;
# server-side includes
# Allows the HTML include statements, set off if you don't need this
ssi on;
# Don't allow access to dotfiles (such as .htaccess)
location ~ /\. {
deny all;
}
# This MUST appear above both the normal userdir and php location blocks
# else it will either attempt to load from your main (non-user) site
# or ask vistors to download PHP files (which can be bad for security)
location ~ ^/~(.+?)(/.+\.php)$ {
alias /home/$1/public_html$2;
autoindex on;
# default fastcgi settings
include fastcgi_params;
# A bit of added security -- not full proof, but can help
fastcgi_split_path_info ^(.+\.php)(/.+)$;
# NOTE: You should have "cgi.fix_pathinfo = 0;" in php.ini
fastcgi_pass unix:/run/php-fpm.sock;
fastcgi_index index.php;
}
# These next two location blocks can be switched without issue, as long
# as you keep them both BELOW the location block above!!!
location ~ ^/~(.+?)(/.*)?$ {
alias /home/$1/public_html$2;
autoindex on;
}
location ~* \.php$ {
# default fastcgi settings
include fastcgi_params;
# A bit of added security -- not full proof, but can help
fastcgi_split_path_info ^(.+\.php)(/.+)$;
# NOTE: You should have "cgi.fix_pathinfo = 0;" in php.ini
fastcgi_pass unix:/run/php-fpm.sock;
fastcgi_index index.php;
}
}
My issue was that I had placed the userdir, userdir php, and normal php in the wrong order. I had my normal php location above my userdir and userdir php locations. Visiting mysite.com/~myuser would first match my non-php userdir location and then see index.php, causing it to search the location blocks again and re-match it against the normal php location. Since the normal php location looks in my main site (not my userdir), it would try to load the file from my main site.
With the order in the config above, mysite.com/~myuser will first match the userdir location (the one without the php), then if it sees index.php it will re-search the location blocks and re-match against the userdir php file.
The reason the order is important is because, as hybinet points it, it stop as soon as it finds a location block that matches the URL. This didn't immediately ocur to me as being a problem – I was thinking that the userdir location would take precedence over the php location by virtue of the fact that it has ~myser in the URL (regardless of whether I'm using .html or .php), but nginx seems not to see it that way. It seems not to care the order that the elements of the URL are in, only the those elements are there (in other words, it doesn't care that ~myuser comes before index.php, it cares only that both ~myuser and index.php are in the URL, and matches whichever comes first in the vhost config).