Looking for a way to redirect several server aliases (both www and non-www) to one non-www domain with forced SSL using Apache VirtualHosts and .htaccess
. I've been searching for a while now and have found several solutions but they all work partially.
The situation is as follows, in my .conf
file I have a virtual host specified as follows:
<VirtualHost *:443>
ServerName example.domain
ServerAlias *.example.domain *.exampledomain.com exampledomain.com
...
</VirtualHost>
<VirtualHost *:80>
ServerName example.domain
ServerAlias *. example.domain *.exampledomain.com exampledomain.com
RewriteEngine on
RewriteCond %{SERVER_NAME} =www.example.domain [OR]
RewriteCond %{SERVER_NAME} =example.domain
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>
Next, I have the following in my .htaccess
:
RewriteEngine On
Options FollowSymlinks
RewriteBase /
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
RewriteCond %{HTTP_HOST} ^www.exampledomain.com$ [OR]
RewriteCond %{HTTP_HOST} ^exampledomain.com$ [OR]
RewriteCond %{HTTP_HOST} ^www\.example\.domain$
RewriteRule ^(.*)$ https://example.domain/$1 [L,R=301]
Result is as follows:
http://example.domain/ -> https://example.domain/ - (correct)
http://www.example.domain/ -> https://example.domain/ - (correct)
http://exampledomain.com/ -> http://exampledomain.com/ - Forbidden, you dont have access...
http://www.exampledomain.com/ -> http://www.exampledomain.com/ - Forbidden, you dont have access...
https://exampledomain.com/ -> https://example.domain/ - (correct)
https://www.exampledomain.com/ -> https://www.exampledomain.com/ - Connection not secure
I really can't figure out where this goes wrong and why some redirects work and others don't. Any hints would be much appreciated.
CodePudding user response:
If you have access to the <VirtualHost>
then you don't need to (should not) use .htaccess
at all for this.
If the goal is to redirect to the canonical domain ( HTTPS) in a single redirect using just the two vHosts as defined then all you need is:
<VirtualHost *:443>
ServerName example.domain
ServerAlias *.example.domain *.exampledomain.com exampledomain.com
RewriteEngine On
# Redirect everything other than the canonical host to the canonical host
RewriteCond %{HTTP_HOST} !=example\.domain
RewriteRule ^ https://example.domain%{REQUEST_URI} [R=301,L]
</VirtualHost>
<VirtualHost *:80>
ServerName example.domain
ServerAlias *.example.domain *.exampledomain.com exampledomain.com
# Unconditionally redirect everything to HTTPS canonical host
Redirect 301 / https://example.domain/
</VirtualHost>
The mod_alias Redirect
directive is prefix matching and everything after the match is appended to the end of the target URL. So, the Redirect
directive above redirects every URL to the same URL at the target.
You should test first with 302 (temporary) redirects and only change to a 301 (permanent) once you have confirmed it works as intended. You will likely need to clear your browser cache since 301s are cached persistently by the browser.
A look at your "results":
http://exampledomain.com/ -> http://exampledomain.com/ - Forbidden, you dont have access...
http://www.exampledomain.com/ -> http://www.exampledomain.com/ - Forbidden, you dont have access...
The current HTTP to HTTPS redirect in the vHost:80 container is only redirecting www.example.domain
and example.domain
and you probably aren't accepting requests in the vHost:80 container, so any HTTP request (that is not redirected to HTTPS) is probably blocked.
https://www.exampledomain.com/ -> https://www.exampledomain.com/ - Connection not secure
Your SSL cert needs to cover all domains and all aliases, otherwise, you will (at best) get a browser SSL cert warning and the browser will refuse to connect to your server (so does not see the redirect).