Skip to content

Lets Encrypt & Nginx: Www-root method and Subject Alt Names

Last updated on August 17, 2018

Digital Ocean has a pretty good guide for setting up Lets Encrypt with Nginx on Ubuntu 14.04. However, their guide requires you to turn down your Nginx server while initially getting you Lets Encrypt TLS certificates, this of course is problematic for server/site operators who either need or want to continue to have service continuity while getting lets Encrypt Certificates. They also don’t explain how to use subject alternative names to handle multiple sub domains on the same server.

Lets Encrypt’s software requires that they be able to connect to your server to verify that the domain you’re attempting to register a certificate for you control. In the Digital Ocean guide, this process is handled by using the built-in web server in the lens encrypt package. However, Lets Encrypt does not need to operate in this manner to create new certificates, it can use the wwwroot/filesystem approach and your existing server configuration.

The process is very similar to Digital Oceans guide, but the order of operations are slightly different.

Deviating from the Digital Ocean Guide

I wasn’t about to take down my http server just to get Lets Encrypt set up. Moreover, Lets Encrypt doesn’t actually require you to do that. And throwing a further laugh in to the situation with respect from the Digital Ocean guide, the eventually reconfigured Nginx to support wwwroot operation which they could have done from the outset and not had to take down Nginx in the first place.

The LE client supports operating through your existing web infrastructure by using wwwroot mode. This creates a hidden folder, “.well-known” in the root of the directory you specify that the LE servers then look at to verify that you have control over the domain in question.

If your Nginx config blocks access to dot-files using the following directive:

# Block access to dot files
location ~ /\. { deny all; access_log off; log_not_found off; }

You will need to add a secondary rule to allow access to .well-known. The following snippit will unblock .well-known.

# Permit access to /.well-known for Lets Encrypt
location ^~ /.well-known { allow all; }

With the latter rule here in place, you can reload Nginx and you should be able to access the .well-known folder from a browser. (Note, if you don’t allow auto indexing, you may have to create a test file in that directory to test.) Make sure that this is share is accessible before you go on.

Subject Alternate Names (SANs)

Lets Encrypt will not provide wildcard certificates, but they will provide certificates with multiple Subject Alternate Names (SANs). This certificate filed allows one to denote several domains that the certificate will be valid for. As with the standard procedure Lets Encrypt needs to validate all of these domains as well.

If all of these domains are handled by the same virtual host, (say the www and non-www versions of the same website), then all you need to do is point things in one place.

However, if you’re serving these sub-domains from different virtual hosts (say a media sub domain that only severs static content and a primary domain that has the full PHP configuration), then all of these domains need to have the same .well-known for the request to be successful.

There are potentially a number of ways to go about doing this, but I wanted to keep all the sub-domains for the same primary domain in the same certificate. This simplifies the number of certificates I have to manage and keeps everything all nice and neat — I can use one include in each virtual host directive for that domain/sub-domain instead of separate domain includes.

The documented mechanism from lets encrypt is to specific the wwwroot directory followed by the domains that are served by it. However, it appears that Lets Encrypt uses the same handshake code for all requests made at a given time. Meaning it appears that you can symlink the .well-known directory across sub-domains of the same request.

E.g I have the domains

  • example.com
  • www.example.com
  • media.example.com

With the www-root structure of:

  • sites
    • example.com (www-root for example.com and www.example.com)
      • media (www-root for media-example.com)

Which would be fairly typical of say a WordPress install where the operator is serveing /wp-content/uploads as a separate potentially cookie free static content domain.

All of these domains are all being registered as SANs on the same certificate for the primary domain.

Alternatively, the LE client allows one to specify wwwroot directories for each of the respective domains. For example.

letsencrypt certonly --wwwroot \
   -w /var/example.com -d example.com -d www.example.com \
   -w /var/example.com/media -d media.example.com

I would venture to say that this is probably the more correct way to do things instead of symlinking. However, I’ve yet to determine the correct way to specify this in the letsencrypt config ini file that would be later used to automatically renew certificates — at least again if you’re following the scripts provided in the Digital Ocean guide.

Beyond these alterations, the rest of the Digital Ocean guide can be followed to setup auto renewal.

 

Published inLinux