caddy-reverse-proxy
Skill1 starsChanged 3 months agoMITView on GitHub
Use when the user wants to expose a local service over HTTPS with a real domain, proxy multiple services through one server with TLS, get automatic certificate management without certbot or manual renewal, or says "set up a reverse proxy", "I need HTTPS for my service", or "proxy my Docker services".
- Installs packages
1 other project uses a version of this.
Adopted by
Most recently taken up by
- ddnetters/homelab-agent-skillstheir own version, first seen Mar 18, 2026
Other versions1 project uses a version of this.
Word for word · 0
None found.
Edited · 0
None found.
Wrote their own version · 1
- ddnetters/homelab-agent-skills★ 5same name
How matches are found. Word for word: the exact same text. Edited: shares passages with this file (“99% same” means 99% of its five-word phrases also appear here; 10% or more counts). Their own version: similar meaning, or, weakest, the same name. We can’t tell which project had it first. Projects are counted among the 200 most-starred candidates, and mentions are links to the repository we found, up to 50 per site, so both counts are a floor.
In this repository58 other files it gives its agents.
- AGENTS.mdAGENTS.md
- CLAUDE.mdCLAUDE.md
- api-test-suiteSkill
- ascii-artSkill
- changelog-generatorSkill
- color-palette-generatorSkill
- cron-taskSkill
- csv-toolkitSkill
- discord-bot-buildSkill
- docker-umbrellaSkill
- dotfiles-manageSkill
- email-sendSkill
- env-config-managerSkill
- excalidraw-diagramSkill
- file-organizerSkill
- forgejo-self-hostSkill
- frontend-design-toolkitSkill
- generate-dockerfileSkill
- gif-searchSkill
- git-backupSkill
- github-actions-ciSkill
- hallmark-readmeSkill
- http-api-testerSkill
- invoice-generatorSkill
- json-formatterSkill
- log-analyzerSkill
- markdown-linterSkill
- markdown-to-pdfSkill
- markdown-to-slidesSkill
- mcp-server-buildSkill
- media-id-mappingSkill
- movie-catalogue-siteSkill
- movie-night-calendarSkill
- ntfy-notifierSkill
- ocr-documentsSkill
- ollama-localSkill
- openapi-generatorSkill
- password-generatorSkill
- pdf-extractSkill
- portfolio-upkeepSkill
- qr-code-generatorSkill
- regex-testerSkill
- resume-builderSkill
- rss-monitorSkill
- searxng-self-hostSkill
- skill-publishSkill
- skill-registry-catalogSkill
- skills-portfolio-scaffoldSkill
- snippet-managerSkill
- sqlite-dashboardSkill
- streaming-provider-embedsSkill
- tailscale-deploySkill
- telegram-bot-buildSkill
- tmdb-metadataSkill
- uptime-kuma-self-hostSkill
- watchlist-syncSkill
- webhook-receiverSkill
- youtube-transcriptSkill
The file
We split this skill into the rules it gives an agent
3 rules. About 0 are common, 0 are distinctive, and 3 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈0
Distinctive · estimate
This author's own choices. Worth a look.
3
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Very specific: line 223
Use host.docker.internal in the Caddyfile to proxy to services running on the host (not in Docker).
- Very specific: line 230
Wrong host resolution in Docker: If Caddy runs in Docker and your backend runs on the host, use host.docker.internal (with extra_hosts in …
- Very specific: line 231
Restarting instead of reloading: Use caddy reload (or systemctl reload caddy) to apply config changes without dropping connections.
≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
caddy-reverse-proxy
Overview
Set up Caddy as a reverse proxy with automatic HTTPS. Caddy obtains and renews Let's Encrypt certificates automatically, handles HTTP-to-HTTPS redirects, and proxies requests to your backend services. No manual certificate management.
When to Use
- The user wants to expose a local service over HTTPS with a real domain.
- The user wants to proxy multiple services through one server with TLS.
- The user wants automatic certificate management (no certbot, no manual renewal).
- The user says "set up a reverse proxy", "I need HTTPS for my service", or "proxy my Docker services".
Prerequisites
- A server with a public IP address
- A domain name pointing to your server (A record)
- Ports 80 and 443 open
Installation
Linux
# Debian/Ubuntu (official repo)
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/debian.deb.txt' | sudo tee /etc/apt/sources.list.d/caddy-stable.list
sudo apt update
sudo apt install caddymacOS
brew install caddyDocker
docker run -d --name caddy \
-p 80:80 -p 443:443 \
-v caddy_data:/data \
-v caddy_config:/config \
-v $PWD/Caddyfile:/etc/caddy/Caddyfile \
caddy:latestCaddyfile Syntax
The Caddyfile is Caddy's configuration format. It's intentionally simple.
Single site
example.com {
reverse_proxy localhost:8080
}This one block does:
- Listens on ports 80 and 443 for
example.com - Obtains a Let's Encrypt certificate automatically
- Redirects HTTP to HTTPS
- Proxies all requests to
localhost:8080
Multiple sites
app.example.com {
reverse_proxy localhost:8080
}
api.example.com {
reverse_proxy localhost:3000
}
docs.example.com {
root * /var/www/docs
file_server
}Reverse proxy with header manipulation
api.example.com {
reverse_proxy localhost:3000 {
header_up Host {host}
header_up X-Real-IP {remote_host}
header_up X-Forwarded-For {remote_host}
header_up X-Forwarded-Proto {scheme}
}
}WebSocket support
Caddy supports WebSockets automatically — no special config needed:
chat.example.com {
reverse_proxy localhost:3000
}Static files + API
example.com {
# Serve static files
handle /assets/* {
root * /var/www/assets
file_server
}
# Proxy API requests
handle /api/* {
reverse_proxy localhost:3000
}
# Everything else → frontend
handle {
reverse_proxy localhost:5173
}
}Load balancing
api.example.com {
reverse_proxy localhost:3000 localhost:3001 localhost:3002 {
lb_policy round_robin
health_uri /health
health_interval 10s
}
}Automatic HTTPS
Caddy handles certificates automatically:
| Feature | How it works |
| Certificate issuance | Caddy obtains certificates from Let's Encrypt on first request |
| Renewal | Caddy renews certificates 30 days before expiry |
| HTTP→HTTPS redirect | Automatic for all sites with a domain name |
| On-demand TLS | Optional — issue certificates on first request for any domain |
On-demand TLS (for wildcard/multi-tenant setups):
{
on_demand_tls {
ask https://api.example.com/check-domain
}
}
https:// {
tls {
on_demand
}
reverse_proxy localhost:8080
}Caddy will ask your API endpoint whether a domain is allowed before issuing a certificate.
Running Caddy
As a system service (Linux)
sudo systemctl enable caddy
sudo systemctl start caddy
sudo systemctl status caddy
# Reload config without downtime
sudo systemctl reload caddy
# View logs
sudo journalctl -u caddy -fWith Docker Compose
version: "3"
services:
caddy:
image: caddy:latest
restart: unless-stopped
ports:
- "80:80"
- "443:443"
volumes:
- caddy_data:/data
- caddy_config:/config
- ./Caddyfile:/etc/caddy/Caddyfile
extra_hosts:
- "host.docker.internal:host-gateway"
volumes:
caddy_data:
caddy_config:Use host.docker.internal in the Caddyfile to proxy to services running on the host (not in Docker).
Common Pitfalls
- No domain name. Caddy's automatic HTTPS requires a domain name pointing to your server. Without a domain, Caddy can't obtain certificates. For local-only HTTPS, use Caddy's internal CA:
localhost:8080 { reverse_proxy localhost:3000 }(generates a self-signed cert). - Ports 80/443 not open. Let's Encrypt uses the HTTP-01 challenge, which requires port 80 to be reachable. If your firewall blocks port 80, certificate issuance fails.
- Hitting Let's Encrypt rate limits. Let's Encrypt allows 50 certificates per domain per week. Don't repeatedly restart Caddy with new domains in testing — you'll hit the limit and have to wait it out.
- Wrong host resolution in Docker. If Caddy runs in Docker and your backend runs on the host, use
host.docker.internal(withextra_hostsin compose). If both are in Docker, put them on the same network and use the container name instead. - Restarting instead of reloading. Use
caddy reload(orsystemctl reload caddy) to apply config changes without dropping connections.caddy stop+caddy startdrops active connections. - Large uploads silently rejected. Caddy has a default body size limit. For large file uploads, set
request_body { max_size 100MB }in the site block.
Verification Checklist
curl -I https://<domain>returns a valid certificate (no-kneeded) and the expected backend response- HTTP requests to the same domain redirect to HTTPS (
curl -I http://<domain>shows a 301/308) caddy validate --config Caddyfile(ordocker exec caddy caddy validate) passes before reload- Config changes were applied with
caddy reload, not a hard restart, if connections needed to stay up - WebSocket-dependent backends were tested with an actual upgrade request, not just a plain GET
- Domain's A record resolves to the server's public IP before expecting certificate issuance to succeed
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

