Egress Gateway for SPF Compliance¶
The Problem: Dynamic Source IPs Break SPF¶
When Mailu pods send outbound email, Kubernetes uses the node’s IP address where the pod is running as the source IP. In a multi-node cluster, this means:
Email from
postfix-abc123pod on node A uses IP168.119.62.98Email from
postfix-def456pod on node B uses IP49.13.2.15Recipients see emails from different IPs for the same domain
Why This Breaks Email Delivery¶
SPF (Sender Policy Framework) is a DNS record that tells receiving mail servers which IPs are authorized to send email for your domain. When your SPF record says:
v=spf1 mx a:mail.kup6s.com ~all
But your emails come from random node IPs (168.119.62.98, 49.13.2.15, etc.), recipients’ mail servers see:
❌ SPF: softfail - “This IP is not authorized”
🚫 Lower reputation score (mail-tester.com: 5/10 instead of 10/10)
📬 Emails may land in spam folders
The Inflexible Solution: Add All Node IPs to SPF¶
You could add all node IPs to your SPF record:
v=spf1 mx a:mail.kup6s.com ip4:168.119.62.98 ip4:49.13.2.15 ip4:... ~all
Problems:
Adding/removing nodes requires DNS updates
SPF records have size limits (10 DNS lookups max)
Brittle and error-prone
The Solution: Cilium Egress Gateway¶
Cilium egress gateway routes all traffic from selected pods through a designated node, ensuring a consistent source IP for all outbound email.
How It Works¶
Internet
(Gmail, etc)
▲
│ Outbound mail
│ (Egress path)
│
┌────────┴─────────┐
│ Egress Gateway │ (control-fsn1 node)
│ IP: 5.75.247.168│ ← Single consistent source IP
└────────┬─────────┘
│
▼
┌─────────────┐
│ Mailu Pods │ (any node)
│ - postfix │
│ - dovecot │
└─────────────┘
▲
│ Inbound mail
│ (Ingress path)
│
┌────────┴─────────┐
│ Traefik Ingress │ (LoadBalancer)
│ mail.kup6s.com │
└────────┬─────────┘
│
▼
Internet
(Senders)
Result: All outbound emails appear to come from 5.75.247.168, matching your SPF record.
Architecture Decisions¶
Server IP vs Floating IP¶
We use the server’s native IP (5.75.247.168) instead of a Hetzner Floating IP because:
Advantages:
✅ Zero additional cost (Floating IP: €1.19/month)
✅ Simpler infrastructure (one less resource)
✅ Adequate for mail server use case
Trade-offs:
⚠️ IP is tied to the node - if node is replaced, IP changes
⚠️ Requires manual DNS updates after node replacement
⚠️ No automatic failover to another node
When to use Floating IP instead:
High-availability requirements (automatic failover)
Frequent node replacements
Multiple services requiring IP stability
For a mail server that’s rarely rebuilt, the server IP is sufficient.
IPv4 vs IPv6 Handling¶
IPv4: Fully supported via egress gateway
All Mailu pods → 5.75.247.168 (control-fsn1)
Consistent source IP guaranteed
IPv6: Limited egress gateway support
Cilium 1.17.0 doesn’t support IPv6 egress gateway policies
IPv6 traffic uses node’s native address (2a01:4f8:c012:f3f0::1)
Still consistent because control-fsn1 is the designated egress node
PTR Records (Forward-Confirmed Reverse DNS)¶
Large providers (notably Gmail) require forward-confirmed reverse DNS (FCrDNS) for the sending IP:
5.75.247.168 → mail-out.kup6s.com (PTR record)
mail-out.kup6s.com → 5.75.247.168 (A record)
Requirements:
The egress IP must have a PTR record
The PTR hostname must have forward DNS (A/AAAA) resolving back to the same IP — this is the “forward confirmation”
PTR set manually in Hetzner Cloud Console (Servers → Networking → Reverse DNS); forward records in the
kup6s.comDNS zone
Why a dedicated mail-out hostname: mail.kup6s.com cannot be used as
PTR target because its A record points at the ingress load balancer
(inbound mail), not at the egress IP — the forward confirmation would fail.
Why it matters: Broken FCrDNS violates Gmail’s sender requirements and gets mail spam-foldered or rejected regardless of SPF/DKIM.
Benefits¶
After implementing egress gateway:
✅ SPF passes: All emails from authorized IP (5.75.247.168)
✅ Consistent sender reputation: Recipients see stable sending IP
✅ mail-tester.com score: 10/10 (up from 5/10)
✅ Better deliverability: Lower spam risk
✅ Flexible pod placement: Mailu pods can run on any node without SPF changes
See Also¶
Configure Egress Gateway (How-to) - Step-by-step setup guide
Traefik TLS Termination Pattern - Inbound TLS architecture for mail protocols