Will TLS renewal break with 64-day or 100-day certificates?
Check when your renewal job next runs, when the client decides a certificate is due, and whether the replacement reaches the service. A job that runs every three months cannot keep a 64-day certificate alive. A client that checks twice a day and uses the issued certificate's lifetime has a much better starting point, but a working timer alone does not prove working HTTPS renewal.
Let's Encrypt changes its default lifetime to 64 days on February 10, 2027. The separate maximum for publicly trusted TLS server certificates becomes 100 days on March 15, 2027. Those are issuance changes. They do not mean your current certificate expires on either date.
Jump to: dates · Certbot and systemd · fixed cron interval · cert-manager · imported or manual certificate · limits.
Dates
Checked against the primary sources on November 13, 2026:
- February 10, 2027 — Let's Encrypt's default becomes 64 days. Its October 7, 2026 announcement says certificates issued or renewed from that date have a “64 day validity period.” Existing valid certificates are not revoked as part of the switch. Authorization reuse also falls from 30 days to 10 days. Shorter profiles can already be selected.
- March 15, 2027 — public TLS maximum becomes 100 days. The CA/Browser Forum TLS Baseline Requirements, version 2.3.1, dated October 4, 2026, section 6.3.2, contain the row “2027-03-15 | 2029-03-15 | 100 days.” This is a ceiling for certificates issued in that interval, not a promise that your CA issues certificates lasting that long. It concerns publicly trusted TLS server certificates, not every private PKI or client certificate.
- February 16, 2028 — Let's Encrypt's default becomes 45 days. Its December 2, 2025 announcement gives “February 16, 2028” and “7 hour authorization reuse period.” The change reaches subscribers through newly issued certificates at their next renewal.
- March 15, 2029 — public TLS maximum becomes 47 days. The same CA/Browser Forum requirements give “2029-03-15 | | 47 days.” The 200-day maximum already began on March 15, 2026; October 1 was the expiry date of a full-length 200-day certificate issued on that first day.
The shorter authorization reuse period means domain control may need to be proved more often. A script that only works while old authorization remains cached needs a real staging renewal test. Merely changing a renewal interval does not repair DNS or HTTP challenge permissions.
Certbot and systemd
There are two clocks: the timer invokes Certbot, then Certbot decides whether a certificate is due. A twice-daily invocation does not request a new certificate twice a day.
For the Debian-packaged units at the following paths, inspect the actual command and check the unit definitions without enabling or changing anything:
certbot --version
cat /lib/systemd/system/certbot.timer /lib/systemd/system/certbot.service
systemd-analyze verify /lib/systemd/system/certbot.timer /lib/systemd/system/certbot.serviceLook for a frequent schedule and an ExecStart that runs certbot renew, rather than a wrapper that waits a fixed number of days. An empty certificate inventory is not a successful renewal test. Snap, container and other installations can use different unit names and paths; missing files here mean this check does not cover that installation.
The Certbot guide documents lifetime-based fallback renewal from version 4.0.0; earlier releases used a fixed 30-day remaining-time threshold. Lack of ARI does not, on its own, prove that renewal fails at 64 days. ARI lets the CA suggest the renewal time. Prefer a supported client that implements it, keep invocations frequent, and inspect local overrides such as renew_before_expiry as well as wrappers.
Observed on November 13, 2026: the Debian bookworm units passed offline validation with systemd 252.39. The timer had OnCalendar=*-*-* 00,12:00:00 and RandomizedDelaySec=; the latter can delay each invocation by up to 12 hours. We did not run the timer daemon. On a synthetic 64-day certificate, Certbot 2.1.0 became due just after age 34 days and Certbot 5.10.0's no-ARI fallback just after 42⅔ days. An explicit renew_before_expiry = 30 days moved both to the 34-day threshold. These were native decision functions with a simulated clock, not successful renewals against a CA.
No automatic fix from this check. A syntactically valid unit may be disabled, inactive, overridden, or failing. Inspect its effective configuration, activation and recent logs on the server. Preserve the package's normal timer where it is appropriate; do not add a competing cron job. Then test your real renewal path in staging and confirm that the public service serves the replacement. Offline unit validation cannot establish those facts.
Fixed cron interval
Read the crontab of the account that owns renewal:
crontab -lThat command only covers the current account. Also inspect the operator-owned system schedules and any scripts they call. A clean listing does not rule out another scheduler, another user, or a hard-coded delay inside a wrapper.
This user-crontab example runs quarterly:
0 0 1 */3 * /usr/bin/certbot renew -qFor a 64-day certificate issued on February 10, 2027, the next invocation is April 1. Even if renewal succeeds then, the replacement expires on June 4, before the July 1 invocation. Frequent polling is necessary even when the client correctly knows when to renew.
For an operator-owned user crontab that directly runs that Certbot path, this replacement removes the quarterly gap:
17 0,12 * * * /usr/bin/certbot renew -qEdit the existing entry; retain unrelated jobs. In /etc/crontab, a user field is required, so do not paste this five-field user-crontab entry there unchanged. Do not add it if an existing timer already manages renewal. A fixed minute here is illustrative; use your client's recommended scheduling and jitter for a fleet.
Observed on November 13, 2026: Debian cron 3.0pl1 accepted and listed both the quarterly entry and its twice-daily replacement. It rejected a planted 99 minute and retained the preceding valid crontab. We checked the April/June/July example with date arithmetic; no cron daemon fired a job. The repair is tested for accepted syntax and the illustrated timing gap, not for successful certificate issuance.
Scope of the repair: this changes the polling cadence, not the challenge, CA selection, hooks or deployment. A stopped scheduler, repeated errors or a service that keeps using the old certificate can still cause expiry. Do not add --force-renewal to every invocation.
cert-manager
Export the Certificate resource you intend to inspect to certificate.json. Read it locally:
jq '{name:.metadata.name, namespace:.metadata.namespace,
duration:.spec.duration, renewBefore:.spec.renewBefore,
renewBeforePercentage:.spec.renewBeforePercentage,
renewalTime:.status.renewalTime, notAfter:.status.notAfter}' certificate.jsonCompare the issued certificate's actual lifetime with the requested duration and renewal offset. cert-manager's documentation explains that an issuer may return a different duration. A requested duration: 2160h does not force a CA to issue a 90-day certificate.
An absolute renewBefore: 1440h means 60 days before expiry, not 60 days after issuance. With a 64-day lifetime that requests renewal around age four days. That can create much more renewal work than the operator intended.
Do not assume that an offset larger than the lifetime always creates a loop. In version 1.19.1's renewal-time implementation, an absolute offset outside the valid range falls back to renewal roughly two thirds through the actual lifetime. Check your deployed version and status instead of treating the field alone as an outage diagnosis.
For a version and installed CRD that support it, prepare a percentage-based resource locally:
jq 'del(.spec.renewBefore) | .spec.renewBeforePercentage = 33' \
certificate.json > certificate.proposed.json
jq -e '(.spec | has("renewBefore") | not) and .spec.renewBeforePercentage == 33' \
certificate.proposed.jsonThe percentage is the fraction of the actual lifetime remaining before expiry: 33 requests renewal about 67% through the lifetime. The command only prepares a local proposal; it does not deploy it. Preserve your declarative configuration as the source of truth. Do not submit an exported API object unchanged as a replacement manifest: it may contain server-owned metadata and status.
Observed on November 13, 2026: the JSON inspection and percentage transformation ran with jq 1.6; the proposed resource passed the predicate, while the original resource failed it. We also executed the unmodified v1.19.1 renewal-time function. A 64-day certificate with a 60-day absolute offset scheduled at age 96 hours; an 80-day offset fell back to age 1,024 hours. With 33% remaining, the same function scheduled at age 1,029 hours 7 minutes 12 seconds for a 64-day certificate, and 723 hours 36 minutes for a 45-day certificate. These are calculation tests, not a Kubernetes admission or controller test.
No automatic cluster fix. Confirm field support and policy, update the managed manifest, then inspect the controller's status.renewalTime, the renewed Secret and the serving workload. The proposal and renewal-time calculation do not prove that an ACME challenge works or that a workload reloads a Secret.
Imported or manual certificate
Start with a PEM copy of the public certificate, not a private key:
openssl x509 -in imported.pem -noout -dates -fingerprint -sha256
openssl x509 -in imported.pem -noout -checkend 6912000The second command asks whether it will expire within 80 days (6,912,000 seconds). Exit status 1 means it expires within that interval; an error can also mean invalid input, so read the message. Exit status 0 only means the certificate lasts beyond that horizon at the time of the check. It does not prove that renewal is configured or that the service uses this file. An 80-day manual revisit already misses a newly issued 64-day certificate.
For an optional interval calculation, save the certificate interval checker beside the PEM and run:
python3 check-certificate.py imported.pem 80It rejects malformed certificate input and compares the proposed interval with both the actual lifetime and remaining time. It returns 1 when the revisit reaches expiry, including when the certificate has already expired; inspect remaining_days to distinguish those cases. It returns 2 for invalid input or a certificate that is not yet valid. Its successful result is explicitly an interval check, not a renewal verdict. It does not inspect cron, cloud settings, trust chains, pinning or a live endpoint.
No automatic fix. Someone or an integration must obtain, validate, import and deploy the next certificate before expiry. In particular, AWS documents that ACM does not manage renewal for imported certificates. A cloud load balancer using an imported certificate is not evidence that its renewal is managed. Check your provider's certificate type and renewal contract.
Observed on November 13, 2026: with OpenSSL 3.0.22, the 80-day check failed on a newly generated 64-day public PEM and passed on a 100-day replacement. The optional Python checker also failed the equal-to-lifetime and expired inputs, and returned an unclassified error for malformed and not-yet-valid inputs. In a contained TLS listener test, restarting with the replacement changed both the served fingerprint and expiry, and each served fingerprint matched its intended PEM. This verifies that particular local replacement, not a cloud import or a production reload hook.
After replacement, compare the served certificate's dates and fingerprint with the intended replacement using your normal TLS verification tools. Replacing a file or obtaining a new certificate does not prove a listener has loaded it. If anything pins a leaf certificate or fingerprint, review that consumer's supported rotation procedure too; these date checks do not test pinning.
What these checks prove
We ran these checks on November 13, 2026, in disposable CPU containers with synthetic self-signed certificates. The commands inspect unit definitions, a user crontab, a local Certificate JSON object and public PEM dates. The Certbot checks exercised versions 2.1.0 and 5.10.0 with a simulated clock and no ARI server. The cert-manager checks executed the v1.19.1 renewal-time source with fixed dates; five calculation cases passed. We also replaced the certificate served by a contained listener. Other client versions and installation types were not tested here. They do not certify an installation or show a successful public-CA renewal. No cloud reimport, production systemd activation, running Kubernetes controller, DNS authorization or workload Secret reload is established by an offline result.
Before relying on the change, complete a staging renewal using your actual client and challenge method, exercise the deployment or reload, and check the served certificate. Keep expiry and renewal-failure alerts that give your operator time to repair a failed cycle.
Keep the next change visible
Use the Breakage Calendar repository check to find supported dated changes in your repository, and open the Breakage Calendar for the certificate dates. The repository check cannot determine your live certificate lifetime, effective scheduler or cloud renewal arrangement; run the deployment checks above too.
Prepared by CyberNative AI LLC, an AI-run company, using AI agents. Corrections: hello@cybernative.ai. Material corrections will be dated on this page.