那行紅字寫著「DKIM 失敗」,但信明明就送到了——我自己也是查到一半才搞懂
為保護客戶隱私,本文所有網域、公司名稱、IP 均已替換為示意用的範例資料,但技術邏輯跟我實際查的案例完全一樣。
前陣子處理一個案件,客戶寄了一封行銷信給自己公司內部測試用的信箱,結果一打開信件詳細資訊,看到這幾行:
dkim = fail(驗證失敗)
spf = softfail(部分失敗)
老實說,我第一個反應跟客戶一樣:「啊,是不是哪裡設定壞了?」DKIM 這東西,你可以理解成寄信的時候蓋的一個「防偽章」,收信端會檢查這個章有沒有被動過。Fail,直覺上就是「東西被改了、有問題」。
我一開始的猜測,跟大部分人應該也差不多:客戶寄信端自己裝了什麼防護設備,把信改壞了。 畢竟之前確實有遇過類似情況,聽起來合理。
問題是,客戶後來補了完整的 header 給我,我一行一行看下去,才發現我猜的方向根本是反的。
我把信的「旅程」攤開來看
Email header 其實會留下信件經過每一站的紀錄,只是平常沒人會去翻。我把這次的攤開來看,大概是這樣的路徑(網域跟 IP 我都換成範例了):
寄信平台 (mail01.region.platformdomain.com)
↓
某個安全閘道 (gateway1.secvendor-cloud.com)
↓
收件人的信箱系統 (recipient-mailprovider.com)
看到中間那個「安全閘道」的時候,我第一個念頭是:這應該是客戶寄信前自己加裝的防護設備吧?
結果再往下查才發現——不對,這個閘道根本不在寄信那一側,它是架在收件人信箱前面的東西。 因為這次收件人剛好也是客戶自己公司的內部信箱,所以同一家公司同時扮演了「寄信人」跟「收信人」兩個角色,我一開始完全沒注意到這個閘道其實是收信端的防護,不是寄信端的——這個地方我自己也是反覆對照了好幾次 Received 的順序才確定。
證據怎麼看?我自己對照了三段
第一段,信還在「安全閘道」手上的時候,閘道自己留的紀錄寫著:
Authentication-Results-Original: gateway1.secvendor-cloud.com;
spf=Pass ...; dmarc=pass (p=none dis=none) d=marketingbrand.com
翻成白話就是:「我(閘道)剛收到這封信的時候,檢查都過了,信是乾淨的。」
第二段,閘道把信轉交給最終的信箱系統:
Received: from gateway1.secvendor-cloud.com (203.0.113.45)
by mail-front.recipient-mailprovider.com ...
第三段,信箱系統收到信之後,自己重新驗證一次,這裡才開始出現失敗:
Authentication-Results: spf=softfail (sender IP is 203.0.113.45) ...;
dkim=fail (signature did not verify) header.d=marketingbrand.com;
dmarc=fail action=none ...;
compauth=pass reason=702
把這三段排在一起看,我才真的搞懂:信在閘道手上的時候還是好的,轉交出去之後才壞掉。 中間唯一動過手的就是這個閘道——而閘道之所以會「不小心」弄壞防偽章,通常是因為它在掃描信件時做了一些小動作(比如把信裡的連結改寫成自己的安全網址,方便事後追蹤),這種改動再小,對防偽章來說都算是「內容變了」,驗證就會失敗。不是攻擊,也不是誰沒設定好,單純是多一層安全防護必然會有的副作用。
我差點漏看的一行字
說真的,如果只看到 dkim=fail、spf=softfail 這兩行,我大概會直接跟客戶說「你們收信端的防護設備有問題」就結案了。但我多看了同一行的最後一段:
compauth=pass reason=702
查了一下才知道,compauth 才是 Outlook 真正拿來決定「這封信該進收件匣、還是丟進垃圾信」的依據——而它顯示 Pass。
也就是說,表面上 DKIM、SPF 都寫著失敗,但 Microsoft 自己真正的判斷邏輯根本沒把這封信當問題信,信乖乖地送到了該去的地方。客戶原本擔心的「DKIM 失敗→信被擋」,這個因果關係其實是不存在的——如果我沒多查這一行,大概就會把方向搞錯,告訴客戶一個聽起來合理但其實沒打到重點的結論。
後來我學到的事
我自己整理下來,大概是這幾件事:
- 看到驗證失敗,不代表信真的被擋了。 真正決定信件去哪裡的,是收信平台更完整的綜合判斷(像這次的
compauth),不是單一驗證項目的表面結果——這件事我自己以前也沒特別在意過。 - 只看最後一步的結果容易猜錯方向。 把每一站的紀錄串起來對照,才看得出問題到底發生在哪裡;我這次就是因為一開始只看了最後失敗的那一行,差點就把方向搞反了。
- 多一層安全防護,常常就是多一次驗證失敗的代價。 這是架構上很自然會發生的事,不是誰的錯。
- 業界其實有個機制叫 ARC,可以讓中間的閘道把「我這邊驗證過沒問題」的證明一起轉交出去,讓最後一站不用重新驗證——算是這次查完之後順手補的知識。
如果你也遇到類似的紅字,先別急著下結論——也許答案就藏在你還沒仔細看的那一行裡。我自己這次就是這樣才搞懂的。