Public names are proxied CNAMEs to the Cloudflare Tunnel since PR #156 and work from the LAN, so they should resolve publicly there too. Replace the address=/${BASE_DOMAIN}/ wildcard with explicit entries: the LAN-only names (derived from every controller:none HTTPRoute), gitea/nextcloud (off Cloudflare's 100 MB / 100 s limits), keycloak/auth, and the L4 VIPs. Add L0 check pihole-lan-names, mutation-tested. Correct docs that still described public names as CNAME to wan. and the cloudflared entrypoint comment. Co-Authored-By: Claude Opus 5.5 <[email protected]>
2.0 KiB
2.0 KiB
platform/cloudflared
Cloudflare Tunnel connector: inbound HTTPS from the Cloudflare edge to the shared Gateway, outbound-only from the cluster (no router port forward, no hairpin, no split-DNS dependency).
- Flux tier:
clusters/base/cloudflared.yaml— its own Kustomization,dependsOn: [platform-config],wait: false, and nothing depends on it. A missing or invalid credential can affect only the tunnel. - Runbook (enrolment, canary, alerts, rollback):
runbooks/cloudflare-tunnel.md - Design record:
decisions/2026-11-08-cloudflare-tunnel.md - Guard:
conformance/tests/l0-static/cloudflared-ingress-rules
| File | What it is |
|---|---|
config.yaml |
The locally-managed tunnel: literal tunnel UUID + ingress rules. LAN/VPN-only hosts → 404, apex + wildcard → https://cilium-gateway-shared.gateway.svc.cluster.local:443 with matchSNItoHost, catch-all 404. Never the Kubernetes API. |
cloudflared-credentials.sops.yaml |
SOPS-encrypted tunnel credentials JSON. Ships with REPLACE-ME; the operator fills it. |
deployment.yaml |
2 replicas, hard spread across nodes, non-root, read-only root fs, pinned digest; PDB minAvailable: 1. |
networkpolicy.yaml |
default-deny (single owner — not an app namespace) + Prometheus scrape allow + egress CNP: world 7844 tcp/udp and 443, the Gateway (ingress entity), and Gateway backends by gateway-access=shared minus the LAN-only namespaces. |
servicemonitor.yaml, alerts.yaml |
Headless metrics Service + ServiceMonitor scraping :2000, and the two alerts, both written to fire (not go quiet) when their series vanish. |
Cloudflare sends a hostname through the tunnel only when its DNS record is a proxied CNAME to
<UUID>.cfargotunnel.com; nothing in this directory creates one. Those records are published by
external-dns from the shared Gateway's target annotation (Phase 2, PR #156; see
platform/externaldns/README.md). LAN resolution: catalog/pihole.yaml (explicit names only since
2026-11-09), so public names reach Cloudflare from the LAN too.