Documentation Index Fetch the complete documentation index at: https://mintlify.com/caddyserver/caddy/llms.txt
Use this file to discover all available pages before exploring further.
xcaddy is the official build tool for Caddy that simplifies building custom binaries with plugins and proper version information.
What is xcaddy?
From README.md:145, xcaddy is our builder tool that automates the build process.
It handles:
Creating proper project structure
Managing Go modules
Injecting version information
Adding custom plugins
Cross-compilation
Installation
Install xcaddy using Go:
go install github.com/caddyserver/xcaddy/cmd/xcaddy@latest
Verify installation:
Ensure $GOPATH/bin is in your PATH to run xcaddy from anywhere.
Basic Usage
Build Standard Caddy
From README.md:148:
This creates a caddy binary in the current directory with:
Proper version information
All standard modules
Platform-specific optimizations
Build Specific Version
Or use a commit hash:
xcaddy build abc123def456
Or a branch:
Building with Plugins
Add a Plugin from GitHub
xcaddy build \
--with github.com/caddyserver/nginx-adapter
Add Multiple Plugins
xcaddy build \
--with github.com/caddyserver/nginx-adapter \
--with github.com/greenpau/caddy-security
Specify Plugin Version
xcaddy build \
--with github.com/caddyserver/nginx-adapter@v0.2.0
Local Plugin Development
For local plugin development, use a local path:
xcaddy build \
--with github.com/example/caddy-plugin=../caddy-plugin
The local path is relative to where you run xcaddy. Use absolute paths to avoid confusion.
Output Control
Specify Output Path
xcaddy build --output /usr/local/bin/caddy
# Linux AMD64
GOOS = linux GOARCH = amd64 xcaddy build
# Windows AMD64
GOOS = windows GOARCH = amd64 xcaddy build --output caddy.exe
# macOS ARM64 (Apple Silicon)
GOOS = darwin GOARCH = arm64 xcaddy build
# Linux ARM (Raspberry Pi)
GOOS = linux GOARCH = arm GOARM = 7 xcaddy build
What xcaddy Automates
From README.md:151, xcaddy performs these steps automatically:
Copy main.go
Copies Caddy’s main.go and adds plugin imports: import (
_ " time/tzdata "
caddycmd " github.com/caddyserver/caddy/v2/cmd "
_ " github.com/caddyserver/caddy/v2/modules/standard "
// Plugins added by xcaddy
_ " github.com/example/plugin "
)
Pin Caddy version
go get github.com/caddyserver/caddy/v2@version
Add plugin dependencies
go get github.com/example/plugin@version
Build with proper flags
go build -tags=nobadger,nomysql,nopgx
Advanced Options
Replace Modules
Replace a dependency with a fork:
xcaddy build \
--with github.com/caddyserver/caddy/v2=github.com/myuser/caddy/v2@mybranch
Build with Specific Go Version
go1.25.0 install github.com/caddyserver/xcaddy/cmd/xcaddy@latest
go1.25.0 run github.com/caddyserver/xcaddy/cmd/xcaddy build
Disable Module Optimization
By default, xcaddy trims unused dependencies:
xcaddy build --with-trimpath=false
Development Workflow
Quick Iteration
For rapid plugin development:
# Build with local plugin
xcaddy build \
--with github.com/myuser/caddy-plugin=./caddy-plugin
# Test
./caddy run --config test.Caddyfile
# Make changes to plugin...
# Rebuild
xcaddy build \
--with github.com/myuser/caddy-plugin=./caddy-plugin
Using xcaddy run
Test without building:
xcaddy run \
--with github.com/myuser/caddy-plugin=./caddy-plugin \
--config Caddyfile
This builds a temporary binary and runs it immediately.
Build Caching
xcaddy leverages Go’s build cache. Subsequent builds are faster:
# First build (slow)
xcaddy build --with github.com/example/plugin
# Subsequent builds (fast, if plugin unchanged)
xcaddy build --with github.com/example/plugin
Clear the cache if needed:
Environment Variables
Proxy Configuration
export GOPROXY = https :// proxy . golang . org , direct
xcaddy build
Private Repositories
export GOPRIVATE = github . com / myorg / *
xcaddy build --with github.com/myorg/private-plugin
Custom Build Flags
export XCADDY_GO_BUILD_FLAGS = "-ldflags='-s -w' -trimpath"
xcaddy build
Common Plugin Examples
Nginx Config Adapter
Convert Nginx configs to Caddy:
xcaddy build \
--with github.com/caddyserver/nginx-adapter
./caddy adapt --config nginx.conf --adapter nginx
CloudFlare DNS Provider
For DNS-01 ACME challenges:
xcaddy build \
--with github.com/caddy-dns/cloudflare
Rate Limiting
xcaddy build \
--with github.com/mholt/caddy-ratelimit
Multiple Plugins Together
xcaddy build \
--with github.com/caddyserver/nginx-adapter \
--with github.com/caddy-dns/cloudflare \
--with github.com/greenpau/caddy-security \
--with github.com/mholt/caddy-ratelimit
Verification
After building, verify your binary includes plugins:
# List all modules
./caddy list-modules
# Check for specific module
./caddy list-modules | grep plugin_name
# Verify version
./caddy version
Troubleshooting
Module Not Found
Ensure the plugin path is correct and accessible:
# Check if module exists
go get -d github.com/example/plugin
# Then build
xcaddy build --with github.com/example/plugin
Version Conflicts
Specify exact versions:
xcaddy build v2.8.0 \
--with github.com/example/plugin@v1.2.3
Permission Denied
On Linux, set capabilities:
sudo setcap cap_net_bind_service=+ep ./caddy
Build Fails with Local Plugin
Ensure your plugin has a go.mod file:
cd caddy-plugin
go mod init github.com/myuser/caddy-plugin
go mod tidy
GOPROXY Timeout
Use direct mode:
GOPROXY = direct xcaddy build \
--with github.com/example/plugin
Comparison with Manual Build
xcaddy (recommended)
Manual Process
xcaddy build \
--with github.com/example/plugin
xcaddy is:
✅ Faster and less error-prone
✅ Handles version information correctly
✅ Manages all dependencies automatically
✅ Supports quick iteration with local plugins
Next Steps
Custom Builds Create production-ready custom builds
Plugin Tutorial Develop your own plugin
Building from Source Manual build process details
Module Development Deep dive into module creation