"Security" by GotCredit; https://flic.kr/p/rEwCxH

Economically monitoring SSL certificate expiration

As noted previously, I’ve opted to serve all of my sites securely. I even went to far as to get ethitter.com on Chrome’s preload list, meaning no major browser even attempts an insecure connection to my site. Try loading http://ethitter.com/ in Chrome, Firefox, or Safari, and the browser will redirect to http://ethitter.com/ before my nginx configuration ever tells it to.

That vaguely-entertaining detail aside, this means that I’ve reason to be concerned about how soon my SSL certificates expire. The HPKP headers I set have 60-day lives, which I need to account for any time I renew the certificate for a pinned domain.

Most of my certificates are issued by StartSSL, but I’ve tested Let’s Encrypt (LE) for certain situations. As LE certificates have four-month lives, compared to the typical minimum of one year, tracking certificate expiration dates becomes a bit more pressing. At this point, I’ve explored four options.


Cost was an understandable concern. I have at least a half dozen domains to monitor, which influences my choices in interesting ways. I’ve started a spreadsheet to track my costs, and it’s an unfortunate tally.

Besides not wanting to spend more than $15, email notifications were necessary, and Jabber/Slack alerts would be nice.

Options I Recommend

Of the many solutions I’ve considered, I recommend any of the following. The first three are free and open-source, while the last option is paid yet affordable.


I already run Nagios, and its check_http command includes a -C flag for checking certificate expiry.

The -C command accepts a single argument in the form of two comma-separated integers. Each value indicates how many days ahead of expiry Nagios should begin WARN and CRITICAL alerts: -C 60,30.

Keep in mind that this flag shouldn’t be added to existing checks. This temptation towards efficiency defeats the check’s other behaviours. In other words, an existing check_http call will no longer return the status code and response time if the -C flag is added; the check will  thereafter only provide details about the SSL certificate’s age.

As far as alerts are concerned, email notifications are native, and Slack provides the necessary configurations for its integration.


certificatemonitor.org is an open-source project from Remy van Elst; it’s available on GitHub at https://github.com/RaymiiOrg/certificate-expiry-monitor to run for yourself.

To host the monitor, you’ll need PHP 5 (I use 5.6); PHP 7 isn’t supported. A cron job powers the daily checks, and the tool uses a set of JSON files for data storage. After providing an email address and a list of up to 20 domains to monitor, the entries are checked for existing SSL certificates and email confirmations are sent. Setup is overall very straightforward.

This monitor doesn’t support Slack, but I could find some sort of email to Slack bridge if I really wanted. IFTTT or Zapier probably offer something.


A GPLv2-licensed command-line monitoring option, this can be used to check domains ad-hoc, or it can be scripted for proactive monitoring. It can check a single domain, and will accept a file of domains to report on. Results can be delivered via email (in addition to CLI output).


A service of ZOHO, this is the only paid monitor I’ve found that’s affordable. Several competitors offer inexpensive plans for one or two domains, after which their pricing models are logarithmic. With Site24x7, the cost is basically $1 per monitor, or less if paid annually. Email notifications are standard, and Slack alerts are possible with the Zapier integration promoted from within the interface.

Site24x7 also offers a host of other monitors, though I’ve only utilized the SSL checks. The others are duplicative of services I already have, which is a topic for another post. 🙂

2 thoughts on “Economically monitoring SSL certificate expiration”

  1. As LE certificates have four-month lives, compared to the typical minimum of one year, tracking certificate expiration dates becomes a bit more pressing. At this point, I’ve explored three options.

    LE certs are not meant to be tracked, but rather automatically renewed every 90 days without you having to ever worry/know about that 🙂

    1. True as that is, I’m a bit paranoid. If I want to use LE for ethitter.com in particular, I need to monitor the expiration more closely because the certificate is used in many more places than just nginx, and in a few formats other than what LE will output. In other words, enough manual intervention that I want some lead time to procrastinate. 🙂

      Also, due to the Public Key Pinning headers I set currently, I need to be more careful about certificate rotation. I haven’t done enough research yet to know if I can set HPKP with LE, but I doubt I can (can’t generate the next private key for the backup pins, I suspect), so that may not even be an issue. Assuming LE doesn’t support HPKP, I’ll need at least 60 days lead time to switch as that’s the life of the header set now.

Comments are closed.