請求
# reserve a single-use address
$ curl -sX POST '.../api/v1/inbox?lang=en'
# send your message to that address, then
$ curl -s '.../api/v1/tests/k7m2x9qplw4tz8vn3b6c/status'
# read the report
$ curl -s '.../api/v1/tests/k7m2x9qplw4tz8vn3b6c'
回應
200 OK
{
"address": "test-k7m2x9qplw4tz8vn3b6c@t.email-spam-tester.com",
"slug": "k7m2x9qplw4tz8vn3b6c",
"expires_at": "2026-10-31T13:00:00Z"
}200 OK
{
"analysis_status": "checks_ready",
"ai_status": "running",
"checks_done": 42,
"checks_total": 42
}200 OK
{
"score_ours": 86.4,
"score_compat": 9.2,
"subscores": {"auth": 100.0, "infra_spam": 78.1, "content": 92.0},
"complete": true,
"checks": [{"id": "auth.dmarc", "status": "warn"}],
"fixes": [{"id": "dmarc-enforce", "gain_ours": 4.0}]
}請求
# create a test
$ curl -sX POST '.../api/v1/placement' \
-d '{"public_results_accepted":true}'
# put the marker in the subject, send once to all, then
$ curl -s '.../api/v1/placement/wR3kP9xLq2vT8mZc'
回應
201 Created
{
"marker": "est-3f9a1c7e2b4d6a80c5e1f2d3",
"status": "waiting",
"results": [{"provider": "gmail", "placement": "pending"}],
"fleet": {"status": "observing", "results": [
{"provider": "yahoo", "placement": "pending"},
{"provider": "outlook", "placement": "pending"}
]}
}200 OK
{
"status": "complete",
"results": [{"provider": "gmail", "placement": "primary"}],
"fleet": {"status": "finished", "results": [
{"provider": "yahoo", "placement": "inbox"},
{"provider": "outlook", "placement": "spam"}
]}
}請求
# no email needed, one GET
$ curl -s '.../api/v1/infra/check?domain=example.com'
# compare with your last run
$ curl -s '.../api/v1/infra/check?domain=example.com&diff=true' \
| jq '.diff'
回應
200 OK
{
"domain": "example.com",
"ok": false,
"status": "fail",
"score": 78,
"coverage": {"answered": 7, "total": 8},
"sections": {"ptr": {"status": "fail", "core": true}}
}200 OK
{
"changed": true,
"worsened": true,
"status_from": "pass",
"score_from": 100,
"changes": [{"path": "dkim.key.mail.sha256", "kind": "removed",
"severity": "critical", "effect": "worsened"}]
}本頁內容
電子郵件測試
我們會端到端檢查一封真實郵件:內容、簽章、標頭,以及傳送它的伺服器。你會取得評分、修正項目清單,以及其背後的每項檢查結果。
快速開始
三次呼叫。不需要金鑰、帳戶或註冊。 兩個請求和一封電子郵件。需要第三次呼叫只是因為分析需要幾秒鐘。
保留一個地址
向收件匣端點傳送 POST。你會取得一個只接受一封郵件且在一小時後到期的地址,以及其他所有項目用作索引的 slug。
請求
# 1. reserve a single-use address curl -sX POST 'https://email-spam-tester.com/api/v1/inbox?lang=en'回應
{ "address": "test-<slug>@t.email-spam-tester.com", "slug": "<slug>", "expires_at": "2026-01-01T12:00:00Z" }將實際郵件傳送到該地址
透過 SMTP,從將傳送行銷活動的平台寄出。半數檢查會讀取傳送平台新增的標頭,因此手動撰寫的郵件會測量到錯誤的項目。
請求
# 2. send your message to that address, from your own platform To: test-<slug>@t.email-spam-tester.com輪詢狀態,然後讀取報告
狀態端點的內容只有數百位元組,並會告知你是否已值得擷取完整報告。報告本身則有數千行。
請求
# 3. poll curl -s 'https://email-spam-tester.com/api/v1/tests/<slug>/status'回應
{ "slug": "<slug>", "analysis_status": "checks_ready", "ai_status": "running", "checks_done": 42, "checks_total": 42 }請求
# 4. read the report once analysis_status is checks_ready curl -s 'https://email-spam-tester.com/api/v1/tests/<slug>'回應
{ "report_url": "https://email-spam-tester.com/t/<slug>", "score_ours": 86.4, "score_compat": 9.2, "subscores": {"auth": 100.0, "infra_spam": 78.1, "content": 92.0, "compliance": 75.0}, "complete": true, "checks": [ { "id": "auth.dmarc", "status": "warn", "title": "DMARC result", "summary": "DMARC passes, but the policy is p=none.", "weight_ours": -4.0, "evidence": {"policy": "none", "aligned": "dkim"}, "citations": {"standards": [{"title": "RFC 9989 §4.7", "quote": "..."}]} } ], "fixes": [ {"id": "dmarc-enforce", "gain_ours": 4.0, "gain_compat": 0.0, "fix": {"title": "Move DMARC to quarantine", "severity": "medium"}} ] }
保留一個地址、傳送你原本要寄給名單的郵件,然後讀取報告。頁面顯示的所有內容都包含在 JSON 中,包括分數、全部 42 項檢查及其證據,以及每項發現所依據的標準章節。
前 100,000 份報告免費,不需要金鑰,也不需要帳戶。如果你要串接的是代理程式而非指令碼,MCP 伺服器會比輪詢更合適。
端點
基底位址為 https://email-spam-tester.com。所有回應皆為 JSON。
POST/api/v1/inbox
保留一個單次使用的地址。兩個參數皆為選填。
| lang | 修正計畫與各項檢查結果所使用的語言,以 ISO 代碼表示。現在就決定,因為郵件會在幾分鐘後透過 SMTP 抵達,且不會提供任何線索指出誰正在等候它。未知的代碼會退回使用英文。 |
| utm_source, utm_medium, utm_campaign | 傳遞至我們的分析系統。如果你要衡量自己的整合成效,這些參數會很有用。 |
GET/api/v1/tests/{slug}/status
輪詢成本低。只傳回兩個狀態欄位及檢查進度,不包含其他內容。
GET/api/v1/tests/{slug}
完整報告。地址已保留但尚未收到任何內容時回應 202,收到後則回應 200。
GET/api/v1/tests/{slug}/message
郵件送達時的原貌:依傳輸順序排列的每個標頭、兩種內文、附件清單及原始來源。由於報告會被輪詢,而此內容可能大到一 MB,因此需另行擷取。
PUT/api/v1/tests/{slug}/locale
變更尚未使用之預留項目的語言。適用於已要求提供地址後,才得知使用者閱讀哪種語言的代理程式。郵件抵達後會拒絕變更,因為屆時分析已在執行。
收件匣投遞位置測試版
將一封郵件傳送至一組測試收件匣,查看它在 Gmail、Outlook、Yahoo 和其他服務供應商中落入哪裡:收件匣、促銷內容或垃圾郵件。
快速開始
建立測試
向投遞位置端點發出 POST。你會收到一個標記和測試收件匣。
請求
# 1. create a test curl -sX POST 'https://email-spam-tester.com/api/v1/placement' \ -H 'Content-Type: application/json' \ -d '{"public_results_accepted":true}'回應
{ "slug": "<slug>", "marker": "est-3f9a1c7e2b4d6a80c5e1f2d3", "status": "waiting", "deadline": "2026-10-31T12:30:00Z", "poll_after_seconds": 60, "results": [ {"address": "<seed>", "provider": "gmail", "kind": "Gmail", "placement": "pending", "observed_at": null} ], "fleet": { "status": "observing", "results": [ {"address": "<mailbox>", "provider": "yahoo", "available": true, "placement": "pending", "coverage": "pending"} ] } }傳送一封郵件至每個收件匣
將標記放入主旨,並從你平常使用的平台一次傳送至所有地址。
請求
# 2. one message to every address, with the marker in the subject Subject: October invoice est-3f9a1c7e2b4d6a80c5e1f2d3 To: <seed>, <mailbox>, ...輪詢資料夾
每個地址都會填入其供應商和資料夾。持續輪詢,直到狀態不再是 waiting。
請求
# 3. poll for the folders curl -s 'https://email-spam-tester.com/api/v1/placement/<slug>'回應
{ "status": "complete", "received": 2, "total": 2, "results": [ {"address": "<seed>", "provider": "gmail", "kind": "Gmail", "placement": "primary", "observed_at": "2026-10-31T12:04:11Z"}, {"address": "<seed>", "provider": "gmail", "kind": "Google Workspace", "placement": "promotions", "observed_at": "2026-10-31T12:04:11Z"} ], "fleet": { "status": "finished", "results": [ {"address": "<mailbox>", "provider": "yahoo", "available": true, "placement": "inbox", "coverage": "ok"}, {"address": "<mailbox>", "provider": "outlook", "available": true, "placement": "spam", "coverage": "ok"} ] } }
端點
An optional test using public GMass seed inboxes and available project test mailboxes, alone or alongside the email score. Explain to the sender that GMass receives their email and publishes its subject, sender name and placement before creating a test. Use all test mailboxes for non-confidential test messages only.
GET /api/v1/placement/availability
Returns providers: the provider identifiers of currently healthy,
admitted project mailboxes. No addresses or credentials are exposed. This read does
not create a test or contact GMass. Actual recipients are allocated at creation and
may differ as availability or capacity changes.
POST /api/v1/placement
Send JSON {"public_results_accepted":true}. Returns HTTP 201 with
slug, marker, results (the seed addresses),
deadline and expires_at. Limit: 20 tests per IP per UTC day.
For one-send combined testing, first reserve an email score address and include
its score_slug in the placement creation JSON. Repeated creation for
that score returns the same placement test. Send the marked email to the score
address, every returned seed and every available fleet.results address;
keep the main /t/<score_slug>
report link. Creating a link after the score address was used or expired returns HTTP 409.
GET /api/v1/placement/by-score/{score_slug}
Read and refresh the placement run attached to the main email test. The response has the same format and polling limits as the standalone endpoint below. HTTP 404 means placement was not included or its stored results have been removed.
GET /api/v1/placement/{slug}
Use poll_after_seconds (normally 60 seconds) while the page is open.
Upstream errors trigger a shared cooldown. Add the marker to the subject and
send through the sender's normal platform to every seed. Observations are saved for
30 days. Collection ends after 30 minutes or when all seeds have results.
status: waiting, complete or timed_out. Each result has an address,
provider, kind, placement and observed_at. Placement is primary, promotions, inbox,
updates, social, forums, spam, unknown, pending or not_observed. Missing results do
not mean Spam; Promotions is an inbox category. provider_error indicates
an upstream outage without discarding saved observations. HTTP 404 means unknown,
410 expired, 429 quota exhausted, and 503 no test inboxes available at creation.
The optional fleet object contains independently collected project
mailbox results, with status observing, settling or finished. Refresh
every 30 seconds until it finishes, even when Gmail has completed. Each fleet result
includes address, provider, available,
placement, category and coverage. Exclude
unavailable addresses from new sends; retain their saved observations. Category
data may be unavailable even when the physical folder is known.
If GMass is unavailable at creation but project mailboxes can be allocated,
provider is fleet and the top-level seed results are empty.
Use fleet.results; do not interpret an empty Gmail list as successful
delivery. Existing runs never gain new recipient addresses silently.
基礎設施檢查
一次 GET 會在不傳送任何內容的情況下檢查網域的郵件設定、保留結果,並告訴你自上次執行後有哪些變更。不需要金鑰。在 cron 中,當網域損壞或其設定發生重要變更時,以下這一行會以非零值結束。
快速開始
發出一次 GET
傳入網域。ip 會加入你的寄件 IP 位址,selector 則指定要讀取的 DKIM selector。
請求
curl -s 'https://email-spam-tester.com/api/v1/infra/check?domain=example.com&selector=mail&diff=true'讀取判定結果
ok 是供指令碼使用的答案,而 sections 會顯示哪個部分失敗。
回應
{ "id": "ir_01JB8Y4T2M6K9QZ7H3V5N1XWDA", "domain": "example.com", "checked_at": "2026-10-31T12:00:00Z", "ok": false, "status": "fail", "score": 78, "coverage": {"answered": 7, "total": 8}, "ips": [{"ip": "203.0.113.5", "sources": ["mx", "spf"], "managed": false}], "sections": { "dkim": {"status": "pass", "core": true, "findings": [], "data": {}}, "ptr": {"status": "fail", "core": true, "findings": [], "data": {}} }, "not_checked": [ {"check": "dkim_signature", "reason": "needs_a_message"}, {"check": "alignment", "reason": "needs_a_message"} ], "diff": { "baseline": {"id": "ir_01JB2...", "checked_at": "2026-10-24T12:00:00Z"}, "first_run": false, "changed": true, "worsened": true, "status_from": "pass", "score_from": 100, "changes": [ {"path": "dkim.key.mail.sha256", "section": "dkim", "kind": "removed", "severity": "critical", "effect": "worsened", "from": "9f2c...", "to": null} ], "not_compared": [ {"path": "blocklist_ip.203.0.113.5.bl.spamcop.net.listed", "reason": "lookup_failed"} ] } }將它加入 cron
使用 diff=true 時,每次執行都會與上一次比較,而 jq 會將答案轉換成結束代碼。
請求
# exits non-zero if the domain is broken or its setup changed curl -s 'https://email-spam-tester.com/api/v1/infra/check?domain=example.com&selector=mail&diff=true' \ | jq -e '.ok and (.diff.changed | not)'
| domain | 必填。接受與工具相同的項目:網域、URL、電子郵件地址。 |
| ip | 你的寄件位址。若有更多位址,可重複傳入,最多 6 個。 |
| selector | DKIM 選擇器。若有更多選擇器,可重複傳入,最多 10 個。你傳入的每個選擇器都必須存在,否則 dkim 區段會失敗。 |
| helo | 你的伺服器在 HELO 中提供的名稱,會與其 PTR 比較。 |
| account | 請求是針對誰。使用服務多人的金鑰時為必填。 |
| checks | 要執行的區段,以逗號分隔。預設執行全部區段。 |
| diff | true 會將這次執行與你上一次對該網域的執行進行比較。 |
| since | 7d、12h 或 ISO 8601 日期。會與你在該時間點前後 12 小時內最接近的執行進行比較,否則使用該時間點之前的最後一次執行。啟用 diff。 |
| baseline | 你其中一次執行的 ID,用來進行比較。啟用 diff。 |
| fresh | true 會略過 60 秒快取。 |
解讀回應
完成的檢查會回傳 200,而判定結果位於本文中。status 是必要區段中最差的結果:spf、dkim、dmarc、ptr、blocklist_ip、blocklist_domain、mx 和 smtp。必要區段中的 unknown 會計為 warn。當 status 為 pass 或 warn 時,ok 為 true。score 依據有回應的必要區段計算,範圍為 0 到 100;當 error 和 unknown 使適用權重剩下不到一半時,則為 null。mta_sts、tls_rpt、bimi、dnssec、dane、ns 和 registration 會被回報和比較,但不會影響 ok 或 score。
區段可以是 pass、warn、fail、error(我們無法檢查)、unknown(資訊太少,無法判斷)或 skipped(不適用)。skipped 不會影響結果,而原因位於 not_checked。dkim_signature 和 alignment 一律存在,因為它們需要真實郵件。
ip 和 selector 會改變什麼
PTR 和封鎖清單是針對位址,因此一次執行需要一些位址。它會使用你傳入的 ip 值。如果沒有,它會從你的 MX 主機以及根 SPF 記錄中的單一位址 ip4: 和 ip6: 項目取得最多四個位址。已知郵件服務供應商的位址會列為 managed 並且不予檢查,而如果沒有剩下任何位址,ptr 和 blocklist_ip 會回傳 skipped。selector 無法從 DNS 讀取,因此一次執行會嘗試你提供的 selector、你先前執行找到的 selector,以及常見名稱清單。找不到任何項目不能證明任何事,因此 dkim 會回傳 unknown。如果你從自己的伺服器寄送郵件,請同時傳入兩者。
變更內容
diff.changes 中的每個項目都有 path、kind(added、removed、changed)、severity(critical、warning、info)和 effect(worsened、improved、neutral)。只有 critical 和 warning 會設定 diff.changed,因此輪替為相同長度的 DKIM 金鑰、新的 MX 位址或續期的憑證不會導致 cron 行失敗。diff.worsened 依據任何變更的 effect 而定。第一次執行時沒有可比較的項目,diff.first_run 會指出這一點。
基準一律是你自己的某次執行,因此其他人在你的兩次執行之間檢查該網域不會隱藏任何內容。這次無法讀取的任何內容都會進入 diff.not_compared,並保留其上次已知值,這表示在中斷期間進行的變更會在查詢恢復運作後顯示。使用不同 ip 或 selector 的執行仍屬於同一系列,而該次執行未要求檢查的內容也不會被比較。
為何排程檢查應使用金鑰
如果沒有金鑰,你的歷史記錄會歸屬於你 IP 位址的加密雜湊,因此當位址變更時,歷史記錄就會中斷,而且共用一個位址的人也會共用該歷史記錄:同事的一次執行會移動你的基準。透過 Authorization: Bearer 中的個人 API 金鑰,歷史記錄會跟隨該金鑰。使用金鑰的執行會保留 365 天,而且只能使用該金鑰開啟。未使用金鑰的執行會保留 30 天,而且任何擁有其 id 的人都能開啟。
每個 IP 每分鐘 6 個請求且每天 50 個,或每個金鑰每分鐘 30 個且每天 500 個。超過限制時,回應為 429 並包含 Retry-After。60 秒內的相同請求會來自快取、標記為 cached: true、不寫入執行記錄,也不計入限制。讀取已儲存的執行記錄時,每個用戶端每分鐘允許 120 個請求。503 並包含 Retry-After 表示執行中的檢查過多,或在讀取已儲存的執行記錄時,表示儲存空間無法使用。401 表示金鑰錯誤。422 會包含 detail.code:invalid_domain、invalid_ip、invalid_selector、invalid_check、invalid_since、unknown_baseline 或 account_required。
端點
GET/api/v1/infra/check
執行檢查。參數列於上表。
GET/api/v1/infra/runs/{public_id}
一筆完整的已儲存執行記錄。如果不存在或屬於另一個金鑰,則回傳 404。
GET/api/v1/infra/domains/{domain}/runs
你對某個網域的執行記錄,依時間由新到舊排列:id、時間、狀態、分數和變更數量。接受 limit(1 到 100,預設為 30)和 before(執行記錄 id)。
GET/api/v1/infra/diff
兩筆已儲存執行記錄之間的相同比較,?from=<id>&to=<id>。你需要有權存取兩者。
GET/api/v1/infra/checks
每個區段及其權重、分數版本和限制。
單項檢查
每次呼叫只回答一個問題,且不保留歷史記錄。除了標頭工具會讀取你已收到的郵件外,每個工具都會自行執行基礎設施檢查的一個部分。
快速開始
選擇檢查
從下方清單中選擇工具,並傳入它要求的網域、地址或 IP。
請求
curl -s 'https://email-spam-tester.com/api/v1/tools/spf?domain=example.com'查看狀態與發現
每個工具都會回傳狀態及其發現。後續欄位則依工具而定。
回應
{ "tool": "spf", "query": {"domain": "example.com"}, "checked_at": "2026-10-31T12:00:00Z", "duration_ms": 412, "status": "fail", "findings": [ {"code": "spf.too_many_lookups", "level": "fail", "params": {"limit": 10, "count": 12}, "message": "RFC 7208 §4.6.4 allows at most 10 DNS lookups, and this record needs 12, so receivers return permerror."} ], "record": "v=spf1 include:_spf.example.net ~all", "lookups": {"count": 12, "limit": 10, "void": 0} }
端點
GET/api/v1/tools/spf
網域的 SPF 記錄:其語法、追蹤的每個 include 與 redirect,以及整棵樹相對於十次上限所耗用的 DNS 查詢次數。傳入 ?domain=example.com。
GET/api/v1/tools/dmarc
網域的 DMARC 記錄,若無記錄則為其組織網域的 DMARC 記錄:標籤、政策,以及每個外部報告位址是否已同意接收報告。傳入 ?domain=example.com。
GET/api/v1/tools/dkim
針對選擇器發布的 DKIM 金鑰:其是否存在且可解碼、類型與大小,以及撤銷和測試旗標。傳入 ?domain=example.com&selector=s1。
GET/api/v1/tools/blocklist
根據報告使用的 DNS 封鎖清單檢查 IPv4 位址、IPv6 位址或網域,並提供每份清單的回應。傳入 ?target=203.0.113.5。
GET/api/v1/tools/mx
網域的 MX 記錄,依寄件者嘗試的順序排列,並列出每個主機的 IPv4 和 IPv6 位址。空 MX、沒有 MX 的網域、屬於 IP 位址或 CNAME 的主機,以及無法解析的主機都會回報,MTA-STS 和 TLS-RPT 記錄也會回報。傳入 ?domain=example.com。
GET/api/v1/tools/bimi
網域的 BIMI 設定分為四個步驟:BIMI 所要求的 DMARC 政策、default._bimi 的記錄、依 Tiny PS 設定檔檢查的 SVG 標誌,以及包含類型、網域和到期時間的商標憑證。傳入 ?domain=example.com;若選擇器不是 default,則另傳入 &selector=。
GET/api/v1/tools/ptr
某個位址的 PTR 記錄,以及其中任何名稱是否會解析回該位址。查詢失敗會給出 error 狀態;缺少記錄會給出 fail 狀態。傳入 ?ip=8.8.8.8。
GET/api/v1/tools/mta-sts
網域的 MTA-STS 記錄及其指向的原則檔案:模式、列出的主機,以及原則遺漏的任何 MX 主機。傳入 ?domain=example.com。
GET/api/v1/tools/tls-rpt
網域的 TLS-RPT 記錄,以及接收其報告的位址。傳入 ?domain=example.com。
GET/api/v1/tools/dnssec
根據網域區域的 DNSKEY 和 DS 記錄,判斷該區域是已簽署、未簽署或損壞。錯誤簽章會與解析器中斷區分開來。傳入 ?domain=example.com。
GET/api/v1/tools/dane
MX 主機的 TLSA 記錄,並在可讀取主機提供的憑證時,將記錄與該憑證比較。傳入 ?domain=example.com。
GET/api/v1/tools/smtp
前兩個 MX 主機的 STARTTLS 和憑證:TLS 版本、簽發者、到期日,以及憑證鏈和名稱是否有效。我們只會連線至你查詢的網域所屬主機,並略過郵件服務供應商,而且每個位址的單一結果會共用 6 小時。不會傳送郵件。傳入 ?domain=example.com。
GET/api/v1/tools/ns
網域的名稱伺服器,以及其區域是否有 SOA 記錄。只有一個名稱伺服器會是 warn。傳入 ?domain=example.com。
GET/api/v1/tools/registration
透過 RDAP 取得網域註冊的到期時間。剩餘不到 30 天會是 warn。沒有 RDAP 服務的區域會回傳 skipped。傳入 ?domain=example.com。
POST/api/v1/tools/header
已接收郵件的標頭,以 JSON {"headers": "..."} 或 text/plain 傳送:逐站列出傳遞路徑及延遲、TLS 和時鐘偏差、收件端本身的 Authentication-Results、From、DKIM d= 和 Return-Path 網域的對齊情況,以及 DKIM、ARC、取消訂閱和垃圾郵件篩選器標頭。第一個空白行之後的所有內容都會直接捨棄而不讀取。標頭會在記憶體中處理,不會儲存、快取或記錄。
每晚檢查網域。
寄出前測試電子郵件。
所有產品共用
存取方式、金鑰、報告格式、狀態、錯誤,以及供機器使用的 OpenAPI 和 llms.txt。
驗證
沒有驗證。無須申請金鑰、無須設定標頭,也無須建立帳戶。你取得的 slug 就是存取憑證:持有它的人都能讀取該報告,其他人則無法猜出它。
個人 API 金鑰
Everything above works without a key. A key is for automation platforms such as
Zapier, where every user's calls come from the platform's servers and per-IP limits
would be shared by all of them. With a key, limits count per key (50 tests a day,
3 with placement, 5 permanent mailboxes), the key's tests form a history, and the
key can keep permanent mailboxes whose reports only it can read. Send the key as
Authorization: Bearer est_live_… on any call on this page. The routes
below also take account, a short name of your choosing
([A-Za-z0-9_-], up to 64 characters) that keeps separate lists under one
key. GET /api/v1/installations/tests requires it; pass the same one on
POST /api/v1/inbox so the test shows up there. The Zapier integration
uses zapier.
POST /api/v1/keys
Send JSON {"email":"you@example.com"}. Returns HTTP 201 with
key and email. The key is shown once; only its hash is
kept. Asking again gives a new key and leaves the earlier ones working. Limit: 5 keys
per IP per UTC day. The form on /zapier/ calls this.
GET /api/v1/keys/me
Returns email, key_prefix and created_at of
the key in the header, or HTTP 401. Use it to check a key.
GET /api/v1/installations/tests
The key's tests, newest first: ?account=…&limit=50 (up to 100),
and before=<slug> for the next page. Each item has
slug, created_at, analysis_status
(waiting or expired before an email arrived),
score_ours, score_compat, placement and
changes, the checks that moved since the previous test of the same
sending domain. Read the full report at /api/v1/tests/{slug}.
POST /api/v1/installations/mailboxes
Send JSON {"domain":"example.com","account":"…"}. Returns the
permanent mailbox of that sending domain: id, address,
domain, state, daily_cap and
created. HTTP 201 when it is new, 200 when it already existed, 409 when
the key keeps as many mailboxes as it may. Subscribe the address to a newsletter or
a sequence and every email that arrives is checked. GET on the same
path with ?account=… lists them, and DELETE
/api/v1/installations/mailboxes/{mailbox_id} stops one.
GET /api/v1/installations/mailboxes/{mailbox_id}/letters
The emails that arrived, oldest first, paged with after_id and
next_after_id. settled=true ends the page before the first
email still being checked, so paging never skips one. newest=true turns
the order round, for a quick look at the latest; settled does nothing
with it. Each has
test_id, slug, received_at,
analysis_status, score_ours, score_compat,
subject, from_addr and kind.
GET /api/v1/installations/letters/{slug}
The report of one email in a permanent mailbox, the same JSON as
/api/v1/tests/{slug} with report_url null: there is no
public page for it. HTTP 410 once the report has expired.
閱讀報告
包含答案的欄位,依照你可能想查看的順序排列。
| score_ours | 0 到 100。我們的模型。驗證和基礎設施占大部分權重,因為它們會在篩選器讀取文案中的任何文字之前決定郵件是否送達。 |
| score_compat | 0 到 10。重現人們已用來比較的 SpamAssassin 式分數,因此該報告可與某人在其他地方看到的結果進行比較。 |
| subscores | 每個區段皆使用相同的 0 到 100 分制:auth、infra_spam、content、compliance。 |
| checks[] | 全部 42 項,每項都有狀態、單行結果、作為判定依據的證據,以及它對兩個分數造成的影響。 |
| checks[].citations | 發現結果的來源:RFC 的相關章節、逐字引用的內容,以及 Google 說明其自身要求的頁面。這些資料是人工整理而非產生,因此可以信賴。 |
| fixes[] | 依序列出要變更的項目,以及每項變更可獲得的分數。分數增益是透過重新評分報告計算得出,而非估算。 |
| complete | 當檢查無法執行時為 False。未檢查的項目絕不算通過,因此在此值變為 true 之前,應將分數視為偏樂觀。 |
| report_url | 供人閱讀的頁面。請將該頁面交給人員,而不是一大串 JSON。 |
狀態
一項檢查會處於五種狀態之一,其中兩種狀態之間的差異比看起來更重要。
| pass | 檢查已執行,且未發現任何問題。 |
| warn | 值得修正。會扣分。 |
| fail | 會影響投遞。會扣除更多分數。 |
| 跳過 | 不適用。沒有可掃描的附件,也沒有可評估的 HTML 部分。不算通過。 |
| 錯誤 | 我們無法確定。已從評分中排除並標記,而不是計為通過。 |
analysis_status 會依序為 received、analyzing、checks_ready、failed。ai_status 會依序為 pending、running、ready、fallback、error。確定性報告在 checks_ready 時即為最終結果;ai_status 只會附加計畫。
可能傳回的內容
| 202 | 此地址已保留,但尚未收到任何郵件。回應本文包含地址、到期時間和語言,因此即使呼叫端不是建立保留的那一方,仍可顯示這些資訊。 |
| 404 | 查無此 slug。它可能從未存在,或保留已被遺忘。 |
| 410 | 此地址在收到郵件前已到期。 |
| 409 | 你嘗試在郵件已送達後變更語言。 |
| 429 | 你的地址已達免費測試上限。目前此服務沒有每人上限;如果日後設定,回應本文會說明何時重設。 |
值得知道的四件事
每個位址限一封郵件
第二封會被拒收。你先前的報告會保持不變,這正是此限制的目的。
一小時內使用
位址會過期;報告不會。報告連結永久有效,因此貼到工單中的連結會持續有效。
從平台寄送
從個人帳號測試行銷活動,衡量的是該帳號。驗證區段中的幾乎所有內容都與寄送基礎架構有關,而不是文字內容。
修正後重新測試
預期改善幅度是逐項修正計算的,無法合併計算。第二份報告才是如實的數字。
供機器使用
- /api/openapi.json OpenAPI 說明是由提供 API 的同一份程式碼產生。
- /llms.txt, /llms-full.txt 依照 llms.txt 慣例提供此網站的簡短導覽,以及將完整流程和報告欄位放在單一檔案中的較長版本。
- /mcp 具備相同功能並提供阻塞式等待的 MCP 伺服器,這比從模型內部進行輪詢更好。
- For agents 代理程式頁面:何時該使用此功能、如何解讀略過的檢查與通過的檢查,以及哪些發現是必須由人員變更的 DNS 記錄,而不是代理程式可編輯的文字。
GET/api/health
存活狀態。無須驗證,沒有副作用。