Mail Ward SPF · DKIM · DMARC
✉️ Header analyzer

Email authentication, without the hand-waving

Mail Ward

Anyone in the world can type your address into the “From” box of an email. The protocol was designed in 1982 and it never asked for proof. SPF, DKIM and DMARC are the three records that bolt proof on afterwards. This page explains what they are, how to switch them on without breaking your own mail, what goes wrong when you rush, and exactly what to do the morning someone starts sending invoices in your name.

Everything on this page runs in your browser. Nothing you type is uploaded, except the one optional live DNS lookup that you have to click yourself.

The 60-second version

SPF Who may send

A public list of the servers allowed to send mail for your domain. “Only these post offices may stamp my letters.”

v=spf1 include:_spf.google.com -all

DKIM Proof it is yours

A cryptographic signature added to every message; the public key sits in your DNS. “A wax seal nobody can forge, that also proves the letter was not edited.”

selector._domainkey → v=DKIM1; k=rsa; p=MIIB…

DMARC What to do about it

Ties SPF and DKIM to the address your reader actually sees, states the punishment, and mails you reports. “And if the seal is missing — burn the letter, then tell me.”

_dmarc → v=DMARC1; p=reject; rua=mailto:dmarc@…

The one thing to remember: SPF and DKIM on their own protect nothing a human ever looks at. They validate hidden, technical addresses. Only DMARC connects them to the From: line displayed in the mail client — and that connection is called alignment. Alignment is the whole game.

📮 How an email actually travels

You cannot reason about spoofing until you have seen that an email is really two things at once: an envelope handled by servers, and a letter read by humans. They contain different addresses, and nothing forces them to match.

The two “From” addresses

  Envelope sender Header From
Also called MAIL FROM, Return-Path, bounce address, RFC5321.From, “envelope from” From:, RFC5322.From, “friendly from”
Who sees it Servers and postmasters. Bounces go here. Your reader. This is the name and address in the mail client.
Checked by SPF DMARC (and it is the only one that matters to a victim)
Typical mismatch [email protected] [email protected]

This gap is the entire attack. A criminal sets the envelope to a domain they legitimately control (so SPF passes for their domain) and writes your address in the From: header. Without DMARC, no one ever compares the two.

Headers worth knowing by name

Want to read a real message? Paste it into the Email Header Analyzer next door — it decodes all of this for you.

📋 SPF — Sender Policy Framework

A single DNS TXT record on your domain that lists which servers are allowed to send mail using your domain in the envelope. Defined in RFC 7208.

What a record looks like, piece by piece

example.com.  IN  TXT  "v=spf1 ip4:203.0.113.7 include:_spf.google.com include:sendgrid.net -all"
Piece Meaning Watch out
v=spf1 Version marker. Must be first, exactly once. A record without it is not an SPF record.
ip4: / ip6: A literal address or CIDR range that may send. Costs zero DNS lookups. Cheapest mechanism.
a / mx Whatever the domain's A record / MX hosts resolve to. 1 lookup each (mx can cost far more). Your mail receiver is rarely your sender — mx is usually lazy, not correct.
include: “Also trust whatever this domain's SPF record says.” How you authorise a provider. 1 lookup plus everything nested inside it. The main cause of the 10-lookup blow-up.
redirect= “Use that domain's record instead of mine.” Only meaningful without an all. Easy to confuse with include. Rarely what you want.
ptr Reverse-DNS match. Deprecated. Never use it. Slow and unreliable.
exists: Macro-based conditional match. Advanced; costs a lookup. You almost certainly do not need it.
-all Fail — anyone not listed is forged. The goal. Only after you are certain the list is complete.
~all Softfail — suspicious but accept. The safe starting point. Fine for weeks, not forever.
?all Neutral — “no opinion”. Equivalent to having no policy. Pointless in practice.
+all “Everyone on earth may send as me.” Catastrophic. If you find this, remove it today.

The five rules people break

  1. Exactly one SPF record per name. Two v=spf1 TXT records on the same domain is a permanent error and SPF stops working entirely. Merge them into one.
  2. Ten DNS lookups, maximum. Counted recursively across every include, a, mx, ptr, exists and redirect. Exceed it and the result is permerror — which most receivers treat as “no SPF”. Flattening tools help but freeze provider IPs; prefer removing unused providers.
  3. Do not put SPF in a SPF-type record. DNS record type 99 was retired in 2014. It is a TXT record.
  4. SPF does not survive forwarding. When someone auto-forwards your mail, the forwarder becomes the sender and SPF fails. DKIM survives; this is precisely why you need both.
  5. SPF alone is invisible to users. It checks the envelope, which nobody reads. It is a building block for DMARC, not a defence in itself.

