Domain IP Lookup

How an email finds your mail server

Sender

you@gmail.com

MX lookup

who takes mail?

Mail server

priority 10 first

Inbox

delivered

Lowest priority number wins; higher numbers are backups

Troubleshooting

SPF Record Not Found: Why It Happens and How to Fix It

8 min readBy Domain IP Lookup Team

A checker says "no SPF record found", or a message header says spf=none. Both reports mean the same thing: the resolver asked for TXT records at one specific name, and none of them started with v=spf1. Nothing is wrong with your mail server. The question is why the answer was empty, and it usually comes down to checking, or publishing at, the wrong name.

This post is the diagnosis path for that empty answer. If your problem is a record that exists but breaks, see the posts on too many DNS lookups and the 10-lookup limit instead.

What "not found" actually means

SPF lives in an ordinary TXT record. A receiver takes the domain from the message (normally the envelope sender, also called the bounce or Return-Path address), requests its TXT records, and keeps only the ones whose text begins with v=spf1. If that filtered list is empty, the result is none. It is not a syntax error; it is the absence of a policy.

That is different from the two other situations people confuse with it. Each has its own result and its own fix.

What you seeWhat is true in DNSResultFix
No SPF record foundNo TXT at that name starts with v=spf1nonePublish one record at the right name
Multiple SPF recordsTwo or more TXT records start with v=spf1permerrorMerge them into one record
Too many DNS lookupsOne record, but evaluating it needs more than 10 lookupspermerrorTrim includes or use IP ranges
SPF fail or softfailA record exists but the sending IP is not listedfail / softfailAdd the sender, or stop using it

Key takeaway

"Not found" is a question about one exact DNS name. Work out which name the receiver asked about before you touch the record.

Cause 1: the record is at the wrong name

SPF is looked up at the domain used in the mail, and nowhere else. It is not inherited from a parent and it is not searched for on www. A record published at www.example.com does nothing for mail sent from @example.com, and a record at example.com does nothing for mail sent from @news.example.com.

The classic mistake happens in DNS panels. For a record on the apex (the bare domain) the host field is usually @, though some panels want it blank or want the full domain. Read the panel's hint text, then confirm with a query rather than trusting the form.

  • Record on www or mail: correct text, wrong host. Move it to the apex if you send from @example.com.
  • Doubled domain: a panel that appends the zone automatically turns example.com into example.com.example.com. Query that name and you will find your record sitting there.
  • Wrong sending domain: you checked example.com, but the envelope sender is bounce.example.net or mail.example.com. The receiver looked at that name, not yours.

Cause 2: you are checking a different domain than the mail uses

The address people see in the From header is one thing. The envelope sender, which SPF evaluates, can be another. Many email service providers use a custom bounce domain, and some use their own domain by default. Then SPF is evaluated on that name, and your own record is not consulted for the check at all.

The message header shows which domain was evaluated (see below). If it is a subdomain of yours, that subdomain needs its own record even when the parent has a perfect one. A subdomain that never sends can publish v=spf1 -all.

Cause 3: the text is not a valid SPF string

The checker is strict about the start of the value. The text must begin with v=spf1, with an equals sign and no spaces inside it. These near misses all produce "not found":

  • spf1 include:_spf.example.net ~all (the v= is missing)
  • v=spf include:_spf.example.net ~all (version should be spf1)
  • v = spf1 ... (spaces around the equals sign)
  • Text pasted with curly "smart" quotes copied from a document or chat

Quotes deserve a note. Most hosted DNS panels add the straight double quotes for you, so typing your own can store them as literal characters. If a dig answer shows two layers of quotes, remove the ones you typed.

Cause 4: the zone you edited is not the live one

This one fools experienced people. You can add a perfect TXT record in a DNS panel and still see nothing in public DNS, because that panel is not the one the internet asks. The usual reason is delegation.

  • Registrar versus DNS host: the domain is registered at one company, but its nameservers point to another (a CDN, a hosting company, a separate DNS provider). Only the zone at the delegated nameservers is live. Records added at the registrar's own DNS page, or in a leftover zone at a previous provider, are ignored.

Find the delegated nameservers with the NS lookup, then edit the zone at exactly that provider. This often explains "I added it an hour ago and it still isn't there" better than propagation does.

Cause 5: legacy record type, cache, or timing

Early SPF drafts used a dedicated record type (number 99, named SPF). That type is deprecated and receivers evaluate TXT records, so a record published only as type SPF is invisible to modern checks. Publish a TXT record even if your DNS provider still offers an SPF type.

