Confidence and fail-open
How to read confidence and evidence on every detect response, and when to fail open at signup.
Every successful GET /api/v1/emails/detect body includes confidence and evidence. Treat those fields as part of the contract. SDKs generated from the public OpenAPI spec expose the same names.
This page is the signup policy. Field-by-field catalog: email detection overview.
confidence is always one of high, medium, or low.
| Value | Typical cause |
|---|---|
low | Syntax failed. Do not treat classification flags as a finished verdict. |
medium | Weaker or partial evidence (for example a thin catalog hit). Log it. Decide in your product whether that is enough to block. |
high | Syntax passed and EmailGuard is not marking the result as low-confidence disposable noise. |
Do not invent extra levels. If you need a team-specific allow or deny, use team email policy instead of stretching confidence.
evidence explains the disposable path without dumping internal catalogs.
| Field | Meaning |
|---|---|
detection_layer | Which layer produced the disposable (or non-disposable) result |
source_count | How many independent sources agreed, when that count is available |
cluster_provider | Infrastructure label when the hit came from a known cluster |
matched_rules is a separate array of {id, label, signal} for catalog or staff rules that fired. Patterns are never included. Do not persist matched_rules as a blocklist of regexes. Use id if you need to talk to support.
When EmailGuard has a cached DNS snapshot for the domain, the response may include:
mx_presentwildcard_dnsinfra_cluster_matchOmitted flags mean there was no snapshot, not that MX is absent on the live internet. None of these open an SMTP session or prove a mailbox exists.
Fail open is for your client when EmailGuard is unreachable or overloaded. It is not a field on the detect body.
| What happened | What to do at ordinary signup |
|---|---|
| Timeout, connection error, 5xx | Create the account, log the miss, recheck later |
| HTTP 429 | Honor Retry-After, then same as timeout if you still cannot complete the check |
HTTP 2xx and disposable: true | Block. This is a classification result, not an outage |
HTTP 2xx and syntax_validation: false | Reject or ask the user to fix the address |
If live DNS fails inside EmailGuard, you still get HTTP 2xx. Disposable stays false and detection_source stays precomputed. Do not treat that 2xx as "unknown" the way SMTP verifiers do.
Live DNS on our side can take up to 2000 ms (EMAIL_DNS_TIMEOUT_MS). If your SDK or HTTP client aborts at 200 ms, you will skip the addresses that most need live DNS: brand-new burner domains. Set the client timeout at 2 seconds or higher, and keep fail-open for when that budget still expires.
Checkout, KYC, or other high-stakes steps can fail closed on timeout. Signup is the path that should stay open.
Longer treatment with timeout taxonomy: fail open vs fail closed.
syntax_validation, then disposable, then optional relay_domain / role_address / team policy_action.confidence, detection_source, and evidence.detection_layer. Skip storing rule patterns. There are none in the payload.Language-specific clients: SDK getting started.