API Documentation

Integrate email validation into your application with a simple REST API. Validate single addresses in real time or process entire lists in bulk.

MCP

Not writing code? Connect your AI assistant instead

The same validation runs over the Model Context Protocol, so Claude, Cursor, or any MCP client can call it directly — OAuth sign-in, no API key. Point your client at https://mcp.mailrook.com/mcp.

MCP setup guide

Quick start

Validate an email address with a single request:

curl -H "Authorization: Bearer YOUR_API_KEY" \
  https://api.mailrook.com/v1/validate/[email protected]

Authentication

All API requests require a Bearer token in the Authorization header. Generate your API key from the dashboard after signing up.

Authorization: Bearer YOUR_API_KEY

Base URL

https://api.mailrook.com

Endpoints

GET /v1/validate/{email}

Validate a single email

Validates one email address and returns detailed verification results. Typical response time is under 500ms.

Path parameters

email
string, required

The email address to validate (e.g. [email protected])

Query parameters

include
string, optional

Comma-separated list of extra data to include. Currently supported: enrichment. When provided, an enrichment object is added to the response containing the same blocks as /v1/enrich. fields and include=category_detail work here too and apply to that block.

Example request

curl -H "Authorization: Bearer YOUR_API_KEY" \
  https://api.mailrook.com/v1/validate/[email protected]

Example response

{
    "data": {
        "id": "673603dc-42da-474c-98cf-531ce11b1bf2",
        "email": "[email protected]",
        "normalized_email": "[email protected]",
        "username": "elon",
        "domain": "x.com",
        "mx_record": "aspmx.l.google.com",
        "provider": "google_workspace",
        "score": 80,
        "isv_format": true,
        "isv_domain": true,
        "isv_deliverable": true,
        "isv_nocatchall": false,
        "isv_nogeneric": true,
        "isv_nodisposable": true,
        "isv_nofreeemail": false,
        "isv_nouniversity": true,
        "result": "risky",
        "reason": "catch_all",
        "reason_label": "Catch-all domain (accepts all emails)",
        "email_security": [],
        "protection_level": "basic",
        "domain_info": {
            "has_spf": true,
            "has_dmarc": true,
            "has_website": true,
            "domain_age_days": 8450,
            "domain_created_at": "2003-03-17T00:00:00+00:00",
            "domain_expires_at": "2026-03-17T00:00:00+00:00",
            "registrar": "CSC Corporate Domains, Inc.",
            "registrant_org": "X Corp.",
            "registrant_country": "US",
            "ns_hosts": [
                "ns1.p09.dynect.net",
                "ns2.p09.dynect.net"
            ],
            "a_record_ip": "104.244.42.193",
            "asn": "AS13414",
            "asn_org": "Twitter Inc.",
            "email_security": [],
            "protection_level": "basic"
        }
    },
    "code": 0,
    "message": "ok"
}

Example request with enrichment

curl -H "Authorization: Bearer YOUR_API_KEY" \
  https://api.mailrook.com/v1/validate/[email protected]?include=enrichment

Example response with enrichment

