Exclude certain subfolders and domains in redirects - html

This is a continuation from Redirect only HTML files?
How can I change my .htaccess to make it exclude certain subfolders or subdomains from the HTML-only redirect? I tried doing using this code to exclude the 'downloads' subfolder and the 'dev' and 'support' subdomains, but it didn't work:
RewriteCond %{HTTP_HOST} ^pandamonia.us$ [OR]
RewriteCond %{HTTP_HOST} ^www.pandamonia.us$ [OR]
RewriteCond %{HTTP_HOST} !download [OR]
RewriteCond %{HTTP_HOST} !faq
RewriteCond %{HTTP_HOST} !support [OR]
RewriteRule /.+\.html$ "http\:\/\/pandamonia\.us\/" [L]

You need to check REQUEST_URI or the whole match of the RewriteRule $0 for this; HTTP_HOST does only contain the host name of the current request. You also need to change the logical expression of your condition:
RewriteCond %{HTTP_HOST} ^pandamonia\.us$ [OR]
RewriteCond %{HTTP_HOST} ^www.pandamonia\.us$
RewriteCond %{REQUEST_URI} !^/download/
RewriteCond %{REQUEST_URI} !^/faq/
RewriteCond %{REQUEST_URI} !^/support/
RewriteRule /.+\.html$ http://pandamonia.us/ [L]

For those looking for a quick bit of insight into Gumbo's previous reply (where he mentions the situations for when to (and not to) use [OR], I found this WMW thread very helpful: http://www.webmasterworld.com/apache/3522649.htm

Related

How To make Custom Links Without Showing page not found error [duplicate]

I want to redirect all pages on my site (including index) to UnderWork.html
and I'm doing this using .htaccess with this code:
RewriteEngine on
RewriteRule ^(.*)$ UnderWork.html
...and its works fine.
Now I am adding some more code to my .htaccess to redirect all traffic to the non-www domain and now my code looks like this:
RewriteEngine on
RewriteCond %{HTTP_HOST} ^www\.domain\.in
RewriteRule ^(.*)$ http://domain.in$1 [R=permanent,L]
RewriteRule ^(.*)$ UnderWork.html
Here is where I have a problem. If I enter a URL like: domain.in/xyz then it works as before, but if I use a URL like: www.domain.in/xyz then Apache converts it to coincart.inxyz/.
What am I doing wrong here? How can I get what i want? Thanks in advance.
Below are rules that work for me:
RewriteEngine On
# Adding trailing slash for directory requests.
RewriteCond %{REQUEST_FILENAME} -d
RewriteCond %{REQUEST_URI} !^/www$
RewriteCond %{HTTP_HOST} !^www\.
RewriteRule ^(.+[^/])$ http://example.com/$1/ [R=permanent]
# External redirection from www subdomain to non-www domain.
RewriteCond %{HTTP_HOST} ^www\. [NC]
RewriteRule ^/?(.*) http://example.com/$1 [L,R=permanent]
# Internal redirection to index.php for nonexistent URLs.
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !\.(jpg|jpeg|png|gif)$
RewriteRule . /index.php [L,QSA]
To show a custom page when a directory root (domain root in particular) is requested, use the Apache's DirectoryIndex directive:
DirectoryIndex UnderWork.html

Combining HTAccess rules into one

