SPF-include-ketens uitgelegd (met voorbeelden)
De meeste SPF-records zien er onschuldig uit. Vier include:-statements, een ~all aan het eind, en een DNS-tool
die de syntax als geldig rapporteert. Dan begint Gmail je mail als niet-geauthenticeerd te behandelen, en in de logs staat
SPF PermError.
Het ontbrekende stuk is de include-keten: elk include: is een DNS-lookup van een ander SPF-record, en dat
record bevat meestal nog meer includes. Ontvangers tellen de hele boom, niet de vier tokens die jij hebt getypt.
In deze gids leggen we uit hoe include-ketens werken, lopen we drie concrete voorbeelden door en laten we zien waarom een record met "maar vier includes" toch de limiet van 10 DNS-lookups uit RFC 7208 kan opmaken.
Wat is een SPF-include-keten?
Een SPF-record is een TXT-record dat geautoriseerde afzenders opsomt. Het include:-mechanisme kopieert geen IP-adressen naar je
record. Het zegt tegen de ontvangende server: zoek het SPF-record van dat andere domein op en evalueer het als onderdeel van het mijne.
v=spf1 include:_spf.google.com ~all
Die ene regel is niet "de IP's van Google". Het is een verwijzing. De ontvanger haalt _spf.google.com op, leest dat
SPF-record en volgt elk mechanisme dat daar staat. Verwijst het record van Google zelf weer met include: naar drie andere domeinen, dan tellen die ook mee. Die
geneste doorloop is de include-keten.
include:-tokens in je eigen TXT-record tellen. Ontvangers tellen elke lookup die
de keten veroorzaakt, inclusief geneste includes, a:, mx:, ptr:, exists: en
redirect=. Directe ip4:- en ip6:-mechanismen tellen niet mee.
Zo werkt de teller van 10 lookups écht
RFC 7208 beperkt het aantal termen dat een DNS-query veroorzaakt tot 10 per SPF-controle. De initiële lookup van je eigen SPF-TXT-record telt niet mee. Alles wat dat record in gang zet wél.
| Mechanisme | Telt mee voor de 10? | Wat de ontvanger doet |
|---|---|---|
include:example.com | Ja (1 + alles wat genest is) | Haalt het SPF-record van dat domein op en evalueert het |
a / a:mail.example.com | Ja | Zoekt A/AAAA-records op |
mx | Ja | Zoekt MX op, daarna de adressen van die hosts |
redirect=other.com | Ja (vervangt de rest van de controle) | Begint opnieuw bij het SPF-record van een ander domein |
ip4: / ip6: | Nee | Vergelijkt het verzendende IP lokaal, geen extra DNS |
Zodra de 11e lookup nodig is, stopt de evaluatie met een PermError. De resterende includes worden nooit gecontroleerd. Een syntactisch perfect record kan tijdens de evaluatie dus toch hard mislukken.
Voorbeeld 1: één include die in werkelijkheid vier lookups kost
Begin met het kleinste realistische record, alleen Google Workspace:
v=spf1 include:_spf.google.com ~all
Op papier is dat één include. De keten die de ontvanger écht doorloopt, ziet er zo uit:
yourdomain.com
└── include:_spf.google.com (+1)
├── include:_netblocks.google.com (+1)
├── include:_netblocks2.google.com (+1)
└── include:_netblocks3.google.com (+1)
Het SPF-record op het hoogste niveau van Google is zelf een bundel includes. Die geneste records publiceren vervolgens ip4:- en
ip6:-ranges, die geen verdere lookups toevoegen. De rekening voor "alleen Gmail" is doorgaans 4 lookups, niet 1.
De aantallen bij aanbieders veranderen in de loop van de tijd. Het gaat om de vorm van de boom: één token in je record kan meerdere lookups verbergen die je zelf nooit hebt getypt.
Voorbeeld 2: Microsoft 365 lijkt plat tot je het uitklapt
Een Microsoft 365-include is de andere klassieke aanname van "dat kost vast weinig":
v=spf1 include:spf.protection.outlook.com ~all
Het record van Outlook combineerde van oudsher directe IP-blokken met extra include:-statements voor aanvullende netblocks. Een
vereenvoudigde keten ziet er zo uit:
yourdomain.com
└── include:spf.protection.outlook.com (+1)
└── include:spfa.protection.outlook.com (+1)
└── verdere includes / mx zoals gepubliceerd
Afhankelijk van hoe Microsoft het record op dit moment publiceert, kost dit vaak 2-3 lookups in plaats van één. Samen met Google uit voorbeeld 1 zit je al rond 6-7 lookups voordat je ook maar één marketing- of CRM-tool toevoegt.
Voorbeeld 3: een doorsnee bedrijfsrecord dat ongemerkt over de 10 gaat
Nu het record dat de meeste middelgrote teams in de praktijk publiceren:
v=spf1 include:_spf.google.com include:spf.protection.outlook.com include:servers.mcsv.net include:_spf.salesforce.com ~all
Vier includes. Veel DNS-dashboards tonen zelfs een groen vinkje. Klap de keten uit met gangbare geneste aantallen en het beeld verandert:
| Wat je schreef | Gangbare geneste lookups | Lopend totaal |
|---|---|---|
include:_spf.google.com | 4 (Google + 3 netblocks) | 4 |
include:spf.protection.outlook.com | 2-3 | 6-7 |
include:servers.mcsv.net (Mailchimp) | 2-3 | 8-10 |
include:_spf.salesforce.com | 2-4 | 10-14 |
Als boom:
yourdomain.com
├── include:_spf.google.com (+1)
│ ├── include:_netblocks.google.com (+1)
│ ├── include:_netblocks2.google.com (+1)
│ └── include:_netblocks3.google.com (+1)
├── include:spf.protection.outlook.com (+1)
│ └── include:spfa.protection.outlook.com (+1)
├── include:servers.mcsv.net (+1)
│ └── geneste Mailchimp-includes (+1-2)
└── include:_spf.salesforce.com (+1)
└── geneste Salesforce-/ExactTarget-includes (+1-3)
De 11e lookup wordt nooit geëvalueerd. Staat Salesforce als laatste in het record, dan kan een deel van je CRM-mail met wat geluk nog slagen terwijl latere mechanismen worden overgeslagen. Het kan ook zijn dat de hele controle mislukt, afhankelijk van waar de limiet wordt bereikt. Hoe dan ook heb je geen betrouwbaar beleid meer.
Een korte keten die je met de hand kunt tellen
Wil je dit zien op een domein dat je beheert? Begin bovenaan en werk recursief naar beneden:
- Zoek het TXT-record van je domein op en vind de
v=spf1-string. - Noteer elk
include:,a,mx,ptr,existsenredirect=. - Zoek voor elke include het SPF-record van dat domein op en herhaal.
- Stop wanneer een record alleen
ip4:/ip6:(enall) bevat. Die eindpunten voegen geen lookups toe.
dig TXT yourdomain.com +short dig TXT _spf.google.com +short dig TXT _netblocks.google.com +short
Dit volledig met de hand doen is vermoeiend, en daarom onderschatten de meeste mensen het aantal lookups. Online validators die bij 10 lookups stoppen, maken het erger: ze melden een fout zonder de rest van de boom te tonen, zodat je nooit ziet welke aanbieder je over de grens duwde.
Wat flattening met de keten doet
SPF-flattening lost de boom één keer op en publiceert daarna de resulterende IP-ranges direct. De include-keten krimpt zo tot een kort record, waardoor ontvangers niet meer bij elk inkomend bericht recursief door Google, Microsoft, Mailchimp en Salesforce hoeven te gaan.
Voor (vier includes, 10+ lookups):
v=spf1 include:_spf.google.com include:spf.protection.outlook.com include:servers.mcsv.net include:_spf.salesforce.com ~all
Na flattening (één include, één lookup):
v=spf1 include:_yourdomain.spf.spflat.cloud ~all
Achter dat ene include houdt een geautomatiseerde flatteningdienst de IP-lijst actueel. Wanneer Google of Microsoft ranges wijzigt, wordt het afgevlakte record bijgewerkt. Je eigen DNS hoeft de keten van aanbieders niet meer te bevatten, en ontvangers betalen de kosten van geneste lookups niet.
Handmatig afvlakken levert één keer dezelfde IP-lijst op, maar kan die lijst niet actueel houden. Dat is het verschil tussen een eenmalige
dig-sessie en een flatteningdienst.
Zo controleer je je eigen include-keten
Gebruik de gratis checker op spflat.cloud. Die lost geneste includes op en toont het aantal lookups zoals een ontvangende server dat telt, niet zoals je TXT-record eruitziet in een DNS-paneel.
Is het getal 8 of 9, dan zit je één nieuwe SaaS-tool van een PermError af. Is het al 10 of meer, dan is flattening de oplossing, niet nog een include.
🔍 Bekijk je include-keten
Tien seconden. Gratis. Klap elk genest include uit en zie precies hoeveel lookups je SPF-record verbruikt.
Controleer je SPFOf start je gratis proefperiode van 14 dagen →
