Caddy is a fast, multi-platform web server with automatic HTTPS.
https://github.com/caddyserver/caddy| Installer Source| Releases (json) (tab)
Caddy is a fast, multi-platform web server with automatic HTTPS.
https://github.com/caddyserver/caddy| Installer Source| Releases (json) (tab)
To update or switch versions, run webi caddy@stable
(or @v2.4
, @beta
,
etc).
Caddy makes it easy to use Let's Encrypt to handle HTTPS (TLS/SSL) and to reverse proxy APIs and WebSockets to other apps - such as those written node, Go, python, ruby, and PHP.
Here's the things we find most useful:
caddy file-server --browse --listen :4040
Caddy can be used to test with https on localhost.
Caddyfile
:
localhost {
handle /api/* {
reverse_proxy localhost:3000
}
handle /* {
root * ./public/
file_server
}
}
caddyfile run --config ./Caddyfile
Here's what a fairly basic Caddyfile
looks like:
Caddyfile
:
# redirect www to bare domain
www.example.com {
redir https://example.com{uri} permanent
}
example.com {
###########
# Logging #
###########
# log to stdout, which is captured by journalctl
log {
output stdout
format console
}
###############
# Compression #
###############
# turn on standard streaming compression
encode gzip zstd
####################
# Reverse Proxying #
####################
# reverse proxy /api to :3000
handle /api/* {
reverse_proxy localhost:3000
}
# reverse proxy some "well known" APIs
handle /.well-known/openid-configuration {
reverse_proxy localhost:3000
}
handle /.well-known/jwks.json {
reverse_proxy localhost:3000
}
##################
# Path Rewriting #
##################
# reverse proxy and rewrite path /api/oldpath/* => /api/newpath/*
handle_path /api/oldpath/* {
rewrite * /api/newpath{path}
reverse_proxy localhost:3000
}
###############
# File Server #
###############
# serve static files
handle /* {
root * /srv/example.com/public/
file_server
}
}
caddyfile run --config ./Caddyfile
example.com {
# ...
# reverse proxy /api/new/ to http://localhost:3100/api/
handle_path /api/new/* {
rewrite * /api{path}
reverse_proxy localhost:3100
}
}
caddy run --config ./Caddyfile
Note: run
runs in the foreground, start
starts a service (daemon) in the
background.
Here are the 3 things you need to do to start Caddy as a system service:
a non-root user
If you don't have a non-root user, consider adding the app
user with
ssh-adduser
.
Using a user named app
to run your services is common industry convention.
port-binding privileges
You can use setcap
to allow Caddy to use privileged ports.
sudo setcap cap_net_bind_service=+ep $(readlink -f $(command -v caddy))
systemd config
You can use serviceman
to create and
start the appropriate systemd launcher for Linux.
Install Serviceman with Webi:
webi serviceman
Use Serviceman to create a systemd config file.
sudo env PATH="$PATH" \
serviceman add --system --username $(whoami) --name caddy -- \
caddy run --config ./Caddyfile
This will create /etc/systemd/system/caddy.service
, which can be managed with
systemctl
. For example:
sudo systemctl restart caddy
Port-Binding Permission
Caddy must run as the root
user in order to bind to ports 80 and 443.
launchd plist
You can use serviceman
to create and
start the appropriate service launcher file for MacOS.
Install Serviceman with Webi:
webi serviceman
Use Serviceman to create a launchd plist file.
serviceman add --username $(whoami) --name caddy -- \
caddy run --config ./Caddyfile
This will create ~//Library/LaunchAgents/caddy.plist
, which can be managed
with launchctl
. For example:
launchctl unload -w "$HOME/Library/LaunchAgents/caddy.plist"
launchctl load -w "$HOME/Library/LaunchAgents/caddy.plist"
You may need to update the Windows Firewall to allow traffic through to Caddy. You'll also need to create a Startup entry in the registry, which can be done with Serviceman.
Windows Firewall
You can use PowerShell to update the firewall, which looks something like this:
powershell.exe -WindowStyle Hidden -Command $r = Get-NetFirewallRule -DisplayName 'Caddy Web Server' 2> $null; if ($r) {write-host 'found rule';} else {New-NetFirewallRule -DisplayName 'Go Web Server' -Direction Inbound C:\\Users\\YOUR_USER\\.local\\bin\\caddy.exe -Action Allow}
Startup Registry
You can use Serviceman to create and start the appropriate service launcher for Windows.
Install Serviceman with Webi:
webi.bat serviceman
Use Serviceman to create a Startup entry in the Windows Registry:
serviceman.exe add --name caddy -- \
caddy run --config ./Caddyfile
You can manage the service directly with Serviceman. For example:
serviceman stop caddy
serviceman start caddy