Hey everyone im trying to use Htaccess to redirect all pages to https:// while keeping the query string without fbclid if it's there.
IE.
https://www.example.com/?sdfuh
http://www.example.com/?sdfuh
www.example.com/?sdfuh
https://www.example.com/?sdfuh&fbclid=azduh
http://www.example.com/?sdfuh&fbclid=azduh
www.example.com/?sdfuh&fbclid=azduh
example.com/?sdfuh&fbclid=azduh
They should return https://example.com/?sdfuh
Ok so after some help Ive got to this
RewriteCond %{HTTP_HOST} ^(www.)?example.com$ [AND]
RewriteCond %{QUERY_STRING} ^(.*)(?:^|&)fbclid=(?:[^&]*)((?:&|$).*)$ [NC]
RewriteRule ^(.*)/?(.*)$ https://example.com/?%1 [R=301,L]
RewriteCond %{HTTP_HOST} ^(www.)?example.com$ [AND]
RewriteCond %{QUERY_STRING} ^(.*)
RewriteRule ^(.*)/?(.*)$ https://example.com/ [R=301,L]
RewriteCond %{HTTP_HOST} ^(www.)?example.com$
RewriteRule ^(.*)/?(.*)$ https://example.com/ [R=301,L]
RewriteCond ^(www.)?example.com$
RewriteRule ^(.*)/?(.*)$ https://example.com/ [R=301,L]
This works with:
https://www.example.com/?sdfuh
http://www.example.com/?sdfuh
www.example.com/?sdfuh
https://www.example.com/?sdfuh&fbclid=azduh
http://www.example.com/?sdfuh&fbclid=azduh
Not with
www.example.com/?sdfuh&fbclid=azduh
example.com/?sdfuh&fbclid=azduh
I need to figure out how to make it shorter and work with all the possibilities
Rather than literally combining the rules, I believe the main piece of knowledge you are missing out on is the use of [OR] - which means a RewriteRule won't fail if only one of the RewriteCond results in true.
RewriteCond %{HTTP_HOST} ^(www.)?example.com$ [OR]
RewriteCond %{QUERY_STRING} ^(.*)(?:^|&)fbclid=(?:[^&]*)((?:&|$).*)$ [NC]
RewriteRule ^(.*)/?(.*)$ https://example.com/?%1%2 [R=301,L]
You can test this out here: https://htaccess.madewithlove.be?share=f4381086-80b4-52b6-883e-8921f5de2316
After alot of help this solved my issue of stripping facebooks tracker, keeping my own query string and confirming https:// is used.
RewriteCond %{QUERY_STRING} ^(.*)(?:^|&)fbclid=(?:[^&]*)((?:&|$).*)$ [NC]
RewriteRule ^(.*)/?(.*)$ https://example.com/?%1%2 [R,N]
RewriteCond %{HTTPS} off [OR]
RewriteCond %{HTTP_HOST} ^www.example.com$
RewriteRule ^(.*)/?(.*)$ https://example.com/$2 [R,L]

Need to remove .html file extension and duplicate names

