Rate-limit pain at the small-operator scale rarely comes from having forty subdomains. It comes from having forty subdomains and a deployment process that keeps inventing new certificate shapes. Reinstall the ACME client, wipe its state directory, add a per-service certificate for a new app, and you have created new exact identifier sets. The tightest limit most people in this range will hit first is not the per-domain ceiling but the exact-set ceiling, and it is easy to trip without ever issuing fifty certificates.
This is a strategy article, not a tutorial. The goal is to decide how many certificates you need, which names go on each, and which challenge type each certificate uses, so that renewals stay boring and troubleshooting does not consume production quota.
The limits that actually matter at this scale
Let’s Encrypt publishes its rate limits in one place, and the mechanics are worth reading directly rather than relying on summaries. Limits are enforced with a token bucket: you can burst up to the limit or space requests out, and capacity refills gradually. Revoking a certificate does not refund anything, because the issuance work has already been done (Let’s Encrypt rate limits documentation).
Three limits dominate the 40+ name case:
- New Orders per Account: up to 300 new orders per account every 3 hours. This is generous for a small shop but not infinite if a broken renewal loop retries aggressively.
- New Certificates per Registered Domain: up to 50 certificates per registered domain every 7 days. This is global across all accounts, so a second ACME account does not buy you headroom.
- New Certificates per Exact Set of Identifiers: up to 5 certificates per exact same set of identifiers every 7 days, also global. This is the one that punishes churn.
The exact-set limit is deliberately low. Let’s Encrypt’s own documentation names the common causes: reinstalling the client to troubleshoot, or deleting the ACME client’s configuration data on each deploy. Both produce a new order for the same set of names, and after five in a week the domain is stuck until capacity refills at roughly one certificate every 34 hours.
There is also a per-identifier failure limit: up to 5 authorization failures per identifier per account every hour, after which new orders for that identifier by that account are blocked until reset. A misconfigured DNS record or a firewall rule that blocks HTTP-01 can burn through that in a single afternoon of retries.
Why “just use a wildcard” is a trade, not a solution
The reflex answer to “too many subdomains” is a wildcard certificate. It is a real option, but it changes where the risk sits.
Wildcards require the DNS-01 challenge. HTTP-01 cannot issue wildcard certificates, and TLS-ALPN-01 cannot either; both facts are stated plainly in the challenge types documentation. DNS-01 works by writing a TXT record under _acme-challenge.<domain>, which means your issuance path needs write access to DNS.
That is the foot-gun. Let’s Encrypt’s own guidance notes that putting full DNS API credentials on a web server significantly increases the impact if that server is compromised, and recommends narrowly scoped credentials or performing DNS validation from a separate machine and copying certificates to the web server. A wildcard certificate does not remove the need to manage credentials; it concentrates them.
There are legitimate reasons to choose a wildcard anyway: a pool of short-lived preview subdomains, names that are not publicly reachable, or a DNS provider with a clean API and scoped tokens. The point is to make that choice deliberately, not because a forum post said wildcards solve rate limits.
The renewal exemption is the lever
The most useful fact in the rate-limit documentation is that renewals are treated differently from new issuance.
Let’s Encrypt recognizes a renewal in two ways. The preferred method is ACME Renewal Info (ARI): a client that supports ARI checks with the server, and an order that explicitly indicates the certificate it replaces is exempt from all rate limits. The older method treats an order with the exact same set of identifiers as a renewal, ignoring capitalization and ordering. Those orders are exempt from New Orders per Account and New Certificates per Registered Domain, but they remain subject to the exact-set limit and the authorization-failure limit.
Two practical consequences follow. First, prefer a client that supports ARI, because ARI renewals are the only ones fully outside the rate-limit system. Second, keep identifier sets stable. A certificate whose names change on every deploy is not a renewal under either definition, and it will consume the exact-set budget.
This is an operational judgment, not a claim about how any specific client behaves. Check your client’s documentation for ARI support before assuming it applies.
A decision procedure for 40+ names
The following is a way to allocate names to certificates. It is a recommendation, not a finding from research.
- Inventory every name and assign it to exactly one certificate. Write the mapping down. A name that appears on two certificates is a name that will eventually be renewed twice for no reason.
- Group by validation path. Names that can all be validated with HTTP-01 belong together. Names that require DNS-01, because they are wildcards or because the host is not publicly reachable, belong on a separate certificate.
- Group by renewal lifecycle. A certificate that serves a stable set of long-lived services should not share an identifier set with a certificate that covers ephemeral preview environments. Different lifecycles mean different renewal timing, and mixing them forces you to reissue the stable certificate whenever the ephemeral one changes.
- Freeze the identifier set. Once a certificate is issued, treat its list of names as a documented object. Adding a name is a deliberate change with a reason, not a side effect of a deploy.
- Split only when a name genuinely cannot share a validation method. The default should be fewer certificates with stable sets, not one certificate per service.
For a shop with 45 names across two registered domains, a plausible allocation is two stable certificates, one per registered domain, covering the names that share HTTP-01 validation, plus one DNS-01 certificate for a wildcard covering a pool of short-lived subdomains. That is three certificates and three stable identifier sets, not forty-five. The numbers are illustrative; the shape is the point.
When a wildcard is the right tool
A wildcard is worth considering when the set of names is genuinely open-ended or not known at issuance time. Preview environments, per-tenant subdomains, and internal names that are not reachable from the public internet all fit. In those cases, DNS-01 is not a workaround; it is the correct challenge type.
If you go that route, scope the credentials. A DNS API token that can edit every record in every zone is a larger blast radius than the certificate problem you were trying to solve. Let’s Encrypt’s documentation recommends narrowly scoped credentials or a separate validation host. Certbot’s DNS plugins are the supported path for wildcard issuance with Certbot, and the Certbot user guide notes that certificates created with the manual plugin do not renew automatically unless you supply an authentication hook.
One detail that catches people: *.example.com does not cover example.com. If you need the apex, request it explicitly alongside the wildcard.
Operational hygiene that prevents self-inflicted limits
Most rate-limit incidents at this scale are self-inflicted. The following practices are cheap and remove the common causes.
- Use the staging environment for troubleshooting. Let’s Encrypt explicitly recommends staging for development and testing because it has significantly higher limits. A broken renewal loop against staging costs nothing in production quota.
- Do not delete ACME client state on redeploy. The configuration directory is the record of what has been issued. Treat it as persistent data, not as a build artifact.
- Keep credentials files next to renewal configs. A credentials file that moves or changes permissions can silently break renewal weeks later, and the failure will look like a validation problem rather than a file problem.
- Watch authorization failures per identifier. Five failures in an hour blocks new orders for that name. If a name is failing, stop retrying and diagnose; the retry loop is the problem.
- Test with a dry run before trusting a new configuration. A dry run against staging exercises the full path, including DNS record creation and cleanup, without consuming production quota.
What about DNS-PERSIST-01?
Let’s Encrypt has described a new challenge type, DNS-PERSIST-01, that replaces repeated challenge records with a persistent authorization TXT record bound to a specific ACME account and CA. The February 2026 announcement states that staging rollout was planned for late Q1 2026 and production for Q2 2026. That is a plan, not a confirmation of current availability. If you are evaluating it, check the current documentation rather than the announcement date.
The relevant point for this article is conceptual: a persistent authorization would remove DNS changes from the renewal path, which addresses one of the operational costs of DNS-01. It does not change the credential-scoping question, because the authorization record still has to be created and protected.
A short checklist
- Inventory every name and assign it to exactly one certificate.
- Group names by validation path and renewal lifecycle.
- Freeze each certificate’s identifier set and document it.
- Confirm whether your ACME client supports ARI; prefer it if it does.
- Scope DNS credentials narrowly if you use DNS-01.
- Use staging for every test and dry run.
- Treat ACME client state as persistent data.
The certificate strategy that survives rate limits is not the one with the fewest certificates or the most automation. It is the one where the identifier sets are stable, the validation paths are deliberate, and the failure modes are understood before they happen at 3 a.m.