↑↓ to move ↵ to open Esc to close Browse all tools

Security guide

SPF vs DKIM vs DMARC: What Each Record Does

SPF, DKIM and DMARC are three DNS records that tell other mail servers whether a message from your domain is really from you. Each one checks something different, and only together do they protect your name and keep your mail out of spam. Here is what each record does, how they fit, example records you can adapt, and what Gmail and Yahoo require.

The short version

SPF answers "is this server allowed to send mail for this domain?" DKIM answers "was this message signed by the domain, and has it changed since?" DMARC ties the two to the address the reader actually sees in the From line and tells the receiver what to do when neither check passes for that address. All three are plain TXT records in your DNS. None of them needs software on your side beyond what your mail provider already runs.

RecordLives atChecksStandard
SPFexample.comThe IP address of the sending server against a list you publishRFC 7208 (2014)
DKIMselector._domainkey.example.comA cryptographic signature in the message header against a public key you publishRFC 6376 (2011)
DMARC_dmarc.example.comThat SPF or DKIM passed for the domain in the visible From address, and what to do if notRFC 7489 (2015), replaced by RFC 9989 (2026)

SPF: which servers may send

An SPF record is a TXT record on your domain that starts with v=spf1 and lists the servers allowed to send mail for it. RFC 7208 says SPF records must be published as TXT records; a separate SPF record type existed during the experimental phase and has been discontinued. The receiving server takes the IP address that connected to it and walks the list from left to right until something matches.

SPF record, TXT at example.com
v=spf1 ip4:192.0.2.10 include:_spf.mailhost.example.net -all

Read it as: the server at 192.0.2.10 may send, so may every server listed in the SPF record of _spf.mailhost.example.net (your mail provider would give you the real name), and everything else fails. Each mechanism can carry a qualifier in front. RFC 7208 defines four: + pass (the default when nothing is written), - fail, ~ softfail, a weak statement that the sender is probably not authorized, and ? neutral, which receivers must treat like no record at all. The all mechanism always matches, so it goes last and sets the answer for every server not listed before it.

What SPF actually checks

SPF does not look at the From address in your mail program. It checks the envelope sender, the address the sending server gives in the SMTP MAIL FROM command, and RFC 7208 recommends also checking the HELO name the server introduces itself with. A newsletter service often uses its own domain in MAIL FROM so bounces come back to it. SPF then passes, but for the service's domain, not yours. That gap is what DMARC closes.

The 10 lookup limit

Each time a receiver evaluates your record, some terms make it ask DNS again. RFC 7208, section 4.6.4, caps the total at 10 during one evaluation. Go over and the result is permerror, which means your SPF counts as broken, not as passing. RFC 7208 also asks receivers to allow no more than two lookups that return nothing, the so-called void lookups.

TermCountsWhy
includeYesEach include, plus every counted term inside the record it pulls in
aYesOne lookup for the A or AAAA records of the name
mxYesOne lookup, and each mail server it returns needs an address lookup (at most 10)
ptrYesRFC 7208 says do not use it
existsYesOne lookup
redirect=YesHands the whole check to another record
ip4, ip6NoThe address is written in the record, nothing to look up
allNoAlways matches; put it last

The trap is the include. Your record may show only four includes, one for your office mail, one for a newsletter tool, one for your shop and one for a help desk. But if each of those records contains two includes of its own, the receiver has already made 12 lookups and your record fails everywhere. Count recursively. Ways back under 10: remove services you no longer use, replace includes with the ip4 and ip6 ranges a service publishes when it allows that, and send bulk mail from a subdomain such as news.example.com with its own SPF record.

One record only

RFC 7208 does not permit more than one SPF record for the same name, and a receiver that finds two returns permerror. When a new service tells you to "add an SPF record", merge its include into the one you have. The DNS lookup reads your SPF record, flags a second one, checks how it ends and counts the lookups at the top level of the record. The lookups inside each include you still have to add yourself.

Where SPF breaks

SPF checks the last server that handed over the message. When someone forwards your mail and keeps your address in MAIL FROM, the forwarding server is not in your list, and RFC 7208 says the check will fail unless the forwarder rewrites MAIL FROM to its own domain. That is the main reason SPF alone is not enough.

DKIM: a signature on every message

With DKIM, your mail server signs each outgoing message with a private key and adds a DKIM-Signature header. The receiver fetches the matching public key from your DNS and checks the signature. If the signed headers or the body changed on the way, the check fails. RFC 6376 describes the purpose as letting the owner of the signing domain claim some responsibility for a message.

The key lives at a name built from a selector you or your provider choose, then _domainkey, then your domain. Selectors let you run several keys at once, one per service, and replace a key without a gap.