Void lookups: there is a second, less-known limit — at most 2 mechanisms may resolve to nothing (NXDOMAIN/empty). Stale include: lines for a provider you left behind are the usual culprit.

🔏 DKIM — DomainKeys Identified Mail

Your outgoing server hashes selected headers plus the body and signs them with a private key. The matching public key lives in DNS, so any receiver can verify it. Defined in RFC 6376.

How it hangs together

  1. You (or your provider) generate a key pair. The private key stays on the mail platform; the public key becomes a DNS record.
  2. The public key is published at <selector>._domainkey.<your-domain>. The selector is just a label, so you can hold several keys at once — that is how rotation works without downtime.
  3. Every outgoing message gets a DKIM-Signature: header naming the domain (d=) and the selector (s=).
  4. The receiver fetches the key, recomputes the hash, and either verifies the signature or does not.
selector1._domainkey.example.com.  IN  TXT  "v=DKIM1; k=rsa; t=s; p=MIIBIjANBgkqhki…"

DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=example.com; s=selector1;
    h=from:to:subject:date:message-id; bh=Wm9…=; b=Hs4…=
Tag Where Meaning
d= signature The signing domain. This is what DMARC compares to your From:. If it says your provider's domain instead of yours, DKIM passes but DMARC still fails.
s= signature Selector — tells the receiver which DNS record holds the key.
h= signature Which headers were signed. Should include at least from, and ideally subject, date, to.
bh= / b= signature Body hash and the signature itself. Change one byte of the body and bh no longer matches.
c= signature Canonicalisation, e.g. relaxed/relaxed — tolerates trivial whitespace rewrites in transit. simple/simple is brittle.
p= DNS The public key. An empty p= means “this key is revoked”.
t=s DNS Strict: the key may not be used by subdomains. Optional.
t=y DNS Test mode: “ignore my failures”. Great for a week, dangerous for a year — remove it when you go live.

Practical rules

🛡️ DMARC — the part that actually protects people

DMARC (RFC 7489) adds the missing question: does the domain that passed SPF or DKIM match the domain your reader sees in the From line? Then it publishes what to do when the answer is no, and asks receivers to report back.

Alignment — read this twice

A message passes DMARC if at least one of these is true:

SPF alignment

SPF passed and the envelope domain matches the From: domain.

MAIL FROM: bounce@example.com
From: sales@example.com

DKIM alignment

A DKIM signature verified and its d= matches the From: domain.

d=example.com
From: sales@example.com

The classic failure

Your newsletter tool signs and bounces with its own domain. Both SPF and DKIM pass — and DMARC still fails, because neither matches what the reader sees.

d=mailtool.net · MAIL FROM: mailtool.net
From: news@example.com

Relaxed vs strict: by default (adkim=r, aspf=r) a subdomain counts as a match — mail.example.com aligns with example.com. With adkim=s / aspf=s the domains must be identical. Start relaxed; strict is for organisations that have finished the job.

Every DMARC tag

Tag Values What it does
v DMARC1 Required, must be first.
p none · quarantine · reject Required, must be second. Monitor only / send to junk / refuse at the door.
sp same values Policy for subdomains. If you omit it, subdomains inherit p. Set it explicitly — attackers love invoices.yourdomain.com.
rua mailto:… Where daily aggregate XML reports go. This is the useful one.
ruf mailto:… Forensic/failure reports — copies of failing messages. Few providers send them, and they can contain personal data. Think before enabling.
fo 0 · 1 · d · s When to generate failure reports. fo=1 = any underlying failure, the most informative.
pct 1100 Apply the policy to only this share of failing mail — your safety valve when ramping up. Ignored at p=none.
adkim / aspf r · s Relaxed or strict alignment, as above.
ri seconds Requested aggregate report interval; 86400 (daily) is the only value anyone honours.

Reading an aggregate report without crying

Reports arrive as gzipped XML, once a day, from every large receiver. Each <record> is one sending IP over one day, and tells you: how many messages, whether SPF and DKIM passed, whether they aligned, and what the receiver did about it. Your job is to put every source into one of four buckets:

1. Mine, and alignedLeave it alone.
2. Mine, but failingThe work. Fix alignment before enforcing.
3. Forwarders & listsBroken SPF, intact DKIM. Usually acceptable collateral.
4. Not mine at allSpoofers. Exactly who you are blocking.

