Enabling Strong HTTPS on Apache

When I first built my Ubuntu web server, I did so using NGINX.  It was fun and interesting to work with something other than Apache, but then, I stumbled upon Google’s PageSpeed module.  This is a module that performs several of the functions necessary to increase a site’s search ranking score for you, and Google offers it as a download package for Apache…but only source code for NGINX.  Since I have yet to venture into the dark waters of compiling source code in Linux, I converted to Apache and have not looked back.

It’s been on my mind for a while to sort out the HTTPS functionality on my server, and after writing my latest X-Cerpt (link to be embedded upon publication) this evening, I decided to mark this item off my list.

I originally planned to create separate Virtual Host files for the HTTPS versions of knightsfallpress.com and Valthon’s Net; however, a recent experience with a client at work showed me that you can have one Virtual Host file perform double duty.

From here on out, things get a little complex, so I feel as though I should preface the rest of this post with the ubiquitous:

Don’t try this at home…unless you have a decent idea of what you’re doing.

Here’s a sanitized version of the Virtual Host file for valthon.net:

Valthon's Net Virtual Host File

I’m writing this with two major assumptions in mind:

  1. You have some pre-existing familiarity with configuring Apache virtual hosts.  If I didn’t, this post would be exponentially longer than it already is.
  2. You already have a certificate (either self-signed or from a CA).  See “If I didn’t…” explanation in #1.

As you can see, you can place multiple entries in one config file.  In all truth, I probably could’ve made a vhosts.conf and put all my virtual hosts in there, but I like the logical organization of having separate config files for each domain.

ExpiresActive On
ExpiresByType text/html "modification plus 1 year"
ExpiresByType text/css "modification plus 1 year"
ExpiresByType image/jpg "modification plus 1 month"
ExpiresByType image/png "modification plus 1 month"

You will see these lines at the bottom of each entry, and they are my attempt to “leverage browser caching.”  To get these directives to work, you’ll have to install and enable the expires module for Apache.  Just between you and me, though, I think I still have some work ahead of me on this part.  But I digress…

Securing any network resource is always a balancing act between security and usability.  The 100% secure server is the box in the corner with no network cable plugged in, but user access for that isn’t so great.  Likewise, the server configured for 100% user access is a security-minded sysadmin’s nightmare.  I still shudder at the thought of a client’s network share I saw one time with “Everyone – Full Control” in both Sharing and NTFS permissions.

The configuration posted above is a good fit between security and access, and it’s not that difficult to enable.

The first step is to enable the headers and ssl modules for apache:

sudo a2enmod headers
sudo a2enmod ssl

Once this is done, open your virtual host file using your editor of choice.  For me, it’s nano:

sudo nano /[YOUR FILE PATH HERE]/site.conf

You will want to change “site.conf” to match your specific virtual host config file, by the way.

From here, I just selected my original Virtual Host (vhost) config for HTTP, copied it, and pasted it with a few blank lines between the two.  I then went about modifying it for HTTPS, as you can see above.  You will want to store your certificate files in a folder location other than your web files for security reasons; keep in mind that, if you choose a location other than the default, you may need to modify permissions to get everything working properly.

For best results in SSL tests, like the SSL Labs Analysis, you’ll want to include the intermediate Certificate Authority certificate in your vhost configuration.  You can download this for free from every Certificate Authority.  As shown in the code above, the command to include this certificate is as follows:

SSLCACertificateFile "/REDACTED/intermediate_ca.crt"

You will want to modify the path between the quotes to match the location where you saved your CA’s intermediate certificate.

Another item of note is the SSLProtocol line:

SSLProtocol All -SSLv2 -SSLv3

This instructs Apache not to use SSLv2 & SSLv3.  “SSL” stands for Secure Sockets Layer, and even though it is still widely used in common parlance, it has actually be superseded by Transport Layer Security or TLS.  I won’t say SSL is as vulnerable to unauthorized access as a sieve is to water, but to have any faith in your secure communications, you shouldn’t use it.

In theory, you could choose to use only the newest implementation of TLS:

SSLProtocol -All +TLSv1.2

However, that will greatly restrict what clients can view your webpage.  Remember the discussion above of security versus usability?

Finally, there are a couple commands you’ll need to put at the bottom of your apache2.conf file (Ubuntu) or httpd.conf (Red Hat/Fedora/CentOS) once you’ve finished with your vhost config file:

SSLUseStapling on
SSLStaplingCache "shmcb:logs/stapling-cache(150000)"

Once this is complete, simply restart Apache (sudo service apache2 restart for Debian/Ubuntu or sudo service httpd restart for RH/Fedora/CentOS), and you should be able to analyze your site at SSL Labs and see a result similar to the graphic below.

I want to thank Remy van Elst at Raymii.org for the post “Strong SSL Security on Apache2” along with the site “Cipherli.st.”  Without either of these resources, implementing secure HTTPS on my Apache web server would have required far more time than the two hours (or so) I spent on it.

Stay In The Know!

* indicates required
Email Format