Skip to content

Limits & quotas

Every limit Mailway enforces, and — just as important — what actually happens when you reach it. Prices live on the pricing page, tier features and add-ons on Plans & add-ons; this page is the engineering view.

Free Pro Team Business Enterprise
Emails / month 1,000 10,000 40,000 100,000 custom
Throughput / month 250 MB 2.5 GB 10 GB 25 GB custom
Retention 30 days 90 days 180 days 1 year custom
Projects 1 5 15 unlimited unlimited
Sender domains 1 10 75 unlimited unlimited

When you hit them:

  • Email volume — Free stops at the cap (402 monthly_quota_exceeded); paid plans keep sending (soft overage) and you’ll get a heads-up email at 80% and 100%.
  • Throughput (total message bytes) — paid plans get a grace margin past the cap, then sends hold (402 throughput_quota_exceeded) until the month rolls over, an add-on, or an upgrade; Free holds at the cap.
  • Free daily ceiling — additionally, Free sends at most 200 messages per UTC day (429 daily_send_cap_exceeded). It’s an abuse valve, not a billing lever — it resets at midnight UTC.
  • Quotas reset with the calendar month (UTC). Sandbox sends count toward nothing.
Limit Value Over it
Recipients per message (to+cc+bcc) 50 422 — split the audience or use batch
Subject 998 bytes 422 (RFC 5322 line limit)
html / text body 2 MB each 422
Attachments per message 20 422
Single attachment (decoded) 10 MB 422 attachments:too_large
All attachments combined (decoded) 25 MB 422 attachments:total_too_large
tags 10 × 64 chars 422
metadata 10 keys · 40-char keys · 500-char values 422
Idempotency-Key 12–40 chars of [A-Za-z0-9_-] 422
Batch elements per request 100 422
scheduled_at horizon ≥ now · ≤ 72 h ahead 422 scheduled_at:too_soon / :too_far

Mail arriving over the SMTP relay isn’t shaped by the API validator — but provider recipient caps still apply, which is where the over-cap fan-out takes over.

Surface Limit Keyed by
Send API, authenticated 600 requests / minute your API key
Send API, unauthenticated 60 requests / minute client IP

Per-key (not per-IP) on purpose: tenants sharing an egress IP — NAT, serverless — never throttle each other. Throttled requests get a 429 with a Retry-After header; back off and retry, with an idempotency key so the retry can’t double-send. One batch request counts once against the rate limit but each accepted element counts against your quotas.

The surface is versioned in the path (/v1/) and changes are additive-only: new optional fields and new endpoints may appear; existing fields, semantics, and error codes don’t change meaning within v1. Branch on error.code, never on error.message.