Skip to content

Why does my SSL auto-renew fail every 89 days exactly?

Web Hosting Locked by FlowSana 23 replies 2.4K views
This thread is locked — new replies are not accepted. (Closed: the question was answered)
#1

Certbot auto-renew failing every 89 days, not 90. Pattern is too consistent to be random.

Environment:

  • OS: Debian 12.5
  • Certbot: 2.10.0
  • Web server: nginx 1.24.0
  • Cron: 0 3 * * * certbot renew --quiet

Log analysis from OVHcloud VPS:

  • Day 89 03:00: certbot starts, gets 429 from LE staging
  • Day 89 03:02: nginx reload fails, port 443 in use
  • Day 89 03:05: second certbot instance detected, both die

Race condition suspected. Two certbot processes spawned within same minute. But why only day 89? The 90-day window should leave 24h buffer.

Attached: full cron logs, systemd timers disabled. Only root crontab active.

Has anyone seen certbot fire twice on identical cron syntax?

It's always DNS. Always.
2 #2
$ systemd-analyze timer
NEXT                          LEFT          LAST                          PASSED        UNIT
Thu 2026-08-21 03:00:00 CEST  4h 12min    Wed 2026-08-20 03:00:13 CEST  19h ago       certbot.timer

$ ps aux | grep certbot
root      1847  0.0  1.2  45212  8924 ?        S    03:00   0:00 certbot renew
root      1852  0.0  1.2  45212  8912 ?        S    03:00   0:00 certbot renew

Decent disk IO, meh network

Race confirmed. Two PIDs same second.

$ timedatectl status
               Local time: Thu 2026-08-21 22:47:33 CEST
           Universal time: Thu 2026-08-21 20:47:33 UTC
                 RTC time: Thu 2026-08-21 20:43:33
                Time zone: Europe/Berlin (CEST, +0200)

RTC 4 min slow. Host clock drift.

fio, iperf, geekbench. results or gtfo.
#3

I see same thing on RackNerd.

Very strange. I check yesterday and the clock is 3 minute behind.

Certbot think "oh no time is up" but actually still 1 day left.

I fix with ntpdate pool.ntp.org.

Now no more problem.

9 #4
FlowSana said:
Race condition suspected. Two certbot processes spawned within same minute. But why only day 89?

Because on day 89 the first certbot instance is slow enough that the second cron tick fires before the first finishes. By day 90 it would already be expired, but you hit the LE rate limit first.

I have seen this on Hetzner cloud instances in Falkenstein when the entropy pool is dry. certbot hangs waiting on /dev/random while Python initializes SSL.

Check with:

cat /proc/sys/kernel/random/entropy_avail

If under 1000, install haveged or rng-tools5. Your 03:00 timing is also when every other VPS in that OVH region runs cron. Network to LE stalls.

#5
frankfurt_ops said:
Entropy pool is dry

That tracks. My entropy_avail was 187 when I checked this morning. Installed rng-tools5, will monitor.

But the double spawn is still unexplained. Cron should not fire twice.

It's always DNS. Always.
8 #6
FlowSana said:
Cron should not fire twice.

Cron doesn't. Something else does.

You said systemd timers are disabled, but is certbot.timer masked or just stopped? On Debian bookworm, installing certbot from snap or apt sometimes drops both a cron job AND a systemd timer. They fight.

systemctl list-timers --all | grep certbot
systemctl status certbot.timer

I have seen this exact failure mode on Linode and Vultr both. Two triggers, same binary, race to the lock file.

IPv4, IRC, and irssi — fight me
#7
haroldgsm said:
certbot.timer masked or just stopped
$ systemctl status certbot.timer
Unit certbot.timer could not be found.


But I found it. /etc/cron.d/certbot from the apt package, plus my root crontab. Two cron entries. I am an idiot.

Removed the duplicate. Still want to know why day 89 specifically though.
It's always DNS. Always.
#8
FlowSana said:
Two cron entries

Classic. I have done worse.

The day 89 thing is LE's renewal window. Certbot starts trying 30 days before expiry, but your cron logs show it only actually executes the full renewal path when within 10 days. The 429 from staging on day 89 suggests it is hitting the failed auth limit because the first attempt partially succeeds, second attempt confuses LE, both get throttled.

Staging and prod share rate limits per IP range on some endpoints. OVH's Singapore routing goes through the same anycast nodes.

fio, iperf, geekbench. results or gtfo.
#9

Same issue on my end with Namecheap shared hosting. They run certbot for you but the cron is doubled up with their own panel job. Every 60 days I get a broken chain.

I just switched to ZeroSSL for that domain. 90 days same as LE, no rate limit headaches.

#10
mikenoan said:
Switched to ZeroSSL

ZeroSSL free tier has 3 certificates limit per account. Fine for one domain, pain for wildcards.

I stay with LE but use acme.sh instead of certbot. Lighter, no Python entropy wait, no systemd timer nonsense.

Thread closed

Replies are closed on this thread. Closed: the question was answered.