security
March 27, 2026 · 11 min read · 0 views

Email Authentication for Developers: SPF, DKIM, and DMARC Explained

Master email authentication protocols. Learn how SPF, DKIM, and DMARC prevent spoofing and improve deliverability for your applications.

Why Email Authentication Matters

Email spoofing is one of the oldest and most effective attack vectors. A malicious actor can send a message that appears to come from your domain, impersonating legitimate users or your application’s alerts. Without proper email authentication, your organization’s reputation suffers, users lose trust, and your messages land in spam folders.

Email authentication protocols—SPF (Sender Policy Framework), DKIM (DomainKeys Identified Mail), and DMARC (Domain-based Message Authentication, Reporting and Conformance)—form a three-layer defense that proves you own the domain sending the message. Together, they protect your brand, improve deliverability, and provide visibility into who’s sending mail on your behalf.

If you’re building applications that send transactional emails, newsletters, or alerts, understanding these protocols is essential. Major email providers (Gmail, Office 365, Yahoo) now enforce DMARC policies, making implementation not optional—it’s mandatory for reaching your users’ inboxes.

Understanding SPF (Sender Policy Framework)

What SPF Does

SPF is a DNS-based mechanism that specifies which mail servers are authorized to send email on behalf of your domain. When a recipient’s mail server receives an email, it performs an SPF check:

  1. It extracts the domain from the email’s From header
  2. It queries DNS for the SPF record of that domain
  3. It compares the sending IP address against the authorized list
  4. It returns a pass, fail, or soft-fail result

SPF is the first line of defense—it’s simple, widely supported, and quick to verify.

SPF Record Syntax

An SPF record is a DNS TXT record that begins with v=spf1. Here’s a typical example:

v=spf1 ip4:192.168.1.1 include:sendgrid.net include:_spf.google.com ~all

Breaking down the components:

  • v=spf1 — SPF version (always v1)
  • ip4:192.168.1.1 — Authorizes a specific IPv4 address
  • ip6:2001:db8::1 — Authorizes a specific IPv6 address
  • include:sendgrid.net — Includes the SPF records of another domain (common for SaaS email providers)
  • a — Authorizes the A record (the domain’s own mail server IP)
  • mx — Authorizes MX record IPs (mail exchange servers)
  • ptr:mail.example.com — Authorizes based on reverse DNS (rarely used, not recommended)
  • exists:%{i}.spf.example.com — Checks if a query returns an A record (advanced)
  • ~all — Soft fail (accept mail but mark as suspicious) for all unauthorized IPs
  • -all — Hard fail (reject) for all unauthorized IPs

Practical SPF Setup

If your application sends email through a third-party service like SendGrid, Mailgun, or AWS SES, add their SPF include:

v=spf1 include:sendgrid.net include:_spf.google.com ~all

If you run your own mail server:

v=spf1 a mx ip4:203.0.113.5 ~all

This authorizes:

  • Your domain’s A record IP
  • Your MX record IPs
  • The explicit IP 203.0.113.5
  • Soft-fails everything else

SPF Limitations

SPF has critical weaknesses:

  1. Header forgery — SPF only checks the envelope From address (used for routing), not the display From header (what users see). An attacker can spoof the display header.
  2. Forwarding breaks SPF — When mail is forwarded, the original sending IP no longer matches the forwarded domain.
  3. DNS lookup limit — SPF records can trigger at most 10 DNS lookups. Complex includes can exceed this and fail silently.

This is why DKIM and DMARC exist.

Understanding DKIM (DomainKeys Identified Mail)

What DKIM Does

DKIM cryptographically signs email messages using a public-key infrastructure. Instead of checking IPs, DKIM proves that a message was actually sent from your domain by attaching a digital signature.

The process:

  1. Your mail server generates an email
  2. It creates a hash of the message body and selected headers
  3. It encrypts the hash with a private key (stored securely on your server)
  4. The signature is added as a DKIM-Signature header
  5. The recipient’s server retrieves your public key from DNS
  6. It decrypts the signature and verifies the hash
  7. If the hash matches, the message is authenticated

Un like SPF, DKIM authenticates the actual message content. It survives forwarding, because the signature remains attached.

DKIM Record Setup

DKIM requires two components: a private key (on your mail server) and a public key (published in DNS).

First, generate a key pair. Most email providers (SendGrid, Mailgun, AWS SES) generate this for you, but if you’re running your own mail server:

openssl genrsa -out dkim_private.pem 2048
openssl rsa -in dkim_private.pem -pubout -out dkim_public.pem

Extract the public key in DKIM format:

openssl rsa -in dkim_private.pem -pubout -outform PEM | sed '1d;$d' | tr -d '\n'

Publish the public key as a TXT record in DNS. The format is:

default._domainkey.example.com. 3600 IN TXT "v=DKIM1; k=rsa; p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDaGaK...."

Key parts:

  • default — The DKIM selector (you can have multiple selectors for key rotation)
  • _domainkey — Required subdomain
  • v=DKIM1 — Version
  • k=rsa — Key type
  • p=... — The public key (base64-encoded)

Configuring Your Mail Server

