I want my nginx make display all url's clean.
http://www.mydomain.com/indexhtml.html as http://www.mydomain.com/indexhtml
http://www.mydomain.com/indexphp.php as http://www.mydomain.com/indexphp
With some research I've made the first case to work. It`s done by following configuration:
location / {
root html;
index index.html index.htm index.php;
try_files $uri.html $uri/ =404;
}
It works for indexhtml.html displaying as indexhtml, but nothing happens with .php. If I change $uri.html to $uri.php, it works neither for .html, neither .php. I`ve tried to put something similar in php location but without any success.
Any advices?
From what I've researched, if you append your /etc/nginx/conf.d/domain.tld.conf file to include:
location / {
try_files $uri $uri.html $uri/ #extensionless-php;
index index.html index.htm index.php;
}
location ~ \.php$ {
try_files $uri =404;
}
location #extensionless-php {
rewrite ^(.*)$ $1.php last;
}
Then restart nginx and give it a go. Hopefully this will help you! More information can be found (where I found it) here # tweaktalk.net
No need for extra blocks and named locations and everything. Also move the index line outside the location block
server {
index index.html index.php;
location / {
try_files $uri $uri/ $uri.html $uri.php$is_args$query_string;
}
location ~ \.php$ {
try_files $uri =404;
# add fastcgi_pass line here, depending if you use socket or port
}
}
Keep in mind that if you have a folder and a file with the same name inside the same folder, like /folder/xyz/ and /folder/xyz.php you won't be able to run the php file if the folder xyz contains an index.php or index.html, just keep this in mind.
To further Mohammad's answer, you might also want to offer redirects from .html and .php to the extensionless versions.
This can be accomplished due to the fact that $request_uri contains "full original request URI (with arguments)", and is not affected by the internal rewrites that are not visible to the user.
server {
index index.html index.php;
location / {
if ($request_uri ~ ^/(.*)\.html$) { return 302 /$1; }
try_files $uri $uri/ $uri.html $uri.php?$args;
}
location ~ \.php$ {
if ($request_uri ~ ^/([^?]*)\.php($|\?)) { return 302 /$1?$args; }
try_files $uri =404;
# add fastcgi_pass line here, depending if you use socket or port
}
}
This has worked for me for more than 5 years going.
location / {
try_files $uri/ $uri.html $uri.php$is_args$query_string;
}
Perhaps this may be of use for you... It' Simple and gets the job done:
location / {
rewrite ^/([^\.]+)$ /$1.html break;
}
Related
I thought I had understood the basics of nginx rewrite rules. How wrong I was.
Can you please let me know what is I am doing so wrong here:
server {
listen 80;
server_name myserver;
index index.php index.html index.htm;
root /apps/user/websites/;
location / {
autoindex on;
}
location ~ myapp {
try_files $uri $uri /office/myapp/api/public/index.php;
}
location ~\.php$ {
try_files $uri $uri /office/fake/index.html;
# include fastcgi.conf;
# fastcgi_pass php-fpm-upstream;
}
}
If I visit http://myserver/office The index.php is accessed, but instead of being caught by the last location (~.php$) as I thought it would, it is processed as a text file and send to the browser.
I was expecting to receive the office/fake/index.html file instead.
Thank you very much,
Andres
Regex matching locations are checked in the same order they are appeared in the config file. Having the
location ~ myapp {
try_files $uri $uri /office/myapp/api/public/index.php;
}
before the
location ~\.php$ {
try_files $uri $uri /office/fake/index.html;
# include fastcgi.conf;
# fastcgi_pass php-fpm-upstream;
}
would give you an endless loop on every URI containing myapp substring (except those that are matching existed files and not ended with .php) because the /office/myapp/api/public/index.php URI matches the myapp regex. You should swap those locations in order to get this configuration workable.
my old server had this in the htaccess file:
< FilesMatch "^resort$">
ForceType application/x-httpd-php
< /FilesMatch>
where I had a resort php file (without the php extension)...
so the file was domain.com/resort/param1/param2
I'm struggling to make the equivalent work for nginx...
i've tried these items, but none work:
location = /resort/ {
try_files $uri /resort.php;
try_files $uri $uri/ #extensionless-php;
try_files $uri $uri/ $uri.html $uri.php?$query_string;
try_files $uri $uri/ /resort.php$is_args$args;
rewrite ^(.*)$ /resort.php last;
}
So how do I execute the resort file as php, when this url is in the browser:
domain.com/resort/param1/param2.php
THANKS!
PS. would love some pages/resources/tutorials that explain "apache to nginx" for people who don't understand nginx :)
i've been to nginx site, but IMO, I need to know more than I do to figure it out or understand what the nginx site is saying.
update:
i think this is close, but still not working :(
this is url: domain.com/resort/city/state.php
here is directive:
location ~ /resort/ {
rewrite ^/resort/(.*)/(.*) /resort/$1/$2 break;
}
this is what worked for me:
location ^~ /resort/ {
try_files $uri $uri/ /resort.php; }
To execute a file without a .php extension as though it was a PHP file, you will need to replicate the location block that handles those types of request.
It will look something like this:
location ~ \.php$ {
try_files $uri =404;
include fastcgi_params;
fastcgi_pass ...;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
}
To process the URI /resort/param1/param2 using the PHP file located at /resort, you might use something like:
location ~ ^/resort/ {
include fastcgi_params;
fastcgi_pass ...;
fastcgi_param SCRIPT_FILENAME $document_root/resort;
}
See this document for location syntax.
I am running CodeIgniter 3.0.6 in an Nginx server and subpaths end up serving /index.php, rather than /<installdir>/index.php. So, if I ask for /CodeIgniter-3.0.6/home/ I get served the /index.php page instead, rather than /CodeIgniter-3.0.6/index.php as expected. Note, that my CodeIgniter application will eventually reside in /2016/.
I suspect this is down to a misconfiguration of my Nginx install, rather than something CodeIgniter related? My Nginx install is running on Ubuntu 16.04. The contents of the /etc/nginx/sites-enabled/default are:
location / {
try_files $uri $uri/ /index.php;
}
location ~ \.php$ {
fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
include fastcgi.conf;
}
Is there something else I should be changing?
If your server has a single application with the main entry point at /CodeIgniter-3.0.6/index.php, you should probably set your locations like this:
location / {
try_files $uri $uri/ /CodeIgniter-3.0.6/index.php;
}
location ~ \.php$ {
try_files $uri =404;
fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
include fastcgi.conf;
}
That way, any URI that is not a match for a resource file or a .php file, will be routed to your applications default entry point /CodeIgniter-3.0.6/index.php.
However, if there is more than one application, such that /index.php and /CodeIgniter-3.0.6/index.php are two distinct entry points, you may want to set up locations for each application, possibly like this:
location / {
try_files $uri $uri/ /index.php;
}
location /CodeIgniter-3.0.6 {
try_files $uri $uri/ /CodeIgniter-3.0.6/index.php;
}
location ~ \.php$ {
try_files $uri =404;
fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
include fastcgi.conf;
}
That way, only URIs that begin with /CodeIgniter-3.0.6 will be routed to that application's default entry point.
I'm writing a simple CMS in PHP. Pages (markdown files) and images are accessed like this (respectively):
example.org/?q=about.md
example.org/?i=photo.jpg
Optionally, I would like to use clean URLs with Nginx, to make the same requests look like this:
example.org/about
example.org/photo.jpg
I rather use try_files than if and rewrite but after experimenting for hours, I can't get it to work.
location / {
try_files $uri $uri/ /?q=$uri.md =404;
}
location ~ \.(gif|jpg|png)$ {
try_files $uri /?i=$uri =404;
}
I don't understand why the above code doesn't work (urls with argument work fine but the pretty ones give 404 errors).
Is there something wrong with passing the folder name as an argument using $uri?
Do I need to escape some weird characters (apart from my landlord)?
To be thorough, I'm running Nginx 1.6.2, using the standard nginx.conf.
Here's the rest of my server block:
server_name example.org;
root /srv/example/;
index index.html index.htm index.php;
(...)
location ~ \.php$ {
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass unix:/var/run/php5-fpm.sock;
fastcgi_index index.php;
include fastcgi.conf;
}
and fastcgi.conf is also standard.
I was able to get your example to work by simply omitting the =404:
location / {
try_files $uri $uri/ /?q=$uri.md;
}
location ~ \.(gif|jpg|png)$ {
try_files $uri /?i=$uri;
}
Quoting the manual:
Checks the existence of files in the specified order and uses the first found file for request processing; [...] If none of the files were found, an internal redirect to the uri specified in the last parameter is made.
You want that internal redirect, which is only happening if none of the files are found, but =404 is always found.
I'm using nginx with PHP-FPM on a ISPConfig3 server.
I put the following rewrite-rule in my nginx-directives (to make prettier links in Pydio):
location ~ \.php$ {
try_files #php;
}
location #php {
try_files $uri =404;
include /etc/nginx/fastcgi_params;
fastcgi_pass 127.0.0.1:9026;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_intercept_errors on;
}
proxy_set_header X-Accel-Mapping /var/www/XXXYYY.com/pydio/data/=/data/;
location /conf/ { deny all; }
location /data/ { internal; }
location /data/public/ {
try_files $uri $uri.php =404 last;
}
I want URLs in pydio.XXXYYY.com/data/public/* to have a .php-extension added.
This rule finds the files without the .php in the address bar but now they are downloaded instead of executed.
Since I use ISPConfig3, the rewrites for .php-files (to have them executed by PHP-FPM) is above the stated part. But I thought adding "last" should take care of that.
What else could I try?
Thank you!
First of all, you misunderstand the try_files directive. There's no "last" argument and it doesn't work like you think. Please, check the documentation: http://nginx.org/r/try_files. It's technical documentation, read it literally, every word has meaning.
To solve your problem you have to remove two last arguments from try_files:
try_files $uri $uri.php =404 last;
should be replaced with:
try_files $uri $uri.php;