Fix missing SPF result for mail relayed through the wg-box edge #18
Labels
No labels
blocked
borg-backup
ceph
forgejo
in-progress
infra
netdata
nextcloud
p:high
p:low
p:medium
searxng
service-onboard
swarm-nodes
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set.
Reference
copper/ccnet-prod-devops#18
Loading…
Add table
Add a link
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Mailcow's WHITELISTED_FWD_HOST exemption for 172.30.0.1 (added to fix RDNS_NONE/HFILTER_HOSTNAME_UNKNOWN false positives on relayed inbound mail) suppresses rspamd's whole 'policies' rule group, which includes SPF -- so inbound mail via the wg-box edge relay no longer shows an spf= result in Authentication-Results at all, rather than evaluating SPF correctly against the real original sender IP.
Root cause: Postfix's XFORWARD command (sent by the wg-box to mailcow to preserve the real client IP) updates the Received: header trail correctly, but rspamd's SPF module still evaluates against the literal TCP peer (172.30.0.1, the wg-box itself) rather than the XFORWARD-updated address -- confirmed via header inspection during the notify.coppercore.net real-world test (see ccnet-mailcow-vm-runbook and the mail migration plan for full context).
Not a security hole -- DKIM/DMARC (the stronger modern signals) still evaluate and score correctly, and this doesn't create a bypass since WHITELISTED_FWD_HOST intentionally leaves KEEP_SPAM unset (spam filtering stays active). Just an accuracy gap worth closing eventually: find the correct Postfix/rspamd config to have the milter macros rspamd reads for its SPF check reflect the XFORWARD-updated client address, rather than suppressing the check entirely.
Investigated 2026-07-14 — root cause confirmed, real fix identified, still deferred (p:low, not a security issue).
Confirmed live via rspamd logs on
ccnet-wv-mailcow(mailcowdockerized-rspamd-mailcow-1): for mail relayed through the wg-box (172.30.0.1), rspamd's task-levelipis172.30.0.1and noR_SPF_*symbol is produced at all, e.g.:Why the "obvious" fixes are already in place and still don't help:
172.30.0.1(smtpd_authorized_xforward_hosts = 172.30.0.1in bothmain.cfandextra.cf){client_addr}macro to rspamd at MAIL FROM stage (milter_mail_macros = i {mail_addr} {client_addr} {client_name} {auth_authen})ipat the milter CONNECT callback — before XFORWARD is even processed — and never re-derives it from the later MAIL-stage macro refresh. This is an rspamd behavior/limitation, not a config gap on our side.Why a narrower composite tweak would make things worse, not better:
WHITELISTED_FWD_HOST/WL_FWD_HOSTin mailcow's stockcomposites.confblanket-disables the wholepoliciessymbol group (SPF included) for known forwarders. That's deliberate: since rspamd genuinely can't see the real sender IP at that hop, letting SPF run un-suppressed would evaluate against172.30.0.1and produce a falsespf=failfor every legitimate sender — strictly worse than the current "no result" state.The real fix, when we pick this back up: ARC-seal at the wg-box.
The wg-box's own local rspamd (
smtpd_milters = inet:127.0.0.1:11332onccnet-wireguard-ub-caddy-2gb-ash-1, currently a vanilla/stock install —local.d/is empty except a greylist override) is the actual first-touch MX listener and does see the true client IP, so its own SPF/DKIM/DMARC evaluation there is already correct. Mailcow's rspamd already validates incoming ARC chains (ARC_SIGNED/ARC_NAsymbols observed scoring on real mail today), so the standards-based fix is:relay._domainkey.coppercore.netor similar — not mailcow's existings=dkimselector).local.d/arc.confon the wg-box enabling ARC sealing for mail passing through that relay hop (keyed by trusted network/relay identity, not by the original sender's envelope-from domain — each ARC hop seals as itself, per spec).ARC-Authentication-Resultscarrying the correctspf=/dkim=/dmarc=from the wg-box hop, and (optionally) narrowWL_FWD_HOSTto only suppress the native (wrong) policies recompute when there's no valid ARC chain backing it (i.e. add!ARC_ALLOWor equivalent to the composite condition).This mirrors the pattern mailcow itself already uses for its own outbound DKIM signing — same idea, one hop earlier, on a box with no existing DNS/key material for it yet.
Not picking this up right now (still
p:low, still not a security issue — DKIM/DMARC score correctly andKEEP_SPAMstays active either way). Leaving this comment so the investigation doesn't need to be redone next time this is revisited.