REST API · WEBHOOKS · POP3 · IMAP

Email testing with serious muscle

Give every test its own real inbox. Capture the email your app sends, wait for it without a fixed sleep, and assert on parsed codes and links — from CI, your code, or an AI agent.

Free plan · No credit card required · 14-day trial on paid plans
signup.test.ts
import { MailhulkClient } from '@mailhulk/sdk'
const apiKey = process.env.MAILHULK_API_KEY!
const mh = new MailhulkClient({ apiKey })
 
// 1. A real inbox for this test only
const inbox = await mh.inboxes.create()
 
// 2. Trigger your app
await signUp(inbox.address)
 
// 3. Bounded wait — no sleep(10)
const mail = await mh.inboxes.waitForMessage(inbox.id, {
timeoutMs: 60_000,
match: (m) => m.codes.length > 0,
})
expect(mail.codes[0]).toHaveLength(6)
One inbox
per test run, 60 s to 30 days TTL
≤ 60 s
server-side long-poll wait
993 / 995
IMAP & POP3 over TLS
OpenAPI
contract for every /v1 route
HOW IT WORKS

Three calls between a flaky test and a green one

  1. 01

    Create an isolated inbox

    Each run gets a fresh address that nothing else writes to, so a stale or parallel message can never satisfy your assertion.

  2. 02

    Wait for the message

    A server-side long poll returns the moment mail lands, with an explicit timeout so a missing email fails fast and clearly.

  3. 03

    Assert on parsed content

    Verification codes, links, bodies, headers and attachments are already extracted — no MIME parsing in your test code.

The usual workaround compared with MailHulk

  • Usual workaround: One shared inbox that every run and every teammate reads

    With MailHulk: A fresh inbox per run that nothing else can write to

  • Usual workaround: sleep(10) and hope the email made it in time

    With MailHulk: A long poll that returns on arrival, or 204 at your timeout

  • Usual workaround: Regex over raw MIME to dig out a code or link

    With MailHulk: Codes, links and bodies arrive already parsed

  • Usual workaround: Cleanup scripts for every inbox a crashed run left behind

    With MailHulk: A TTL from 60 s to 30 days expires the inbox by itself

FEATURES

Everything email, done heavy-duty

REST API for everything

Create inboxes, list messages, read links and attachments — one bearer token, JSON envelopes and a published OpenAPI contract.

Signed webhooks

An authenticated callback after each message is stored, with retries and a visible delivery history when an endpoint misbehaves.

POP3/IMAP access

Standard TLS mail protocols when your system needs a real mailbox. Dedicated server capacity starts on Pro.

Unlimited inboxes on paid plans

A fresh address per test run with no pooling or cleanup scripts. Paid plans never meter inboxes; Free includes 25.

Deep email parsing

HTML and plain-text bodies, links, verification codes and attachment metadata extracted automatically on arrival.

Custom domains

Receive on your own domain with a copy-ready DNS guide and automatic verification, from Pro upwards.
API FIRST

Use the API or a standard mail protocol

Every capability is plain HTTP and JSON. Wait on an inbox with a long poll, receive signed webhook deliveries, or connect a mail client over POP3/IMAP.

  • Responses wrapped in a stable data envelope
  • 204 until mail arrives, never a guess
  • Full MIME, attachments, HTML & links parsed
Browse the API reference
# Wait up to 30 s for the next message
BASE=https://mailhulk.net/v1
curl "$BASE/inboxes/$INBOX_ID/messages/latest?wait=30" \
-H "Authorization: Bearer $MAILHULK_API_KEY"
 
# → 200 OK (204 No Content if nothing arrived)
{ "data": {
"subject": "Verify your email",
"from": { "email": "noreply@yourapp.com", "name": "YourApp" },
"codes": ["481902"],
"links": ["https://yourapp.com/verify?token=…"]
} }
WORKS WITH YOUR STACK

Fits the way you already test

Call the API directly, or reach for a client built around the same bounded-wait semantics. Availability is labelled honestly.

AVAILABLE

JavaScript SDK

Typed TypeScript client with zero dependencies. waitForMessage scans existing mail before it waits.

npm install @mailhulk/sdk
AVAILABLE

REST API + OpenAPI

Every capability over HTTP and JSON, documented by a downloadable OpenAPI contract.

GET /v1/inboxes/{id}/messages/latest?wait=30
AVAILABLE

POP3 / IMAP

Point an existing mail library or client at a real mailbox over TLS.

imap.mailhulk.net:993 · pop3.mailhulk.net:995
PREVIEW

MCP server

Eleven inbox and message tools for coding and QA agents, over stdio or HTTP, scoped to a Test project.

wait_for_message · get_message · release_session
COMING SOON

CLI

Create an inbox and wait for a code from any shell step, with CI-friendly exit codes.

mailhulk mail wait "$ADDRESS" --extract code
COMING SOON

Python & PHP SDKs

The same inbox and wait semantics for pytest and PHPUnit suites. Plain HTTP works today.

mh.inboxes.wait_for_message(inbox.id, timeout=60)
PRICING

Choose the isolation your tests need

Free
$0 /mo
No card required
Prove one real email flow end to end.
✓ 3-day retention
✓ 25 concurrent inboxes
✓ 3 team members
✓ 50 MiB per inbox
✓ 250 MiB team storage
✓ REST API + webhooks
Start for free
Starter
$9 /mo
Billed monthly
A first suite in CI, without a shared inbox.
✓ 7-day retention
✓ Unlimited inboxes
✓ 5 team members
✓ 250 MiB per inbox
✓ 2 GiB team storage
✓ REST API + webhooks
Start free trial
Business
$99 /mo
Billed monthly
More projects, retention, storage, and support.
✓ 90-day retention, or custom
✓ Unlimited inboxes
✓ Unlimited team members
✓ 10 custom domains
✓ 5 GiB per inbox
✓ 50 GiB team storage
✓ REST API + webhooks
Start free trial

Dedicated POP3/IMAP servers and custom domains start on Pro; Enterprise and custom terms are on the pricing page. Compare every plan capability.

FROM THE BLOG

Guides for deterministic email tests

All articles
FAQ

Frequently asked questions

MailHulk creates isolated inboxes for testing. Send your application email to those addresses, then inspect captured messages through REST, webhooks, POP3, or IMAP. It is receive-only: nothing is sent or relayed onward.

Give your test suite real muscle

Create an isolated inbox and make email failures reproducible.

No credit card required · 14-day trial on paid plans