If you use Postfix, add to /etc/postfix/main.cf:

smtpd_milters = inet:localhost:8891
non_smtpd_milters = inet:localhost:8891
milter_default_action = accept

Then run OpenDKIM:

apt-get install opendkim opendkim-tools

Configure /etc/opendkim.conf:

Socket inet:8891@localhost
KeyFile /etc/opendkim/dkim_private.pem
Selector default
Domain example.com

For SaaS Providers

If you use SendGrid, Mailgun, or AWS SES, they provide CNAME records or TXT records to add to your domain. For example, SendGrid provides:

mail.sendgrid.net CNAME example.sendgrid.net
default._domainkey.example.com CNAME example.sendgrid.net

Or a TXT record with the public key already included.

Understanding DMARC (Domain-based Message Authentication, Reporting and Conformance)

What DMARC Does

DMARC is a policy layer that sits on top of SPF and DKIM. It:

  1. Aligns — Checks that the domain in the From header matches the domain in the SPF/DKIM authentication
  2. Enforces — Specifies what the recipient should do if authentication fails (reject, quarantine, or monitor)
  3. Reports — Sends detailed reports about authentication results and failures

DMARC is powerful because it finally closes the header forgery loophole. Even if an attacker can forge the display From header, DMARC alignment checks that the authenticated domain matches.

DMARC Record Syntax

DMARC records are published as DNS TXT records under _dmarc.yourdomain.com:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=none; rua=mailto:[email protected]; ruf=mailto:[email protected]"

Key fields:

  • v=DMARC1 — Version
  • p= — Policy (required)
    • none — Monitor only, don’t enforce
    • quarantine — Fail messages to spam folder
    • reject — Hard reject failures
  • rua= — Reporting URI for aggregate reports (sent daily)
  • ruf= — Reporting URI for forensic reports (sent on failure)
  • fo= — Failure reporting options (0=any, 1=DKIM and SPF both fail, d=DKIM only, s=SPF only)
  • aspf= — SPF alignment mode (r=relaxed, s=strict)
  • adkim= — DKIM alignment mode (r=relaxed, s=strict)
  • pct= — Percentage of messages to apply policy to (0-100, default 100)
  • subdomain_policy= — Policy for subdomains

DMARC Alignment Modes

Relaxed alignment (default) — The authenticated domain is a parent domain of the From header domain:

From: [email protected]
SPF/DKIM authenticated domain: example.com
✓ PASSES relaxed alignment (mail.example.com is subdomain of example.com)

Strict alignment — The domains must match exactly:

From: [email protected]
SPF/DKIM authenticated domain: example.com
✗ FAILS strict alignment

Gradual DMARC Rollout

Don’t jump straight to p=reject. Start with monitoring:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=none; rua=mailto:[email protected]"

After a week, review the aggregate reports. Once you’ve fixed authentication issues, upgrade to quarantine:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=quarantine; pct=50; rua=mailto:[email protected]"

Gradually increase the percentage, then move to reject:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=reject; rua=mailto:[email protected]"

Getting Started: Step-by-Step Implementation

Step 1: Audit Your Current Setup

First, determine what’s currently sending email on your domain. Use our SPF Analyzer to validate existing records:

Examining: example.com
Current SPF: v=spf1 include:sendgrid.net ~all
Status: ✓ Valid syntax
DNS lookups: 2/10

Step 2: Publish an SPF Record

Identify all services sending mail on your behalf:

  • SendGrid? Add include:sendgrid.net
  • AWS SES? Add include:amazonses.com
  • Google Workspace? Add include:_spf.google.com
  • Your own mail server? Add a mx or ip4:203.0.113.5

Publish the combined record:

v=spf1 include:sendgrid.net include:_spf.google.com a mx ~all

Test using a tool like Kloubot’s DNS Lookup:

nslookup -type=TXT example.com

Step 3: Enable DKIM

If using a third-party service:

  1. Log into your provider’s dashboard
  2. Navigate to “Domain Authentication” or “DKIM Settings”
  3. Add your domain
  4. Copy the CNAME or TXT record they provide
  5. Publish to your DNS
  6. The provider will verify and enable DKIM

If self-hosting, install OpenDKIM and follow the configuration steps outlined above.

Step 4: Implement DMARC

Start with monitoring:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=none; rua=mailto:[email protected]; ruf=mailto:[email protected]"

Create mailboxes to receive reports. You’ll receive XML reports detailing:

  • Which messages passed/failed SPF and DKIM
  • Which IPs sent mail from your domain
  • Authentication alignment results

Step 5: Review Reports and Iterate

Analyze aggregate reports to find:

  • Legitimate senders you haven’t authorized
  • Services that need SPF/DKIM configuration
  • Alignment failures that need fixing

After a week, upgrade to quarantine with a phased rollout:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=quarantine; pct=25; rua=mailto:[email protected]"

Increase pct in increments of 25% weekly, monitoring for legitimate mail hitting spam. Once confident, move to reject:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=reject; rua=mailto:[email protected]"

Common Pitfalls and How to Avoid Them

Pitfall 1: SPF Record Too Complex