{
    "data": {
        "id": "673603dc-42da-474c-98cf-531ce11b1bf2",
        "email": "[email protected]",
        "normalized_email": "[email protected]",
        "username": "elon",
        "domain": "x.com",
        "mx_record": "aspmx.l.google.com",
        "provider": "google_workspace",
        "score": 80,
        "isv_format": true,
        "isv_domain": true,
        "isv_deliverable": true,
        "isv_nocatchall": false,
        "isv_nogeneric": true,
        "isv_nodisposable": true,
        "isv_nofreeemail": false,
        "isv_nouniversity": true,
        "result": "risky",
        "reason": "catch_all",
        "reason_label": "Catch-all domain (accepts all emails)",
        "email_security": [],
        "protection_level": "basic",
        "domain_info": {
            "has_spf": true,
            "has_dmarc": true,
            "has_website": true,
            "domain_age_days": 8450,
            "domain_created_at": "2003-03-17T00:00:00+00:00",
            "domain_expires_at": "2026-03-17T00:00:00+00:00",
            "registrar": "CSC Corporate Domains, Inc.",
            "registrant_org": "X Corp.",
            "registrant_country": "US",
            "ns_hosts": [
                "ns1.p09.dynect.net",
                "ns2.p09.dynect.net"
            ],
            "a_record_ip": "104.244.42.193",
            "asn": "AS13414",
            "asn_org": "Twitter Inc.",
            "email_security": [],
            "protection_level": "basic"
        },
        "enrichment": {
            "domain": "glossier.com",
            "website": {
                "url": "https://glossier.com",
                "title": "Glossier",
                "is_reachable": true,
                "is_crawl_blocked": false
            },
            "tech_stack": {
                "cms": "wordpress",
                "ecommerce": null,
                "pixels": [
                    "meta_pixel"
                ],
                "analytics": [
                    "google_analytics"
                ],
                "marketing": [],
                "chat": [],
                "affiliate": [],
                "email_security": [
                    "proofpoint"
                ]
            },
            "social_links": {
                "twitter": "glossier",
                "instagram": "glossier",
                "linkedin": "company/glossier"
            },
            "company": {
                "name": "Glossier",
                "industry": "Cosmetics",
                "size": "201-500",
                "type": "Private",
                "founded": 2014,
                "city": "New York",
                "state": "NY",
                "country_code": "US"
            },
            "category": {
                "level": "niche",
                "source": "website",
                "sector": "beauty",
                "sector_label": "Beauty & Personal Care",
                "niche": "beauty.makeup",
                "niche_label": "Makeup & colour cosmetics brand",
                "customer_type": "b2c",
                "customer_type_label": "Consumers",
                "tags": [
                    "sells_online",
                    "d2c_brand"
                ],
                "tag_labels": [
                    "Sells online",
                    "D2C brand"
                ],
                "confidence": 0.93,
                "reason": null,
                "reason_label": null,
                "checked_at": "2026-09-22T09:14:03+00:00",
                "taxonomy_version": "2026-09-22"
            },
            "dns": {
                "has_spf": true,
                "has_dmarc": true,
                "ns_hosts": [
                    "ns1.example.com"
                ],
                "a_record_ip": "93.184.216.34",
                "asn": "AS15133",
                "asn_org": "Edgecast Inc."
            },
            "whois": {
                "registrar": "RESERVED-Internet Assigned Numbers Authority",
                "registrant_org": "IANA",
                "registrant_country": "US",
                "domain_created_at": "1995-08-14T00:00:00+00:00",
                "domain_expires_at": "2025-08-13T00:00:00+00:00",
                "domain_age_days": 10818
            }
        }
    },
    "code": 0,
    "message": "ok"
}
POST /v1/validate/batch

Submit a batch of emails

Submit an array of email addresses for bulk validation. Returns a list ID that you can poll for results.

Request body

emails
array of strings, required

Array of email addresses to validate

Example request

curl -X POST \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"emails": ["[email protected]", "[email protected]"]}' \
  https://api.mailrook.com/v1/validate/batch

Example response (201 Created)

{
    "data": {
        "list_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
        "emails_count": 2
    },
    "code": 0,
    "message": "ok"
}
POST /v1/validate/batch/upload

Upload a file for batch validation

Upload a CSV or TXT file containing one email per line. Maximum file size is 10 MB.

Request body (multipart/form-data)

file
file, required

A .csv or .txt file with one email address per line (max 10 MB)

Example request

curl -X POST \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -F "[email protected]" \
  https://api.mailrook.com/v1/validate/batch/upload

Example response

{
    "data": {
        "list_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
        "emails_count": 150
    },
    "code": 0,
    "message": "ok"
}
GET /v1/validate/list/{list_id}

Get batch results

Retrieve the results of a batch validation. Returns 202 while processing is in progress and 200 when complete.

Path parameters

list_id
string (UUID), required

The list ID returned from the batch submit or upload endpoint

Example request

curl -H "Authorization: Bearer YOUR_API_KEY" \
  https://api.mailrook.com/v1/validate/list/a1b2c3d4-e5f6-7890-abcd-ef1234567890

Response while processing (202)

{
    "data": [],
    "code": 0,
    "message": "List is still processing: 45 of 100 emails done"
}

Example response

