Ingress & TLS
Denia is its own L7 ingress and ACME client. There is no separate Traefik, nginx, or certbot — the proxy runs in-process on a dedicated thread. See ADR-020 (which supersedes the earlier managed-Traefik ADR-016), plus ADR-032 and ADR-035.
In-process Pingora proxy
- An embedded Pingora (0.8, boringssl) proxy binds
:80and:443(ports configurable viaDENIA_HTTP_PORT/DENIA_HTTPS_PORT). - On each request it resolves the
Hostheader to aservice_id, then dials one of that service's replicas directly over its Unix socket (HttpPeerover UDS) — there is no loopback bridge port. - Routing state (
IngressState: the route table + replica pools) is held in anArcSwapfor lock-free reads; deploys and autoscale events swap a new table in atomically. - The ingress also records the per-request access log.
- HTTP/2 is hardened per ADR-032.
In-process ACME / TLS
- TLS certificates are issued and renewed in-process via
instant-acmeusing the HTTP-01 challenge — no certbot, no sidecar. - Certificates are served per-SNI and persisted
0600underDENIA_TLS_DIR; a background scan renews them before expiry, and certs are boot-loaded before:443accepts connections. - ACME is gated to services with
tls_enabledand verified domains. SetDENIA_ACME_EMAIL, and use the Let's Encrypt stagingDENIA_ACME_DIRECTORY_URLwhile testing.
Domain verification gate
Only verified domains enter the route table. Verification serves a token at
GET /.well-known/denia-challenge/{token} that is returned only when the request
Host matches — proving DNS points here before any cert is requested
(ADR-013). Every hostname passes validate_domain before
becoming a route, SNI, or ACME identifier.
Control-plane domain
The management API can be served on the same ingress under
DENIA_CONTROL_DOMAIN (+ DENIA_CONTROL_TLS); a workload service may not claim
that hostname (ADR-035). See the
Custom domains & TLS guide.