Trailing slash 'bug' in mod_rewrite www-removal snippet - apache

I got a snippet to redirect all www.domain.com requests to domain.com from another SO question:
RewriteEngine On
RewriteCond %{HTTP_HOST} ^www\.(.*)$ [NC]
RewriteRule ^(.*)$ http://%1/$1 [R=301,L]
Unfortunately it results in an extra trailing slash:
www.domain.com redirects to domain.com// and
www.domain.com/path/ redirects to domain.com//path/
Should I really add an extra rule to remove the trailing slash? Or is there a problem with the above snippet?

Just removing the slash from the third line should work:
RewriteEngine On
RewriteCond %{HTTP_HOST} ^www\.(.*)$ [NC]
RewriteRule ^(.*)$ http://%1$1 [R=301,L]

Related

Mod_rewrite on a dynamic rule not working

I have several web sites and using the same mod_rewrite. I like to add two additional conditions to it and based on many of solutions that I have found on here and none seem to be working.
RewriteEngine On
RewriteCond %{HTTP_HOST} !^www\. [NC]
RewriteCond %{HTTP_HOST} !^$
RewriteRule ^ http://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
I have my sites working with the following solution.
domain.com forwards to www.domain.com
I like to add the following two conditions to my conditions above.
Remove trailing slashes. If I have www.domain.com/ it does remove
that trailing slash, unfortunately, for some reason if there are
multiple slashes at the end it doesn't www.domain.com//
Removing index.html from www.domain.com/index.html
Making this dynamic is what may be through this off. If I use the suggestion on domain itself, I have not problems. It is once I add http://www.%{HTTP_HOST}%{REQUEST_URI} where everything goes wonky.
i use this rewrite for redirecting domain.com to www.domain.com. No problems with //
RewriteEngine on
RewriteCond %{HTTP_HOST} !^www.domain.com$ [NC]
RewriteRule ^(.*)$ http://www.domain.com$1 [R,L]
#this could work for you (untested)
RewriteCond %{HTTP_HOST} !^www.\$ [NC]
RewriteCond %{HTTP_HOST} !^$
RewriteRule ^(.*)$ http://www.%{HTTP_HOST}$1 [R,L]
#redirect /index.html to /
RewriteRule ^/index.html / [R=301,L]

Non www to www redirect doesn't removes trailing backslash

I'm having a bit of problem with Apache redirect.
While bellow rules work for any page on site, mydomain.com will get redirected to mydomain.com//, which ignores trailing slash removal rule.
Also is it efficient to use multiple rules such as this or should I try to combine them or chain them somehow together in order to avoid multiple redirects for single url?
Thanks
#Turn on options for url rewriting
Options +FollowSymlinks
RewriteEngine on
#lovercase all urls
RewriteMap lc int:tolower
RewriteCond %{REQUEST_URI} [A-Z]
RewriteCond %{REQUEST_URI} ^/fonts/.*
RewriteCond %{REQUEST_URI} ^/css/.*
RewriteCond %{REQUEST_URI} ^/js/.*
RewriteRule (.*) ${lc:$1} [R=301,L]
#redirect all requests made to http:// to http://www.
RewriteCond %{HTTP_HOST} ^mydomain\.com$ [NC]
RewriteRule ^(.*)$ http://www.mydomain.com/$1 [R=301,L]
#removes trailing slash
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{HTTP_HOST} !^\.localhost$ [NC]
RewriteRule ^(.+)/$ http://%{HTTP_HOST}$1 [R=301,L]
The reason the mydomain.com gets redirected to www.mydomain.com// is because you have an extra "/" in your rewrite rule target:
RewriteRule ^(.*)$ http://www.mydomain.com/$1 [R=301,L]
^----here
When you have rules in your server/vhost config, the leading slash isn't removed so that gets match and used as a backreference, so mydomain.com is / which matches ^(.*)$ and the target becomes http://www.mydomain.com//. So you can either remove the slash in the target or add one to the regex:
RewriteRule ^(.*)$ http://www.mydomain.com$1 [R=301,L]
or
RewriteRule ^/(.*)$ http://www.mydomain.com/$1 [R=301,L]
Your other rule you have:
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{HTTP_HOST} !^\.localhost$ [NC]
RewriteRule ^(.+)/$ http://%{HTTP_HOST}$1 [R=301,L]
are fine. They are for removing trailing slashes when there is something between them, e.g. /something/, because of the (.+). It wouldn't match // anyways because that inherently gets turned into just /. You just need to prevent redirecting to http://www.mydomain.com//