DKIM key record, TXT at s1._domainkey.example.com
"v=DKIM1; k=rsa; p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA5l75B6Q4U5aZZSvwt2o+kvGS8sKUk7aFOZ4jVkZaPCiEKrgfY6B+KtK00cJp6D47jPjLgJPtUecGv7n381kQyO/mUTNSunb/a/q+cVZc50tWh1VUBzoDD8OOHuk/Z5w8U1B+acVSG3YBdwK5dcAcgnIQ46VuUIe4pZHRtUXFXE9yl2s99C9+0tAb58" "4IRwdsGUlZn5yPGAAcV+rmHZ2qqlTxgHrpX5ochQShkMsPEN0rhqTmEMiOW1vZg2in7EUq0Kc4lHlOfdgsgsJt51Fddl+wqAOIfDBPnwqnCUrFel4n6mgThOR2J2yEg5ejB/w5NO3WEoHq71oNTEs7+qOY5wIDAQAB"

The value after p= is the public key in base64, the same text you get from the RFC's Appendix C commands without the BEGIN and END lines. A 2048-bit key is too long for one DNS string, since a string holds at most 255 characters (RFC 1035), so it is published as two strings that receivers join without spaces, as RFC 6376 requires. An empty p= means the key has been revoked, and t=y marks a key in testing mode, where receivers should treat signed mail like unsigned mail.

What the signature header says

The header that travels with each message names the signing domain in d= and the selector in s=, so the receiver knows to look up s1._domainkey.example.com. h= lists the signed headers, and RFC 6376 requires the From header to be among them. bh= is the hash of the body and b= the signature itself. RFC 6376 recommends rsa-sha256 for a=.

Key length

RFC 6376 requires at least 1024-bit RSA keys for long-lived keys. Google's sender guidelines ask for at least 1024 bits and recommend 2048. If your provider still gives you a 1024-bit key, ask whether it offers 2048.

DKIM survives forwarding better than SPF, because the signature travels inside the message rather than depending on which server delivers it. RFC 6376 notes that relays typically leave the content alone and preserve the signature, while mailing lists that add a footer can break it.

DMARC: the rule that ties them together

SPF and DKIM can both pass for a domain that is not yours, as the newsletter example showed. DMARC adds one condition, called alignment: the domain that passed must match the domain in the From header, the one your reader sees. A message passes DMARC when at least one of the two checks passes and is aligned. In the default relaxed mode, a subdomain counts as aligned with its parent, so mail.example.com aligns with example.com. Strict mode, aspf=s or adkim=s, demands an exact match.

DMARC record, TXT at _dmarc.example.com
v=DMARC1; p=none; rua=mailto:dmarc-feedback@example.com

That is the monitoring record from RFC 9989's examples. v=DMARC1 must come first. p= is your request to receivers for mail that fails: none means only report, quarantine means treat it as suspicious, usually the spam folder, and reject means refuse it. rua= is where aggregate reports go; without it receivers send none. These reports are how you find every service that sends mail as you, including the ones nobody told you about.

TagMeaningDefault
pPolicy for the domain: none, quarantine or rejectnone, if the record is otherwise valid (RFC 9989)
spPolicy for subdomains that existSame as p
npPolicy for subdomains that do not exist (new in RFC 9989)Same as sp, else p
ruaAddresses for aggregate reportsNo reports
rufAddresses for failure reports on single messagesNo reports
adkim, aspfAlignment mode for DKIM and SPF: r relaxed, s strictr
tTest mode: y asks receivers to apply one level less than the policy (new in RFC 9989)n

The standard changed in 2026

DMARC was first published in 2015 as RFC 7489, an informational document. In May 2026 it was replaced by RFC 9989, now on the Standards Track. The new version removes the pct, rf and ri tags, adds np, psd and t, and finds the organizational domain by walking up the DNS tree instead of using the public suffix list. Receivers ignore tags they do not know, so an older record with pct=100 keeps working, but new records should use t=y for a trial run instead of a percentage.

From none to reject

Do not jump straight to reject. Any legitimate service you forgot, such as an invoicing tool or a form plugin on your website, will have its mail refused. RFC 9989, section 7.4, describes the path: publish p=none for at least a month and read the reports, then p=quarantine for a similar period, then reject. It also says domains whose users post to mailing lists should not publish p=reject, because lists often change messages in ways that break both checks.

One message, three checks

