Let’s Encrypt rilascia certificati per novanta giorni e li rinnova automaticamente, motivo per cui si smette di pensarci una settimana dopo la configurazione. Il guaio è che il rinnovo automatico si rompe in silenzio: nessuno vede gli errori, e tre mesi dopo il sito accoglie i visitatori con un avviso del browser. Dal 2025 Let’s Encrypt non invia più avvisi di scadenza per posta, quindi è sparito anche l’ultimo promemoria esterno.

Di seguito i motivi per cui il rinnovo smette di funzionare, in ordine di frequenza decrescente.

1. Il certificato è stato rinnovato e il servizio non lo ha riletto

Il più frequente. certbot renew ha funzionato, il file nuovo è sul disco, e nginx o Apache tengono in memoria quello vecchio, consegnandolo ai visitatori finché la configurazione non viene ricaricata. Formalmente va tutto bene; di fatto il sito ha un certificato scaduto.

Si cura con un hook eseguito dopo un rinnovo riuscito:

sudo certbot renew --deploy-hook "systemctl reload nginx"

Lo si scrive una volta nel file di rinnovo (/etc/letsencrypt/renewal/example.com.conf, sezione [renewalparams], riga renew_hook) e da lì in poi funziona da solo.

2. È cambiato il server web e la validazione no

La validazione HTTP-01 richiede che un file da /.well-known/acme-challenge/ sia servito su HTTP semplice. Di solito la si rompe così:

  • è stato aggiunto alla configurazione un reindirizzamento incondizionato da HTTP a HTTPS: la validazione finisce nel reindirizzamento e non passa;
  • è comparsa una regola location ~ /\. con deny all che chiude tutte le cartelle con un punto, .well-known compresa;
  • la radice del sito si è spostata mentre nelle impostazioni di certbot è rimasto il vecchio --webroot-path;
  • è stato attivato un blocco per paese o un’autenticazione di base che ha travolto anche il server di validazione.

L’ordine corretto nella configurazione: prima un location dedicato a /.well-known/acme-challenge/ e solo dopo il reindirizzamento generale.

3. Il timer è spento

Il rinnovo viene avviato da un timer di systemd o da un lavoro di cron, ed entrambi possono essere disattivati per distrazione durante un debug o persi in un trasloco di server.

systemctl list-timers | grep certbot
sudo certbot renew --dry-run

Il secondo comando esegue un ciclo di rinnovo completo in modalità di prova senza consumare la sua quota. È l’unica verifica che risponde in anticipo a «si rinnoverà fra un mese?» invece che a posteriori.

4. Un dominio non punta più qui

Il certificato copre cinque domini, uno di essi è passato a un altro hosting, il DNS è cambiato. La validazione di quel dominio smette di passare, e certbot non rinnova l’intero certificato, con i quattro domini funzionanti compresi. I domini di troppo vanno tolti dal certificato, non ignorati insieme al messaggio.

5. Ha raggiunto i limiti

Let’s Encrypt limita il numero di certificati per dominio a settimana. Di solito è la conseguenza del ciclo «non ha funzionato, riprovo» durante il debug. Per gli esperimenti esiste un server di prova (--dry-run o --test-cert), e va usato prima di esaurire il limite, non dopo.

Verifichi ciò che viene consegnato, non ciò che è archiviato

Ogni verifica basata sui file ha lo stesso difetto: il file può essere fresco mentre il visitatore riceve il certificato vecchio. Guardi dal lato del client:

echo | openssl s_client -connect example.com:443 -servername example.com 2>/dev/null \
  | openssl x509 -noout -dates -subject -issuer

L’opzione -servername è indispensabile: senza di essa, su un server con più siti otterrà il certificato del primo host virtuale che capita e non quello che cercava. Nell’output, notAfter è la vera data di scadenza.

Ne approfitti per verificare la catena:

echo | openssl s_client -connect example.com:443 -servername example.com -showcerts 2>/dev/null | grep -c 'BEGIN CERTIFICATE'

Se c’è un solo certificato, l’intermedio non viene consegnato. I browser di solito perdonano questa configurazione — costruiscono la catena da soli — ma curl, le applicazioni mobili e i client in Java falliranno la validazione. È il classico «da me si apre tutto e al cliente non funziona».

Quanti giorni di preavviso

Trenta giorni sono una prima soglia ragionevole: è anche quanto resta quando certbot comincia i tentativi di rinnovo, quindi se per allora non è successo nulla, il meccanismo è rotto. Quattordici giorni sono il secondo segnale, quello che impone di agire oggi. Sette sono un’emergenza.

L’importante è seguire tutti i certificati insieme, compresi quelli che non vengono da Let’s Encrypt: quelli acquistati per un anno sono i più sicuramente dimenticati, perché in un anno tutti hanno dimenticato sia loro sia a quale casella arrivano gli avvisi. Una pagina con i domini, le date e i giorni rimanenti chiude del tutto la questione, come nella dimostrazione qui sotto.