Auto-renewal and key rotation
A certificate is a 90-day commitment, every 90 days, forever. CertMate's scheduler handles the renewal arithmetic, but the operational discipline around it — monitoring failures, rotating keys, surviving a DNS API outage — is yours. Here's the contract.
Let's Encrypt certificates are valid for 90 days. The community consensus, baked into every ACME client, is to renew at 60 days — giving you a 30-day buffer before expiry to notice and fix a broken renewal. CertMate follows that consensus. The interesting questions aren't "when does it renew" but "what happens when it doesn't, and how do you know."
The scheduler
CertMate's background scheduler runs an APScheduler
job. Every certificate has a per-record renewal_threshold_days (default 30, override per cert).
The scheduler wakes regularly — frequently enough that a freshly
expiring certificate is picked up within hours, not days — walks the
certificate list, and for each one whose days_until_expiry <= renewal_threshold_days AND
auto_renew == true, fires a renewal.
Renewals always preserve the shape that was in effect at creation
time: certbot persists --key-type,
--rsa-key-size and --elliptic-curve into
its own renewal/<domain>.conf during the first
issuance, and certbot renew --cert-name <domain>
reuses those values automatically. You don't have to remember
whether you originally asked for RSA 4096 or ECDSA P-256; certbot
does.
The per-certificate knobs
| Field | Default | Purpose |
|---|---|---|
auto_renew | true | Master switch per certificate. |
renewal_threshold_days | 30 | Renew when expiry is within N days. Some operators set this lower (14) for low-traffic certs to minimize unnecessary issuance; some set it higher (45) when the deploy hook is heavy. |
dns_provider + dns_account_id | at-creation values | Renewals use the same DNS path that issued the cert. Switch providers by PATCHing the record before the next renewal window. |
Force a renewal
If you need a renewal now — most commonly because a key compromise was suspected, or because a deploy hook bug means the live cert is out of sync with the on-disk cert — POST to the per-cert renew endpoint:
curl -X POST http://localhost:8000/api/certificates/example.com/renew \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{ "force": true }'
Without force, CertMate refuses to renew a certificate
whose expiry is still far enough away — Let's Encrypt has rate
limits (50 certs / domain / week, 5 duplicates / week) and a renewal
loop bug is one of the few ways to hit them.
Key rotation: same name, new private key
Every renewal in CertMate is what certbot calls a "true renewal" — it generates a fresh private key, builds a new CSR, and gets a new certificate from the CA. The certificate's serial number changes, the public key changes, the private key changes. The CN and SAN list don't.
This means you don't need a separate "rotate the key" workflow. You rotate the key by forcing a renewal:
curl -X POST http://localhost:8000/api/certificates/example.com/renew \
-H "Authorization: Bearer $TOKEN" \
-d '{ "force": true, "reason": "scheduled-key-rotation" }'
The reason field lands in the audit log alongside the
new serial number, which is helpful when an auditor asks "when was
the key for this cert last rotated."
When auto-renewal fails
The four failure modes you'll actually see, in rough order of frequency:
DNS API credential expired or rotated
Someone rotated the Cloudflare token in the Cloudflare UI without updating CertMate. The next renewal attempt returns 401 from Cloudflare's API. CertMate writes a failed audit row with the upstream message and stops retrying for an exponential back-off window.
The only way you notice this in time is by watching the
audit log or wiring a deploy hook on a synthetic revoked event. CertMate is honest about this — the
v2.5.5 release notes call out audit log monitoring as the
operator's responsibility.
CAA record drift
Someone added a CAA record that excludes Let's Encrypt. Renewal worked last week. This week, it doesn't. CertMate surfaces the CA's exact error message in the audit log — the words "CAA record prevents issuance" are unambiguous enough that the fix is obvious.
Let's Encrypt rate limit
Usually a sign of a renewal loop, not legitimate traffic. The audit log will show many failed renewals for the same domain in a short window. Stop the loop, wait out the week-long rate-limit window, and configure stricter renewal thresholds going forward.
DNS provider outage
Rare but real. CertMate's behavior is to retry with the back-off schedule baked into the certbot plugin (typically 3 attempts over a few minutes). If the outage outlasts that, the renewal fails and is retried on the next scheduler pass — usually several hours later. For a sub-30-day expiry buffer this is fine; for a tight renewal window you'll want to pin to a DR account (multi-account DNS) or delegate validation to a more reliable provider (CNAME delegation).
What you should monitor
Two queries against the audit log give you most of the operational signal you need:
- Recent failed renewals. Anything with
operation=renewandstatus=errorin the last 24 hours. A single failure is recoverable on the next pass; the same cert failing three times running is a paging event. - Certs within 14 days of expiry that haven't renewed.
A renewal that hasn't fired by then is almost always a config
issue (auto_renew off, or threshold misconfigured). Query the
cert list and filter on
days_until_expiry < 14 && auto_renew.
The conversational sidecar's /expiring 14 slash
command runs the second query for you. The first one is just a
ranged audit-log read against /api/audit?operation=renew&status=error.
Disabling auto-renewal
Sometimes you don't want a certificate auto-renewed — a one-off cert for a migration, a deprecated service, a cert that's being moved off CertMate. PATCH the record:
curl -X POST http://localhost:8000/api/certificates/example.com/auto-renew \
-H "Authorization: Bearer $TOKEN" \
-d '{ "enabled": false }' CertMate keeps the certificate on disk (you still control when to delete it) but stops touching it. The audit log records who turned auto-renewal off and when.