caddyserver/caddy · error
getting tls app: %v
Error message
getting tls app: %v
What it means
The http app's Provision first loads the tls app via ctx.App("tls"); if the tls app's own provisioning or validation fails (bad certificate config, invalid issuer, bad automation policy), the failure is wrapped as 'getting tls app'. The http app hard-depends on tls, so a broken TLS config breaks HTTP startup.
Source
Thrown at modules/caddyhttp/app.go:196
// CaddyModule returns the Caddy module information.
func (App) CaddyModule() caddy.ModuleInfo {
return caddy.ModuleInfo{
ID: "http",
New: func() caddy.Module { return new(App) },
}
}
// Provision sets up the app.
func (app *App) Provision(ctx caddy.Context) error {
// store some references
app.logger = ctx.Logger()
app.ctx = ctx
// provision TLS and events apps
tlsAppIface, err := ctx.App("tls")
if err != nil {
return fmt.Errorf("getting tls app: %v", err)
}
app.tlsApp = tlsAppIface.(*caddytls.TLS)
eventsAppIface, err := ctx.App("events")
if err != nil {
return fmt.Errorf("getting events app: %v", err)
}
repl := caddy.NewReplacer()
// this provisions the matchers for each route,
// and prepares auto HTTP->HTTPS redirects, and
// is required before we provision each server
err = app.automaticHTTPSPhase1(ctx, repl)
if err != nil {
return err
}
View on GitHub (pinned to 50e54ee279)
Solutions
- Ignore the wrapper and read the nested cause after the colon — fix the tls-side problem it names.
- Run 'caddy validate' on the full config to surface the tls error directly.
- Common fixes: correct cert/key paths, valid issuer module names, well-formed automation policies.
- Bisect by removing tls customization (fall back to automatic HTTPS defaults) and re-adding piecewise.
Example fix
// before (caddyfile) tls /etc/caddy/cert.pem /etc/caddy/key.pem # key.pem path wrong // after tls /etc/caddy/cert.pem /etc/caddy/cert.key
Defensive patterns
Strategy: try-catch
Validate before calling
// pre-flight: confirm cert/key files referenced by the tls app exist and parse
for _, pair := range certPairs(cfg) {
if err := checkPair(pair.Cert, pair.Key); err != nil {
return err // report before caddy load wraps it
}
} Try / catch
if err := caddy.Validate(cfg); err != nil {
if strings.Contains(err.Error(), "getting tls app") {
// root cause is the nested tls error — fix tls config, not http
}
return err
} Prevention
- Read past the wrapper to the nested cause before changing http settings.
- Keep certificate files under paths the service user can read.
- Use automatic HTTPS defaults until the rest of the config is proven, then add tls customization stepwise.
When it happens
Trigger: Any config where the tls app config is invalid: malformed automation policies, bad ACME issuer fields, unreadable certificate files via files loader, etc. — loaded indirectly while the http app provisions.
Common situations: TLS directives with wrong paths or PEM parse errors; issuer module typos; on-demand TLS misconfiguration; version changes to caddytls config schema. The error text says 'getting tls app' but the root cause is inside the tls app's config.
Understand the failure class
- SSL/TLS and certificate errors — how TLS handshakes and certificate validation fail.
Related errors
- getting events app: %v
- server listening on %v is HTTP, but attempts to configure TL
- problem calling http loader url: %v
- loading %s app module: %v
- server %s: %v
AI-assisted analysis of caddyserver/caddy@50e54ee279 (2026-08-15).
Data as JSON: /api/errors/d6106960e9f43948.
Report an issue: GitHub.