I am trying to accomplish two things in regards to nginx rewrites. First is to rewrite something like this:
oldvhost.domain.com/?dir=Dir1/Dir2/Dir3 -->
newvhost.domain.com/?dir=./Dir1/Dir2/Dir3
Notice the "./" in front of the second vhost?
Secondly I am trying to rewrite something like this:
oldvhost.domain.com/orginal.php?file=Dir1/Dir2/Dir3/file.zip ->
newvhost.domain.com/newphpfile.php?file=./Dir1/Dir2/Dir3/file.zip
I have managed to get this to work "somewhat" by doing this on the new vhost before any location commands:
rewrite ^/original.php$ /newphpfile.php$1 last;
But this isn't working 100% and is only remedied by the $realpath PHP function. I still need this working via regex rewrite but there's something about the "?"s that are making it fail.
As for the redirection you can do this in a location
location /something
return 301 http://example.com/?dir=./$arg_dir;
}
Or if you want it as a rewrite
rewrite /old-example.com/location-from.php http://example.com/new-location.php?./$arg_dir permanent;
and for the rewrite it should be similar as the second redirection, but no need for full host name
rewrite /old-location.php /new-location.php?./$arg_dir;
And here's the documentation of the $arg_name
The best way to do this in Nginx would be a rewrite, using reg expressions.. Try the code below in your virtual host.
location / {
#Rewrite for directory
rewrite ^/?dir=(.*) http://yoururl.com/?dir=./$1;
#rewrite for file
rewrite ^/origional.php?file=(.*) http://yoururl.com/newphpfile.php?file=./$1;
}
The first rewrite takes care of your directory. Please note it is being assumed that all incoming links do not have the necessary ./ you need. If they come with the ./ it may cause breakage. Or it may cause nothing, depending on what the PHP is doing.
Related
I was wondering how I can make the URL of my website different from the path of the file in my website directory.
For example, let's say I want my website language to be in the URL (mywebsite/en/index.php) but I don't want to manually have to create each php file in my website directory containing just an include from my main files, how could I do that please? I'm using Nginx if needed
You can use nginx rewrite regex rules.
Nginx rewrite rules
Let's say you want the url below to hit index.php with the language code.
Url: https://yourwebsite.com/en/index.php
FilePath: /path/to/www/index.php
rewrite ^/(.*)/index.php$ /index.php?lang=$1 last;
# another example
# $1 is the matching characters in regex `(.*)`
rewrite ^/sales/(.*)/categories.php$ /some/path/cat.php?categories=$1 last;
Do not forget. All URL's are imaginary but all files are real. URLs do not need to match the real files.
URL: https://yourwebsite.com/index.php may hit /some.file.asp
Look at the official nginx documentation for more details.
Hope, it helps.
I have been looking to rewrite my api URLs so they don't have a trailing slash. I use NGinx and not Apache. I did find this answer to the same question for an Apache server, but it is not going to work out of the box for NGinx.
I ended up taking this sample Apache config and used a config rewrite service to convert the config to Nginx format. It produces a mostly working, but slightly broken solution. It accesses the URLs like it is supposed to, but it breaks accessing resources and causes the /api/index.php to be dumped as a download when accessing a non-existent file or directory in /api/.
I played around with the config to produce the below config which uses the html 404 message provided to the whole server.
NGinx
location /api {
if (-e $request_filename){
rewrite ^/(.*[^/])$ /$1/;
}
}
My File structure is:
/api/index.php
/api/hotbits/index.php
/api/cryptography/index.php
With the new config option, this translates to these functional URLs:
/api
/api/
/api/hotbits
/api/hotbits/
/api/cryptography
/api/cryptography/
I'm performing a migration from an Apache server to Nginx and missed a .htaccess file that performs a rewrite:
RewriteRule ^(.*)$ routes.php?params=$1 [NC,QSA]
For example, this endpoint example.com/api/v1/param1/param2/param3 would be rewritten as https://example.com/api/v1/routes.php?params=/param1/param2/param3
Can someone confirm that this is the correct equivalent for Nginx before I re-attempt the migration?
rewrite "(?i)^(.*)$" routes.php?params=$1
and is this how it would be used in the config file since /api/v1 is the only path that requires the rewrite?
location /api/v1 {
rewrite "(?i)^(.*)$" routes.php?params=$1
}
UPDATE
Adding this to the conf file in Laravel Forge appears to just break the application and prevents displaying any views. Instead, it says This site can’t be reached example.com refused to connect.
All nginx URIs begin with a leading /, and your regular expressions do not attempt to remove the /api/v1/ prefix before appending the parameter list.
Try:
location /api/v1 {
rewrite ^/api/v1(/.*)$ /api/v1/routes.php?params=$1 last;
}
Recently I use nginx, but i have a problem with rewriting.
When i go to the orginal url there is no problem, when i use the rewrited url and its no *.php There is no problem. But when i use the rewrited url with a php file i get the error: no input file specified.
I think the rewrited url go to php and php can't find it because its rewrited and not a real file.
This is my rewrite rule:
location /folder {
if (!-e $request_filename){
rewrite ^/folder\/.*?\/(.*) /folder/$1 break;
}
}
You can probably simplify this by just using a different location path, then you can completely avoid the if statement.
This is untested and might need some tweaking, but the general idea should be clear
location ~ /folder\/.*?\/(.*).php$ {
rewrite ^ /folder/$1 permanent;
}
I am running a joomla 2.5 site on ubuntu server with php/nginx/mysql (fairly new to nginx)
My problem is that when a user hits a url, I need it to ignore the .html file extension.
For example, if you hit mysite.com/page then it renders the page fine.
If you hit mysite.com/page.html then it will throw a 404 error. Which is because there isn't actually a 'page.html' page on my site. Its a K2 article alias. Yes, I could not put .html in but its not me adding content to the site, its the client. I have recently moved server and before it worked fine, now it doesnt so I know I have missed something in the config.
I know I can get nginx to do the opposite of what I want, with try files. Not sure how to get it to do the reverse.
This is my nginx config:
location / {
# First attempt to serve request as file, then
# as directory, then fall back to index.html
try_files $uri $uri/ /index.php;
# Uncomment to enable naxsi on this location
# include /etc/nginx/naxsi.rules
}
Now I know if i had a page.html page and I wanted to hide the .html I could add $uri.html
What I want to know is how to get nginx to try page.html if it cant find it try page
So turned out to be a Joomla Config variable. Under SEO settings in global config set 'apply suffix' to yes. I feel quite stupid. Thanks to all those that tried to help, as always much appreciated.
Here's a potential solution I managed to come across:
location / {
# If /{foo} is not an existing file or directory, rewrite to /{foo}.html
if (!-e $request_filename) {
rewrite ^(.+)$ /$1.html break;
}
# Redirect all {foo}.html URLS to /{foo}
rewrite ^/(.*)\.html$ /$1 redirect;
}
If you can correctly write .htaccess rewrite lines, try using a htaccess-to-nginx converter
As commented, this will check for the existence of a directory, file, etc. using the current URL. If nothing exists, it will attempt to request the url with .html appended.
Additionally, if .html is already present in the URL, it will redirect to the URL without .html
Quick workaround:
rewrite ^(. *)\.html$ $1 break;
Should be the first rewrite in the stack, even before try_files.