At 8:40 on the morning of July 13, 2026, Hetzner's Ashburn (ASH) load balancers went dark. StatusGator logged it as a "Load Balancer Disruption in ASH" with severity Down, and the tenants who felt it worst were the ones who had done the reasonable thing: terminate TLS on the managed load balancer and let the provider handle certificates. When the LB is both your front door and your certificate authority liaison, one incident takes both.
Follow-up urgent LB maintenance landed on July 16, and a broader Cloud incident touching load balancers, networks, and servers ran July 27–28. July 2026 was a rough month to have your renewal path share fate with your provider's data plane — and with Let's Encrypt certificates shrinking from 90 days toward 45 and even 6, renewals are about to happen far more often.
This post compares the three TLS paths a self-hosted PaaS on owned hardware can run — managed load-balancer certificates, Caddy's automatic HTTPS, and cert-manager plus Gateway API — on the one question July forced: which path keeps renewing when the provider's load balancer doesn't?
The three TLS paths, compared
The short version up front. Each path issues from the same public ACME CAs; what differs is where the renewal loop lives and what else breaks when that place breaks.
| Dimension | Managed LB certificates | Caddy automatic HTTPS | cert-manager + Gateway API |
|---|---|---|---|
| Who issues and renews | The cloud provider, on the LB | Caddy itself, in-band on your nodes | cert-manager controllers, on your cluster |
| Renewal during a provider LB outage | Stops with the LB; new issuance and some renewals stall | Continues; HTTP-01/DNS-01 run from your nodes | Continues; solvers run from your cluster |
| Wildcard support (DNS-01) | Depends on the provider's managed offering | Yes, via DNS plugins (one per provider) | Yes, via DNS-01 solvers and webhook providers |
| Hetzner DNS TTL handling | Hidden by the provider | You set the TXT TTL in plugin config | You set ttl explicitly; tune propagation checks |
| Blast radius of a bug | Every tenant on that LB, at once | Per Caddy instance or storage backend | Per issuer/cluster, scoped by namespace |
| Fleet-size fit | Any size, until the outage | 1 box to a handful of nodes; needs shared storage past that | 3+ nodes and up; overhead pays off at fleet scale |
| Operational cost | Lowest day-to-day, highest incident coupling | One binary and a config file | CRDs, issuers, solvers, upgrades to track |
If you only take one row from this table, take the second: the renewal loop must live somewhere your provider's load balancer outage cannot reach. The rest of this post walks each path so you can see exactly where that loop lives.
The three paths in detail
Path 1: Terminate on the managed load balancer
Hetzner Cloud load balancers support managed certificates: point the LB at your domains, and Hetzner obtains and renews Let's Encrypt certificates on your behalf. Day to day, this is the cheapest TLS you can run. There is no renewal cron to monitor, no solver to debug, no storage backend holding private keys that you must back up. For a single service behind one LB, it is genuinely hard to beat.
The cost is coupling, and July priced it. Managed issuance means the provider's control plane is in your certificate path: validation, issuance, and renewal all transit infrastructure you neither run nor observe. When ASH load balancing degraded on July 13, tenants terminating there lost traffic and the machinery that would mint their next certificate. A renewal due that week had nowhere to go until the provider recovered.
The follow-on urgent maintenance on July 16 and the July 27–28 incident affecting load balancers among other Cloud systems underlined the pattern: provider maintenance windows and your renewal windows now overlap by calendar chance, and as certificate lifetimes shrink, the overlap stops being a coincidence and becomes a standing risk.
There is a second, quieter coupling: feature ceiling. Wildcard handling, challenge-type choice, and renewal timing are whatever the managed offering exposes. If your platform needs DNS-01 wildcards for per-tenant subdomains or wants renewal windows suggested by the CA, you get them when the provider ships them, not when the ecosystem does.
Use managed LB certificates for what they are good at — a cheap front door for a small static set of domains — and treat them as borrowed machinery, not owned infrastructure.
Path 2: Caddy's automatic HTTPS
Caddy inverted the TLS responsibility: instead of configuring certificates, you configure hostnames, and the server obtains, installs, and renews certificates itself over ACME with zero configuration. Point a reverse_proxy at your app, give Caddy a public hostname on ports 80/443, and the first handshake triggers issuance; renewals run automatically well before expiry with no cron to maintain. For a single box or a small fleet behind DNS, this is the fastest route to correct, always-fresh TLS, and the renewal loop lives on your machines — a provider LB outage cannot stall it because it never touches the provider.
Two details decide whether Caddy carries you past the first handful of nodes. The first is storage. Certificates and ACME state live in Caddy's storage backend, file-based by default. One Caddy instance is trivially consistent; two Caddy instances behind round-robin DNS each managing their own store will duplicate issuance, race renewals, and can trip CA rate limits. Past one node, point every instance at shared storage (a volume, Consul, Redis, or a database backend) so the fleet acts as one ACME client.
The second is On-Demand TLS, the feature that issues certificates at handshake time for hostnames Caddy has never seen. It is exactly what a multi-tenant PaaS wants — customer brings app.customer.com, first request mints the cert — and exactly what an attacker abuses to make your fleet mint certificates for arbitrary names. Caddy ships the guardrails (ask endpoint to approve hostnames, rate limits), but you must configure them; On-Demand without an ask gate is an open issuance oracle that burns your CA rate-limit budget. With shared storage and a gated ask endpoint, Caddy scales further than its single-binary reputation suggests — but past roughly a dozen nodes with per-tenant issuance policy, you are re-implementing the issuer/solver separation that cert-manager gives you declaratively.
Path 3: cert-manager plus Gateway API
cert-manager moves the renewal loop into the cluster as declarative API objects: Issuer/ClusterIssuer says which CA to use, Certificate says what to mint, and controllers reconcile the difference — requesting, renewing, and storing certificates as Secrets. Nothing in that loop transits the provider's load balancer, so July's outage class cannot stall it. Pair it with Gateway API listeners (Gateway TLS config referencing cert-manager-managed certificates, including per-protocol listeners) instead of annotations on Ingress, and TLS attachment becomes typed configuration rather than stringly annotation folklore.
The reason to prefer this path in late 2026 specifically is renewal intelligence. cert-manager v1.21 added experimental support for ACME Renewal Information (ARI, RFC 9773) behind the ACMEUseARI feature gate: instead of renewing on a fixed fraction of certificate lifetime, the client asks the CA's renewalInfo endpoint for a suggested window, and the CA can pull renewals earlier during mass-revocation events or key rollovers. Fixed-schedule renewal was tuned for 90-day certificates; it quietly misbehaves on shorter ones.
And shorter ones are here: Let's Encrypt made 6-day shortlived certificates generally available in January 2026, moved the tlsserver profile to 45-day certificates in May, and has the default classic profile stepping down to 64 days in February 2027 and 45 days in February 2028, ahead of the CA/Browser Forum mandate dropping maximum lifetimes toward ~47 days by 2029. On a 6-day certificate, "renew at two-thirds lifetime" means a renewal every four days per cert — a schedule only a controller consulting ARI windows should be trusted to run. Early ecosystem momentum agrees: acme.sh 3.1.4 enabled ARI by default and moved its cron to every 6 hours to react to CA-suggested windows in time.
The price is operational surface: CRDs to upgrade, issuers and solvers to configure per DNS provider, and version tracking (v1.21's ARI is experimental and gated; Gateway API ListenerSet support is alpha). For a fleet of three or more nodes already running Kubernetes, that surface is routine controller maintenance. For a single box, it is more machinery than Caddy with no additional renewal safety.
Wildcards and DNS-01: the TTL you must set and the wait you must tune
Whichever self-run path you choose, wildcard certificates force you onto DNS-01: the CA demands a _acme-challenge TXT record, which means your renewal loop must write to your DNS provider's API and then wait out propagation. On Hetzner DNS this has a sharp edge worth knowing before your first 2 AM renewal failure: the API requires an explicit ttl on every record you create — there is no server-side default to catch you — and the value you pick directly shapes challenge reliability.
Set the challenge TXT TTL low (60–120 seconds). A high TTL on _acme-challenge records lets resolvers cache a stale challenge token across retries, turning one failed validation into a string of them. Then tune the solver's propagation wait to match: cert-manager's DNS-01 solvers and Caddy's DNS plugins both poll for the TXT record before telling the CA to verify, and the check interval plus timeout must exceed your real propagation delay with margin, not the optimistic one from the docs. The failure mode of getting this wrong is silent and intermittent — renewals that pass for months and then flap during a window when the CA's resolvers see a cached record — which is precisely the failure you will misdiagnose as a CA outage at 2 AM.
This is also where owning the path pays its clearest dividend: when a renewal fails, the logs, the retry policy, and the fix are all yours. On the managed-LB path, the same failure is a support ticket whose status page says everything is green.
The recommendation: own the certificate path
For a self-hosted PaaS on owned Hetzner hardware, the default should be: terminate TLS on infrastructure you run, with the renewal loop on your own nodes or cluster, and keep the provider's load balancer (if you use one at all) as dumb TCP plumbing in front of it. Concretely:
- Single box or two nodes: Caddy with automatic HTTPS, certificates on a persisted volume, On-Demand TLS gated by an
askendpoint if tenants bring custom domains. This is the smallest setup whose renewals survive a provider LB outage. - Three nodes and up, or Kubernetes already: cert-manager plus Gateway API, DNS-01 via a Hetzner-compatible solver with explicit low TTLs, and the
ACMEUseARIgate enabled so renewals follow CA-suggested windows as lifetimes shrink. - Migrating off managed LB certificates: stand up the new path alongside the LB first, cut one low-risk domain over and watch a full renewal cycle, then move the fleet domain by domain. Never migrate the week a large batch of certificates is due — stagger expirations first so no single incident window can catch every cert at once.
- Every path: alert on certificate expiry with a threshold measured in fractions of lifetime, not days. "Warn at 21 days" was fine for 90-day certs; on 45-day and 6-day certs it fires after the cert is already dead. Warn at one-third of lifetime remaining, and page at one-sixth.
July's lesson generalizes beyond Hetzner and beyond load balancers. Every managed convenience in your TLS path is a renewal dependency you cannot observe, retry, or fix — and the industry is simultaneously multiplying how often renewals must succeed. A fleet that renews on its own machines treats a provider outage as a traffic problem; a fleet that renews through its provider treats it as an identity problem, with every certificate in the blast radius. Own the certificate path, and the next July 13 is someone else's outage.
Bex.co is the open-source, AI-native Render alternative — push a git repo, get a running HTTPS service on machines you own. Star the repo on GitHub or deploy your first app today.



