lucaslorentz / caddy-docker-proxy

Caddy as a reverse proxy for Docker
MIT License
2.86k stars 168 forks source link

Use the same wildcard certificate for multiple sub domains #581

Closed mrkhdev closed 8 months ago

mrkhdev commented 8 months ago

I've built my caddy-proxy container, including caddy docker proxy (and namecheap dns module) myself, using the caddy-builder.

Below is my initial Caddyfile - as you see I requeest a wild card certificate for my domain.

{env.NAMECHEAP_WILDCARD_DOMAIN}:443 {
    file_server
    tls {
        dns namecheap {
            api_key {env.NAMECHEAP_API_KEY}
            user {env.NAMECHEAP_API_USER}
            api_endpoint {env.NAMECHEAP_API_ENDPOINT}
            client_ip {env.PUBLIC_IP}
        }
    }
}

I want to use this wild card certificate too for my sub domains as well. How can I configure this, using the label system of caddy proxy? I don't want to change the Caddyfile every time I spin up a new app.

I stumbled upon this link: https://caddy.community/t/utilizing-wildcard-certificate-for-subdomains/9319, which says that you should put the sub domain info inside the site block. Is it possible that I can this with labels?

francislavoie commented 8 months ago

Yes it's possible. Essentially you want this pattern https://caddyserver.com/docs/caddyfile/patterns#wildcard-certificates

caddy=*.example.com
caddy.1_@foo = host foo.example.com
caddy.1_handle = @foo
caddy.1_handle.reverse_proxy = {{ upstreams 8080 }}

Add something like this to each container.

mrkhdev commented 8 months ago

I've had my compose file as follows:

      caddy: "*.example.com"
      caddy.1_@foo: "host whoami.example.com"
      caddy.1_handle: "@foo"
      caddy.1_handle.reverse_proxy: "{{upstreams 80}}"

In the docker container with caddy running the following files: /etc/Caddyfile

{env.NAMECHEAP_WILDCARD_DOMAIN}:443 {
    file_server
    tls {
        dns namecheap {
            api_key {env.NAMECHEAP_API_KEY}
            user {env.NAMECHEAP_API_USER}
            api_endpoint {env.NAMECHEAP_API_ENDPOINT}
            client_ip {env.PUBLIC_IP}
        }
    }
}

/data/caddy/Caddyfile.autosave

*.example.com {
        @foo host whoami.example.com
        handle @foo {
                reverse_proxy 172.18.0.3:80
        }
}

But I'm getting the following error in de Caddy log:

{"level":"error","ts":1707021034.4923482,"logger":"tls.obtain","msg":"could not get certificate from issuer","identifier":"*.example.com","issuer":"acme-v02.api.letsencrypt.org-directory","error":"[*.example.com] solving challenges: *.example.com: no solvers available for remaining challenges (configured=[http-01 tls-alpn-01] offered=[dns-01] remaining=[dns-01]) (order=https://acme-v02.api.letsencrypt.org/acme/order/1552483107/241717342837) (ca=https://acme-v02.api.letsencrypt.org/directory)"}

It seems like caddy proxy merges those two? Or am I doing something wrong?

francislavoie commented 8 months ago

I don't think your first config is being loaded in. If it was, it would be visible in your Caddyfile.autosave. Please follow the instructions in the README for loading an initial Caddyfile.

You need to make sure the site addresses match for merging to happen. This means you shouldn't use env vars for the site address, or always use env vars, no mixing is possible because merging happens before env vars are replaced.

mrkhdev commented 8 months ago

Thank you for your comment! I didn't realize that is was possible to set global options in the labels of the docker compose of the caddy container itself.