Free and paid analysers turn that XML into a dashboard. If you prefer to keep it in-house, a shared mailbox plus a parser is enough — but do not point rua at a personal inbox and then never look at it. An unread report is the same as no report.

External reporting addresses need permission. If rua points at a different domain than the one being reported on, that domain must publish an authorisation record such as example.com._report._dmarc.reporter.net TXT "v=DMARC1", or the reports are silently never sent. This trips up almost everyone using a third-party analyser.

🧩 The rest of the family

SPF, DKIM and DMARC are the core. These are the records that surround them — worth knowing, mostly worth doing, none of them a substitute for the big three.

BIMI

Puts your logo next to your mail in supporting clients. Requires DMARC at quarantine or reject first, an SVG Tiny PS logo, and for Gmail/Apple a paid Verified Mark Certificate.

Marketing reward for doing DMARC properly. Not a security control.

MTA-STS

A policy file at https://mta-sts.<domain>/.well-known/mta-sts.txt plus a _mta-sts TXT record, telling senders “always use TLS to reach me, and here are my valid MX hosts”. Stops downgrade and interception attacks on incoming mail.

Protects delivery in transit, not identity.

TLS-RPT

_smtp._tls TXT record asking senders to report failed TLS connections to you. The companion to MTA-STS: without it you never learn the policy is broken.

Cheap, zero risk, do it with MTA-STS.

ARC

Authenticated Received Chain. Lets a forwarder or mailing list record “this passed authentication when I got it”, so the final receiver can forgive a broken SPF/DKIM. You do not configure it; your provider either supports it or does not.

The reason p=reject is survivable in 2026.

Reverse DNS (PTR)

If you run your own mail server, its IP must resolve back to a hostname that resolves forward to the same IP, and the HELO/EHLO name should match. Missing PTR is an instant reputation penalty.

Only relevant if you operate your own MTA.

Null MX

For a domain that receives no mail: MX 0 ".". Senders fail immediately and cleanly instead of queueing for days.

Pair with v=spf1 -all on parked domains.

DNSSEC

Signs your DNS zone. Without it, every record on this page can in principle be forged in transit by an attacker who can tamper with DNS answers.

Foundation. Enable it at your registrar if supported.

DANE / TLSA

Pins your mail server's certificate in DNSSEC-signed DNS. Stronger than MTA-STS, but requires DNSSEC and is mostly used by mail-heavy operators in Europe.

Advanced. Skip unless you run the server.

Bulk-sender rules

Since Feb 2024 Gmail and Yahoo require bulk senders to have SPF, DKIM and DMARC, one-click List-Unsubscribe, and a spam-complaint rate under 0.3%. Microsoft followed in 2025.

DMARC is no longer optional if you send newsletters.

🪜 The step-by-step plan