URL Canonicalization - Apache mod_rewrite

I am probably attempting to take URL Canonicalization a bit too far but here it goes anyway.
Basically I am looking to the following:
301 redirect every base url to http://www.mydomain.com/ some pages are https it should recognize that and continue to use https where already used/requested
301 redirect away any trailing slashes ie http://www.mydomain.com/page/ becomes http://www.mydomain.com/page (I already have a line of code that finds the index.php page - this site is built on Codeigniter)
I Don't want the base url to have the slash stripped that is the only time a slash should be left behind
Find any instances of index.php (in the front middle or end of the url) and 301 redirect them out
ie http://www.mydomain.com/index.php/page/index.php/ becomes http://www.mydomain.com/page
301 redirect any use of my ip address to the actual domain
ie 11.11.111.111/page/index.php would become http://www.mydomain.com/page
Here is what I have so far in my htaccess file in my root directory:
RewriteEngine on
Options +FollowSymLinks
RewriteCond %{REQUEST_URI} ^(.*)(/index\.php)$
RewriteRule ^(.*)index\.php/$ http://www.mydomain.com/$1 [R=301,L]
RewriteCond %{HTTP_HOST} ^(mydomain\.com)(:80)? [NC]
RewriteRule ^(.*)$ http://www.mydomain.com/$1 [R=301,L]
RewriteCond %{HTTP_HOST} ^11\.11\.111\.111$
RewriteRule ^(.*)$ http://www.mydomain.com/$1 [R=301,L]
#This makes sure that the server actually finds the index file although its not in the url
RewriteCond $1 !^(index\.php|images|assets|downloads|css|js|robots\.txt)
RewriteRule ^(.*)$ /index\.php/$1 [L]
I am stuck right now any help would be greatly appreciated!!
Revisions!!
I have made some progress and here is what I have so far
<IfModule mod_rewrite.c>
RewriteEngine on
# index.php to /
RewriteCond %{THE_REQUEST} ^GET\ /.*/index\.(php|html)\ HTTP
RewriteRule (.*)index\.(php|html)$ /$1 [r=301,L]
# index.php to / at the base url
RewriteCond %{THE_REQUEST} ^GET\ /index\.(php|html)\ HTTP
RewriteRule (.*)index\.(php|html)$ /$1 [r=301,L]
# force www.
rewritecond %{HTTP_HOST} ^paolienvelope.com [nc]
rewriterule ^(.*)$ http://www.paolienvelope.com/$1 [r=301,L]
# force no IP
RewriteCond %{HTTP_HOST} ^70.40.204.154
RewriteRule ^(.*) http://www.paolienvelope.com/$1 [r=301,L]
#codeigniter direct
RewriteCond $1 !^(index\.php|images|assets|downloads|css|js|robots\.txt)
RewriteRule ^(.*)$ /index.php/$1 [L]
</IfModule>
This successfully forces ip to url
Removes index.php or index.html from the url but correctly directs to the index file despite
makes sure the base url has www.
Still dont have the code to remove the trailing slash from only the request
any help would be appreciated!! Thanks!
RewriteEngine on
# index.php remove any index.php parts
RewriteCond %{THE_REQUEST} /index\.(php|html)
RewriteRule (.*)index\.(php|html)(.*)$ $1$3 [R=301,L]
# force www. (also does the IP thing)
RewriteCond %{HTTP_HOST} !^www\.paolienvelope\.com [NC]
RewriteRule ^(.*)$ http://www.paolienvelope.com/$1 [R=301,L]
# remove tailing slash
DirectorySlash off
RewriteCond $1 !^(index\.php|images|assets|downloads|css|js)
RewriteRule ^(.*)/$ $1 [R=301,L]
# codeigniter direct
RewriteCond $1 !^(index\.php|images|assets|downloads|css|js|robots\.txt)
RewriteRule ^(.*)$ /index.php/$1 [L]
Let's try to solve this one point at the time. As said I'm no pro at this yet but any bit helps i guess:
I'll start with 2. because that one seems easier:
#get rid of trailing slashes
RewriteCond %{HTTP_HOST} ^(www.)?mydomain.\.com$ [NC]
RewriteRule ^(.+)/$ http://www.mydomain.com/$1 [R=301,L]
Does this work, instead of what you have?
source:
http://blog.valtersboze.com/2009/06/add-or-remove-trailing-slash-in-url-with-htaccess/

