1

I am trying to setup HSTS for my website but running into some problems regarding HSTS and the use of the www. sub domain. What I would like is for all HTTP and HTTPS traffic to redirect to https://www.example.co.uk.

I have been using the information on the following websites as a guide: https://www.danielmorell.com/blog/how-to-configure-hsts-on-www-and-other-subdomains

The examples on the above websites show the strict-transport-security (STS) header at all the redirect stages.

E.g. http://example.com 301 redirects to https://example.com (STS in header). Then https://example.com redirects to https://www.example.com (STS in header).

However when I try my own domain I only get the STS header on the initial redirect and not the next redirection to the https://www. sub domain.

Examples from my own testing:

  1. http://example.co.uk (301) to https://example.co.uk (STS in header) (301) to https://www.example.co.uk (No STS in header).

  2. http://www.example.co.uk (301) to https://www.example.co.uk (No STS in header).

  3. https://example.co.uk (STS in header) then (301) to https://www.example.co.uk (No STS in header).

  4. https://www.example.co.uk (No STS in header).

Below is a copy of the header response using option 1 above:

http://example.co.uk

HTTP/1.1 301 Moved Permanently
Date: Mon, 04 Feb 2019 18:14:30 GMT
Server: Apache
Location: `https://example.co.uk`/
Content-Length: 237
Content-Type: text/html; charset=iso-8859-1

https://example.co.uk/

HTTP/1.1 301 Moved Permanently
Date: Mon, 04 Feb 2019 18:14:33 GMT
Server: Apache
Strict-Transport-Security: max-age=31557600; includeSubDomains;
Location: https://www.example.co.uk/
Content-Length: 241
Content-Type: text/html; charset=iso-8859-1

https://www.example.co.uk/

HTTP/1.1 200 OK
Date: Mon, 04 Feb 2019 18:14:35 GMT
Server: Apache
Expires: Thu, 19 Nov 1981 08:52:00 GMT
Cache-Control: no-store, no-cache, must-revalidate, post-check=0, pre-check=0
Pragma: no-cache
Set-Cookie: PHPSESSID=fkjqaomopnp03uforuptdu3u17; path=/
Transfer-Encoding: chunked
Content-Type: text/html; charset=ISO-8859-1

My website is running on a shared Apache server. I have a valid Let's encrypt cert with CN = example.co.uk.

I have tried the suggestions at: https://webmasters.stackexchange.com/questions/115125/hsts-implementation-when-using-www-tld but it didn't seem to solve my problem.

My .htaccess is shown below:

<if "%{HTTPS} == 'on'">
  Header always set Strict-Transport-Security "max-age=31557600; includeSubDomains;"
</if>

## Base Redirects ##

# Turn on Rewrite Engine
RewriteEngine On

# Redirect to secure HTTPS before changing host
RewriteCond %{HTTP_HOST} !^www\.(.*)$ [NC]
RewriteCond %{https} off  
RewriteRule ^(.*)$ https://example.co.uk/$1 [R=301,L]

# Remove trailing slash from non-filepath urls
RewriteCond %{REQUEST_URI} /(.+)/$
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^ https://www.example.co.uk/%1 [R=301,L]

# Include trailing slash on directory 
RewriteCond %{REQUEST_URI} !(.+)/$
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^(.+)$ https://www.example.co.uk/$1/ [R=301,L]

# Force HTTPS and WWW 
RewriteCond %{HTTP_HOST} !^www\.(.*)$ [OR,NC]
RewriteCond %{https} off  
RewriteRule ^(.*)$ https://www.example.co.uk/$1 [R=301,L]

I have tried a couple of my other sub domains and they all send the STS in their response.

So the problem appears to be with the https://www. sub domain despite the directive includeSubDomains being present and I'm at a loss as to why and how to get it working. Could it be a problem with the server settings if so which settings should be checked?

migrated from security.stackexchange.com Feb 15 at 8:56

This question came from our site for information security professionals.

  • includeSubDomains has nothing to do with the header being sent or not. It just tells the client (browser) that when it receives such a header it should act as though it had received HSTS headers for all subdomains as well. – AndrolGenhald Feb 6 at 20:04
1

Answer is paritially from this answer.

RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule .* https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
RewriteCond %{HTTP_HOST} !^www\. [NC]
RewriteRule .* https://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]

# Only set HSTS header if protocol is HTTPS
<if "%{HTTPS} == 'on'">
        Header always set Strict-Transport-Security "max-age=31557600; includeSubDomains;"
</if>

# Remove trailing slash from non-filepath urls
RewriteCond %{REQUEST_URI} /(.+)/$
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^ https://www.example.co.uk/%1 [R=301,L]

# Include trailing slash on directory 
RewriteCond %{REQUEST_URI} !(.+)/$
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^(.+)$ https://www.example.co.uk/$1/ [R=301,L]

This should work. I tested it.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.