{
    "data": [
        {
            "email": "[email protected]",
            "isv_format": true,
            "isv_domain": true,
            "isv_deliverable": true,
            "isv_nocatchall": true,
            "isv_nogeneric": true,
            "isv_nodisposable": true,
            "isv_nofreeemail": true,
            "isv_nouniversity": true,
            "protection_level": "enterprise"
        }
    ],
    "code": 0,
    "message": "ok"
}
GET /v1/enrich/{input}

Enrich a domain or email

Everything we know about the company behind a domain, without running a deliverability check: what it sells (category), its website and tech stack, the company record, DNS and WHOIS. Results are stored, so the same domain returns the same answer instantly on the next call.

Path parameters

input
string, required

An email address (e.g. [email protected]) or domain (e.g. example.com). When an email is provided, the domain is extracted automatically.

Query parameters

fields
string, optional

Comma-separated list of blocks to return: website, tech_stack, social_links, company, category, dns, whois. Omit it and you get all of them. A block you leave out is absent from the response rather than null — and leaving out category is the one that makes a call measurably faster, because it is the only block behind a classifier call. An unknown value is a 422, so a typo never silently bills you for work you tried to skip.

include
string, optional

Set to category_detail to add category.detail: the probabilities, the runner-up niches and the per-tag scores behind the verdict, for callers who want to apply their own thresholds. Absent (null) when the category did not come from the website.

Example request

curl -H "Authorization: Bearer YOUR_API_KEY" \
  https://api.mailrook.com/v1/enrich/glossier.com

Example response

{
    "data": {
        "domain": "glossier.com",
        "website": {
            "url": "https://glossier.com",
            "title": "Glossier",
            "is_reachable": true,
            "is_crawl_blocked": false
        },
        "tech_stack": {
            "cms": "wordpress",
            "ecommerce": null,
            "pixels": [
                "meta_pixel"
            ],
            "analytics": [
                "google_analytics"
            ],
            "marketing": [],
            "chat": [],
            "affiliate": [],
            "email_security": [
                "proofpoint"
            ]
        },
        "social_links": {
            "twitter": "glossier",
            "instagram": "glossier",
            "linkedin": "company/glossier"
        },
        "company": {
            "name": "Glossier",
            "industry": "Cosmetics",
            "size": "201-500",
            "type": "Private",
            "founded": 2014,
            "city": "New York",
            "state": "NY",
            "country_code": "US"
        },
        "category": {
            "level": "niche",
            "source": "website",
            "sector": "beauty",
            "sector_label": "Beauty & Personal Care",
            "niche": "beauty.makeup",
            "niche_label": "Makeup & colour cosmetics brand",
            "customer_type": "b2c",
            "customer_type_label": "Consumers",
            "tags": [
                "sells_online",
                "d2c_brand"
            ],
            "tag_labels": [
                "Sells online",
                "D2C brand"
            ],
            "confidence": 0.93,
            "reason": null,
            "reason_label": null,
            "checked_at": "2026-09-22T09:14:03+00:00",
            "taxonomy_version": "2026-09-22"
        },
        "dns": {
            "has_spf": true,
            "has_dmarc": true,
            "ns_hosts": [
                "ns1.example.com"
            ],
            "a_record_ip": "93.184.216.34",
            "asn": "AS15133",
            "asn_org": "Edgecast Inc."
        },
        "whois": {
            "registrar": "RESERVED-Internet Assigned Numbers Authority",
            "registrant_org": "IANA",
            "registrant_country": "US",
            "domain_created_at": "1995-08-14T00:00:00+00:00",
            "domain_expires_at": "2025-08-13T00:00:00+00:00",
            "domain_age_days": 10818
        }
    },
    "code": 0,
    "message": "ok"
}
GET /v1/taxonomy/company-categories

List the company categories

The full value list behind the category block: every sector, every niche, every business-model tag and every customer type, with a human label and a one-line description each. Static, free, and unmetered — fetch it once to build a dropdown or a set of CRM properties. version changes only when a key is added, renamed or removed, so compare it against the taxonomy_version on any enrichment response to know whether your copy is current.

Example request

curl -H "Authorization: Bearer YOUR_API_KEY" \
  https://api.mailrook.com/v1/taxonomy/company-categories

Example response