I have a .htaccess file with the contents below, that removes the .html file extension for all of my website's pages.
Options +MultiViews
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^([^\.]+)$ $1.html [NC,L]
RewriteEngine On
RewriteCond %{SERVER_PORT} !=443
RewriteCond %{HTTP_HOST} ^(www\.)?james-lee\.io$ [NC]
RewriteRule ^$ https://www.james-lee.io%{REQUEST_URI} [R,L]
My links now look like www.james-lee.io/resume/resume when before they looked like www.james-lee.io/resume/resume.html. I would like to remove the folder name so the name of the folder is not duplicated by the name of the file minus the .html and the final result looks like www.james-lee.io/resume.
I have seen similar questions but not exactly what I am looking for.
So I have done this task!
Try this code:
RewriteCond %{REQUEST_URI} ^/(.*)/(.*)$
RewriteCond %{DOCUMENT_ROOT}/%1 -d
RewriteCond %{DOCUMENT_ROOT}/%1/%2 -f
RewriteCond %1::%2 ^(.*)::\1$
RewriteRule ^(.*)$ /%1 [R,L]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^(.*)/(.*)$ /$1/$1 [END]
Now I try to explain this rules.
first line: you do request like /folder/file
second line: check if /folder/ real existing folder
third line: check if /folder/file is real existing file
fourth line: I use notation %1::%2 because backreferences can only
be used in the left part of RewriteCond. But it possible to reuse
left part in pattern of the right part. So, in the "^(.*)::\1$" I
check all before ::. Then I have result at the \1 backreference. So,
if folder is equal to file, text after :: will be equal to %2.
Next I just redirect to the result (/folder or /file, doesn't
matter, because both are equal)
But if folder == file, redirect will be always to the directory.
So, next I check, if redirect result is existing dir and change the link.
Request example:
http://yourdomain/test/test
(this will be redirected to http://yourdomain/test, but will reference to original link)
I hope, I explain clearly, but if you have any questions, I would glad to answer.
Thank you for insteresting task!
P.S. see also %N backreference inside RewriteCond
UPDATED. Your htaccess have to be like below:
RewriteEngine on
RewriteCond %{SERVER_PORT} !=443
RewriteCond %{HTTP_HOST} ^(www\.)?james-lee\.io$ [NC]
RewriteRule ^$ https://www.james-lee.io%{REQUEST_URI} [R,L]
RewriteCond %{REQUEST_URI} ^/(.*)/(.*)$
RewriteCond %{DOCUMENT_ROOT}/%1 -d
RewriteCond %{DOCUMENT_ROOT}/%1/%2\.html -f
RewriteCond %1::%2 ^(.*)::\1$
RewriteRule ^(.*)$ /%1 [R,L]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^(.*)/(.*)$ /$1/$1.html [END]
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^([^\.]+)$ $1.html [NC,L]

Infinite loop htaccess

Im trying to make a simple html web page in 3 languages. Each language has its directory, so the index.html in "/" is in english, the spanish index in "/es" and the french index is in "/fr". Im trying to create a redirection rule for each language based on browser language or a cookie establised in the href onclick by javascript. This is my .htaccess code:
RewriteEngine on
RewriteCond %{HTTP_COOKIE} !^.*lang=ES.*$ [OR]
RewriteCond %{HTTP:Accept_Language} (es) [NC]
RewriteRule .* http://myweb.com/es/$1 [R=301,L]
RewriteCond %{HTTP_COOKIE} !^.*lang=FR.*$ [OR]
RewriteCond %{HTTP:Accept_Language} (fr) [NC]
RewriteRule .* http://myweb.com/fr/$1 [R=301,L]
RewriteRule .* http://myweb.com/$1 [R=301,L]
RewriteCond %{ENV:REDIRECT_STATUS} 200
RewriteRule .* - [L]
It is not working because a infinite loop.
Thank you very much.
Redirect loop is happening due to unconditional last rule RewriteRule .* http://myweb.com/$1 [R=301,L]. Your first 2 rules also have have an error where they are not capturing any group but using them as $1.
Have your rules this way:
RewriteEngine on
RewriteCond %{HTTP_COOKIE} !^.*lang=ES.*$ [OR]
RewriteCond %{HTTP:Accept_Language} (es) [NC]
RewriteRule ^((?!es/).*)$ http://myweb.com/es/$1 [R=301,L,NE]
RewriteCond %{HTTP_COOKIE} !^.*lang=FR.*$ [OR]
RewriteCond %{HTTP:Accept_Language} (fr) [NC]
RewriteRule ^((?!fr/).*)$ http://myweb.com/fr/$1 [R=301,L,NE]
RewriteRule ^((?!(?:es|fr)/).*)$ http://myweb.com/$1 [R=301,L,NE,NC]
What happens is that each time a user enters a page they get redirected.
e.g.: someone has a cookie that says "es" but they go to the es directory, you will still redirect them to the es page, over and over again.
You should ad a condition saying on what page each redirect should work.
something like RewriteCond %{REQUEST_URI}
edit:
Here goes:
RewriteCond %{HTTP_COOKIE} !^.*lang=ES.*$ [OR]
RewriteCond %{HTTP:Accept_Language} (es) [AND]
RewriteCond %{REQUEST_URI} !^myweb.com/fr.*$
RewriteRule .* myweb.com/es/$1

Regex to avoid "dirty" web links

If this is my actual URL to a file:
http://www.example.org/posts.php?post=example-post-name
In my .htaccess file, how can I use a regular expression to get to this path when a user submits:
http://www.example.org/posts/example-post-name
So far I've come up with this bringing together a few examples (this also included a www redirect):
RewriteEngine On
RewriteCond %{HTTP_HOST} ^www\.(.*) [NC]
RewriteRule ^(.*) http://%1/$1 [R=301,L]
RewriteCond %{REQUEST_URI} !(\.[^./]+)$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule (.*) /$1.php [L]
RewriteRule ^posts/([A-Za-z])/$ /posts.php?post=$1
But I'm not having much luck with it, can anyone tell me where I'm going wrong?
You need a + after your A-Za-z group to indicate one or more characters, and also you need to add a - to the end of that group. At the end, the /? indicates that the final slash may or may not be present.
Finally, add [L] to be sure no further rewrite rules get processed.
RewriteEngine On
RewriteCond %{HTTP_HOST} ^www\.(.*) [NC]
RewriteRule ^(.*) http://%1/$1 [R=301,L]
# First rewrite the posts:
RewriteRule ^posts/([A-Za-z-]+)/?$ /posts.php?post=$1 [L]
# ing0 edit: add in dirs that need changing back.
# (I dont know if there is an easier way to do this).
RewriteRule ^posts/css/(.*)$ /css/$1 [L]
RewriteRule ^posts/img/(.*)$ /img/$1 [L]
# etc
# Then, if it's not a real file and doesn't already end in .php
# Note change here ...
RewriteCond %{REQUEST_URI} !\.php$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
# redirect it to PHP.
RewriteRule (.*) /$1.php [L]
I think you need to match the whole url and the regex wasn't quite right. Try this:
RewriteRule ^(.*)/posts/([\w-]+)$ $1/posts.php?post=$2
If it works only matching the non-base part of the url, this this:
RewriteRule ^posts/([\w-]+)$ posts.php?post=$1
Why not use:
RewriteRule ^posts/(.*)/$ posts.php?post=$1