REST API · v1

Drop-in email verification in three lines.

Generate a key, POST an email, get a verdict. JSON in, JSON out. No SDK required.

Base URL

https://mailoclean.com/api/v1

Rate limit

60 req/min per key

Auth

Bearer token in header

On this page

Quickstart

Three steps

  1. 1

    Create an account

    Free starter credits, no card needed. Sign up →

  2. 2

    Generate a key

    Inside the dashboard, hit Create new key. Copy it once — we hash it on save.

  3. 3

    Send a request

    Pass the key as a bearer token. Every endpoint returns JSON with a clear shape.

Your first request
curl -X POST "https://mailoclean.com/api/v1/verify" \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"email":"hello@company.com"}'
POST /api/v1/verify 1 credit · cached responses are free

Verify a single email

Returns the deliverability verdict, confidence score (0–100), and a breakdown of every check.

Request
curl -X POST "https://mailoclean.com/api/v1/verify" \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"email":"jane@company.com"}'
Response · 200
{
  "email": "jane@company.com",
  "status": "valid",
  "score": 95,
  "checks": {
    "syntax": true,
    "domain": true,
    "mx": true,
    "smtp": true,
    "mailbox_exists": true,
    "disposable": true,
    "catch_all": true,
    "role_based": true,
    "greylisted": true,
    "blacklisted": true,
    "mailbox_full": true
  },
  "provider_status": "safe",
  "provider_message": "Mailbox exists and is safe to send.",
  "cached": false
}
Status values & field reference

status — one of: valid invalid risky catch_all disposable role_based spamtrap unknown

score — int 0–100. 95+ is safe to send.

checks — object. Each key is true (passed), false (failed), or null (skipped).

cached — boolean. True if the result was served from the 24-hour cache (no credit charged).

POST /api/v1/bulk Returns 202 with a batch id you poll

Submit a bulk batch

Submit comma, newline, or array of emails. We queue it, charge credits as items finish, and you poll for status.

Request
curl -X POST "https://mailoclean.com/api/v1/bulk" \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"emails":"a@x.com,b@y.com,c@z.com"}'
Response · 202
{
  "id": 42,
  "status": "queued",
  "total": 3,
  "processed": 0,
  "poll_url": "https://mailoclean.com/api/v1/bulk/42",
  "created_at": "2026-05-18T07:42:11+00:00"
}

Duplicates and invalid-syntax addresses are dropped before queueing. emails can be a comma/newline string or a JSON array.

GET /api/v1/bulk/{id} Poll for progress + items

Get batch status

Returns the current state plus the latest 200 items. Batch status moves through queued → processing → done (or partial/cancelled/failed).

Request
curl "https://mailoclean.com/api/v1/bulk/42" \
  -H "Authorization: Bearer YOUR_API_KEY"
Response · 200
{
  "id": 42,
  "status": "processing",
  "total": 5000,
  "processed": 3200,
  "valid_count": 2640,
  "invalid_count": 380,
  "risky_count": 180,
  "created_at": "2026-05-18T07:42:11+00:00",
  "updated_at": "2026-05-18T07:51:04+00:00",
  "items": [
    {
      "email": "jane@company.com",
      "status": "valid",
      "score": 95,
      "checks": { "syntax": true, "mx": true, "smtp": true },
      "created_at": "2026-05-18T07:50:58+00:00"
    }
  ]
}
GET /api/v1/usage Free · returns balance + activity

Account usage

Check remaining credits, rate-limit ceiling, and the last 20 API requests on this key.

Request
curl "https://mailoclean.com/api/v1/usage" \
  -H "Authorization: Bearer YOUR_API_KEY"
Response · 200
{
  "credits_total": 50000,
  "credits_used": 12480,
  "credits_available": 37520,
  "rate_limit_per_minute": 60,
  "requests_today": 412,
  "requests_last_30_days": 9784,
  "api_key_last_used_at": "2026-05-18T07:55:12+00:00",
  "recent_requests": [
    { "endpoint": "api/v1/verify", "method": "POST", "ip": "203.0.113.10", "created_at": "..." }
  ]
}

SDK-free

Code snippets

No package to install. Plain HTTP works in every language.

cURL
curl -X POST "https://mailoclean.com/api/v1/verify" \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"email":"hello@company.com"}'
JavaScript (fetch)
const res = await fetch("https://mailoclean.com/api/v1/verify", {
  method: "POST",
  headers: {
    "Authorization": `Bearer ${process.env.MAILOCLEAN_KEY}`,
    "Content-Type": "application/json",
    "Accept": "application/json",
  },
  body: JSON.stringify({ email: "hello@company.com" }),
});
const data = await res.json();
if (data.status !== "valid") {
  throw new Error(`Rejected: ${data.status}`);
}
PHP / Laravel
use Illuminate\Support\Facades\Http;

$response = Http::withToken(config('services.mailoclean.key'))
    ->acceptJson()
    ->post('https://mailoclean.com/api/v1/verify', ['email' => 'hello@company.com']);

$data = $response->json();
abort_if(($data['status'] ?? null) !== 'valid', 422, 'Bad email.');
Python (requests)
import os, requests

res = requests.post(
    "https://mailoclean.com/api/v1/verify",
    headers={"Authorization": f"Bearer {os.environ['MAILOCLEAN_KEY']}"},
    json={"email": "hello@company.com"},
    timeout=10,
)
data = res.json()
if data["status"] != "valid":
    raise ValueError(f"Bad email: {data['status']}")

Errors

Error codes

Every error returns JSON. Status code maps directly to cause.

401 Invalid or missing API key
402 Insufficient credits
404 Resource not found (batch/endpoint)
422 Validation failed (missing/invalid fields)
429 Rate limited — back off + retry
500 Server error — retry with backoff

Rate limits

Stay polite

Defaults work for most apps. Need more? Open a support ticket.

  • 1 60 requests/min per API key. Counts every successful, validated request.
  • 2 429 means back off. Retry with exponential delay (1s, 2s, 4s, 8s).
  • 3 Use bulk for lists. A single /bulk call beats 1000 loop iterations.

Try it live

Test against the real endpoint

Paste an API key, hit a real POST /api/v1/verify call. One credit per successful response (cache hits are free).

Sign up to get one in seconds.

Start verifying in minutes

Free starter credits. Credits never expire. One wallet for API, single, and bulk.