Need help with certificate creation with zerossl and Caddy using Redis Storage module connected to AWS Elasticache

1. The problem I’m having:

Howdy! I need to run Caddy in AWS with auto-scaling and that requires shared storage. I have gone down the path of building Caddy with GitHub - gamalan/caddy-tlsredis: Redis Storage using for Caddy TLS Data and have managed to get caddy to start with the following settings:

“storage”: {
“Client”: null,
“ClientLocker”: null,
“Logger”: null,
“address”: “”,
“aes_key”: “a key”,
“db”: 0,
“host”: “a host”,
“key_prefix”: “caddytls”,
“module”: “redis”,
“password”: “”,
“port”: “6379”,
“timeout”: 5,
“tls_enabled”: false,
“tls_insecure”: true,
“username”: “”,
“value_prefix”: “redis”

I noticed after running caddy adapt --pretty that the Client and ClientLocker lines were present. I did not add these to my Caddyfile, so the system must need or want them? IDK

2. Error messages and/or full log output:

tail -f /logs/caddy-shared.log 
{"level":"debug","ts":1689223460.606051,"logger":"tls.handshake","msg":"no certificate matching TLS ClientHello","remote_ip":"24.17.48.38","remote_port":"36340","server_name":"bleem-api.peoplebrowser.com","remote":"24.17.48.38:36340","identifier":"bleem-api.peoplebrowser.com","cipher_suites":[51914,4865,4866,4867,49195,49199,49196,49200,52393,52392,49171,49172,156,157,47,53],"cert_cache_fill":0,"load_if_necessary":true,"obtain_if_necessary":true,"on_demand":false}
{"level":"debug","ts":1689223460.6061308,"logger":"http.stdlib","msg":"http: TLS handshake error from 24.17.48.38:36340: no certificate available for 'bleem-api.peoplebrowser.com'"}
{"level":"debug","ts":1689223460.6861198,"logger":"events","msg":"event","name":"tls_get_certificate","id":"48ac316a-2b50-4407-aad8-78bfe9387c5f","origin":"tls","data":{"client_hello":{"CipherSuites":[51914,4865,4866,4867,49195,49199,49196,49200,52393,52392,49171,49172,156,157,47,53],"ServerName":"bleem-api.peoplebrowser.com","SupportedCurves":[35466,29,23,24],"SupportedPoints":"AA==","SignatureSchemes":[1027,2052,1025,1283,2053,1281,2054,1537,513],"SupportedProtos":["h2","http/1.1"],"SupportedVersions":[51914,772,771],"Conn":{}}}}
{"level":"debug","ts":1689223460.6861966,"logger":"tls.handshake","msg":"no matching certificates and no custom selection logic","identifier":"bleem-api.peoplebrowser.com"}
{"level":"debug","ts":1689223460.6862082,"logger":"tls.handshake","msg":"no matching certificates and no custom selection logic","identifier":"*.peoplebrowser.com"}
{"level":"debug","ts":1689223460.6862137,"logger":"tls.handshake","msg":"no matching certificates and no custom selection logic","identifier":"*.*.com"}
{"level":"debug","ts":1689223460.6862192,"logger":"tls.handshake","msg":"no matching certificates and no custom selection logic","identifier":"*.*.*"}
{"level":"debug","ts":1689223460.6862261,"logger":"tls.handshake","msg":"all external certificate managers yielded no certificates and no errors","remote_ip":"24.17.48.38","remote_port":"36350","sni":"bleem-api.peoplebrowser.com"}
{"level":"debug","ts":1689223460.6862345,"logger":"tls.handshake","msg":"no certificate matching TLS ClientHello","remote_ip":"24.17.48.38","remote_port":"36350","server_name":"bleem-api.peoplebrowser.com","remote":"24.17.48.38:36350","identifier":"bleem-api.peoplebrowser.com","cipher_suites":[51914,4865,4866,4867,49195,49199,49196,49200,52393,52392,49171,49172,156,157,47,53],"cert_cache_fill":0,"load_if_necessary":true,"obtain_if_necessary":true,"on_demand":false}
{"level":"debug","ts":1689223460.6863856,"logger":"http.stdlib","msg":"http: TLS handshake error from 24.17.48.38:36350: no certificate available for 'bleem-api.peoplebrowser.com'"}

3. Caddy version:

caddy version
v2.6.4 h1:2hwYqiRwk1tf3VruhMpLcYTg+11fCdr8S3jhNAdnPy8=

4. How I installed and ran Caddy:

308 wget https://github.com/caddyserver/xcaddy/releases/download/v0.3.4/xcaddy_0.3.4_linux_amd64.tar.gz
309 tar xvzf xcaddy_0.3.4_linux_amd64.tar.gz
310 install -v xcaddy /usr/local/bin
313 rm -rvf /tmp/xcaddy
317 xcaddy build --with GitHub - gamalan/caddy-tlsredis: Redis Storage using for Caddy TLS Data

a. System environment:

Ubuntu Server 22.04 running in EC2

$echo $CADDY_CLUSTERING
redis

caddy list-modules
admin.api.load
admin.api.metrics
admin.api.pki
admin.api.reverse_proxy
caddy.adapters.caddyfile
caddy.config_loaders.http
caddy.listeners.http_redirect
caddy.listeners.tls
caddy.logging.encoders.console
caddy.logging.encoders.filter
caddy.logging.encoders.filter.cookie
caddy.logging.encoders.filter.delete
caddy.logging.encoders.filter.hash
caddy.logging.encoders.filter.ip_mask
caddy.logging.encoders.filter.query
caddy.logging.encoders.filter.regexp
caddy.logging.encoders.filter.rename
caddy.logging.encoders.filter.replace
caddy.logging.encoders.json
caddy.logging.writers.discard
caddy.logging.writers.file
caddy.logging.writers.net
caddy.logging.writers.stderr
caddy.logging.writers.stdout
caddy.storage.file_system
events
http
http.authentication.hashes.bcrypt
http.authentication.hashes.scrypt
http.authentication.providers.http_basic
http.encoders.gzip
http.encoders.zstd
http.handlers.acme_server
http.handlers.authentication
http.handlers.copy_response
http.handlers.copy_response_headers
http.handlers.encode
http.handlers.error
http.handlers.file_server
http.handlers.headers
http.handlers.map
http.handlers.metrics
http.handlers.push
http.handlers.request_body
http.handlers.reverse_proxy
http.handlers.rewrite
http.handlers.static_response
http.handlers.subroute
http.handlers.templates
http.handlers.tracing
http.handlers.vars
http.ip_sources.static
http.matchers.expression
http.matchers.file
http.matchers.header
http.matchers.header_regexp
http.matchers.host
http.matchers.method
http.matchers.not
http.matchers.path
http.matchers.path_regexp
http.matchers.protocol
http.matchers.query
http.matchers.remote_ip
http.matchers.vars
http.matchers.vars_regexp
http.precompressed.br
http.precompressed.gzip
http.precompressed.zstd
http.reverse_proxy.selection_policies.cookie
http.reverse_proxy.selection_policies.first
http.reverse_proxy.selection_policies.header
http.reverse_proxy.selection_policies.ip_hash
http.reverse_proxy.selection_policies.least_conn
http.reverse_proxy.selection_policies.random
http.reverse_proxy.selection_policies.random_choose
http.reverse_proxy.selection_policies.round_robin
http.reverse_proxy.selection_policies.uri_hash
http.reverse_proxy.transport.fastcgi
http.reverse_proxy.transport.http
http.reverse_proxy.upstreams.a
http.reverse_proxy.upstreams.multi
http.reverse_proxy.upstreams.srv
pki
tls
tls.certificates.automate
tls.certificates.load_files
tls.certificates.load_folders
tls.certificates.load_pem
tls.certificates.load_storage
tls.client_auth.leaf
tls.get_certificate.http
tls.get_certificate.tailscale
tls.handshake_match.remote_ip
tls.handshake_match.sni
tls.issuance.acme
tls.issuance.internal
tls.issuance.zerossl
tls.stek.distributed
tls.stek.standard

Standard modules: 100

caddy.storage.redis

Non-standard modules: 1

Unknown modules: 0

b. Command:


To start - systemctl start caddy
To reload - systemctl reload caddy

$systemctl edit caddy

GNU nano 4.8                        /etc/systemd/system/caddy.service.d/.#override.confd81dc227b1553c05 
                                  
[Service]
ExecStart=
ExecReload=

ExecStart=/usr/local/bin/caddy run --environ --config /etc/caddy/Caddyfile
ExecReload=/usr/local/bin/caddy reload --config /etc/caddy/Caddyfile

c. Service/unit/compose file:

d. My complete Caddy config:

{
        debug
        admin 0.0.0.0:2019
        storage redis {
                host caddy-ssl-redis-cluster-0001-001.ab000000001.usw1.cache.amazonaws.com
                port 6379
                aes_key 21111111-911b-4114-a111-311111111117
                module redis
                password ""
                db 0
                key_prefix caddytls
                value_prefix redis
                timeout 5
                tls_enabled false
                tls_insecure true
        }

        log {
                output file /logs/caddy-shared.log {
                        roll_size 20M
                        roll_keep 5
                }
        }
        on_demand_tls {
                ask http://api1:9005/
                interval 1m
                burst 10
        }
}

bleem-api.peoplebrowser.com {
        header Strict-Transport-Security "max-age=31536000"
        encode zstd gzip

        tls {
                issuer zerossl akeywithnumbers {
                        email contact@example.com
                }
        }

        reverse_proxy 172.31.43.231:1210
}

5. Links to relevant resources:

Howdy! I am hoping to have a central Elasticache Redis database store domain certificates for my 80k+ domains. My plan is to utilize auto-scaling with multiple caddy servers running as any given time. They will all be serving the same domains and therefore I need shared storage. I think I’ve exhausted my Google Fu and sure would appreciate some help.
Prior to attempting to change storage to Redis, Caddy did work and certificates were generated as needed with storage set like this:

storage file_system {
root /mnt
}
I

Ah, I think that’s a bug in the plugin. See these lines:

These shouldn’t have uppercase letters, which “exports” them causing them to appear in JSON when serializing the struct to JSON (that’s what the adapter does). It’s harmless though because null is already the default value, but changing them to anything non-null in the config would not work because there’s no valid JSON types that would deserialize into those types.

I opened an issue to track that: Internal struct fields should not be exported · Issue #43 · gamalan/caddy-tlsredis · GitHub

I’m not seeing any other problem in your post. Is that all? I’m not sure if that was your only point of confusion? Your config should work as-is I think.

1 Like

Thanks so much for your reply Francis.

My current problem is that no acme.zerossl certificate is being generated for the bleem-api site I have configured in the Caddyfile when I have storage set to redis. This is my Caddyfile currently:

Global Options

{
debug
admin 0.0.0.0:2019

storage file_system {

root /mnt

}

    storage redis {
            host pb-caddy-ssl-redis-cluster-0001-001.oc0tu2.0001.usw1.cache.amazonaws.com
            port 6379
            aes_key 22e64714-909b-44f4-a9b1-3b0de976e6f7
            module redis
            password ""
            db 0
            key_prefix caddytls
            value_prefix redis
            timeout 5
            tls_enabled false
            tls_insecure true
    }

    log {
            output file /logs/caddy-shared.log {
                    roll_size 20M
                    roll_keep 5
            }
    }
    on_demand_tls {
            ask http://api1.pb:9005/
            interval 1m
            burst 10
    }

}

bleem-api.peoplebrowser.com {
header Strict-Transport-Security “max-age=31536000”
encode zstd gzip

    tls {
            issuer zerossl mykey {
                    email contact@email.com
            }
    }

    reverse_proxy 172.31.43.231:1210

}

With the storage set to file_system - certificates are normally created in the /mnt directory.

/mnt/certificates/acme.zerossl.com-v2-dv90# ls -lha
total 12K
drwxr-xr-x 3 caddy caddy 4.0K Jul 13 20:45 .
drwxr-xr-x 4 caddy caddy 4.0K Jul 13 18:22 …
drwx------ 2 caddy caddy 4.0K Jul 13 20:45 bleem-api.peoplebrowser.com

My production Caddy servers get Caddy installed like this:

sudo apt update -y
sudo apt upgrade -y
sudo apt install -y debian-keyring debian-archive-keyring apt-transport-https
curl -1sLf ‘https://dl.cloudsmith.io/public/caddy/stable/gpg.key’ | sudo gpg --dearmor -o /usr/share/keyrings/caddy-stable-archive-keyring.gpg
curl -1sLf ‘https://dl.cloudsmith.io/public/caddy/stable/gpg.key’ | sudo gpg --dearmor -o /usr/share/keyrings/caddy-stable-archive-keyring.gpg
curl -1sLf ‘https://dl.cloudsmith.io/public/caddy/stable/debian.deb.txt’ | sudo tee /etc/apt/sources.list.d/caddy-stable.list
sudo apt update
sudo apt install caddy -y
sudo systemctl enable --now caddy

I have the exact structure, permissions and files in /mnt on my test machine which are in place on my working Caddy server.

ls -lha /mnt
total 28K
drwxr-xr-x 7 caddy caddy 4.0K Jul 13 18:44 .
drwxr-xr-x 21 root root 4.0K Jul 13 17:34 …
drwxr-xr-x 5 caddy caddy 4.0K Jul 13 18:21 acme
drwxr-xr-x 4 caddy caddy 4.0K Jul 13 18:22 certificates
drwxr-xr-x 2 caddy caddy 4.0K Jul 13 18:44 locks
drwxr-xr-x 2 caddy caddy 4.0K Jul 13 18:15 ocsp
drwxr-xr-x 3 caddy caddy 4.0K Jul 13 18:25 pki

The installation directions to include the redis module have Caddy running out of /usr/local/bin rather than /usr/bin but I get the same certificate retrieval error running it from either directory.

This is what happens in the log when I refresh the bleem-api site:

{“level”:“debug”,“ts”:1689280514.100683,“logger”:“events”,“msg”:“event”,“name”:“tls_get_certificate”,“id”:“2f85bfdc-4d2e-4cfc-b4fc-5583e1bf82b7”,“origin”:“tls”,“data”:{“client_hello”:{“CipherSuites”:[27242,4865,4866,4867,49195,49199,49196,49200,52393,52392,49171,49172,156,157,47,53],“ServerName”:“bleem-api.peoplebrowser.com”,“SupportedCurves”:[6682,29,23,24],“SupportedPoints”:“AA==”,“SignatureSchemes”:[1027,2052,1025,1283,2053,1281,2054,1537,513],“SupportedProtos”:[“h2”,“http/1.1”],“SupportedVersions”:[31354,772,771],“Conn”:{}}}}
{“level”:“debug”,“ts”:1689280514.1008513,“logger”:“tls.handshake”,“msg”:“no matching certificates and no custom selection logic”,“identifier”:“bleem-api.peoplebrowser.com”}
{“level”:“debug”,“ts”:1689280514.1008666,“logger”:“tls.handshake”,“msg”:“no matching certificates and no custom selection logic”,“identifier”:“.peoplebrowser.com"}
{“level”:“debug”,“ts”:1689280514.1008725,“logger”:“tls.handshake”,“msg”:“no matching certificates and no custom selection logic”,“identifier”:"
..com"}
{“level”:“debug”,“ts”:1689280514.1008773,“logger”:“tls.handshake”,“msg”:“no matching certificates and no custom selection logic”,“identifier”:"
..”}
{“level”:“debug”,“ts”:1689280514.1008835,“logger”:“tls.handshake”,“msg”:“all external certificate managers yielded no certificates and no errors”,“remote_ip”:“24.17.48.38”,“remote_port”:“40442”,“sni”:“bleem-api.peoplebrowser.com”}
{“level”:“debug”,“ts”:1689280514.100892,“logger”:“tls.handshake”,“msg”:“no certificate matching TLS ClientHello”,“remote_ip”:“24.17.48.38”,“remote_port”:“40442”,“server_name”:“bleem-api.peoplebrowser.com”,“remote”:“24.17.48.38:40442”,“identifier”:“bleem-api.peoplebrowser.com”,“cipher_suites”:[27242,4865,4866,4867,49195,49199,49196,49200,52393,52392,49171,49172,156,157,47,53],“cert_cache_fill”:0,“load_if_necessary”:true,“obtain_if_necessary”:true,“on_demand”:false}
{“level”:“debug”,“ts”:1689280514.1010666,“logger”:“http.stdlib”,“msg”:"http: TLS handshake error from 24.17.48.38:40442: no certificate available for 'bleem-api.peoplebrowser.com

journalctl -u caddy --no-pager | less +G

Jul 13 20:34:43 ip-172-31-32-91 caddy[58782]: {“level”:“info”,“ts”:1689280483.718665,“msg”:“using provided configuration”,“config_file”:“/etc/caddy/Caddyfile”,“config_adapter”:“”}
Jul 13 20:34:43 ip-172-31-32-91 systemd[1]: Reloaded Caddy.

I have no idea what’s missing and why certificates are not being generated with Redis enabled. Are there other logs that might indicate the root issue?

Thanks for your time!

John

Howdy!

I decided to try installing Redis locally and it bloody works!

I had to work through some weirdness with Elasticache Redis at AWS and eliminated some settings from the storage configuration.

My final Caddyfile is here. Hopefully it will help someone else in the future.

# Global Options
{
        debug
        admin 0.0.0.0:2019
        storage redis {
                address caddy-ssl-redis-cluster.ab2de3.clustercfg.usw1.cache.amazonaws.com:6379
                module redis
                key_prefix caddytls
                value_prefix redis
                timeout 5
                tls_enabled false
                tls_insecure true
        }

        log {
                output file /logs/caddy-shared.log {
                        roll_size 20M
                        roll_keep 5
                }
        }
        on_demand_tls {
                ask http://api1.pb:9005/
                interval 1m
                burst 10
        }
}

bleem-api.peoplebrowser.com {
        header Strict-Transport-Security "max-age=31536000"
        encode zstd gzip

        tls {
                issuer zerossl mykey {
                        email contact@contact.com
                }
        }

        reverse_proxy 172.31.43.231:1210
}

It seems so simple now…four days later. This was a learning experience for me and I’m grateful for the access to the Community.

Be well!

John

1 Like

Please use markdown code block formatting in your posts when sharing your config and logs. Your post is extremely difficult to read without it.

Use triple bacticks (```) on their own line before and after your config. Or click the </> button when writing a post.

Considering this was my very first post to the Community, I would have expected a kinder reply.

It’s a forum rule. See FAQ - Caddy Community

Your posts must be properly formatted. Use the formatting buttons if you don’t know Markdown. Improperly formatted posts are hard to read and will discourage helpers to the point where you might not get an answer at all.

No rudeness intended, but the same rules apply to everyone.

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