Hosting multiple SSL enabled domains off a single address with SNI on Linux

Server Name Indication or SNI allows webserver software to take requests for multiple sites secured by SSL without the need to have a separate address for each certificate.  This functionality is supported by Apache, Nginx, and Microsoft IIS, which are the most commonly used webserver suites.

This article will cover how to set up SNI on both Apache and Nginx as the process is extremely similar for both.  Windows users utilizing IIS should look here instead.

Prerequisites

  • A Linux Server
  • An updated install of Apache or Nginx
  • An updated install of OpenSSL (at least version 0.9.8j or newer)
  • Valid  SSL certificates of the sites in question

Ensure your install of Apache or Nginx supports SNI

SNI was added to both Nginx and Apache after their initial releases.  While it is now included by default on both systems, older installs may need to be updated.  This is easy to check in both cases though.

For Apache, you are looking for the mod_ssl module to be loaded.  This information is included in the server line for a simple curl against the Apache site:

curl --head http://localhost/

You should see a response which contains something similar to the following:

Server: Apache/2.2.12 (Unix) mod_ssl/2.2.12 OpenSSL/0.9.8j

If you can verify that mod_ssl is in this line somewhere, then your Apache install supports SNI.  

For Nginx users, you can verify SNI support by simply running a version command.

nginx -v

The output of this command should contain the following line which indicates that it has SNI support.

TLS SNI support enabled

If you have verified that your respective webserver has SNI support you can skip the next step.

Install and enable SNI support if necessary

This step is only necessary if you were unable to confirm SNI support in the previous step.  Otherwise please skip to the next section of this article.

For Apache webservers, SNI support is available via the mod_ssl extension.  You will want to install this with your appropriate package manager as shown below.

For RHEL or CentOS based systems

yum install mod_ssl 

For Ubuntu or Debian based systems (the second line enables the module and restarts Apache)

apt-get install apache2.2-common
a2enmod ssl; /etc/init.d/apache2 reload

Enable SNI in the Apache configuration

This step can be skipped by Nginx users.

Apache needs to know to listen for multiple sites on port 443.  In order to do this ensure the following lines are in the .conf file for Apache (either apache2.conf or httpd.conf depending on your distro).

# Ensure that Apache listens on port 443
Listen 443

# Listen for virtual host requests on all IP addresses
NameVirtualHost *:443

# Accept connections for these vhosts from non-SNI clients
SSLStrictSNIVHostCheck off

Create the necessary vhosts

From here on in SNI setup is almost identical to setting up a single host.  Simply create a vhost for each site inside your Apache or Nginx configuration files or folders.  The vhost should be created just as you would normally with the appropriate ssl settings.  Some examples are provided below.

Apache example



 ServerName www.yoursiteexample.com

 DocumentRoot /var/www/site

 SSLEngine on

 SSLCertificateFile /path/to/www_yoursiteexample_com.crt

 SSLCertificateKeyFile /path/to/www_yoursiteexample_com.key

 SSLCertificateChainFile /path/to/YourCRTProvidersCA.crt




 ServerName www.yoursiteexamplenumber2.com

 DocumentRoot /var/www/site

 SSLEngine on

 SSLCertificateFile /path/to/www_yoursiteexamplenumber2_com.crt

 SSLCertificateKeyFile /path/to/www_yoursiteexamplenumber2_com.key

 SSLCertificateChainFile /path/to/YourCRTProvidersCA.crt


Nginx example

server {

        listen   443;
        server_name yoursiteexample.com;

        root /usr/share/nginx/www;
        index index.html index.htm;

        ssl on;
        ssl_certificate /etc/nginx/ssl/www_yoursiteexample_com/server.crt;
        ssl_certificate_key /etc/nginx/ssl/www_yoursiteexample_com/server.key;
}
server {

        listen   443;
        server_name yoursiteexamplenumber2.com;

        root /usr/share/nginx/www;
        index index.html index.htm;

        ssl on;
        ssl_certificate /etc/nginx/ssl/www_yoursiteexamplenumber2_com/server.crt;
        ssl_certificate_key /etc/nginx/ssl/www_yoursiteexamplenumber2_com/server.key;
}

Activate your vhosts

For Apache on a Debian or Ubuntu based system or any install of Nginx, the vhosts need to be activated.

For Apache, use a2ensite as the example below.

sudo a2ensite yourexample.com

For Nginx, create a symbolic link between the vhost file location and the Nginx ‘sites-enabled’ directory.  An example of the link creation is shown below.

sudo ln -s /etc/nginx/sites-available/yourexample.com /etc/nginx/sites-enabled/yourexample.com

Do this for all sites you wish to serve.

Restart your webserver

Restart Apache or Nginx and, provided no mistakes, the server should now supply requests for any and all sites you have configured.

You can restart Apache by running the following.

sudo /etc/init.d/apache2 reload

You can restart Nginx with the following.

sudo service nginx restart

Leave a Reply

Your email address will not be published. Required fields are marked *