Timing is the last suspect and the weakest. If a resolver already learned that the name had no TXT record, it may keep serving that empty answer for a period tied to the zone's negative-caching settings. Querying the authoritative nameserver directly removes the doubt. Our post on how long DNS propagation takes covers the mechanics.

Confirm what DNS really returns

Before changing anything, ask DNS the same question the receiver asked. On Linux or macOS:

dig
dig TXT example.com +short
# a healthy answer includes a line like:
# "v=spf1 include:_spf.example.net ~all"
Windows
nslookup -type=TXT example.com

An empty answer, or answers that contain only things such as site verification tokens, confirms "not found". To bypass your own resolver's cache, ask a nameserver directly: dig TXT example.com @ns1.example.net +short, using a nameserver from the NS lookup. If that returns the record and your normal query does not, you are looking at caching. If neither does, the record is not in the live zone.

The SPF checker on this site queries the TXT records of the domain you enter, keeps those starting with v=spf1, and reports "No SPF record" when it finds none. If it finds one it also walks the includes and counts lookups. The TXT lookup shows every TXT value at a name, which helps when the record is present but malformed, since you can see the raw text.

Read the header of a message that failed

Open the original source of a delivered message and find the Authentication-Results header added by the receiving server. The SPF part names the result and usually the domain that was evaluated. Header wording varies by receiver, so treat the examples as a pattern, not an exact format.

Authentication-Results patterns
spf=none (example.com does not designate permitted sender hosts)
spf=fail smtp.mailfrom=example.com
spf=permerror smtp.mailfrom=example.com
  • spf=none: no record at the evaluated domain. Use this post.
  • spf=fail or softfail: a record exists, but the sending IP is not authorized. Add the sender or fix the policy.
  • spf=permerror: the record is broken, either two records or too many lookups.

Note the smtp.mailfrom (or Return-Path) domain. That, not the From address, is what SPF evaluated. For the mechanics of reading headers in full, see how to trace an email's original sender.

Publish a minimal, safe record

Publish one TXT record at the name used in the envelope sender. A record is a list of mechanisms read left to right, ending with a default for everyone else.

  • ip4 / ip6: authorize an address or range, for example ip4:203.0.113.25. Costs no DNS lookup.
  • include: authorize whatever another domain's SPF record authorizes, for example include:_spf.example.net. Costs a lookup.
  • a: authorize the IP addresses in the domain's own A (or AAAA) record. Costs a lookup.
  • mx: authorize the hosts named in the domain's MX records. Costs a lookup; wrong when your inbound host is not the one that sends.
  • ~all, -all, ?all: the default. ~all is softfail, -all is fail, ?all is neutral.
SituationRecord to publish at that name
One outside provider sends your mailv=spf1 include:_spf.example.net ~all
Your own server with a fixed IP sends mailv=spf1 ip4:203.0.113.25 ~all
Subdomain or parked domain that never sendsv=spf1 -all

Start with ~all while you confirm every sender is listed, then consider -all once you are sure. ?all makes no claim and is mostly transitional. A correct list matters more than the ending, since receivers weigh SPF together with DKIM and DMARC.

Quick pointers for common platforms

The menus differ and change, but the failure patterns repeat. Check these on each type of setup.

  • Microsoft 365 and Google Workspace: both publish an include for you to copy from the admin console or setup guide. A "not found" there usually means the record went to the wrong DNS provider or host.
  • GoDaddy and other registrars: if the nameservers were changed to a CDN or hosting company, the registrar's DNS page is no longer authoritative. Edit the records at the provider the NS lookup shows.
  • Cloudflare: when the domain uses Cloudflare nameservers, add the TXT record in the Cloudflare DNS tab.

What receivers do when there is no SPF

SPF none is not an automatic rejection. The standard leaves the decision to the receiver's local policy, so outcomes vary. Mail with no SPF and no DKIM or DMARC to compensate is more likely to look suspicious, and some providers publish authentication requirements for bulk senders. Check the current rules of the providers you send to.

SPF checks the envelope sender, so it does not on its own stop someone forging your visible From address; that is DMARC's job. See SPF, DKIM and DMARC explained and how to check an SPF record.

Need to check a domain's public DNS addresses? Use the Domain IP Lookup tool.

spfemail dnstxt recordsemail deliverabilitytroubleshooting

Frequently asked questions