Ten steps, in this order. The order matters more than the speed: every step exists to make the next one safe. A small organisation can do this in a month; a large one should budget a quarter. Nobody should do it in an afternoon.

  1. 0 Take stock before you touch anything

    Goal — know every system on earth that sends mail using your domain.

    Do: Get administrative access to your DNS zone and to every mail platform. Then write the list: mailbox provider, newsletter tool, CRM, invoicing/ERP, ticketing/helpdesk, e-commerce platform, HR and payroll, appointment reminders, website contact forms, monitoring and backup alerts, the scanner in the corridor that emails PDFs, and anything a department signed up for on a credit card.

    Verify: ask Finance, Marketing, HR and IT separately — they will each name a tool the others forgot. Read your current SPF record for stale include: lines.

    Risk if skipped: you will discover the forgotten sender on the day you switch to enforcement, and the thing that stops working will be payroll or invoices.

  2. 1 Publish SPF — gently

    Goal — one correct SPF record that fails soft.

    Do: create a single TXT record on the domain apex listing every provider from step 0, ending in ~all. Use the record builder below. Prefer include: tokens from your vendor's documentation over hand-typed IP addresses.

    Verify: exactly one record starts with v=spf1; the recursive lookup count is ≤10; a test message shows spf=pass in Authentication-Results.

    Wait: one TTL (lower the TTL to 300 s a day before you make changes, then raise it again afterwards).

    Risks: two SPF records or >10 lookups → permerror and SPF is effectively off; going straight to -all with an incomplete list → legitimate mail rejected immediately; using mx out of habit authorises your inbound servers, which is not what you meant.

  3. 2 Turn on DKIM on every platform

    Goal — every legitimate message carries a signature with d=yourdomain.

    Do: in each platform, enable DKIM / “authenticate your domain” / “branded sending”. It will give you either a TXT record or one or more CNAMEs. Publish them, wait, then press the platform's “verify” button, then enable signing.

    Verify: send a test to a Gmail address and to a Microsoft 365 address; the header must show dkim=pass and header.d=yourdomain.com. If d= shows the vendor's domain, you have enabled their shared signing, not yours — find the “custom/branded domain” setting.

    Wait: propagation, typically minutes to a few hours.

    Risks: enabling signing before DNS resolves → every message fails DKIM; leaving t=y test mode on forever; 1024-bit keys where 2048 was available; forgetting one platform, which then becomes the thing that breaks at step 6.

  4. 3 Publish DMARC in monitor mode — today

    Goal — start collecting evidence. Nothing changes for anyone.

    Do: add a TXT record at _dmarc.yourdomain.com:

    v=DMARC1; p=none; rua=mailto:[email protected]; fo=1;

    Verify: the record resolves; the mailbox exists and is monitored; reports start arriving within 24–72 hours.

    Risk: essentially zero — p=none changes no delivery decision. The only real mistakes are pointing rua at a mailbox nobody reads, or at an external analyser without its authorisation record (see the DMARC section), so the reports never arrive at all.

  5. 4 Read reports for two to four weeks

    Goal — a complete inventory of who sends as you, from the data rather than from memory.

    Do: feed the XML into an analyser (or a spreadsheet). Sort every source IP into the four buckets from the DMARC section. Chase down every unknown source until you can name it.

    Verify: you can account for >98% of your volume, and the remainder is low-volume noise you have consciously decided to ignore.

    Wait: at least one full monthly cycle if you have monthly processes — invoicing, payroll and annual renewals only show up when they run.

    Risk of hurrying: a sender that only fires once a month is invisible in a two-week window, and you will block your own invoices in step 7.

  6. 5 Fix alignment for everything legitimate

    Goal — every source in bucket 2 either aligns or is retired.

    Do: for each failing-but-legitimate source, one of:

    • Enable the vendor's custom DKIM domain so d= becomes yours.
    • Configure a custom return-path / bounce subdomain (e.g. bounce.yourdomain.com) so SPF aligns too.
    • Move bulk or transactional mail to a dedicated subdomain (news.yourdomain.com, billing.yourdomain.com) — this isolates reputation and makes each stream easy to reason about.
    • Stop the sender: the abandoned trial account from three years ago should simply be turned off and removed from SPF.

    Verify: the source appears as aligned in the next aggregate report.

    Risk: this is where projects stall for a year. Assign an owner per sender with a date, or nothing will move.

  7. 6 Ramp to quarantine

    Goal — failing mail goes to junk instead of the inbox, gradually.

    Do: tighten SPF from ~all to -all first, then step the DMARC policy over two to four weeks:

    v=DMARC1; p=quarantine; pct=25; rua=mailto:[email protected]; fo=1;
    … then pct=50 … then pct=100

    Verify: after each increase, check reports and your helpdesk queue for two to three days before increasing again.

    Tell people first: warn IT support and department heads that some mail may land in junk, and give them a single place to report it.

    Risks: legitimate mail junked (recoverable — the user can still find it); auto-forwarded mail failing SPF but usually saved by DKIM or ARC; mailing lists that rewrite subjects breaking DKIM. pct is your dimmer switch — use it.

  8. 7 Go to reject

    Goal — nobody can send mail as your domain. This is the actual protection.

    v=DMARC1; p=reject; sp=reject; rua=mailto:[email protected]; fo=1;

    Do: move to p=reject once a full reporting cycle at quarantine; pct=100 is clean. Set sp=reject explicitly. Consider adkim=s; aspf=s only if every stream is exactly aligned.

    Verify: reports show near-zero failures from your own sources; spoofed traffic now shows disposition reject.

    Risks: failing mail is now bounced, not junked — unrecoverable. A newly onboarded vendor added after step 4 will break loudly. Some old-fashioned mailing lists will mangle messages beyond DKIM's tolerance; the mature ones rewrite the From address to their own domain precisely to avoid this.

    Have a rollback ready: dropping back to p=quarantine is one DNS edit plus a TTL. Keep the TTL low during the ramp.

  9. 8 Lock down every domain that does not send mail

    Goal — parked, legacy and typo-defence domains cannot be abused either.

    Do: on each non-sending domain publish:

    @                 TXT  "v=spf1 -all"
    _dmarc            TXT  "v=DMARC1; p=reject; sp=reject; rua=mailto:[email protected];"
    *._domainkey      TXT  "v=DKIM1; p="
    @                 MX   0 .

    Verify: a test message from an external tool to that domain is refused, and the records resolve.

    Risk if skipped: forgotten domains are the favourite launch pad for invoice fraud, because they still carry your brand name. Also remember the domains you bought defensively and never configured.

  10. 9 Harden the transport and the brand

    Goal — the surrounding controls, now that identity is solved.

    Do: enable DNSSEC at the registrar; publish MTA-STS in testing mode plus TLS-RPT, then move MTA-STS to enforce; fix reverse DNS if you run your own server; add BIMI if the marketing value justifies a VMC. Add List-Unsubscribe and one-click support to all bulk mail.

    Risk: MTA-STS in enforce with a wrong MX list will make incoming mail fail. Always run it in testing first and read the TLS reports.

  11. 10 Keep it alive

    Goal — the configuration decays without maintenance.

    • Quarterly: re-count SPF lookups, remove includes for vendors you have left, review who reads the reports.
    • Every 6–12 months: rotate DKIM keys.
    • On every new vendor: SPF include + DKIM + a test before the first campaign, not after.
    • Continuously: alert on a sudden spike of DMARC failures — it is either your own change or an active phishing campaign, and you want to know which within hours.
    • Watch for lookalikes: newly registered domains resembling yours are the early warning of a targeted campaign.

    Risk if skipped: silent drift. The record still says p=reject, but a stale include pushed you past ten lookups six months ago and SPF has been in permerror ever since.

