{"id":130,"date":"2026-10-09T09:01:24","date_gmt":"2026-10-09T06:01:24","guid":{"rendered":"https:\/\/mx1mail.com\/blog\/spf-10-dns-lookup-limit-include-chains-failures-spf-flattening\/"},"modified":"2026-10-09T09:01:24","modified_gmt":"2026-10-09T06:01:24","slug":"spf-10-dns-lookup-limit-include-chains-failures-spf-flattening","status":"publish","type":"post","link":"https:\/\/mx1mail.com\/blog\/en\/spf-10-dns-lookup-limit-include-chains-failures-spf-flattening\/","title":{"rendered":"What Is the SPF 10 DNS Lookup Limit? include Chains, Common Failures, and When to Use SPF Flattening"},"content":{"rendered":"<h2>What the SPF 10 DNS lookup limit actually means<\/h2>\n<p>SPF (Sender Policy Framework) lets you publish, in DNS, which servers are allowed to send email on behalf of a domain. When a receiving mail server checks SPF for an incoming message, it fetches your domain\u2019s SPF record and then performs additional DNS queries to evaluate the mechanisms inside that record.<\/p>\n<p>A key technical constraint is easy to miss: during SPF evaluation, a receiver can perform a maximum of <strong>10 DNS lookups<\/strong>. If SPF evaluation requires more than 10, the check typically results in a <strong>PermError<\/strong> (permanent error). PermError doesn\u2019t necessarily mean your SPF record is \u201cwrong\u201d; it often means the receiver cannot evaluate it safely within SPF\u2019s required limits. In practice, that can hurt deliverability: some systems may reject the message, while others may increase spam scoring or treat the authentication result as unreliable.<\/p>\n<p>This issue is common in organizations that send mail from multiple sources\u2014cloud email, marketing platforms, ticketing tools, CRMs, billing systems, website servers, and so on. Each tool often adds an <strong>include<\/strong> to SPF, and include chains can quickly push you over the lookup budget.<\/p>\n<h2>Which SPF mechanisms count toward the limit?<\/h2>\n<p>Not everything inside an SPF record consumes a lookup. The 10-lookup limit applies to specific mechanisms that require DNS queries during evaluation, most notably:<\/p>\n<ul>\n<li><strong>include:<\/strong> Pulls in another domain\u2019s SPF policy. Each include typically costs at least one DNS lookup\u2014and the included policy may contain more includes.<\/li>\n<li><strong>a<\/strong> and <strong>mx<\/strong>: Resolve A records or MX records and can consume lookups.<\/li>\n<li><strong>exists<\/strong>: Performs a DNS-based conditional check, consuming a lookup.<\/li>\n<li><strong>redirect=<\/strong>: Redirects evaluation to another domain\u2019s SPF record, consuming a lookup.<\/li>\n<\/ul>\n<p>Mechanisms like <strong>ip4<\/strong> and <strong>ip6<\/strong> do not require DNS queries because the IP ranges are explicitly listed. That\u2019s why many SPF simplification efforts aim to reduce lookups (includes, mx, a, redirect, exists) and rely more on direct IP entries where appropriate.<\/p>\n<h2>What happens when you exceed 10 lookups?<\/h2>\n<p>When the receiver hits the lookup limit, SPF evaluation can\u2019t complete. Common real-world symptoms include:<\/p>\n<ul>\n<li>Bounce messages or mail logs mentioning <strong>PermError<\/strong><\/li>\n<li>Errors like \u201ctoo many DNS lookups\u201d or similar wording<\/li>\n<li>Inconsistent results across recipients (delivered to some providers, spammed or rejected by others)<\/li>\n<li>A sudden deliverability drop after adding a new sending service<\/li>\n<\/ul>\n<p>At this point, the problem is less about authorization and more about evaluation reliability. The fix is to restructure SPF so it stays within SPF\u2019s technical constraints.<\/p>\n<h2>Why include chains get out of hand<\/h2>\n<p>Most companies grow their SPF record incrementally. A marketing tool asks you to add an include. A support platform asks for another include. A cloud service adds yet another. Meanwhile, those vendors\u2019 SPF records may include additional domains. You may see only three includes in your own record, but the total evaluation can trigger a dozen lookups once the chain is expanded.<\/p>\n<p>Typical causes of avoidable SPF bloat:<\/p>\n<ul>\n<li>Adding multiple includes for the same service due to outdated internal notes or changing vendor documentation<\/li>\n<li>Leaving legacy providers in SPF after migrations<\/li>\n<li>Using <strong>mx<\/strong> or <strong>a<\/strong> \u201cjust in case,\u201d even when you don\u2019t send from those hosts<\/li>\n<li>Publishing multiple SPF TXT records (SPF should be a single record; multiple records can break evaluation)<\/li>\n<\/ul>\n<h2>A practical SPF audit workflow<\/h2>\n<h3>1) Inventory every outbound mail source<\/h3>\n<p>Start by listing where your organization sends email from. This usually includes user mailboxes via authenticated SMTP submission, website\/application servers, marketing platforms, monitoring systems, and devices like multifunction printers.<\/p>\n<p>Your goal is to identify what is <strong>actually<\/strong> sending as your domain today. Removing unused sources from SPF is often the fastest win.<\/p>\n<h3>2) Read your current SPF record like a policy document<\/h3>\n<p>Most SPF records look like \u201cv=spf1 &#8230; -all\u201d. Write down every lookup-consuming mechanism: include, a, mx, exists, and redirect. Also note the all-mechanism qualifier:<\/p>\n<ul>\n<li><strong>-all<\/strong> is strict (unauthorized sources fail)<\/li>\n<li><strong>~all<\/strong> is softer (softfail)<\/li>\n<\/ul>\n<p>This article isn\u2019t about choosing -all vs ~all; the key point is that your record must be evaluatable under the lookup limit.<\/p>\n<h3>3) Estimate your real lookup budget<\/h3>\n<p>Counting includes in your SPF record is not enough. You must account for what those includes pull in. A single include can expand into several additional lookups depending on how that provider structures their SPF. The \u201creal\u201d lookup count is the total across the entire expanded chain.<\/p>\n<h2>What SPF flattening is\u2014and when it\u2019s worth considering<\/h2>\n<p><strong>SPF flattening<\/strong> is the practice of resolving include chains and publishing the resulting IP ranges directly in your SPF record (using ip4\/ip6). The goal is to reduce DNS lookups by replacing lookup-heavy includes with explicit IP entries.<\/p>\n<p>Flattening is usually considered when:<\/p>\n<ul>\n<li>You are already exceeding, or are very close to, the 10-lookup limit<\/li>\n<li>You must support multiple sending services and cannot reduce includes enough<\/li>\n<li>You see SPF PermError-related deliverability problems<\/li>\n<\/ul>\n<p>However, flattening is not a \u201cset it and forget it\u201d solution. It introduces ongoing operational responsibilities.<\/p>\n<h3>Pros of flattening<\/h3>\n<ul>\n<li>Fewer lookups, lower risk of SPF PermError<\/li>\n<li>More deterministic SPF evaluation<\/li>\n<li>Less dependence on long include chains that change outside your control<\/li>\n<\/ul>\n<h3>Cons and operational risks<\/h3>\n<ul>\n<li>Vendor IP ranges can change, and your flattened SPF can become outdated<\/li>\n<li>Missing or incorrect IP ranges can cause legitimate mail to fail SPF<\/li>\n<li>Your SPF record can become very long (be mindful of DNS TXT size limits and splitting behavior)<\/li>\n<\/ul>\n<p>Because of these risks, many teams treat flattening as a managed process with periodic review, rather than a one-time cleanup.<\/p>\n<h2>Simpler fixes to try before flattening<\/h2>\n<p>In many environments, you can get under the lookup limit without flattening:<\/p>\n<ul>\n<li><strong>Remove unused includes:<\/strong> Old platforms frequently linger in SPF long after they\u2019re retired.<\/li>\n<li><strong>Deduplicate providers:<\/strong> If the same vendor appears multiple times, you may only need one include.<\/li>\n<li><strong>Question mx\/a mechanisms:<\/strong> If you do not send mail directly from your MX hosts or A-record hosts, these may be unnecessary.<\/li>\n<li><strong>Split sending domains:<\/strong> Using a subdomain for marketing or automated traffic can simplify the main domain\u2019s SPF and reduce blast radius when changes are needed.<\/li>\n<\/ul>\n<h2>Change management: avoiding disruption<\/h2>\n<p>SPF changes are DNS changes, so propagation takes time. A few practical habits make updates safer:<\/p>\n<ul>\n<li><strong>DNS TTL planning:<\/strong> Lower TTL ahead of major edits, then raise it again once stable, so you can roll adjustments out more predictably.<\/li>\n<li><strong>Validate critical flows:<\/strong> Test the most important senders (executives, billing, support, automated systems) after changes.<\/li>\n<li><strong>Document intent:<\/strong> Keep an internal note stating why each include or IP block exists and which system depends on it.<\/li>\n<\/ul>\n<h2>Don\u2019t treat SPF in isolation: SPF, DKIM, and DMARC<\/h2>\n<p>SPF is only one part of modern email authentication. If you use DMARC, alignment and DKIM signatures matter as well. When SPF produces a PermError, a correctly configured and aligned DKIM signature may still allow DMARC to pass in some scenarios. The practical takeaway is that SPF cleanup should be coordinated with DKIM\/DMARC governance rather than handled as a standalone tweak.<\/p>\n<h2>Quick checklist<\/h2>\n<ul>\n<li>Do you have exactly one SPF TXT record?<\/li>\n<li>Have you removed obsolete includes and unnecessary mx\/a mechanisms?<\/li>\n<li>Is the total DNS lookup count under 10 when the chain is expanded?<\/li>\n<li>Did you test the key outbound mail streams after the update?<\/li>\n<li>Is the SPF record documented so future changes don\u2019t reintroduce bloat?<\/li>\n<\/ul>\n<h2>A practical note for MX1Mail customers<\/h2>\n<p>Most SPF lookup-limit incidents are caused by gradual complexity rather than a single bad change. If you\u2019re managing business email on MX1Mail, it\u2019s worth building a routine around sender inventory, controlled DNS changes, and periodic authentication review. That discipline helps keep SPF evaluatable, reduces the chance of PermError surprises, and supports stable long-term deliverability as your organization adds new tools and workflows.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Learn how the SPF 10-DNS-lookup limit works, why include chains break SPF checks, and practical ways to simplify SPF\u2014including when SPF flattening makes sense.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[263],"tags":[281,94,99],"class_list":["post-130","post","type-post","status-publish","format-standard","hentry","category-email-authentication","tag-deliverability","tag-dns","tag-spf"],"_links":{"self":[{"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/posts\/130","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/comments?post=130"}],"version-history":[{"count":0,"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/posts\/130\/revisions"}],"wp:attachment":[{"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/media?parent=130"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/categories?post=130"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/mx1mail.com\/blog\/wp-json\/wp\/v2\/tags?post=130"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}