Problem: Each include:, a, mx, and other mechanism counts as one DNS lookup. Exceeding 10 lookups causes SPF to fail silently.

Example of too many includes:

v=spf1 include:sendgrid.net include:mailgun.org include:amazonses.com include:_spf.google.com include:sendkeys.io include:stripe.com include:twilio.com include:auth0.com include:mailchimp.com include:wordpress.com ~all

This can exceed the 10-lookup limit.

Solution: Consolidate includes. Create your own _spf.yourdomain.com record that includes other domains:

v=spf1 include:_spf.yourdomain.com ~all

_spf.yourdomain.com. 3600 IN TXT "v=spf1 include:sendgrid.net include:_spf.google.com include:amazonses.com ~all"

This uses only 1 lookup in the main record.

Pitfall 2: Misaligned DKIM Signatures

Problem: Your mail server signs with mail.example.com, but DMARC checks alignment with example.com.

Solution: Use strict alignment for DKIM:

_dmarc.example.com. 3600 IN TXT "v=DMARC1; p=reject; adkim=s; aspf=s; rua=mailto:[email protected]"

Or ensure your mail server signs as the primary domain, not a subdomain.

Pitfall 3: Forwarding Breaks SPF

Problem: User forwards your email from their corporate domain. The forwarded message now comes from their mail server, not yours, breaking SPF.

Solution: SPF can’t be fixed for forwarding. This is why DKIM and DMARC exist—they survive forwarding. Ensure your DKIM signatures are correct, and recipients can verify authenticity even after forwarding.

Pitfall 4: Third-Party Senders Not Configured

Problem: Your support team uses Zendesk, your billing system uses Stripe, and your alerts come from PagerDuty—none are authorized in SPF.

Solution: Create a comprehensive audit:

# Check email logs to find unauthorized senders
grep "Return-Path:" /var/log/mail.log | cut -d'<' -f2 | cut -d'>' -f1 | sort | uniq

Add each service’s SPF include:

v=spf1 include:sendgrid.net include:zendesk.com include:stripe.com include:pagerduty.com ~all

Pitfall 5: Not Monitoring DMARC Reports

Problem: You publish DMARC but never read the reports.

Solution: Set up automated DMARC report aggregation. Services like Dmarcian, Valimail, or Agari parse reports and visualize failures. Or use a simple Python script:

import email
import zipfile
from io import BytesIO

def parse_dmarc_report(raw_email):
    msg = email.message_from_string(raw_email)
    for part in msg.walk():
        if part.get_content_type() == "application/zip":
            z = zipfile.ZipFile(BytesIO(part.get_payload(decode=True)))
            for name in z.namelist():
                with z.open(name) as f:
                    print(f.read().decode())

Testing and Validation

Use Online Tools

Validate your setup with:

  1. SPF Analyzer — Check SPF record validity and DNS lookup count
  2. DNS Lookup — Query TXT records directly
  3. Send a test email to mail-tester.com or appmailtest.com — These services receive your email and show SPF/DKIM/DMARC results

Example Test Email Output

SPF: PASS (192.168.1.1 is authorized by v=spf1 include:sendgrid.net ~all)
DKIM: PASS (Signature verification successful)
DMARC: PASS (DKIM alignment satisfied)
Spam Score: 0.0 / 10 (Excellent)

Command-Line Testing

Check SPF records:

nslookup -type=TXT example.com

Check DKIM public key:

nslookup -type=TXT default._domainkey.example.com

Check DMARC policy:

nslookup -type=TXT _dmarc.example.com

Verify DKIM signature on a received email (Gmail):

  1. Open the email
  2. Click “Show original”
  3. Search for DKIM-Signature
  4. Look for authentication results headers

Why It Matters for Your Applications

Deliverability

Gmail, Microsoft, and Yahoo now require DMARC enforcement. Without it, your mail may be marked spam or rejected entirely. Implementing these protocols directly improves inbox placement.

Brand Protection

Email spoofing costs billions in fraud and credential theft. Criminals impersonate banks, payment processors, and popular SaaS platforms. SPF, DKIM, and DMARC make spoofing significantly harder, protecting your users and brand.

Compliance

Industries like finance and healthcare increasingly require email authentication proof. Implementing these protocols helps meet regulatory requirements.

Debugging Email Issues

When legitimate email fails, DMARC reports tell you exactly why. Aggregate reports show:

  • How many messages passed/failed authentication
  • Which IPs are sending from your domain
  • Which alignments succeeded or failed

This intelligence is invaluable for diagnosing email problems.

Summary

  • SPF — Authorizes IP addresses to send mail from your domain (simple, widely supported)
  • DKIM — Digitally signs messages with a cryptographic signature (survives forwarding, stronger authentication)
  • DMARC — Enforces policy based on SPF/DKIM alignment and generates reports (highest security, enables compliance)

Implement all three in order: SPF first for basics, then DKIM for robustness, then DMARC for enforcement. Start with monitoring (p=none), review reports for a week, then gradually enforce (p=quarantine then p=reject).

Your users deserve mail that reaches their inbox safely. These protocols make that possible.

Related Kloubot Tools

This post was generated with AI assistance and reviewed for accuracy.