DKIM, SPF, and DMARC Explained Simply
A developer-friendly explanation of email authentication. What these acronyms mean, why they matter, and how to set them up correctly.
Email authentication is confusing. Three acronyms, multiple DNS records, cryptographic keys—it's a lot. Let's break it down in terms that actually make sense.
The Problem These Solve
Email was invented in 1971. Security wasn't a priority. Anyone can send an email claiming to be from ceo@yourcompany.com. That's how phishing works.
SPF, DKIM, and DMARC are band-aids on this fundamental design flaw. They let receiving servers verify that you're actually authorized to send email from your domain.
SPF: Who Can Send
What it does: Lists which servers are allowed to send email for your domain.
Analogy: It's like a guest list. "These IP addresses/services are authorized to speak on my behalf."
How it works
- You publish a TXT record in DNS
- Receiving server gets an email "from" your domain
- Server checks: "Is the sending IP on the SPF list?"
- If yes, SPF passes. If no, SPF fails.
Example record
v=spf1 include:sendpigeon.com include:_spf.google.com ~all
Breaking this down:
v=spf1- Version 1 of SPFinclude:sendpigeon.com- Trust servers listed in SendPigeon's SPFinclude:_spf.google.com- Also trust Google (if you use Gmail)~all- Soft fail everything else (treat with suspicion but don't reject)
Common mistakes
- Too many lookups: SPF allows max 10 DNS lookups. Each
includecounts. Flatten if needed. - Using
+all: This authorizes everyone. Never do this. - Forgetting a service: If you use Mailchimp AND SendPigeon, include both.
DKIM: Message Integrity
What it does: Adds a digital signature to prove the email wasn't modified in transit.
Analogy: It's like a wax seal on a letter. If the seal is broken, you know someone tampered with it.
How it works
- You generate a public/private key pair
- Public key goes in DNS as a TXT record
- When you send an email, your server signs it with the private key
- Receiving server uses the public key to verify the signature
Example DNS record
sendpigeon._domainkey.yourdomain.com TXT "v=DKIM1; k=rsa; p=MIGfMA0GCS..."
The record name format is selector._domainkey.yourdomain.com. The selector (like sendpigeon) identifies which key to use—you can have multiple.
What gets signed
DKIM signs specific headers and the body:
- From address
- Subject
- Date
- Body content hash
If any of these change after signing, verification fails.
Common mistakes
- Key too short: Use at least 1024-bit keys. 2048-bit is better.
- Forgetting to rotate: Keys should be rotated periodically. Old keys get compromised.
- Wrong selector: Make sure you're using the selector your email provider gave you.
DMARC: The Policy Layer
What it does: Tells receiving servers what to do when SPF/DKIM fail, and where to send reports.
Analogy: It's the rule book. "If authentication fails, here's what you should do about it."
How it works
- Receiving server checks SPF and DKIM
- Receiving server looks up your DMARC policy
- If SPF or DKIM fails, server follows your policy (nothing, quarantine, or reject)
- Server sends you a report about what happened
Example record
_dmarc.yourdomain.com TXT "v=DMARC1; p=quarantine; rua=mailto:dmarc@yourdomain.com"
Breaking this down:
v=DMARC1- Version 1 of DMARCp=quarantine- Put failing emails in spamrua=mailto:...- Send aggregate reports to this address
Policy progression
Start strict and move gradually:
p=none- Monitor only. See what's happening without affecting delivery.p=quarantine- Send failures to spam.p=reject- Block failures entirely.
Don't jump to p=reject immediately. You'll block legitimate email you forgot about.
DMARC alignment
Here's the tricky part. DMARC requires "alignment"—the domain in the From header must match:
- The domain that passed SPF, OR
- The domain that signed with DKIM
If your From address is hello@myapp.com, but you send through a service that uses bounce.emailservice.com for SPF... that's a mismatch. You need DKIM alignment instead.
How They Work Together
Email arrives from "you@yourdomain.com"
│
├─► SPF Check: Is sending IP authorized?
│ └─► Pass/Fail
│
├─► DKIM Check: Is signature valid?
│ └─► Pass/Fail
│
└─► DMARC Check: Did either SPF or DKIM pass WITH alignment?
│
├─► Yes → Deliver normally
└─► No → Apply DMARC policy (none/quarantine/reject)
Quick Setup Checklist
1. Set up SPF (5 minutes)
Add TXT record to your domain:
v=spf1 include:YOUR_EMAIL_PROVIDER ~all
2. Set up DKIM (10 minutes)
Get the DKIM record from your email provider. Add it to DNS. Enable DKIM signing in your provider's dashboard.
3. Set up DMARC (5 minutes)
Add TXT record at _dmarc.yourdomain.com:
v=DMARC1; p=none; rua=mailto:dmarc@yourdomain.com
4. Verify everything
Send test emails. Check headers for:
spf=pass
dkim=pass
dmarc=pass
5. Gradually tighten DMARC
After a few weeks of monitoring, move from p=none to p=quarantine to p=reject.
Tools for Testing
- MXToolbox - Check SPF, DKIM, DMARC records
- Mail-tester - Send a test email, get a deliverability score
- Google Postmaster - See how Gmail views your domain
Bottom Line
- SPF = Who can send
- DKIM = Message wasn't tampered
- DMARC = What to do when checks fail
All three work together. Missing any one weakens the whole system. Set them up, monitor the reports, and gradually enforce stricter policies.