Mailgun vs Amazon SES: Which Should You Build On?
The comparison that matters is not the price page. It is how much of the email pipeline you have to build yourself.
If you are building anything where email is the product surface — a helpdesk, a ticketing system, anything that turns inbound mail into records — the provider choice is an architectural decision, not a billing one. Price pages will not tell you which one to pick, because the difference that matters is how much of the pipeline you inherit and how much you build.
The Short Version
- Mailgun gives you a working inbound pipeline in an afternoon. You pay for that convenience every month.
- Amazon SES is dramatically cheaper and has no inbound pipeline at all. You build it.
If email is incidental to your product, the convenience is worth the money. If email is your product, you will end up wanting control over the pipeline anyway.
Sending: Barely Different
For outbound mail the two are close enough that it should not decide anything. Both do Easy-DKIM-style signing, both want SPF and DMARC, both give you a REST call and a message ID back. SES asks you to set up a MAIL FROM subdomain so bounces come back to a domain you control; Mailgun handles the equivalent for you.
The one real difference is reputation model. Mailgun pools reputation across its own infrastructure and polices who sends through it. SES makes reputation yours: your bounce and complaint rates sit on your account, and AWS will put you back in the sandbox if you let them drift. That is more responsibility, and also more upside — nobody else's spam affects your delivery.
Receiving: Where the Real Difference Lives
Mailgun has an inbound webhook. You point a route at a URL, Mailgun parses the MIME for you, and you receive tidy JSON with body-plain, body-html, a parsed sender, and attachments.
SES has no such thing. Inbound on SES is a receipt rule that drops raw MIME into an S3 bucket and notifies you. What you build on top is your problem:
- An S3 bucket with a policy allowing SES to write to it
- An SNS topic or SQS queue to learn that an object landed
- A worker that fetches the object and parses raw MIME yourself
- Your own deduplication, because the delivery guarantee is at-least-once
- Your own spam and virus handling from the verdict headers SES stamps on
That is a real chunk of engineering. It is also the part where you gain the most, because you end up owning the parse — and email parsing is where all the interesting bugs live.
The Message-ID Trap
This is the single most important operational difference, and it is barely documented.
Mailgun preserves the sender's Message-ID. SES rewrites it. If your threading logic matches an inbound In-Reply-To against the message IDs you stored — which is the obvious way to build it, and what almost everyone does — that logic silently breaks the day you move to SES. Replies stop threading and every response opens a new ticket.
If you build on SES, threading must not depend on the provider leaving the ID alone. In practice that means layering: inject your own stable reference into outbound headers, match the provider's ID by prefix, and keep a heuristic fallback on sender plus normalised subject plus recency. Get this wrong and the symptom is not an error — it is a quietly duplicating ticket list.
Cost
SES is roughly an order of magnitude cheaper at small-to-mid volume, and the gap widens as you grow. For a bootstrapped product that difference is not a rounding error — it is the difference between email being a line item and email being invisible.
But price the engineering honestly. If building and maintaining the inbound pipeline costs you a week now and an afternoon a quarter forever, that is a real number too. The saving only wins if email volume is central enough to justify it.
How To Decide
Choose Mailgun if email is a supporting feature, you want inbound working this week, and you would rather not own a queue, a bucket, and a MIME parser.
Choose SES if email volume is core to the product economics, you are already on AWS, and you want control over parsing and threading — because sooner or later you will need it.
If you land on SES, the pipeline is the work. Receiving inbound email with Amazon SES walks through the receipt rule, the S3 and SQS wiring, MIME parsing, and the deduplication you will need on day one.
Want to skip the pipeline entirely? GoPimi runs it for you — inbound email becomes a ticket, replies thread correctly, and bounces are handled. See the Email Pipeline guide.