Quick start
The imail API uses standard REST conventions: JSON bodies, predictable URLs, HTTP verbs that mean what you think they mean. Available on Surge and above.
1. Get an API key
Generate a key in Settings → API keys. Keys are scoped to a workspace. Rotate any time.
2. Make a request
3. Parse the response
Authentication
All requests must include a bearer token in the Authorization header. Keys are scoped to a single workspace — to access multiple workspaces, generate one key per workspace.
Test mode keys start with imk_test_ and operate against a separate ledger — useful for CI without burning real warmup quota.
Error handling
Errors use standard HTTP codes plus a structured body. We try to make the error message actionable, not just descriptive.
| Status | When |
|---|---|
| 400 | Malformed request, validation failed |
| 401 | Missing or invalid API key |
| 403 | Key valid but workspace lacks the feature (tier gate) |
| 404 | Resource doesn't exist or isn't yours |
| 409 | Conflict (e.g. duplicate inbox connection) |
| 429 | Rate limited — see Retry-After header |
| 5xx | Our fault. Includes request_id — send it to support and we'll dig. |
Rate limits
Per API key. Token bucket. Burst-friendly.
| Tier | Sustained | Burst |
|---|---|---|
| Surge | 100 req/min | 240 req |
| Velocity | 500 req/min | 1,200 req |
| Apex | Negotiated | Negotiated |
Every response includes X-RateLimit-Remaining and X-RateLimit-Reset headers. On a 429, retry after the value in Retry-After (seconds).
Campaigns
A campaign is a multi-step sequence sent to a list of leads from one or more connected inboxes.
Create a campaign
| Field | Type | Description | |
|---|---|---|---|
| name | string | required | Display name. Max 120 chars. |
| inbox_ids | string[] | required | Connected inboxes to send from. |
| steps | Step[] | required | Sequence of up to 20 steps with conditional branches. |
| daily_limit | integer | Cap emails/day. Default: tier max. | |
| send_window | SendWindow | Local timezone send hours. Default: 9–17 weekdays in lead's tz. | |
| track_opens | boolean | Default: true. | |
| track_clicks | boolean | Default: true. |
Leads
Leads are the recipients in a campaign. Bring your own (CSV / Apollo / Hunter / scraping pipeline) — imail doesn't host a lead database.
Inboxes
Sending mailboxes connected via SMTP/IMAP. Adding an inbox returns a setup_url for OAuth providers.
Analytics
Per-campaign, per-inbox, per-day. Returns raw counts; you compute rates. CSV export available via ?format=csv.
Public metrics
No auth required. Used to power the public metrics page. Cached 30s at the edge.
Webhooks
Subscribe to real-time events. HMAC-signed (SHA-256) using your webhook secret. Retries on failure: exponential backoff up to 24h.
Event types
| Event | Fires when |
|---|---|
| email.sent | Email successfully handed to SMTP |
| email.delivered | 250 OK from recipient ESP |
| email.opened | Tracking pixel hit |
| email.clicked | Tracked link clicked |
| email.bounced.hard | Hard bounce (auto-suppressed) |
| email.bounced.soft | Soft bounce with category |
| reply.received | New reply from a lead |
| reply.classified | iBrain finished classifying |
| warmup.threshold_paused | Auto-pause triggered on warmup |
| inbox.disconnected | IMAP/SMTP connection lost |
| inbox.reconnected | Connection restored |
Verifying signatures
Versioning
Major versions in the path: /v1/.... Within a major version, we never break existing fields — only add new ones. Deprecations get a minimum 12-month sunset with email warnings starting at 6 months out.
Pinning to a specific minor: set the Imail-Version header to a date string, e.g. 2026-03-01. We'll route to that snapshot of the API.
API changelog
API-specific changes. Product changelog is at /changelog.
| Date | Change |
|---|---|
| 2026-05-10 | Added email.bounced.soft and warmup.threshold_paused webhook events. |
| 2026-04-22 | New endpoint POST /v1/leads/bulk (up to 5000 per call). |
| 2026-03-10 | v1 stable. Public OpenAPI 3.1 spec at /openapi.json. |