Let's Encrypt (LE) is an awesome project and a boon for the entire internet community. Not only have they made HTTPS accessible to everyone, but the whole process of creating and renewing certs is much more user-friendly and thought-through than any commercial certificate authority I've dealt with in the past.
… but
If you've ever had to manage a larger number of certs, for different services, you may have noticed that the default challenge and verification method on FreeBSD, when using nginx (webroot) can become a bit messy and fragile. Creating virtual hosts or modifying old ones in nginx
may introduce changes that break certbot
, different web app backends might need slightly different configs (e.g. static pages vs a PHP-base webmail vs Django apps)
and bugs in the agent itself make it difficult to automate the process reliably.
Luckily, the webroot plugin is just one of the many methods for provisioning certs:
pkg search py36-certbot
py36-certbot-0.22.2,1 Let's Encrypt client
py36-certbot-apache-0.22.2 Apache plugin for Certbot
py36-certbot-dns-cloudflare-0.22.2 Cloudflare DNS plugin for Certbot
py36-certbot-dns-cloudxns-0.22.2 CloudXNS DNS Authenticator plugin for Certbot
py36-certbot-dns-digitalocean-0.22.2 DigitalOcean DNS Authenticator plugin for Certbot
py36-certbot-dns-dnsimple-0.22.2 DNSimple DNS Authenticator plugin for Certbot
py36-certbot-dns-dnsmadeeasy-0.22.2 DNS Made Easy DNS Authenticator plugin for Certbot
py36-certbot-dns-google-0.22.2 Google Cloud DNS Authenticator plugin for Certbot
py36-certbot-dns-luadns-0.22.2 LuaDNS Authenticator plugin for Certbot
py36-certbot-dns-nsone-0.22.2 NS1 DNS Authenticator plugin for Certbot
py36-certbot-dns-rfc2136-0.22.2 RFC 2136 DNS Authenticator plugin for Certbot
py36-certbot-dns-route53-0.22.2 Route53 DNS Authenticator plugin for Certbot
py36-certbot-nginx-0.22.2 NGINX plugin for Certbot
I've been using DNS Made Easy for all my DNS hosting for a few years now and decided to give their plugin a shot. It worked really well, sidestepping all the issues I had run into with the webroot plugin, so here's a short how-to on setting that up. These instructions will work even if you're renewing from webroot - based challenges.
{Install|configur}ation
Let's start by installing the DNS Made Easy certbot
plugin. I prefer to use the Python 3.6 version - just substitute with py27-certbot-dns-dnsmadeeasy
if you're still in v2.
sudo pkg install py36-certbot-dns-dnsmadeeasy
Go to https://cp.dnsmadeeasy.com/account/info, check the Generate New API Credentials and hit Save. You should now see some random strings after the API Key: and Secret Key: labels. Let's put those credentials into /usr/local/etc/letsencrypt/dnsmadeeasy.conf
:
# /usr/local/etc/letsencrypt/dnsmadeeasy.conf
# DNS Made Easy API credentials used by Certbot
dns_dnsmadeeasy_api_key = supersecret
dns_dnsmadeeasy_secret_key = supersecreter
Those credentials give access to your entire DNS configuration, so let's make sure only root can read them, shall we?:
sudo chmod 0400 /usr/local/etc/letsencrypt/dnsmadeeasy.conf
Finally, let's request the certs:
sudo certbot-3.6 certonly --dns-dnsmadeeasy -d www.example.com -d mail.example.com -d example.com --dns-dnsmadeeasy-credentials /usr/local/etc/letsencrypt/dnsmadeeasy.conf
Saving debug log to /var/log/letsencrypt/letsencrypt.log
Plugins selected: Authenticator dns-dnsmadeeasy, Installer None
Cert is due for renewal, auto-renewing...
Renewing an existing certificate
Performing the following challenges:
dns-01 challenge for www.example.com
dns-01 challenge for mail.example.com
dns-01 challenge for example.com
Waiting 60 seconds for DNS changes to propagate
Waiting for verification...
Cleaning up challenges
Don't forget to also reload nginx for the new certs to take effect immediately:
sudo service nginx reload
If you want to make absolutely sure everything is kosher, go check your web server with SSL Labs’ SSL Server Test. While you're waiting for the results, go check out the certbot plugin's documentation which is refreshingly succinct.
One quick note - the DNS Made Easy API uses timestamps in the authentication request so if you ever run into spurious 403 errors (“Error determining zone identifier …") with renewal, make sure your system's date is set correctly. I once nuke-and-paved my entire certbot setup just to finally realize the clock had simply drifted too far:
sudo ntpdate pool.ntp.org
That's it! You now have an out-of-band Certbot setup that you can safely certbot renew
without breaking it every time you make changes to your nginx
virtualhosts. Even if you don't use DNS Made Easy, I highly recommend looking into some of the alternative Certbot challenge methods.