🧱 Record builder

Tick what you use and copy the records out. Everything is computed locally — nothing is sent anywhere. Always cross-check the include: value against your provider's own documentation before publishing; vendors do change them.

Who sends mail as you?
How far along are you?

🔬 Record inspector

Paste an SPF, DMARC, DKIM, BIMI or MTA-STS record and get it back in plain English, with the problems flagged. Parsing happens in your browser.

Optional: look a real domain up over the network opt-in

This is the only feature on the page that leaves your browser. When you press the button, the domain name you type is sent to a public DNS-over-HTTPS resolver (Cloudflare, falling back to Google) to read its public TXT records. Nothing else is transmitted, and nothing happens automatically. Some corporate networks block DNS-over-HTTPS entirely — if the lookup fails, that is usually why.

⚠️ What can go wrong — and what it looks like

Almost every email authentication outage in the world is one of these. The symptom is what a user reports; the cause is what you will actually find.

Symptom Cause Fix
All outbound mail suddenly rejected after a DNS change -all published with an incomplete sender list, or a typo in an include: Revert to ~all immediately, fix the list, re-test, re-tighten
SPF reported as permerror; receivers behave as if you have no SPF More than 10 DNS lookups, or two v=spf1 records on one name Merge records; drop unused includes; replace mx/a with ip4:; last resort, flatten
Marketing mail lands in junk while normal mail is fine The bulk platform signs with its own d= — DMARC-unaligned Enable the vendor's custom DKIM domain and custom return-path
DKIM fails on every message right after enabling it Signing switched on before the DNS key propagated, or the key was truncated by the DNS panel Re-check the record character-for-character; long values must be split into ≤255-char quoted strings
Mail fails only when a recipient forwards it SPF cannot survive forwarding; the forwarder is not the authorised sender Nothing to fix — this is why DKIM alignment and ARC exist. Do not weaken your policy for it
Mailing-list posts bounce after p=reject The list edits the subject or appends a footer, invalidating DKIM Ask the list to enable From-rewriting or ARC; or post from a subdomain with a looser policy
No DMARC reports ever arrive rua is on a different domain without the _report._dmarc authorisation record — or the mailbox does not exist Publish the authorisation record on the reporting domain; verify the mailbox accepts mail
Everything passes, yet fraud still happens Display-name spoof, lookalike domain, or a compromised real mailbox DMARC cannot help here — see the what-if section. Training and out-of-band verification are the controls
A subdomain is being spoofed although the apex is at p=reject An explicit sp=none, or a separate DMARC record on the subdomain that overrides the parent Set sp=reject; audit for stray _dmarc records on subdomains
Personal data ends up in a third party's system ruf= forensic reports contain message content; rua pointed at an external analyser Treat this as a processing decision: check your privacy notice and DPA before enabling ruf
Spoofing resumes months after the project “finished” A new vendor was added to SPF, pushing lookups past 10 — SPF silently died Quarterly audit; automated monitoring of the record's lookup count
Someone else's mail is signed as you A leaked or shared DKIM private key, or a hosting provider's shared signing domain Rotate the key, revoke the old selector with an empty p=, review who has platform admin
+all found in the record Copy-pasted from a bad tutorial, or a “fix” for a delivery problem Remove it now. It authorises the entire internet to send as you
Incoming mail stops after enabling MTA-STS The policy file lists the wrong MX hosts, or the certificate does not match Set mode: testing, read TLS-RPT, only then move to enforce
Changes take a day to appear A long TTL, or resolvers caching an NXDOMAIN Lower the TTL to 300 s before a change window; raise it again afterwards
An old domain you forgot about is sending invoices A parked or expired-project domain with no SPF/DMARC at all Step 8 — lock every non-sending domain down