Say your shop sends order confirmations through a mail service. The From line reads orders@example.com. The service uses bounces.mailservice.example.net as the envelope sender and signs with DKIM.

  • SPF: the receiver checks the connecting IP against the SPF record of bounces.mailservice.example.net. It passes, but for mailservice.example.net, which does not align with example.com.
  • DKIM, default setup: the service signs with d=mailservice.example.net. The signature is valid, but again not aligned.
  • DMARC: neither passing check is aligned with example.com, so DMARC fails and your p= policy applies.

The fix is in the service's settings, if it supports signing with your own domain. You publish the key they give you at their selector, for example s1._domainkey.example.com, the signature then carries d=example.com, DKIM passes aligned, and DMARC passes even though SPF still is not aligned. One aligned pass is enough. Some services also let you set a custom bounce domain, such as bounces.example.com, which makes SPF align as well.

What Gmail and Yahoo require

Both providers turned these records from good practice into conditions in February 2024. Google's rules apply to mail sent to personal Gmail accounts; Yahoo's to Yahoo Mail.

RequirementGmail, all sendersGmail, bulk sendersYahoo, bulk senders
SPF and DKIMSPF or DKIMBothBoth
DMARCNot requiredRequired, p=none is enoughRequired, at least p=none, must pass
From aligned with SPF or DKIMNoYesYes
Valid forward and reverse DNS for the sending IPYesYesYes (all senders)
One-click unsubscribe for marketing mailNoYesYes, honored within 2 days
Spam rateBelow 0.30%, aim for 0.10%Below 0.30%, aim for 0.10%Below 0.3%

Google counts you as a bulk sender once you send close to 5,000 messages or more to personal Gmail accounts within 24 hours, adding up all subdomains of the same primary domain, and you stay one permanently after reaching that once. Senders with an existing unsubscribe link had until June 1, 2024 to add one-click unsubscribe, and Google's FAQ says it is ramping up enforcement from November 2025, with temporary and permanent rejections for mail that does not comply. Yahoo does not publish a volume number for its bulk sender rules. Google also requires TLS for sending and DKIM keys of at least 1024 bits.

Setting up all three, in order

  1. List every service that sends mail as your domain: your mailbox provider, newsletter tool, shop, invoicing, help desk, website forms. Check the nameservers first with the WHOIS lookup or DNS lookup, so you edit the zone that is actually live.
  2. Build one SPF record with each service's include or IP range, count the lookups, and end it with ~all.
  3. Turn on DKIM in every service and publish each key at the selector it names. Prefer 2048-bit keys.
  4. Publish DMARC with p=none and a rua address, then read the reports for a few weeks.
  5. Fix what fails, mostly services that sign with their own domain, then move SPF to -all and DMARC to quarantine and, if no mailing list issue stands in the way, to reject.
  6. Check the live records with the DNS lookup after each change. DNS answers are cached for the TTL, so a change can take up to that long to show everywhere.

Authentication gets your mail judged on its merits; it does not make readers want it. If you send newsletters, the email subject line checker flags subject lines that look like spam before they ever reach a filter.

Frequently asked questions

Do I need all three records?

If you send more than a few thousand messages a day to Gmail or Yahoo, yes. Since February 2024 both require bulk senders to have SPF and DKIM and to publish a DMARC record with at least p=none, with the visible From domain aligned with SPF or DKIM. For smaller senders, Gmail asks for SPF or DKIM at a minimum, but setting up all three costs nothing and is the only way to stop others from sending mail in your name.

Should my SPF record end with ~all or -all?

In RFC 7208, the qualifier "-" means fail, a clear statement that any server not listed is not authorized, and "~" means softfail, a weaker statement that it is probably not authorized. Start with ~all while you are still finding every service that sends for you, then switch to -all once your DMARC reports show nothing legitimate failing. Never use +all: it authorizes every server on the internet.

Can I have two SPF records?

No. RFC 7208 does not permit multiple SPF records for the same name, and a receiver that finds more than one returns permerror, which means your SPF does not work at all. When a new service asks you to "add an SPF record", add its include to the one record you already have instead.

Why does the DNS lookup tool not show my DKIM record?

A DKIM key lives at a name made of a selector and _domainkey, for example s1._domainkey.example.com, and the selector is chosen by whoever signs your mail. There is no standard way to list all selectors of a domain. Look up the s= value from the DKIM-Signature header of a message you sent, then query that name for a TXT record.

Is p=none enough?

For Gmail and Yahoo bulk sender rules, yes: both ask for a DMARC policy of at least p=none. But p=none only asks receivers to report, not to act, so it does not stop someone from sending mail that pretends to be you. Use it to collect reports, fix every legitimate source, then move to quarantine. The current DMARC standard, RFC 9989, suggests at least a month at p=none and a similar period at quarantine before reject.

Sources