Testing Email Verification

How to robustly automate registration flows with Playwright or Cypress.

your address

-

OTP codessignup confirmationspassword resetsmagic linksverification emailsnewsletter testswebhook receipts
OTP codessignup confirmationspassword resetsmagic linksverification emailsnewsletter testswebhook receipts

Live inbox

Auto-refreshing every 10 seconds.

Nothing here yet

Send a test mail or use the address on a signup form. New messages land here automatically.

The Challenge of Email Verification

Email verification is a critical security step for any modern web application. It proves that the user owns the email address they registered with and prevents bot networks from creating millions of fake accounts.

However, testing this flow in an automated E2E (End-to-End) suite is notoriously difficult. Testing frameworks like Cypress and Playwright are designed to automate browsers, but they struggle when forced to interact with third-party email clients (like Gmail or Outlook) due to CAPTCHAs, 2FA, and cross-origin security policies.

The Headless API Solution

The industry standard approach to testing email verification is to use a headless disposable email API. Instead of driving a browser to read an email, your test script makes an HTTP request to an API to fetch the raw email data.

Step-by-Step with Playwright

Here is a conceptual guide on how to test a standard "Magic Link" or OTP verification flow using Test Emails and Playwright.

1. Provision the Test Inbox

At the very beginning of your test, generate a new inbox.

const inboxRes = await request.post('https://test-emails.com/hcgi/api/mailbox');
const { address, token } = await inboxRes.json();

2. Execute the Signup Flow

Drive the browser to your application's signup page and input the newly generated address.

await page.goto('https://staging.your-app.com/signup');
await page.fill('input[name="email"]', address);
await page.click('button[type="submit"]');

3. Poll for the Email

Email delivery is asynchronous. Your test must poll the Test Emails API until the verification email arrives.

let messages = [];
// Poll every 1 second, up to 10 seconds
for (let i = 0; i < 10; i++) {
  const messagesRes = await request.get('https://test-emails.com/hcgi/api/mailbox/messages', {
    headers: { 'x-mail-token': token }
  });
  const data = await messagesRes.json();
  if (data.messages.length > 0) {
    messages = data.messages;
    break;
  }
  await new Promise(r => setTimeout(r, 1000));
}
expect(messages.length).toBeGreaterThan(0);

4. Assert and Extract

Parse the email body to extract the verification link or OTP, and complete the test.

const emailBody = messages[0].text;
const otp = emailBody.match(/Your code is (\d{6})/)[1];

await page.fill('input[name="otp"]', otp);
await page.click('button:has-text("Verify")');
await expect(page.locator('.dashboard')).toBeVisible();

Why Test Emails?

Test Emails provides this API completely free of charge. It's fast, doesn't require API keys or accounts, and provides isolated inboxes perfect for parallelized test execution. Give it a try on your next project!