Disable TLS-ALPN, use existing LE account, stateless mode like acme.sh

1. Output of caddy version:

v2.6.2 h1:wKoFIxpmOJLGl3QXoo6PNbYvGW4xLEgo32GPBEjWL8o=

2. How I run Caddy:

systemd from official package repo

a. System environment:

Ubuntu 20.04.5
5.4.0-1073-raspi
aarch64
systemd

b. Command:

N/A

c. Service/unit/compose file:

[Unit]
Description=Caddy
Documentation=https://caddyserver.com/docs/
After=network.target network-online.target
Requires=network-online.target

[Service]
Type=notify
User=caddy
Group=caddy
ExecStart=/usr/bin/caddy run --environ --config /etc/caddy/Caddyfile
ExecReload=/usr/bin/caddy reload --config /etc/caddy/Caddyfile --force
TimeoutStopSec=5s
LimitNOFILE=1048576
LimitNPROC=512
PrivateTmp=true
ProtectSystem=full
AmbientCapabilities=CAP_NET_BIND_SERVICE

[Install]
WantedBy=multi-user.target

d. My complete Caddy config:

I am still reading the docs, no running config yet.

N/A

3. The problem I’m having:

As you can read in the title, I want to do multiple things.

a) Globally disable TLS-ALPN

I want to globally only use the HTTP challenge and don’t fallback to TLS-ALPN. I did not find any option to configure that in Global options (Caddyfile) — Caddy Documentation

b) Use an existing account for Let’s Encrypt

I use acme.sh on some other servers and have the same account configured for all of them. How do I instruct Caddy to use this account, i.e. where do I need to put the accounts key? Again, in the docs I only found the ability to set the acme email Global options (Caddyfile) — Caddy Documentation

c) stateless mode like acme.sh

acme.sh has what it calls the Stateless-Mode
In essence you hardcode the accounts JWK thumbprint into i.e. nginx and it responds to challenges from memory.
I want to get the JWK thumbprint from caddy in order to use this with an internal server.

What I essentially want to setup:
I have split DNS, internal is serving private IP ranges, external is serving the IP of a server in a datacenter.
I configure the datacenter server with the snippet from stateless mode and the correct JWK.
When caddy on the internal server requests a cert, the HTTP challenge is served valid by the datacenter server and the cert is issued.

It’s there, albeit subtly You want cert_issuer:

Something like this:

cert_issuer acme {
    disable_tlsalpn_challenge
}

You can do this, but I don’t think there’s been any requests before to do this in the Caddyfile. So it’s in the ACME issuer config in the JSON:

Caddy’s not really in the business of interactive cert operations so you’ll need to use a command line tool dedicated to that. I’ve never done that before (nor had any requests for this before). Maybe something like this? JSON Web Key (JWK) thumbprints | Connect2id

But, I’d highly recommend simplifying your infrastructure rather than complicating it by just using Caddy for all your TLS needs.

1 Like

Thanks for helping me out :smiling_face:
I got it working to my wishes.

For others looking at the thread, it had one too many underscores.

cert_issuer acme {
        disable_tlsalpn_challenge
 }

It would be very cool though. I got it the hacky way, by triggering a challenge and cating it out of the challenge file now ^^

For me, this is a quite simple but elegant solution in not having to expose something in my internal network and still get certificates over the HTTP challenge. If the server falls victim to a 0-day RCE, I wouldn’t care remotely as much, as when it would hit my internal network. I mean, caddy still does 99% of the stuff, just not serving the challenge. Also I don’t have to deal with stupid CGNAT this way :wink:
It might even be of value to others who are for some reason unable/unwilling to put their caddy on the network edge and/or have a bad DNS provider. I get your point though.

This topic was automatically closed after 30 days. New replies are no longer allowed.