🚨 What if… someone is spoofing you

A customer forwards you an email. It has your logo, your signature and your name — and a bank account that is not yours. Here is how to tell what actually happened and what to do about it, in order.

First: which of these five is it?

They look identical to a victim, and they need completely different responses.

1 Exact-domain forgery

From: [email protected] — genuinely your domain, not sent by you.

Tell-tale: dmarc=fail or spf=fail in the headers; the sending IP is unknown to you; it appears in your DMARC reports as an unaligned source.

You can stop this completely. DMARC at p=reject makes it undeliverable to every serious mail provider.

2 Display-name spoof

From: "Your Company Billing" <[email protected]>

Tell-tale: everything authenticates — for gmail.com. Phones show only the friendly name, which is why this works so well.

DMARC cannot help. Mitigations: an external-sender banner, an inbound rule flagging your own executives' names arriving from outside, and training.

3 Lookalike / cousin domain

yourdornain.com, your-domain.com, yourdomain.co, yourdomain-invoices.com

Tell-tale: perfect authentication for a domain registered eleven days ago. Check the registration date.

DMARC cannot help — it is not your domain. Response: registrar abuse report, hosting abuse report, blocklist submissions, and an inbound filter rule for near-miss variants of your name.

4 Reply-To hijack

A real-looking From: with Reply-To: [email protected].

Tell-tale: the reply address only becomes visible when you press Reply. Often combined with types 2 and 3.

Mitigation: a rule that flags a Reply-To whose domain differs from From, plus the habit of checking before answering anything about money.

5 A genuinely compromised mailbox

The mail really was sent from your account. SPF, DKIM and DMARC all pass, because it is authentic.

Tell-tale: the message appears (or suspiciously does not appear) in Sent Items; unfamiliar sign-in locations; a hidden inbox rule moving replies to RSS Feeds or Deleted Items; a mail thread that quotes real internal history.

The worst case, and the most common in real fraud. Treat it as an active incident, not an email problem — go to the account recovery steps below.

Answer four questions

The runbook

0–60 min Confirm and contain

  1. Get the raw message, not a screenshot. Ask the recipient to forward it as an attachment (or to send you “show original” / “view source”). Headers are the only evidence that matters; screenshots prove nothing.
  2. Read Authentication-Results and the From, Return-Path and Reply-To fields. That determines which of the five types you have. Paste it into the header analyzer if you want it decoded.
  3. Rule out a compromised account first. Check sign-in logs for impossible travel and for legacy protocols, look in Sent Items and Deleted Items, and — critically — look for mailbox rules you did not create. Auto-forwarding to an external address and “move anything containing invoice to RSS Feeds” are the two classic fingerprints.
  4. If compromised: reset the password, revoke all active sessions and refresh tokens (a password reset alone does not log the attacker out), remove the rogue rules and forwarders, review connected OAuth apps and app passwords, re-register MFA, and check whether any other accounts share that password.
  5. Preserve evidence before deleting anything: export the message with full headers, take copies of the mailbox rules and sign-in logs, note timestamps in UTC.
  6. If money has moved, call the bank immediately — the first hours decide whether a recall is possible.

