Overview
This Email Validator API goes beyond basic syntax checking. Most email validators only check if the format looks correct. This API actually connects to the mail server via SMTP and confirms the address exists — catching fake signups, disposable addresses, and dead mailboxes that simple checks completely miss.
Imagine someone signs up on your website with a throwaway email. They pollute your database and never become a real user. This API catches those bad emails at the point of entry — before they ever reach your system.
Unlike other validators that always run every check regardless of what you need, this API lets you specify exactly which checks to run using the fields parameter. Only the checks you request actually execute — so a disposable-only check responds instantly, while a full SMTP probe only fires when you explicitly ask for it. You get responses as fast as the check you need, nothing more.
What Gets Checked — 11 Fields
| Field | What It Does |
|---|---|
syntax | Checks email format against RFC 5321/5322 rules |
mx | DNS MX lookup — confirms the domain is set up to receive email |
smtp | Live SMTP probe — confirms the mailbox exists on the server |
disposable | Detects throwaway emails — 769,000+ domains, live-updated from community blocklists |
role | Detects shared inboxes: admin@, noreply@, support@, sales@, and 100+ variants (two-layer: exact match + fuzzy pattern) |
subaddress | Detects plus-tag addressing like [email protected] |
provider | Detects free email providers — Gmail, Yahoo, Outlook, and 30+ more (two-layer: exact match + MX fingerprint) |
spamtrap | Detects spam trap patterns like honeypot@, trap@, abuse@, blacklist@ |
intelligence | Domain entropy scoring + risky TLD detection (53+ TLDs hardcoded, live-updated from community list) |
auth | Checks SPF, DMARC, and DKIM DNS records |
typo | Detects common domain typos and suggests corrections (two-layer: dictionary + Levenshtein fuzzy matching) |
All 11 fields run when no fields param is provided. Pass fields= to run only what you need.
Quick Start
Step 1 — Subscribe to any plan including free and copy your RapidAPI key from the dashboard.
Step 2 — Make your first request. Replace YOUR_API_KEY_HERE with your actual key.
JavaScript
const response = await fetch(
'https://email-validator-rjwr.onrender.com/v1/[email protected]',
{
headers: {
'x-rapidapi-key': 'YOUR_API_KEY_HERE',
'x-rapidapi-host': 'email-validator-rjwr.onrender.com'
}
}
);
const data = await response.json();
console.log(data);
Python
import requests
url = "https://email-validator-rjwr.onrender.com/v1/validate"
headers = {
"x-rapidapi-key": "YOUR_API_KEY_HERE",
"x-rapidapi-host": "email-validator-rjwr.onrender.com"
}
response = requests.get(url, params={"email": "[email protected]"}, headers=headers)
print(response.json())
PHP
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://email-validator-rjwr.onrender.com/v1/[email protected]",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => [
"x-rapidapi-key: YOUR_API_KEY_HERE",
"x-rapidapi-host: email-validator-rjwr.onrender.com"
],
]);
$response = json_decode(curl_exec($curl));
curl_close($curl);
print_r($response);
cURL
curl -X GET \
"https://email-validator-rjwr.onrender.com/v1/[email protected]" \
-H "x-rapidapi-key: YOUR_API_KEY_HERE" \
-H "x-rapidapi-host: email-validator-rjwr.onrender.com"
The fields Parameter — Run Only What You Need
This is the most important feature in v5.0. By default, all 11 fields run. If you pass
fields=, only those specific checks execute — the rest never run. Response time depends
entirely on which checks you request.
fields=syntax,role,provider,spamtrap → ~0ms (zero network I/O)
fields=disposable → ~0ms (in-memory lookup)
fields=typo → ~5ms (dictionary lookup)
fields=mx → ~200ms (one DNS query)
fields=auth → ~300ms (3 DNS TXT queries)
fields=mx,disposable,role → ~200ms (MX + disposable in parallel)
fields=smtp → ~1-3s (TCP + SMTP handshake)
no fields param / fields=all → ~2-3s (all 11 fields)
Available field names:
| Field | What Runs | Speed | Returns |
|---|---|---|---|
syntax | RFC 5321/5322 format check | instant | syntax_valid |
mx | DNS MX record lookup | ~200ms | mx_found, mx_records |
smtp | Live SMTP mailbox probe | ~1-3s | smtp_verified, smtp_catch_all, smtp_greylisted, smtp_skipped |
disposable | 769,000+ domain blocklist, live-updated | instant | is_disposable, disposable_method |
role | Role-based prefix detection | instant | is_role_based |
subaddress | Plus-tag detection | instant | is_sub_address |
provider | Free provider detection | instant | is_free_provider |
spamtrap | Spam trap pattern matching | instant | spam_trap_suspected |
intelligence | Domain entropy + TLD risk | instant | risky_tld, domain_entropy, intelligence |
auth | SPF, DMARC, DKIM DNS records | ~300ms | email_auth |
typo | Common domain typo detection | instant | suggestions |
The response only includes fields for the checks that actually ran. Fields you did not
request are simply absent — the response is clean and minimal.
Example — signup form, fast, no SMTP:
Example — typo correction only, near-zero latency:
Example — security audit only:
Pass fields=all or omit the parameter to run all checks. Unknown field names are ignored
and reported back in _unknown_fields so you can catch typos in your integration.
Endpoints
1. Validate Single Email
GET /v1/validate
| Parameter | Type | Required | Description |
|---|---|---|---|
| string | Yes | The email address you want to validate | |
| fields | string | No | Comma-separated list of checks to run. Omit for all 11 fields. |
| quick | boolean | No | Set to true to skip SMTP. Ignored if smtp is not in your fields list. |
Full Response — Valid Email
{
"email": "[email protected]",
"result": "VALID",
"reason": "All checks passed",
"score": 100,
"score_label": "Excellent",
"checks": {
"syntax_valid": true,
"mx_found": true,
"mx_records": [
"gmail-smtp-in.l.google.com",
"alt1.gmail-smtp-in.l.google.com",
"alt2.gmail-smtp-in.l.google.com",
"alt3.gmail-smtp-in.l.google.com",
"alt4.gmail-smtp-in.l.google.com"
],
"smtp_verified": null,
"smtp_catch_all": false,
"smtp_greylisted": false,
"smtp_skipped": true,
"is_disposable": false,
"disposable_method": null,
"is_role_based": false,
"is_sub_address": false,
"is_free_provider": true,
"spam_trap_suspected": false,
"risky_tld": false,
"domain_entropy": 25,
"email_auth": {
"spf": true,
"spf_policy": "neutral",
"dmarc": true,
"dmarc_policy": "none",
"dkim": false
}
},
"intelligence": null,
"suggestions": null,
"latency_ms": 2536
}
Response — Disposable Email Rejected
{
"email": "[email protected]",
"result": "REJECT",
"reason": "Disposable email detected via domain_list",
"score": 2,
"score_label": "Very Poor",
"checks": {
"syntax_valid": true,
"mx_found": true,
"mx_records": ["mx.tempmail.com"],
"smtp_verified": null,
"smtp_catch_all": false,
"smtp_greylisted": false,
"smtp_skipped": false,
"is_disposable": true,
"disposable_method": "domain_list",
"is_role_based": false,
"is_sub_address": false,
"is_free_provider": true,
"spam_trap_suspected": false,
"risky_tld": false,
"domain_entropy": 12,
"email_auth": {
"spf": false,
"spf_policy": null,
"dmarc": false,
"dmarc_policy": null,
"dkim": false
}
},
"intelligence": {
"risk_score": 85,
"flags": [
"Domain registered only 12 days ago",
"MX IP shared by 620 domains — disposable infrastructure",
"No web presence detected"
]
},
"suggestions": null,
"latency_ms": 891
}
Response — Selective fields (fields=mx,disposable,role)
When you pass a fields parameter, only those checks run and only those fields are returned.
The response is clean — no null placeholders for checks that did not run.
{
"email": "[email protected]",
"result": "REJECT",
"reason": "Disposable email detected via domain_list",
"score": 25,
"score_label": "Poor",
"checks": {
"syntax_valid": true,
"mx_found": true,
"mx_records": ["mail.mailinator.com"],
"is_disposable": true,
"disposable_method": "domain_list",
"is_role_based": true
},
"latency_ms": 203
}
Notice: no smtp fields, no email_auth, no intelligence, no suggestions — because none of
those checks were requested. The response time is 203ms instead of 2-3 seconds.
Understanding Every Field
Top Level Fields
| Field | What It Means |
|---|---|
| The email address you submitted | |
| result | The final verdict. See the Result Values table below. |
| reason | A plain English explanation of why this result was given |
| score | A number from 0 to 100 showing how trustworthy this email is |
| score_label | A label for the score — Excellent, Good, Fair, Poor, or Very Poor |
| intelligence | Extra analysis for suspicious unknown domains. Only present if intelligence was requested. |
| suggestions | If the domain looks like a typo this shows the corrected version. Only present if typo was requested. |
| latency_ms | How long the validation took in milliseconds |
| _unknown_fields | Only present if you passed unrecognised field names. Lists them so you can fix your integration. |
Result Values
| Result | What It Means | What To Do |
|---|---|---|
| VALID | Email passed all checks | Accept it |
| REJECT | Email definitively failed — fake, disposable, or non-existent | Reject it |
| RISKY | Email passed basic checks but has suspicious signals | Flag for review or require email confirmation |
| UNKNOWN | SMTP was inconclusive — server blocked the probe | Allow but send a confirmation email |
Score Guide
| Score | Label | What To Do |
|---|---|---|
| 80 to 100 | Excellent | Accept with confidence |
| 60 to 79 | Good | Accept — minor concerns only |
| 40 to 59 | Fair | Consider requiring email confirmation |
| 20 to 39 | Poor | Flag for manual review |
| 0 to 19 | Very Poor | Reject |
The checks object — every field explained
syntax_valid — true means the email format is correct. false means it is not a properly
formatted email at all — for example missing the @ symbol or having illegal characters.
If this is false everything else is skipped.
mx_found — true means the domain is set up to receive emails. false means even if the
email looks correct it can never receive any messages because the domain has no mail servers.
mx_records — The list of mail servers responsible for delivering email to this domain.
Multiple entries are normal — they are fallback servers listed in order of priority.
You do not need to act on this directly.
smtp_verified — The result of the live SMTP check. true means the mailbox was confirmed
to exist on the mail server. false means it was confirmed to not exist. null means the
check was skipped or the server blocked the probe — see smtp_skipped for why.
smtp_catch_all — true means the mail server accepts every email address regardless of
whether the mailbox actually exists. This makes individual verification impossible for
this domain. Do not outright reject these — flag them for manual review instead.
smtp_greylisted — true means the server temporarily rejected the SMTP probe using a
technique called greylisting. The API automatically waits and retries when this happens.
If it is still true after retry it means the server is being cautious — not that the
email is invalid.
smtp_skipped — true means SMTP verification was not performed. This happens for two
reasons: either you used quick=true mode, or the domain belongs to a major provider like
Gmail or Yahoo that blocks automated SMTP probing. When skipped the result is based on
the other 11 checks.
is_disposable — true means this is a known throwaway email address. People use these
to sign up without giving their real email. You should reject these.
disposable_method — How the disposable email was detected. Can be domain_list
(matched against 769,000+ known domains updated live from community blocklists),
keyword_match (domain contains a known disposable keyword), or mx_fingerprint
(mail server is known disposable infrastructure). null if the email is not disposable.
is_role_based — true means this is a shared inbox address like admin@, info@,
support@, noreply@, sales@, or similar. Detection uses two layers: an exact match
against 50+ known role prefixes, then fuzzy segment matching to catch variants like
noreply2@, admin.team@, or support_dept@. For consumer apps and newsletters you
should reject these. For B2B tools and contact forms they are perfectly legitimate.
is_sub_address — true means the email uses plus addressing like [email protected].
This is a real technique used by legitimate users but also sometimes used to bypass
duplicate email checks. The base address without the tag is the real mailbox.
is_free_provider — true means this is from a free email provider like Gmail, Yahoo,
Hotmail, or Outlook. Detection uses two layers: a hardcoded list of 30+ known free
providers, then MX fingerprinting to catch custom domains that route through the same
infrastructure (e.g. a Google Workspace or O365 domain). Useful if your application
requires a business email address. Has no impact on validity — Gmail addresses are
perfectly valid.
spam_trap_suspected — true means the email address matches known spam trap patterns
like spamtrap@, honeypot@, or abuse@. These addresses are set up specifically to catch
spammers. If you are seeing this on real user emails it means someone is entering fake
data — reject it.
risky_tld — true means the domain uses a top-level domain statistically associated
with spam and disposable email services. The check uses 53+ hardcoded TLDs (.xyz,
.top, .click, .loan, etc.) plus a live-updated community list fetched at server
startup. A risky TLD alone does not mean the email is invalid but it lowers the trust
score.
domain_entropy — A score from 0 to 100 measuring how pronounceable and human-like
the domain name is. Higher is better. A score below 25 suggests the domain name may
be randomly generated — a common characteristic of disposable email services. 25 or
above is normal. You do not need to act on this field directly — it feeds into the
overall score automatically.
The email_auth object
spf — true means the domain has an SPF record published. SPF lets domain owners
declare which mail servers are allowed to send email on their behalf. Legitimate
domains almost always have this configured.
spf_policy — How strictly SPF is enforced. strict means hard fail — unauthorized
senders are rejected. softfail means soft fail — unauthorized senders are flagged but
not necessarily rejected. neutral means no policy preference. null means no SPF record.
dmarc — true means the domain has a DMARC record. DMARC builds on SPF and tells
receiving mail servers what to do with emails that fail authentication.
dmarc_policy — How the domain handles authentication failures. none means monitoring
only — no action taken. quarantine means send suspicious emails to spam. reject means
block them completely. null means no DMARC record exists.
dkim — true means the domain has DKIM signing keys published. DKIM is a digital
signature system that proves an email actually came from the domain it claims to be
from. false does not automatically mean the email is bad — many legitimate domains
do not publish DKIM selectors publicly, including Gmail which manages DKIM internally.
The intelligence object
The intelligence engine runs additional analysis on domains that are not in the known
disposable list. It checks domain age, how many other domains share the same mail
server IP, the hosting provider reputation, and whether the domain has a real website.
This catches brand new disposable email services before they appear in any blocklist.
intelligence.risk_score — A number from 0 to 100 representing how suspicious the
domain appears based on infrastructure signals. Above 60 is flagged as likely disposable.
30 to 60 is considered risky.
intelligence.flags — A list of human readable reasons for the risk score. Examples
are "Domain registered only 3 days ago", "MX IP shared by 800 domains — disposable
infrastructure", or "No web presence detected". null means no red flags were found.
When intelligence is null it means the domain passed all infrastructure checks cleanly
and no red flags were detected.
The suggestions object
suggestions.did_you_mean — If the domain looks like a common typo this field shows
the corrected version. Uses two layers: a dictionary of known typos (e.g. gmial.com →
gmail.com), then Levenshtein fuzzy matching for variants not in the dictionary. For
example [email protected] suggests [email protected]. null means no typo detected.
2. Validate Single Email via POST
POST /v1/validate
Identical to the GET endpoint but accepts the email in the request body.
Useful when you do not want the email address to appear in server logs or URLs.
Request Body:
| Field | Type | Required | Description |
|---|---|---|---|
| string | Yes | The email address to validate | |
| fields | string | No | Comma-separated checks to run. Omit for all. |
| quick | boolean | No | Skip SMTP if true |
Response format is identical to the GET endpoint.
3. Bulk Validate Emails
POST /v1/validate/bulk
Validate multiple emails in one request. Much faster and more efficient than
calling the single endpoint repeatedly. Ideal for cleaning existing email lists
before sending campaigns.
Request Body:
{
"emails": [
"[email protected]",
"[email protected]",
"[email protected]"
],
"fields": "disposable,role",
"quick": false
}
| Field | Type | Required | Description |
|---|---|---|---|
| emails | array | Yes | Array of email addresses to validate |
| fields | string | No | Comma-separated checks to run. Omit for all. |
| quick | boolean | No | Skip SMTP if true |
Plan limits:
| Plan | Max emails per bulk call |
|---|---|
| BASIC (free) | 5 |
| PRO | 50 |
| ULTRA | 100 |
| MEGA | 500 |
Response:
{
"count": 3,
"results": [
{
"email": "[email protected]",
"result": "VALID",
"reason": "All checks passed",
"score": 100,
"score_label": "Excellent",
"checks": { "..." },
"intelligence": null,
"suggestions": null,
"latency_ms": 1243
},
{
"email": "[email protected]",
"result": "REJECT",
"reason": "Disposable email detected via domain_list",
"score": 2,
"score_label": "Very Poor",
"checks": { "..." },
"intelligence": { "risk_score": 85, "flags": ["..."] },
"suggestions": null,
"latency_ms": 312
},
{
"email": "[email protected]",
"result": "RISKY",
"reason": "Role-based address — low engagement, high spam risk",
"score": 65,
"score_label": "Good",
"checks": { "..." },
"intelligence": null,
"suggestions": null,
"latency_ms": 890
}
]
}
| Field | What It Means |
|---|---|
| count | How many emails were processed in this request |
| results | An array with one full result per email in the same order you sent them |
Each entry in results is the same response object as the single validate endpoint.
If you passed a fields parameter, each result only contains the checks you requested.
4. List Available Fields
GET /v1/fields
Returns the complete list of all available field names with their speed estimates
and what they return. Useful for building dynamic integrations or confirming field names.
No parameters needed.
{
"available_fields": [
{ "field": "syntax", "speed": "instant", "returns": ["checks.syntax_valid"] },
{ "field": "mx", "speed": "~200ms", "returns": ["mx_found", "mx_records"] },
{ "field": "smtp", "speed": "~1-3s", "returns": ["smtp_verified", "smtp_catch_all", "smtp_greylisted", "smtp_skipped"] },
{ "field": "disposable", "speed": "instant", "returns": ["is_disposable", "disposable_method"] },
{ "field": "role", "speed": "instant", "returns": ["is_role_based"] },
{ "field": "subaddress", "speed": "instant", "returns": ["is_sub_address"] },
{ "field": "provider", "speed": "instant", "returns": ["is_free_provider"] },
{ "field": "spamtrap", "speed": "instant", "returns": ["spam_trap_suspected"] },
{ "field": "intelligence", "speed": "instant", "returns": ["risky_tld", "domain_entropy", "intelligence (top-level)"] },
{ "field": "auth", "speed": "~300ms", "returns": ["email_auth (spf, spf_policy, dmarc, dmarc_policy, dkim)"] },
{ "field": "typo", "speed": "instant", "returns": ["suggestions (top-level)"] }
],
"always_returned": ["email", "result", "reason", "score", "score_label", "latency_ms", "checks.syntax_valid"],
"usage": "Pass ?fields=mx,disposable,auth — only those checks run. Omit for full validation."
}
5. Health Check
GET /health
Check if the API is online. No parameters needed. Use this before making
bulk requests to confirm the service is running.
{
"status": "ok",
"version": "5.0.0",
"ts": 1741267200000
}
| Field | What It Means |
|---|---|
| status | ok means everything is working normally |
| version | The current version of the API |
| ts | Current server timestamp in milliseconds |
Quick Mode vs Full Mode vs Selective Fields
| Mode | How To Use | Speed | Best For |
|---|---|---|---|
| Full mode | No params | ~2-3s | Maximum accuracy — all 11 fields run |
| Quick mode | quick=true | ~300ms | Skip SMTP only, all other checks run |
| Selective fields | fields=mx,disposable | Depends on fields | Run only what you need — fastest option |
| Selective + quick | fields=smtp&quick=true | ~300ms | Selective without SMTP |
The fields parameter is more powerful than quick=true alone. With fields you control
exactly which checks execute. With quick=true you only skip SMTP — everything else still runs.
For real-time typing validation, fields=syntax,typo gives you instant feedback with near-zero
latency. Then run fields=mx,disposable,role on submit for a thorough but fast check. Only
use fields=smtp for high-value signups where confirming the mailbox is worth the extra
1-3 seconds.
How To Use The Results In Your Code
Simple accept or reject based on result:
const res = await fetch('/v1/validate?email=' + email, { headers });
const data = await res.json();
if (data.result === "VALID") {
proceedWithSignup(email);
} else if (data.result === "RISKY" || data.result === "UNKNOWN") {
sendConfirmationEmail(email); // allow but verify
} else {
showError("Please enter a valid email address");
}
Use the score for more nuanced decisions:
if (data.score >= 80) {
acceptDirectly(email);
} else if (data.score >= 50) {
requireEmailConfirmation(email);
} else {
rejectSignup(email);
}
Handle catch-all domains separately:
if (data.checks.smtp_catch_all) {
// Cannot verify individual mailbox — allow but flag
flagForManualReview(email);
} else if (data.result === "REJECT") {
rejectSignup(email);
}
Help users fix typos:
if (data.suggestions?.did_you_mean) {
showMessage(`Did you mean ${data.suggestions.did_you_mean}?`);
}
Require business email only:
if (data.checks.is_free_provider) {
showError("Please use your business email address");
}
Use selective fields for a fast signup form:
// Only run mx + disposable + role — responds in ~200ms
const res = await fetch(
'/v1/validate?email=' + email + '&fields=mx,disposable,role',
{ headers }
);
const data = await res.json();
if (data.checks.is_disposable) showError("Disposable emails not allowed");
if (data.checks.is_role_based) showError("Please use a personal email address");
if (!data.checks.mx_found) showError("This email domain does not exist");
Clean an email list before sending a campaign:
const { data } = await bulkValidate(emailList, { fields: "disposable,role,spamtrap" });
const cleanList = data.results
.filter(r => r.result === "VALID" && r.score >= 70)
.map(r => r.email);
Recommended Combinations By Use Case
| Use Case | fields= | Speed | Why |
|---|---|---|---|
| Signup form | mx,disposable,role | ~200ms | Blocks the most common bad emails, no SMTP wait |
| Real-time typing | syntax,typo | ~0ms | Instant format + typo correction as user types |
| Email marketing list clean | disposable,spamtrap,role,mx | ~200ms | Removes all bad senders before a campaign |
| Security audit | auth,intelligence | ~300ms | SPF/DMARC/DKIM + domain reputation |
| High-value lead verification | mx,smtp,disposable | ~1-3s | Full SMTP mailbox confirmation |
| Business email gate | provider,syntax | ~0ms | Block free providers instantly |
| Bulk list cleaning | disposable | ~0ms | In-memory lookup — instant even for thousands |
Honest Limitations
We believe in being upfront about what this API can and cannot do.
Major providers like Gmail, Yahoo, Outlook, iCloud, and ProtonMail block automated SMTP
probing. For these domains smtp_skipped will be true and smtp_verified will be null.
The result is still based on the other 11 checks and is reliable for detecting obvious
fakes and disposable patterns — but we cannot confirm whether a specific Gmail mailbox
exists.
Catch-all domains accept every email address regardless of whether the individual mailbox
exists. smtp_catch_all will be true for these. We cannot tell you if a specific address
on that domain is real — we recommend flagging these for manual review rather than
outright rejecting.
No email validator guarantees 100% accuracy. Some valid emails will occasionally score
lower than expected due to server timeouts, temporary DNS issues, or conservative server
configurations. Use the result and score together to make decisions, and always give
users a way to receive a confirmation email if they believe their address is valid.
We do our best across 11 fields but we are not the only option and may not be
perfect for every use case. Test on the free tier first to confirm it meets your needs.
Every live data source has a hardcoded fallback built in. If the
disposable blocklist fetch fails, 769,000+ built-in domains still run.
If the risky TLD live fetch fails, 53 hardcoded TLDs still fire. If MX
fingerprinting cannot resolve, the hardcoded provider list covers all
major cases. The API never returns an error due to a failed external
fetch — it degrades gracefully and silently to its hardcoded layer.
FAQ
Is this GDPR compliant?
Yes. Email addresses submitted for validation are never stored, logged, or shared with
any third party. Every request is processed in memory and discarded immediately after
the response is sent.
Why is smtp_verified null for Gmail addresses?
Gmail and other major providers block automated SMTP verification by design — they
return 250 for every address regardless of whether it exists, making the check useless.
We detect this and skip SMTP for these providers, marked by smtp_skipped: true. The
result is still based on 11 other checks and is reliable.
What is the fields parameter?
It lets you specify exactly which checks to run. Only those checks execute — the rest
are skipped entirely. This means the response time depends on what you ask for. Asking
for just disposable takes under 10ms. Asking for smtp takes 1-3 seconds. Pass
fields=mx,disposable,role for a fast signup form check, or omit fields entirely for
full validation.
What is a catch-all domain?
Some domains are configured to accept every email address regardless of whether the
individual mailbox actually exists. smtp_catch_all: true indicates this. We recommend
flagging these for manual review and sending a confirmation email rather than rejecting.
What does is_sub_address mean?
It means the email uses plus addressing — for example [email protected]. This
is a real technique where email goes to the base address ([email protected]). Some users
do this to track who shares their email. It is valid but worth knowing about.
How often is the disposable domain list updated?
The list is fetched from live community blocklists every time the server starts. The
769,000+ domain fallback is always available even if the live fetch fails. New disposable
services are typically picked up within hours of being added to community sources.
What does the intelligence object tell me?
It runs deeper analysis on unknown domains — checking how old the domain is, how many
other domains share its mail server, the reputation of its hosting provider, and whether
it has a real website. A domain registered 3 days ago with 800 other domains on the
same IP and no website is almost certainly a disposable email service even if it is not
in any blocklist yet.
Should I reject RISKY emails outright?
Not necessarily. RISKY means there are signals worth noting but nothing definitive.
The best approach is to allow the signup but send a confirmation email — if they can
confirm it the address is real enough to use.
What is domain_entropy?
It is a measure of how pronounceable and human-like the domain name is. Randomly
generated domains like xk7mq2p.com score very low. Real business domains and well
known providers score high. It feeds into the overall score automatically — you do
not need to check it directly.
What happens if I pass an unknown field name?
The API runs the valid field names you provided and returns the unrecognised ones in
_unknown_fields. So fields=mx,typo,fakething would run mx and typo normally, and
return "_unknown_fields": ["fakething"] in the response so you can fix your integration.