{
    "data": {
        "version": "2026-09-22",
        "sector_count": 25,
        "niche_count": 224,
        "sectors": [
            {
                "key": "beauty",
                "label": "Beauty & Personal Care",
                "description": "\u2026 (one line per sector)",
                "niches": [
                    {
                        "key": "beauty.skincare",
                        "label": "Skincare brand",
                        "description": "\u2026 (one line per niche)"
                    },
                    {
                        "key": "beauty.retailer",
                        "label": "Multi-brand beauty retailer",
                        "description": "\u2026"
                    },
                    "\u2026 11 more"
                ]
            },
            "\u2026 24 more sectors"
        ],
        "tags": [
            {
                "key": "d2c_brand",
                "label": "D2C brand",
                "description": "\u2026"
            },
            "\u2026 12 more"
        ],
        "customer_types": [
            {
                "key": "b2c",
                "label": "Consumers",
                "description": "Sells mainly to individual consumers and households"
            },
            {
                "key": "b2b",
                "label": "Businesses",
                "description": "\u2026"
            },
            {
                "key": "both",
                "label": "Consumers and businesses",
                "description": "\u2026"
            },
            {
                "key": "not_applicable",
                "label": "Not a seller",
                "description": "\u2026"
            }
        ]
    },
    "code": 0,
    "message": "ok"
}

Enrichment fields

The enrichment object is returned by the /v1/enrich/{input} endpoint and optionally included in validation responses via ?include=enrichment.

Field Type Description
domain string The domain that was enriched
category
category.level string How precisely the company was placed, and therefore which of the two keys below you can trust: niche (both), sector (sector only — two neighbouring niches split the vote), unclear (neither; see reason). Nothing is forced into a category to look complete.
category.source string What the answer was read from. website: the company's own homepage, the answer you want. domain_name: no usable page text, but the brand was recognised from the domain. company_record: the homepage said nothing, so the industry on our imported company record was mapped onto this taxonomy — coarser and older, never more than a sector or an obvious niche. none: nothing placed it.
category.sector string|null Sector key, e.g. beauty. The value a CRM "Industry" field wants. Null when level is unclear.
category.sector_label string|null Display name, e.g. "Beauty & Personal Care". Labels can be reworded; store and filter on the key.
category.niche string|null Niche key in sector.niche form, e.g. beauty.skincare — the sub-segment a sequence is written for. Set only when level is niche.
category.niche_label string|null Display name, e.g. "Skincare brand".
category.customer_type string|null Who they sell to: b2c, b2b or both. Null when unclear, and always null for a company_record answer, which carries no evidence about customers.
category.customer_type_label string|null Display name: "Consumers", "Businesses", "Consumers and businesses".
category.tags array Business-model tag keys that apply, e.g. ["sells_online", "d2c_brand"]. Independent of the sector and of each other: a D2C skincare brand and Sephora share a sector, and this is what separates them. Empty for a company_record answer.
category.tag_labels array The same tags as display names, in the same order.
category.confidence number|null 0–1 confidence in the niche. Null for a company_record answer — a lookup table has no probability behind it, and inventing one would invite comparison with a number that means something else.
category.reason string|null Why nothing was placed, when level is unclear: crawl_blocked, no_website, parked_page, personal_site, weak_homepage, too_vague, classifier_unavailable. The last one is temporary and worth retrying; the others are about the site itself.
category.reason_label string|null The same reason as a sentence you can show a user.
category.checked_at string|null When this category was determined (ISO 8601). Stored, so a repeat call returns the same answer and the same timestamp until the homepage is crawled again.
category.taxonomy_version string Version of the key list this answer uses. Compare with /v1/taxonomy/company-categories.
category.detail object|null Only with ?include=category_detail. Carries basis, evidence_score, niche_probability, sector_probability, the top three candidates and a probability per tag in signals, for applying your own thresholds. Null unless source is website or domain_name.
website
website.url string|null Resolved website URL
website.title string|null Page title from the website
website.is_reachable boolean Whether the website is reachable
website.is_crawl_blocked boolean Whether crawling is blocked by the website
tech_stack
tech_stack.cms string|null Detected CMS (e.g. wordpress, shopify)
tech_stack.ecommerce string|null Detected e-commerce platform
tech_stack.pixels array Tracking pixels detected (e.g. meta_pixel, tiktok_pixel)
tech_stack.analytics array Analytics tools (e.g. google_analytics, hotjar)
tech_stack.marketing array Marketing tools (e.g. hubspot, mailchimp)
tech_stack.chat array Chat/support widgets (e.g. intercom, zendesk)
tech_stack.affiliate array Affiliate/referral tools
tech_stack.email_security array Email security providers detected from MX records (e.g. proofpoint, mimecast)
social_links
social_links object|null Social media handles found on the website. Keys: twitter, instagram, facebook, youtube, tiktok, linkedin, github. Values are normalized handles/paths (e.g. "acme", "company/acme", "@acme").
company
company.name string|null Company name
company.industry string|null Industry classification
company.size string|null Employee count range (e.g. 51-200)
company.type string|null Company type (e.g. Private, Public)
company.founded integer|null Year founded
company.city string|null City
company.state string|null State or region
company.country_code string|null ISO 3166-1 alpha-2 country code
dns
dns.has_spf boolean|null Domain has an SPF record
dns.has_dmarc boolean|null Domain has a DMARC record
dns.ns_hosts array|null Nameserver hostnames
dns.a_record_ip string|null Primary A record IP address
dns.asn string|null Autonomous System Number
dns.asn_org string|null ASN organization name
whois
whois.registrar string|null Domain registrar
whois.registrant_org string|null Registrant organization
whois.registrant_country string|null Registrant country code
whois.domain_created_at string|null Domain registration date (ISO 8601)
whois.domain_expires_at string|null Domain expiration date (ISO 8601)
whois.domain_age_days integer|null Domain age in days since registration