1–4 hours Shut the door

  1. Type 1 (your domain forged): check your DMARC record right now. If it is p=none, this is the moment the risk calculus changes — move to quarantine at minimum, and to reject if your reports are clean. If you have no DMARC at all, publish p=none with rua today and start the ramp.
  2. Type 3 (lookalike): record the domain, its registrar, its DNS host and the IP of any phishing page. Then file abuse reports with all of them; include full headers and a timestamp. A phishing site hosted at a mainstream provider is often gone within hours.
  3. Block inbound: add the lookalike domain and the sending IPs to your own mail filter, and add a rule flagging external mail that uses your executives' display names.
  4. Submit the URL to Google Safe Browsing, Microsoft's report page, Netcraft and the APWG so browsers start warning users.
  5. Check whether more than one person received it — a message trace across the organisation tells you whether this is a broad campaign or a targeted one.

Same day Tell people, in plain words

  1. Internally: what the fake looks like, what to do if they receive it (report, do not reply, do not pay), and who to call. Include a real screenshot.
  2. To customers and suppliers, if they were targeted: a short, calm notice. Something like — “Emails are circulating that appear to come from us and ask for payment to a new account. We never change our bank details by email. Please verify any payment request by phoning the number on our website.” Do not over-explain the technical details, and do not imply a breach if there was none.
  3. Publish it on your website and, if relevant, on your social channels — people who search for “is this email from you real?” must find your answer.
  4. Warn the specific people who were being impersonated; they will get the phone calls.

This week Report, review, harden

  1. Report it. Where fraud occurred, to the police; in the EU also to your national CERT/CSIRT. If personal data was accessed, a compromised mailbox is very likely a notifiable data breach — involve your DPO and mind the 72-hour clock under the GDPR.
  2. Finish the DMARC ramp. Nothing else you do this week reduces future risk as much.
  3. Fix the process, not just the mail. Bank-detail changes must require a call-back to a number already on file. Payments above a threshold need two people. These controls stop the fraud even when the email is perfect.
  4. Consider defensive registrations of the two or three most convincing lookalikes, and set up monitoring for newly registered similar domains.
  5. Write it down. A one-page after-action note — timeline, what worked, what was missing — is worth more than the incident cost.

The honest limit: you cannot stop a stranger from typing your name into a From field, registering a similar domain, or writing a convincing letter. What you can do is make your real domain impossible to forge, make lookalikes short-lived, and make sure that no single email can move money. Everything above serves one of those three.

🔎 Recognising a fake — the one-page version

Hand this part to colleagues. No jargon required.