Redirect subdomain to subdirectory - trailing slash

I want to redirect [abc].apps.example.com to the following apps.example.com/[abc] but still showing the using the [abc].apps.example.com in the url.
[abc] an be anything eg.
calendar.apps.example.com
books.apps.example.com
etc
With a bit of digging around and tweaking, I have the following setup but doesn't work when an ending slash is missing:
RewriteEngine On
RewriteBase /
# Fix missing trailing slashes.
RewriteCond %{HTTP_HOST} !^www\.apps\.example\.com$ [NC]
RewriteCond %{HTTP_HOST} ^(www\.)?([^\.]+)\.apps\.example\.com$ [NC]
RewriteCond %{DOCUMENT_ROOT}/%2%{REQUEST_URI}/ -d
RewriteRule [^/]$ %{REQUEST_URI}/ [R=301,L]
# Rewrite sub domains.
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{HTTP_HOST} !^www\.apps\.example\.com$ [NC]
RewriteCond %{HTTP_HOST} ^(www\.)?([^\.]+)\.apps\.example\.com$ [NC]
RewriteRule ^.*$ /%2/$0 [QSA,L]
When the following is entered:
calendar.apps.example.com/showcalendar/
it's redirected correctly to: apps.example.com/calendar/showcalendar/
But for when a trailing slash is missing
calendar.apps.example.com/showcalendar
I get a 404 error saying /calendar/calendar/showcalendar/ not found.
Please, if you know what's wrong with the above code or have a better solution do let me know.
Cheers,
Doggy
try the following rewrite rule for adding trailing slashes.
# add trailing slash
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^.*[^/]$ /$0/ [L,R=301]

mod_rewrite and double slash issue

I applied the following mod_rewrite rule in Apache2 to redirect from non-www to www:
RewriteEngine On
RewriteCond %{HTTP_HOST} ^example\.com$ [NC]
RewriteRule ^(.*)$ http://www.example.com/$1 [R=301,L]
However, there's a double slash issue:
When I go to http://www.example.com it
correctly rewrites the URL to
http://www.example.com/
When I go to
http://www.example.com/somepage, it correctly
rewrites the URL to
http://www.example.com/somepage
If I
go to http://example.com, it
rewrites the URL to
http://www.example.com// (double final slash)
If I go to
http://example.com/somepage, it
correctly rewrites it to
http://www.example.com/somepage
Is my configuration good for SEO?
Fixed with:
RewriteEngine On
RewriteCond %{HTTP_HOST} ^example\.com$ [NC]
RewriteRule ^(.*)$ http://www.example.com$1 [R=301,L]
because $1 by default contains the index path /
RewriteRule ^\/?(.*)$ http://www.example.com/$1 [R=301,L]
Actually, you will always have double slashes due to
RewriteRule ^(.*)$ http://www.example.com/$1 [R=301,L]
combined with the fact that REQUEST_URI (that you are matching on) normally contains a starting slash. What you can try is RewriteRule ^(.*)$ http://example.com$1, and then send a broken HTTP request GET foo HTTP/1.0 and see if Apache deals with it properly.
Putting a slash into your pattern should resolve this issue:
RewriteRule ^/(.*)$ http://www.example.com/$1 [R=301,L]
That is because the root path is /, and you are appending whatever you get in RewriteRule (the first case works fine because it doesn't match the condition so no rewrite is performed).
You can try something like this:
RewriteEngine On
RewriteCond %{HTTP_HOST} ^example\.com$ [NC]
# for the home page
RewriteRule ^/$ http://www.example.com/ [R=301,L]
# for the rest of pages
RewriteRule ^(.*)$ http://www.example.com/$1 [R=301,L]