Company categories

The category block answers four questions about the company behind a domain, read from its own homepage. They are separate on purpose: a D2C skincare brand and Sephora share a sector, and it is the other three that tell you which pitch to send.

sector

What industry

25 values — what a CRM "Industry" field wants. beauty, software, food.

niche

What sub-segment

224 values, keyed sector.niche so the sector always falls out of the niche. This is the level a sequence is written for: a skincare brand and a salon-supply distributor are not the same prospect.

customer_type

Who they sell to

b2c Consumers · b2b Businesses · both Consumers and businesses · not_applicable Not a seller

tags

How they sell

13 independent yes/no business-model flags, cutting across every sector. A brand can be a makeup brand and premium and sold direct; these are three answers, not one category.

How sure the answer is

Read level before anything else: it tells you which keys are safe to use. Nothing is forced into a category to make the response look complete.

level Meaning
niche Both sector and niche are set and safe to route on. Around 90% of domains with a readable homepage land here.
sector sector is set, niche is null: two neighbouring niches split the vote — a soap-and-skincare brand, a furniture maker that is also a store. Use the sector; ?include=category_detail names both candidates if you want to pick one.
unclear Neither is set, and reason says why. Better an honest blank than a wrong industry in your CRM. A classifier_unavailable reason is the only temporary one — retry that domain later.

Where the answer came from

source tells you how much the answer is worth, which level alone cannot. A sector read off a homepage this month and a sector mapped from a LinkedIn industry field typed years ago are both "sector" — and you may well want to treat them differently.

source Meaning
website Read from the company's own homepage — title, description, headlines, first paragraph. The answer you want, and the most current description of the business that exists.
domain_name The site blocked our crawler or had no usable text, but the brand was recognised from the domain itself. Held to a stricter confidence bar than a page read, because there is nothing to check it against.
company_record The homepage said nothing usable, so the LinkedIn-style industry on our company record was mapped onto this taxonomy. A fallback: coarser, older, usually sector-level, and always with confidence: null, tags: [] and customer_type: null, because an industry label is no evidence about those.
none Nothing placed it. level is unclear and reason says why.

Business-model tags

