Documentation

Learn how to use EmailSpect's SMTP behavior simulation and webhook features

Quick Start

EmailSpect uses plus addressing to simulate different SMTP behaviors. Send an email to any address with a +command suffix to trigger the behavior.

Example:

test+550@yourdomain.com

This will simulate a "550 Mailbox unavailable" bounce response.

Local Development Setup

To send emails directly to EmailSpect from your local application, configure your app to use our SMTP server.

Laravel .env configuration:

MAIL_MAILER=smtp
MAIL_HOST=retty.email
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null

Why port 2525 instead of 25?

Most ISPs and cloud providers block outbound connections to port 25 to prevent spam. Port 2525 is a common alternative that bypasses these restrictions. Both ports are supported by EmailSpect.

How It Works

EmailSpect acts as the receiving mail server for your domain. When you send an email through your provider, here's what happens:

1

Your Application Sends Email

Your app (Laravel, Node.js, etc.) sends an email through your SMTP provider (Postmark, SendGrid, Mailgun, etc.) to an address like test+550@retty.email

2

Provider Delivers to EmailSpect

Your email provider looks up the MX record for the domain and connects to EmailSpect's SMTP server to deliver the email.

3

EmailSpect Receives & Logs

EmailSpect receives the email, parses the +550 behavior command, and logs the email to the inbox for your review.

4

EmailSpect Simulates Response

EmailSpect returns the simulated SMTP response (e.g., 550 5.1.1 Mailbox unavailable) to your email provider during the SMTP transaction.

5

Provider Reports the Bounce

Your email provider (Postmark, etc.) sees the 550 response and reports it as a bounce through their dashboard and webhooks, just like a real bounce would occur.

Key Insight: This lets you test how your application handles bounce notifications from your email provider without affecting real users. The entire flow is identical to a real-world bounce scenario.

Behavior Simulation

Control how EmailSpect responds to incoming emails using plus addressing.

By default, all emails are accepted normally with a 250 OK response. Add a +command to the email address to simulate different SMTP responses.

Unrecognized suffixes are ignored. Sending to test+anything@domain.com will be accepted normally if anything isn't a known command. This lets you use plus addressing for organization (like Gmail) while reserving specific commands for behavior simulation.

Success Responses (2xx)

Normal delivery - email is accepted and stored.

Address SMTP Code Description
test@domain.com 250 2.0.0 Email accepted and delivered (default behavior)
test+spam@domain.com 250 2.0.0 Email accepted but marked as spam
test+blackhole@domain.com 250 2.0.0 Email accepted but silently discarded (not stored)
Permanent Failures (5xx)

These errors indicate the delivery permanently failed and should not be retried.

Command Aliases SMTP Code Description
+550 +bounce, +reject, +nouser 550 5.1.1 Mailbox unavailable - user does not exist
+551 +moved 551 5.1.6 User not local / mailbox has moved
+552 +full, +quota 552 5.2.2 Mailbox full - exceeded storage allocation
+553 +notallowed 553 5.1.3 Mailbox name not allowed
+554 +failed 554 5.7.1 Transaction failed - message rejected
Temporary Failures (4xx)

These errors indicate a temporary issue - the sender should retry later.

Command Aliases SMTP Code Description
+421 +unavailable, +down 421 4.3.2 Service temporarily unavailable
+450 +busy 450 4.2.1 Mailbox temporarily unavailable
+451 +tempfail, +retry 451 4.3.0 Local error in processing
+452 +nostorage 452 4.3.1 Insufficient system storage
Special Behaviors

Advanced testing scenarios for edge cases and specific behaviors.

Command Aliases Description
+timeout +hang, +freeze Server never responds - connection hangs until client timeout
+greylist +graylist First attempt returns 450, retry within 5 minutes succeeds
+blackhole +drop, +null, +devnull Accepts email but does not store it (returns 250 OK)
+spam +junk Accepts and stores email, marks as spam
+delay{N} +slow{N} Delays SMTP response by N seconds (max 120)

Delay Example:

test+delay30@yourdomain.com

This will delay the SMTP response by 30 seconds, useful for testing timeout handling.

Webhooks

Receive real-time notifications when emails arrive.

Configuration

Configure webhooks per domain in Domain Settings. When an email is received, we'll send a POST request to your configured URL.

Request Headers
Content-Type: application/json
User-Agent: EmailSpect-Webhook/1.0
X-EmailSpect-Event: email.received
X-EmailSpect-Delivery-ID: <email-uuid>
X-EmailSpect-Signature: <hmac-sha256> (if secret configured)
Payload Structure
{
  "event": "email.received",
  "timestamp": "2026-02-06T22:10:00+00:00",
  "email": {
    "uuid": "550e8400-e29b-41d4-a716-446655440000",
    "message_id": "<abc123@example.com>",
    "from_address": "sender@example.com",
    "from_name": "John Doe",
    "to_address": "test@yourdomain.com",
    "subject": "Hello World",
    "text_body": "Email content...",
    "html_body": "<p>Email content...</p>",
    "has_attachments": false,
    "received_at": "2026-02-06T22:10:00+00:00"
  },
  "smtp": {
    "behavior": "550",
    "behavior_label": "Bounced (550)",
    "response_code": 550,
    "response_message": "550 5.1.1 Mailbox unavailable",
    "is_delivered": false
  },
  "inbox": {
    "uuid": "...",
    "address": "test@yourdomain.com"
  },
  "domain": {
    "name": "yourdomain.com"
  }
}
Verifying Signatures

If you've configured a webhook secret, verify the signature to ensure the request is authentic:

// PHP Example
$payload = file_get_contents('php://input');
$signature = $_SERVER['HTTP_X_EMAILSPECT_SIGNATURE'];
$expected = hash_hmac('sha256', $payload, $secret);

if (hash_equals($expected, $signature)) {
    // Signature valid
}
Common Use Cases

Ideas for testing your email functionality.

Test Bounce Handling

Send to user+550@domain to verify your app correctly handles permanent bounces and updates user records.

Test Retry Logic

Send to user+451@domain to test that your app properly retries on temporary failures.

Test Timeout Handling

Send to user+timeout@domain to verify your app handles SMTP timeouts gracefully.

Test Slow Servers

Send to user+delay10@domain to test how your app handles slow SMTP responses.