Parse Email Headers Fast (hoptrace)
Turn jumbled headers into a readable hop trail with SPF/DKIM/DMARC snapshots — evidence only.
8/24/2025 • 2 min
Scenario: I’ve got messy headers and zero patience. I want the route, what changed, and what the receiver said about SPF/DKIM/DMARC — fast.
TL;DR
- Run it
python3 hoptrace.py message.eml
# or
cat headers.txt | python3 hoptrace.py -
-
Read the top block
AUTH (snapshot)
shows the latest SPF / DKIM / DMARC receivers reported.
DMARC rule: pass if SPF=pass & mfrom aligns with From, or DKIM=pass & d= aligns with From. -
Skim the hops
Look for+ DKIM added here
and per-hopauth:
lines to see where changes happened.
What This Is
A tiny, evidence-first header parser. It prints:
- AUTH (snapshot) — last reported SPF/DKIM/DMARC (no guessing)
- Path — hop count + final receiver (e.g., “Gmail mailbox” / “Microsoft 365 mailbox”)
- HOPS —
from → by
, with per-hopauth:
and “DKIM added here” markers
No verdicts. No DNS. Just the parts you actually need.
Why I Built It
I don’t like reading jumbled headers. Manually diffing Received:
lines and three flavors of Authentication-Results:
is slow. I wanted a quick, consistent readout that surfaces where things changed and what the receiver claimed so I can decide faster.
Quick use
# basic
python3 hoptrace.py message.eml
# show protocol/time columns
python3 hoptrace.py message.eml --proto
# JSON for tooling
python3 hoptrace.py message.eml --json | jq .
Example (what you’ll see)
hoptrace — evidence
AUTH (snapshot):
SPF: pass (mfrom=mail.n.convertkit.com)
DKIM: pass (d=n.convertkit.com,sendgrid.info)
DMARC: fail (from=random.com, p=none)
Path: 4 hops → final 2002:a05:…:be61 (Gmail mailbox)
HOPS (4):
1) MTI5NTYxNDE → geopod-ismtpd-26
2) geopod-ismtpd-26 → recvd-dfd74b7d5-8gmfn
+ DKIM added here: d=n.convertkit.com (s=s1)
+ DKIM added here: d=sendgrid.info (s=smtpapi)
3) o38.ck.n.convertkit.com → mx.google.com
auth: SPF=pass; DKIM=pass; DMARC=fail (mfrom=mail.n.convertkit.com) (d=n.convertkit.com,sendgrid.info) (from=random.com, p=none)
4) mx.google.com → 2002:a05:…:be61
Notes
- DKIM header present but
DKIM=unknown
? Receiver didn’t publish a DKIM result; hoptrace will say “header present” when it detects one. - No inbox/spam guesses. It only reports what receivers wrote.
- Headers-only input works (just keep one blank line before the body).