Key Label On when
sells_online Sells online The site itself sells: product pages with prices, add-to-cart, checkout, or paid online booking. An e-commerce platform such as Shopify or WooCommerce in `tech` is strong evidence.
d2c_brand D2C brand Own-brand physical goods (cosmetics, apparel, food, gadgets, supplements) sold to shoppers on the brand's own site, whether or not also sold in stores.
multibrand_retailer Multi-brand retailer Multi-brand shop, marketplace, department store, pharmacy chain, grocery, distributor: most products carry other companies' brand names.
marketplace Marketplace Third-party sellers, creators, hosts, drivers or vendors list on it (Etsy, Airbnb, Upwork, Amazon Marketplace).
saas SaaS Software product with plans, pricing, login, features, integrations, or API as the core offering.
mobile_app Mobile app The site mainly promotes downloading its app; the app is the product.
services_agency Services / agency Agencies, consultants, law or accounting firms, studios, contractors, freelancers, clinics, salons.
manufacturer_wholesale Manufacturer / wholesale Factory, contract manufacturer, ingredients supplier, wholesale-only, "trade customers", minimum order quantities, industrial catalogue.
local_physical_business Physical locations Addresses, opening hours, "visit us", store locator, local city named as the service area, appointments in person.
nonprofit_public Nonprofit / public Charity, NGO, foundation, public agency, municipality, public school or university, religious organisation, association.
restricted_category Restricted category Pornography, casino or betting, cigarettes or vapes, cannabis or CBD products, guns and ammunition, crypto trading or tokens.
natural_clean_positioning Natural / clean Natural/organic/clean/vegan/non-toxic is the headline claim across the range (clean beauty, organic food, natural deodorant).
premium_luxury Premium / luxury Luxury language, high prices, designer, couture, bespoke, prestige, "finest", flagship boutiques.

Sectors and niches

All 24 sectors below, plus other for pages that are not a business at all (parked, personal, unidentifiable). Consumer categories go deep because that is where a generic industry label fails hardest; B2B categories are broad by design. Fetch the full list with descriptions from /v1/taxonomy/company-categories.

Beauty & Personal Care beauty
skincare makeup haircare fragrance nails bath_body mens_grooming oral_care beauty_devices professional_salon_supply salon_spa_services retailer beauty_media
Fashion & Apparel fashion
womenswear menswear unisex_streetwear kidswear activewear lingerie_swimwear footwear jewelry watches bags_accessories eyewear luxury_house sustainable_resale retailer fashion_media
Health & Medical health
hospital_clinic dental pharma_biotech medical_devices telehealth_digital_health mental_health pharmacy healthcare_software health_insurance senior_home_care medical_aesthetics
Fitness, Wellness & Nutrition wellness
supplements gym_studio fitness_equipment fitness_app_coaching yoga_meditation sexual_wellness cbd_cannabis sleep_recovery weight_management wellness_spa
Food & Beverage food
packaged_food confectionery_bakery beverages coffee_tea alcohol restaurant meal_kits_delivery grocery_specialty_retail baby_food plant_based_alt food_manufacturing_b2b catering_foodservice
Home, Garden & Living home
furniture decor kitchen_tableware bedding_bath appliances home_improvement garden_outdoor cleaning_household home_services home_retailer
Consumer Electronics & Hardware electronics
audio wearables phones_accessories computers_peripherals cameras_drones smart_home gaming_hardware ev_micromobility electronics_retailer hardware_b2b
Gaming & Entertainment gaming
game_studio_publisher gaming_platform_esports streaming_video music film_tv_production live_events_venues gambling_betting adult_entertainment toys_collectibles hobbies_crafts
Media, Publishing & Creators media
news_magazine blog_content_site book_publishing podcast_network creator_influencer community_forum newsletter_media
Software & SaaS (B2B) software
marketing_sales_software ecommerce_platform_tools hr_recruiting_software finance_accounting_software developer_tools_infra cybersecurity data_analytics_ai productivity_collaboration customer_support_software vertical_saas it_services_consulting enterprise_software
Consumer Internet & Apps internet
social_dating consumer_utility_app email_webmail_provider web_hosting_domains search_directories gig_sharing_platform telecom_isp consumer_ai
Marketing, Advertising & Agencies marketing
influencer_marketing digital_marketing_agency seo_content_agency creative_branding_agency pr_communications ad_tech_network market_research events_experiential photo_video_production printing_promo
Financial Services finance
bank payments_fintech investing_trading crypto_web3 insurance lending_credit accounting_tax_services personal_finance_app real_estate_finance_proptech
Retail & Marketplaces (multi-category) retail
marketplace department_general_store gift_novelty subscription_box dropship_general_store wholesale_b2b_marketplace
Travel & Hospitality travel
hotel_resort airline booking_ota vacation_rental tours_experiences travel_gear destination_tourism travel_media
Automotive & Transport automotive
vehicle_manufacturer dealership auto_parts_accessories car_rental_sharing ev_charging auto_services logistics_shipping boats_aviation
Sports & Outdoors sports
sporting_goods outdoor_camping cycling water_sports hunting_shooting sports_team_league sports_retailer sports_media golf
Pets pets
pet_food pet_supplies pet_services pet_retailer
Baby, Kids & Family family
baby_gear kids_products parenting_family_media childcare_kids_activities wedding_events fertility_maternity
Education & Training education
k12_school university_college online_courses_platform language_learning tutoring_test_prep bootcamp_professional_training edtech_software kids_education creator_education
Real Estate & Construction realestate
brokerage_listings developer_builder property_management construction_contractor architecture_interior building_materials coworking_office proptech
Professional & Business Services services
law_firm management_consulting staffing_recruiting bpo_outsourcing translation_localization coaching_speaking security_facilities freelance_studio
Industrial, Manufacturing & Supply industrial
machinery_equipment chemicals_materials packaging contract_manufacturing wholesale_distribution energy_utilities agriculture aerospace_defense environmental_services conglomerate_holding textiles_apparel_manufacturing office_supplies_b2b
Government, Nonprofit & Community public
government charity_ngo association_professional_body religious museum_culture political
Keys are the contract, labels are not. Store and filter on sector, niche and tags; the *_label twins are display strings and may be reworded at any time. taxonomy_version (currently 2026-09-22) changes only when a key is added, renamed or removed — never for a wording change — so comparing that one string is enough to know whether your copy is stale. Want to see it on your own domains first? Try the free category check.

