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-abc123 pod on node A uses IP 168.119.62.98

  • Email from postfix-def456 pod on node B uses IP 49.13.2.15

  • Recipients 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:

  1. The egress IP must have a PTR record

  2. The PTR hostname must have forward DNS (A/AAAA) resolving back to the same IP — this is the “forward confirmation”

  3. PTR set manually in Hetzner Cloud Console (Servers → Networking → Reverse DNS); forward records in the kup6s.com DNS 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