ory/hydra · error
can not serve request over insecure http
Error message
can not serve request over insecure http
What it means
The TLS termination middleware rejects requests that arrive over plain HTTP when no trusted termination networks are configured. Because TLS termination is not enabled, the proxy cannot verify that the connection was secured upstream, so it responds 502 Bad Gateway with this message and logs 'TLS termination is not enabled'.
Source
Thrown at oryx/tlsx/termination.go:50
_, network, err := net.ParseCIDR(rn)
if err != nil {
return nil, errors.WithStack(err)
}
networks = append(networks, network)
}
return negroni.HandlerFunc(func(rw http.ResponseWriter, r *http.Request, next http.HandlerFunc) {
if r.TLS != nil ||
r.URL.Path == healthx.AliveCheckPath ||
r.URL.Path == healthx.ReadyCheckPath ||
r.URL.Path == prometheusx.MetricsPrometheusPath {
next(rw, r)
return
}
if len(networks) == 0 {
d.Logger().WithRequest(r).WithError(errors.New("TLS termination is not enabled")).Error("Could not serve http connection")
d.Writer().WriteErrorCode(rw, r, http.StatusBadGateway, errors.New("can not serve request over insecure http"))
return
}
if err := matchesRange(r, networks); err != nil {
d.Logger().WithRequest(r).WithError(err).Warnln("Could not serve http connection")
d.Writer().WriteErrorCode(rw, r, http.StatusBadGateway, errors.New("can not serve request over insecure http"))
return
}
proto := r.Header.Get("X-Forwarded-Proto")
if proto == "" {
d.Logger().WithRequest(r).WithError(errors.New("X-Forwarded-Proto header is missing")).Error("Could not serve http connection")
d.Writer().WriteErrorCode(rw, r, http.StatusBadGateway, errors.New("can not serve request over insecure http"))
return
} else if proto != "https" {
d.Logger().WithRequest(r).WithError(errors.New("X-Forwarded-Proto header is missing")).Error("Could not serve http connection")
d.Writer().WriteErrorCode(rw, r, http.StatusBadGateway, errors.Errorf("expected X-Forwarded-Proto header to be https but got: %s", proto))
returnView on GitHub (pinned to 4174065ffb)
Solutions
- Configure the trusted TLS-termination proxy networks (CIDR ranges) so the middleware accepts forwarded connections
- If TLS termination is not used, serve over HTTPS directly or skip installing the termination middleware
- Ensure the proxy's source IP actually falls within the configured networks
- For local development, run with HTTPS or disable the middleware
Example fix
// before
// termination middleware enabled, no networks configured -> 502
// after
err := d.TerminationMiddleware([]string{"10.0.0.0/8"})(next).ServeHTTP(rw, r) // trust internal LB range Defensive patterns
Strategy: try-catch
Validate before calling
if !tlsTerminationEnabled && requestIsHTTP {
// do not install the termination middleware, or configure networks first
} Type guard
func isTerminationRejection(status int) bool {
return status == http.StatusBadGateway // middleware responds 502 with "can not serve request over insecure http"
} Try / catch
// client side
resp, err := http.Get(url)
if err == nil && resp.StatusCode == http.StatusBadGateway {
body, _ := io.ReadAll(resp.Body)
if strings.Contains(string(body), "insecure http") {
// switch to HTTPS or route via the trusted TLS-terminating proxy
}
} Prevention
- When deploying behind a TLS-terminating LB, always configure the trusted proxy CIDR networks
- For local dev, run HTTPS or skip the termination middleware
- Monitor for 502 responses with this message as a signal of missing termination config
When it happens
Trigger: An HTTP request reaches the middleware while the terminator allowlist is empty (len(networks) == 0) — i.e. the middleware was installed but no trusted CIDR ranges for TLS-terminating proxies were configured.
Common situations: Deploying behind a load balancer (AWS ELB, Cloudflare, nginx) that terminates TLS but forgetting to configure the proxy's IP ranges; running the service on http:// during local development while the middleware is enabled; misread environment/config causing the networks list to load empty.
Related errors
- %s content encoding not supported
- expected X-Forwarded-Proto header to be https but got: %s
- http(s) loader disabled
- no tls configuration was found
- tls configuration is invalid
AI-assisted analysis of ory/hydra@4174065ffb (2026-09-03).
Data as JSON: /api/errors/07fb87996b8db89d.
Report an issue: GitHub.