Files
home-network-k3s/docs/09-dns-and-ingress.md
T
jakman85andClaude Opus 4.8 cde2f2330c Resolve OQ-4: scoped Cloudflare API token for DNS-01 + ExternalDNS
Operator chose Option A. cert-manager solves ACME DNS-01 and ExternalDNS
manages *.home.keithjackson.dev records via a scoped Cloudflare token
(Zone.DNS.Edit, keithjackson.dev), stored SOPS-encrypted. Operator provides
the token once (new prereq T-2.4p); T-2.4/T-2.5 unblocked. Only OQ-BKP
(off-cluster DR backup target, Phase 4) remains open.

Updated: docs 00,08,09; task board.

Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
2026-08-15 23:02:59 -05:00

4.9 KiB

09 — DNS & Ingress

Serves: R-DNS-01/02/03, R-C2-01, works with R-TLS-*. Related: ADR-0002 (Cilium/Gateway API).

Naming model

  • All services live at <service>.home.keithjackson.dev (e.g. plex.home.keithjackson.dev).
  • The root home.keithjackson.dev serves the Command & Control UI (12).
  • Public apex *.keithjackson.dev resolves to the network's public IP; *.home.keithjackson.dev is the platform's zone.

DNS automation (R-DNS-02)

  • ExternalDNS watches Gateway/HTTPRoute (and Service) resources and manages records in the authoritative DNS provider (Cloudflare, per OQ-4) automatically — a new service's DNS appears from its declared intent, no manual record editing.
  • Records for *.home.keithjackson.dev are created/updated/removed as services come and go.

Split-horizon resolution (R-DNS-03)

Internal and external answers differ:

  • External (*.home.keithjackson.dev from the internet): resolves to the public IP; reaches the edge router, which forwards public-class services to the in-cluster Gateway.
  • Internal (LAN clients): resolves <service>.home.keithjackson.dev to the internal Gateway address directly, avoiding hairpinning through the public IP.
  • PiHole (itself an onboarded service) provides internal LAN DNS and the split-horizon answers for .home.keithjackson.dev; the trusted Let's Encrypt cert is served either way (08).

DNS is thus both a platform capability and a hosted service. Bootstrapping order matters: the platform needs working DNS before PiHole is fully managed — handled by the bring-up sequence in roadmap/phases.md.

Ingress (north-south) via Gateway API

  • Gateway API implemented by Cilium is the ingress layer (no separate ingress controller; reuses the CNI, ADR-0002).
  • A shared Gateway defines HTTPS listeners on *.home.keithjackson.dev terminating TLS with the cert-manager cert (08).
  • Each service contributes an HTTPRoute mapping its hostname to its Service — rendered from the ServiceDefinition, not hand-authored.
  • Exposure class is declared per service:
    • internal — reachable only on the LAN (no edge port-forward; internal DNS only).
    • public — additionally reachable from the internet via the edge router forwarding 80/443 to the Gateway.

Edge integration (single SOHO router — OQ-1 resolved)

  • The environment has one SOHO edge router: no VLANs, no VPN, no services, no API/IaC. Its only ingress job is manual port-forwarding of 80/443 (and specific service ports, e.g. Plex 32400, Minecraft 25565) to the Gateway VIP for public services. This is a documented manual edge step (the SOHO device has no automation) — the analogue of the old pfSense manual-config exception. Confirm the router can port-forward (basic NAT; almost all can).
  • No multi-WAN inbound rules — single WAN (03).
  • internal services are never port-forwarded; they rely on internal DNS + Gateway on the LAN.
  • Ingress VIP mechanism — resolved: Cilium L2 announcement (ARP/NDP) on the flat LAN. BGP is not available on a SOHO router, and a single flat subnet makes L2 announcement the natural choice.

DNS record depth (note for *.home.keithjackson.dev)

A wildcard *.keithjackson.dev matches only one label deep — it covers home.keithjackson.dev but not plex.home.keithjackson.dev. Consequences:

  • internal services need no public record — PiHole resolves <svc>.home.keithjackson.dev to the internal Gateway VIP (split-horizon). This is the majority of services.
  • public services need a public record for <svc>.home.keithjackson.dev. Per OQ-4 (resolved), ExternalDNS manages these automatically via the scoped Cloudflare API token — no manual record editing (see 08).

Interaction with default-deny

Ingress opens north-south paths to the specific service; it does not relax east-west default-deny (03). A service being publicly reachable does not let other in-cluster services reach it unless an explicit allow rule exists.

Acceptance gates

  • A new service's <service>.home.keithjackson.dev record appears automatically and routes to it.
  • internal services are unreachable from the public internet; public services are reachable and TLS-valid.
  • Internal clients resolve to the internal Gateway (no public hairpin) and get a trusted cert.
  • The root home.keithjackson.dev serves the C2 UI.

Resolved

  • OQ-1 — single SOHO edge (manual port-forward only); ingress VIP via Cilium L2 announcement.
  • OQ-4 — scoped Cloudflare API token drives ExternalDNS (records) and cert-manager DNS-01 (certs) automatically; see 08.