* caddytls: Support multiple issuers
Defaults are Let's Encrypt and ZeroSSL.
There are probably bugs.
* Commit updated integration tests, d'oh
* Update go.mod
* caddytls: Add support for ZeroSSL; add Caddyfile support for issuers
Configuring issuers explicitly in a Caddyfile is not easily compatible
with existing ACME-specific parameters such as email or acme_ca which
infer the kind of issuer it creates (this is complicated now because
the ZeroSSL issuer wraps the ACME issuer)... oh well, we can revisit
that later if we need to.
New Caddyfile global option:
{
cert_issuer <name> ...
}
Or, alternatively, as a tls subdirective:
tls {
issuer <name> ...
}
For example, to use ZeroSSL with an API key:
{
cert_issuser zerossl API_KEY
}
For now, that still uses ZeroSSL's ACME endpoint; it fetches EAB
credentials for you. You can also provide the EAB credentials directly
just like any other ACME endpoint:
{
cert_issuer acme {
eab KEY_ID MAC_KEY
}
}
All these examples use the new global option (or tls subdirective). You
can still use traditional/existing options with ZeroSSL, since it's
just another ACME endpoint:
{
acme_ca https://acme.zerossl.com/v2/DV90
acme_eab KEY_ID MAC_KEY
}
That's all there is to it. You just can't mix-and-match acme_* options
with cert_issuer, because it becomes confusing/ambiguous/complicated to
merge the settings.
* Fix broken test
This test was asserting buggy behavior, oops - glad this branch both
discovers and fixes the bug at the same time!
* Fix broken test (post-merge)
* Update modules/caddytls/acmeissuer.go
Fix godoc comment
Co-authored-by: Francis Lavoie <lavofr@gmail.com>
* Add support for ZeroSSL's EAB-by-email endpoint
Also transform the ACMEIssuer into ZeroSSLIssuer implicitly if set to
the ZeroSSL endpoint without EAB (the ZeroSSLIssuer is needed to
generate EAB if not already provided); this is now possible with either
an API key or an email address.
* go.mod: Use latest certmagic, acmez, and x/net
* Wrap underlying logic rather than repeating it
Oops, duh
* Form-encode email info into request body for EAB endpoint
Co-authored-by: Francis Lavoie <lavofr@gmail.com>
Panic would happen if an automation policy was specified in a singular
server block that had no hostnames in its address. Definitely an edge
case.
Fixed a bug related to checking for server blocks with a host-less key
that tried to make an automation policy. Previously if you had only two
server blocks like ":443" and another one at ":80", the one at ":443"
could not create a TLS automation policy because it thought it would
interfere with TLS automation for the block at ":80", but obviously that
key doesn't enable TLS because it is on the HTTP port. So now we are a
little smarter and count only non-HTTP-empty-hostname keys.
Also fixed a bug so that a key like "https://:1234" is sure to have TLS
enabled by giving it a TLS connection policy. (Relaxed conditions
slightly; the previous conditions were too strict, requiring there to be
a TLS conn policy already or a default SNI to be non-empty.)
Also clarified a comment thanks to feedback from @Mohammed90
The comments in the code should explain the new logic thoroughly.
The basic problem for the issue was that we were overriding a catch-all
automation policy's explicitly-configured issuer with our own, for names
that we thought looked like public names. In other words, one could
configure an internal issuer for all names, but then our auto HTTPS
would create a new policy for public-looking names that uses the
default ACME issuer, because we assume public<==>ACME and
nonpublic<==>Internal, but that is not always the case. The new logic
still assumes nonpublic<==>Internal (on catch-all policies only), but
no longer assumes that public-looking names always use an ACME issuer.
Also fix a bug where HTTPPort and HTTPSPort from the HTTP app weren't
being carried through to ACME issuers properly. It required a bit of
refactoring.
* pki: Initial commit of PKI app (WIP) (see #2502 and #3021)
* pki: Ability to use root/intermediates, and sign with root
* pki: Fix benign misnamings left over from copy+paste
* pki: Only install root if not already trusted
* Make HTTPS port the default; all names use auto-HTTPS; bug fixes
* Fix build - what happened to our CI tests??
* Fix go.mod
It's still not perfect but I think it should be more correct for
slightly more complex configs. Might still fall apart for complex
configs that use on-demand TLS or at a large scale (workarounds are
to just implement your own redirects, very easy to do anyway).
This is a breaking change primarily in two areas:
- Storage paths for certificates have changed
- Slight changes to JSON config parameters
Huge improvements in this commit, to be detailed more in
the release notes.
The upcoming PKI app will be powered by Smallstep libraries.
This is necessary to avoid a race for sockets. Both the HTTP servers and
CertMagic solvers will try to bind the HTTP/HTTPS ports, but we need to
make sure that our HTTP servers bind first. This is kind of a new thing
now that management is async in Caddy 2.
Also update to CertMagic 0.9.2, which fixes some async use cases at
scale.
The fix that was initially put forth in #2971 was good, but only for
up to one layer of nesting. The real problem was that we forgot to
increment nesting when already inside a block if we saw another open
curly brace that opens another block (dispenser.go L157-158).
The new 'handle' directive allows HTTP Caddyfiles to be designed more
like nginx location blocks if the user prefers. Inside a handle block,
directives are still ordered just like they are outside of them, but
handler blocks at a given level of nesting are mutually exclusive.
This work benefitted from some refactoring and cleanup.
This splits automatic HTTPS into two phases. The first provisions the
route matchers and uses them to build the domain set and configure
auto HTTP->HTTPS redirects. This happens before the rest of the
provisioning does.
The second phase takes place at the beginning of the app start. It
attaches pointers to the tls app to each server, and begins certificate
management for the domains that were found in the first phase.