Six checks, in order of speed

  1. Expand the sender. Tap the name to reveal the actual address. “Accounts Payable” is not an address. Phones hide it by default — that is the point.
  2. Read the domain right-to-left. The real domain is the bit just before the first single slash: yourbank.com.secure-login.xyz/… is secure-login.xyz. Look for swapped letters (rn/m, l/I, 0/O) and extra hyphens.
  3. Press Reply and look where it goes — then press Discard. A different reply domain is a red flag on its own.
  4. Hover every link (long-press on mobile) and read the real destination before clicking. Do the same for QR codes — photograph, decode, read.
  5. Ask what it wants. Urgency + money or credentials + secrecy + a new channel (“don't call, just reply here”) is the universal fraud signature.
  6. Check the story out-of-band. Call the person on a number you already have. Never on a number from the email.

Reading the technical verdict

In Gmail: ⋮ → Show original. In Outlook: File → Properties, or open the message and use … → View → View message source. Look for one line:

Authentication-Results: mx.example.net;
   spf=pass smtp.mailfrom=sender.com;
   dkim=pass header.d=sender.com;
   dmarc=pass header.from=sender.com
  • dmarc=pass means only that the message really came from the domain shown. It does not mean the domain is trustworthy — spammers pass DMARC on their own domains all day long.
  • dmarc=fail on a message claiming to be from a big brand is close to proof of forgery.
  • No Authentication-Results at all usually means the message never left your own organisation — or that you are looking at a header the attacker wrote.
  • Compare header.from with smtp.mailfrom and header.d. Three different domains deserve suspicion.

Never trust these as proof: a logo, a real signature block, a padlock on the linked site, a correct invoice number, or the fact that the message is a reply inside a real thread. All of them are copied or stolen routinely.

If you already clicked or paid: disconnect nothing in a panic — instead, in this order: change the password from a different device, revoke sessions, tell IT or your manager immediately (there is no shame; speed is everything), call the bank, and keep the email. Reporting fast is what makes recovery possible.

The working checklist

Ticks are stored in this browser only, so you can close the tab and come back.

0 / 0

📖 Glossary

Alignment
The requirement that the domain which passed SPF or DKIM matches the domain in the visible From:. Without it, SPF and DKIM prove nothing to a reader.
ARC
Authenticated Received Chain — a forwarder's signed statement that authentication passed before it handled the message.
Backscatter
Bounce messages you receive for mail you never sent, because a spoofer used your address as the envelope sender. A symptom, not an attack on you directly.
BEC
Business Email Compromise — fraud driven by impersonating or hijacking a colleague, supplier or executive. Usually no malware at all.
BIMI
Brand Indicators for Message Identification — your logo shown beside authenticated mail. Requires DMARC enforcement.
Cousin domain
A lookalike domain registered to resemble yours. Outside DMARC's reach.
Disposition
What a receiver actually did with a failing message: none, quarantine or reject. Shown in DMARC reports.
Envelope sender
The MAIL FROM address used during the SMTP conversation; where bounces go. Checked by SPF, invisible to readers.
Flattening
Replacing include: with the IP addresses they currently resolve to, to stay under the 10-lookup limit. Works, but you now own a list that your provider will change without telling you.
HELO / EHLO
The hostname a sending server announces itself with. Should be a real name that matches its reverse DNS.
MTA
Mail Transfer Agent — the server software that moves mail between organisations.
Permerror
An SPF record that cannot be evaluated (too many lookups, syntax error, duplicate record). Most receivers treat it as no SPF at all.
Return-Path
The envelope sender as recorded in the delivered message.
Selector
The label that picks which DKIM public key to fetch, e.g. selector1 in selector1._domainkey.example.com.
Softfail
~all — “this probably isn't us, but accept it anyway”. The safe intermediate state.
Subdomain policy
sp= in DMARC. Governs everything under your domain, which is where attackers go when the apex is locked.
TTL
How long resolvers may cache a DNS answer. Lower it before a change, raise it afterwards.
VMC
Verified Mark Certificate — the paid attestation of your trademarked logo required by Gmail and Apple for BIMI.

💬 Questions people actually ask

Do I need all three, or is SPF enough?

All three. SPF alone validates an address nobody sees and breaks on forwarding. DKIM alone proves integrity but tells receivers nothing about what to do when it fails. DMARC is what connects either of them to the visible From: and states a policy. One or two out of three is a very common configuration and it stops approximately no fraud.

Will DMARC hurt my deliverability?

Done properly, the opposite: aligned, authenticated mail is treated better everywhere, and Gmail, Yahoo and Microsoft now require it from bulk senders. Done in a hurry — jumping to p=reject before fixing alignment — it will absolutely bounce your own mail. The ramp exists for a reason.

Can I just use -all and skip DMARC?

No. -all constrains the envelope only. An attacker simply uses their own domain in the envelope — SPF passes for that domain — and puts yours in the header. Nothing in SPF looks at the header.

How long does the whole thing take?

The DNS edits take an afternoon. The discovery takes weeks, because you have to see a full business cycle of your own mail in the reports. Small organisation: 4–6 weeks. Enterprise with dozens of senders: a quarter or more. Rushing does not compress the discovery — it just moves the discovery to the day you break something.

What about my subdomains?

They inherit p unless you set sp, and a DMARC record published directly on a subdomain overrides everything the parent says. Audit for stray _dmarc records, set sp=reject explicitly, and give bulk mail its own subdomain so its reputation stays away from your invoices.

My provider says I do not need DKIM because they sign for me.

Then check the d= value on a real message. If it is their domain, DMARC does not align and their signature protects their reputation, not yours. Ask for custom/branded domain signing — every serious platform offers it.

Do these records cost anything?

The records themselves are free — they are DNS entries. Report analysis tools cost money above a free tier, and a BIMI VMC is a genuine annual expense. Nothing about SPF, DKIM or DMARC itself requires a purchase.

We are a two-person company. Is this overkill?

Small companies are the preferred target for invoice fraud, precisely because they have no policy and no verification procedure. For you the entire job is roughly: turn on DKIM in your mail provider, publish two DNS records, and agree out loud that bank details are never changed by email. That is an hour of work against the most common financial crime you will face.

📚 Where this comes from

The specifications, if you want the primary sources: RFC 7208 (SPF), RFC 6376 (DKIM), RFC 7489 (DMARC), RFC 8617 (ARC), RFC 8461 (MTA-STS), RFC 8460 (TLS-RPT), RFC 7505 (Null MX), RFC 5321/5322 (SMTP and the message format). Vendor include: values and DKIM selectors change over time — always confirm them in your provider's current documentation rather than in any guide, including this one.