Enrichment provider keys

Both /v1/enrich/{input} and /v1/validate/{email}?include=enrichment support third-party enrichment providers for deeper data. Pass provider API keys via the X-Enrich-Providers header as a JSON object:

curl -H "Authorization: Bearer YOUR_API_KEY" \
  -H 'X-Enrich-Providers: {"snov": "your-snov-api-key"}' \
  https://api.mailrook.com/v1/enrich/example.com

Provider keys are never stored — they are only used for the current request. More providers will be added over time.

Response fields

Field Type Description
id string Unique identifier for this validation
email string The email address that was validated
normalized_email string Normalized form of the email (dots removed, +tags stripped, alias domains canonicalized)
username string Local part of the email (before @)
domain string Domain part of the email (after @)
mx_record string|null Primary MX record for the domain
provider string|null Detected email provider (e.g. gmail, google_workspace, microsoft_365, outlook, yahoo, protonmail, icloud, zoho, yandex, mailru, proofpoint, mimecast, aol, fastmail). Null if unknown.
score integer Overall quality score from 0 to 100
isv_format boolean Email has valid syntax (RFC compliant)
isv_domain boolean Domain exists and has valid DNS records
isv_deliverable boolean|null Mail server accepts email for this address. Null if unable to verify.
isv_nocatchall boolean|null Domain is not a catch-all (accepts mail for any address)
isv_nogeneric boolean Not a generic/role address (e.g. info@, support@)
isv_nodisposable boolean Not a disposable/temporary email address
isv_nofreeemail boolean Not from a free email provider (e.g. Gmail, Yahoo)
isv_nouniversity boolean Not from an educational institution domain
result string Overall result: deliverable, undeliverable, risky, or unknown
reason string Reason code: accepted_email, rejected_email, invalid_format, invalid_domain, disposable_email, catch_all, unable_to_verify, sender_blocked
reason_label string|null Human-readable reason label (e.g. "Mailbox not found"). Null for accepted_email.
email_security array Email security gateways detected from MX records (e.g. proofpoint, mimecast, barracuda). Empty array if none detected.
protection_level string Synthesized email protection level: none (no gateway or DMARC enforcement), basic (SPF + strict DMARC policy), or enterprise (dedicated security gateway like Proofpoint or Mimecast).
domain_info object|null Domain WHOIS and DNS information. Null if domain data is not yet available.
domain_info.has_spf boolean|null Domain has an SPF record
domain_info.has_dmarc boolean|null Domain has a DMARC record
domain_info.has_website boolean|null Domain has a reachable website
domain_info.domain_age_days integer|null Domain age in days since registration
domain_info.domain_created_at string|null Domain registration date (ISO 8601)
domain_info.domain_expires_at string|null Domain expiration date (ISO 8601)
domain_info.registrar string|null Domain registrar
domain_info.registrant_org string|null Registrant organization
domain_info.registrant_country string|null Registrant country code
domain_info.ns_hosts array|null Nameserver hostnames
domain_info.a_record_ip string|null Primary A record IP address
domain_info.asn string|null Autonomous System Number
domain_info.asn_org string|null ASN organization name
domain_info.email_security array Email security gateways (same as top-level email_security)
domain_info.protection_level string Protection level (same as top-level protection_level)

