Automated community build of Caddy v2 based on DHI Hardened Images. Includes essential modules for DNS validation, Geo-blocking and CrowdSec integration.
Not affiliated with the official Caddy or DHI projects.
Builds automatically on the 1st of every month to pull the latest upstream Caddy version and Go dependencies.
This image is based on DHI (Docker Hardened Images), offering significantly higher security compared to standard Docker images.
- Non-Root by Default: Runs as user
65532, preventing potential container breakout attacks from gaining root access to your host. - Minimal Attack Surface: Based on a "distroless-like" environment. No shell (
sh,bash), no package managers (apt,apk), and no unnecessary binaries. Even if an attacker compromises Caddy, they have no tools to expand their foothold. - Software Bill of Materials (SBOM): DHI images are strictly monitored for vulnerabilities and dependencies.
- Production Ready: Designed for environments where security compliance and stability are critical.
Instead of relying on xcaddy, the Dockerfile uses go mod edit -replace to force a few libraries to patched versions when possible.
To keep the image reasonably safe, I build the image locally, scan it with trivy and other tools, then update the Dockerfile on the repo. I override a few Go dependencies that were pulling older vulnerable versions via transitive deps.
This repository runs automated vulnerability scans using Trivy via GitHub Actions. You can always check the latest public reports and verify the security posture by visiting the Security -> Code scanning alerts tab of this repository.
Don't trust, verify! If you want to run a security scan locally on your own machine before deploying the container, you can use any standard OCI vulnerability scanner.
Using Trivy:
trivy -v /var/run/docker.sock:/var/run/docker.sock aquasec/trivy image ghcr.io/olife97/dhi-caddy-cloudflare:latest| Module | Description | Link |
|---|---|---|
| Cloudflare DNS | DNS-01 challenge support for TLS (essential for wildcard certs or internal services). | Repo |
| Dynamic DNS | Automatic DNS A record updater. | Repo |
| MaxMind GeoIP | Filter traffic by country (e.g., block CN, RU, etc.). | Repo |
| CrowdSec Bouncer | Block malicious IPs using CrowdSec's collaborative threat intelligence. | Repo |
Base image documentation: DHI Caddy Guides
Note: Since this is based on DHI hardened images, it runs as non-root user 65532. You cannot bind to ports < 1024 inside the container. Map external 80/443 to internal 8080/8443.
It is highly recommended to use an .env file for your Cloudflare API token instead of hardcoding it in the compose file.
If you need to write to volumes or use UNRAID with bind, ensure permissions are set for uid 65532
services:
caddy:
image: ghcr.io/olife97/dhi-caddy-cloudflare:latest
container_name: caddy
restart: unless-stopped
security_opt:
- no-new-privileges:true
cap_drop:
- ALL
ports:
- "80:8080"
- "443:8443"
- "443:8443/udp" # HTTP/3
environment:
# Always pass the variables from your .env file
- CLOUDFLARE_API_TOKEN=${CLOUDFLARE_API_TOKEN}
- CROWDSEC_API_KEY=${CROWDSEC_API_KEY} # If using CrowdSec - Requires a running CrowdSec agent (in another container or on host).
volumes:
- ./Caddyfile:/etc/caddy/Caddyfile:ro
- ./data:/data
- ./config:/config
- ./GeoLite2-Country.mmdb:/config/GeoLite2-Country.mmdb:ro # path for MaxMind GeoLite2.mmdb fileThis project builds upon the work of several open-source projects.
- Caddy: Licensed under Apache 2.0.
- Docker Hardened Images (DHI): Base images provided by Docker, Inc. under Apache 2.0.
- caddy-dns/cloudflare: Licensed under Apache 2.0.
- mholt/caddy-dynamicdns: Licensed under Apache 2.0.
- porech/caddy-maxmind-geolocation: Licensed under Apache 2.0.
- hslatman/caddy-crowdsec-bouncer: Licensed under Apache 2.0.
This repository itself is licensed under the Apache 2.0 License.
Note on MaxMind GeoIP: This product includes GeoLite2 data created by MaxMind, available from https://www.maxmind.com. If you use the GeoIP module, you must comply with the MaxMind End User License Agreement (EULA).