Credits & headers

Calls are metered in credits. Every authenticated response carries your balance, so an integration can pace itself without a second request.

What each call costs

Operation Credits Notes
GET /v1/validate/{email} 1 Per address.
GET /v1/validate/{email}?include=enrichment 3 The validation plus the enrichment lookup.
GET /v1/enrich/{input} 2 Per domain, whatever fields you ask for — the company category costs no more than the rest, and a domain already in our index costs the same as a cold one.
GET /v1/taxonomy/company-categories 0 Free and unmetered. It is a static list; fetch it once and cache it against its version.
POST /v1/validate/batch 1 Per unique address. The list is de-duplicated first, and the whole batch is charged up front — a batch you cannot afford is rejected with 402 and nothing is charged.
POST /v1/validate/batch/upload 1 Per unique address, charged up front, same as the JSON batch.
GET /v1/validate/list/{list_id} 0 Reading results is free — the batch was already charged on submission, so polling costs nothing.

Balance headers

Returned on every authenticated response, including the 402. Credits are spent soonest-to-expire first: the daily allowance, then the plan allowance, then purchased credits.

Header Type Description
X-Credits-Remaining integer Everything spendable right now: today's free allowance, plus whatever the plan has left this period, plus purchased credits. This is the one number to poll — it is what runs out.
X-Credits-Free-Today integer Of that total, how much is today's free allowance. Resets at midnight UTC.
X-Credits-Plan integer Of that total, how much of the plan's monthly allowance is left this billing period. Absent on accounts with no plan.
X-Credits-Paid integer Of that total, the purchased balance. Purchased credits never expire and are spent last.
X-Plan string Key of the active plan. Absent on accounts with no plan.

The three bucket headers add up to X-Credits-Remaining; read the total unless you need to know which bucket a call will draw from. Headers for a bucket you do not have are omitted rather than sent as zero, so treat a missing header as "not applicable", not as "empty".

Running out

Once your balance cannot cover a call, it returns 402 and nothing is charged. The body says which allowance ran out and when it comes back, so an integration can back off until then rather than retrying into a wall:

{
    "data": null,
    "code": 402,
    "message": "Insufficient credits to validate",
    "details": {
        "reason": "free_allowance_exhausted",
        "plan": null,
        "daily_free_allowance": 25,
        "free_resets_at": "2026-01-02T00:00:00+00:00",
        "hint": "Your free allowance for today is used up and it resets at midnight. A plan gives you a monthly allowance instead.",
        "billing_url": "https://mailrook.com/billing"
    }
}
details.reason Meaning
free_allowance_exhausted No plan on the account and today's free allowance is spent. It comes back at free_resets_at.
plan_allowance_exhausted The plan's allowance for this billing period is spent and there is no purchased balance to fall back on.

Error responses

Every response carries the same envelope: data, a numeric code, and a message. On success code is 0; on failure it mirrors the HTTP status, and data is null.

HTTP Status Meaning
200 Success.
201 Batch accepted. The body carries the list_id to poll.
202 Batch still processing. The message reports how many of the addresses are done; poll again.
401 Missing or invalid API key.
402 Out of credits. See the credits section below — the body says which allowance ran out and when it comes back.
404 Unknown list id, or no such endpoint.
422 Invalid email format, unresolvable domain, or a missing required field.
500 Internal server error.

Rate limits

API requests are rate-limited per account. If you exceed your limit, you will receive a 429 response. Contact us if you need higher limits for your use case.

Ready to get started?

Create a free account and get your API key in seconds.

Get your API key