Skip to content
Blog / Developer Resources

Email Deliverability 101

Michael Kim

A high-level, engineering-first guide to why emails land in the inbox (or don't).

  • email
  • deliverability
  • smtp
  • spf
  • dkim
  • dmarc
  • reputation

Email Deliverability 101

Most people treat deliverability like a checkbox.

We set up SPF and DKIM. Why are we still going to spam?

The frustrating truth is: deliverability is not one setting. It's a trust system. Mailbox providers (Gmail, Outlook, Yahoo, etc.) are constantly scoring whether you deserve inbox placement.

I will be using a credit score analogy throughout this blog because it is quite analagous.

This post is a high-level mental model of deliverability. I'll walk through the layers in the order they're actually evaluated:

  1. Authentication & Identity (SPF, DKIM, DMARC)
  2. Reputation (Domain, IP, Sender)
  3. Sending Behavior (Bounces, Volume, Patterns)
  4. Content & Message Quality
  5. Engagement & User Signals

Then I'll cover why emails go to spam and give you a practical checklist.

TL;DR

  • "250 OK" is not the same as "inbox." It just means the receiver accepted the message.
  • Deliverability is a pipeline of trust: identity → reputation → behavior → content → engagement.
  • SPF / DKIM prove identity, and DMARC enforces and aligns it.
  • Bounces and complaints destroy reputation fast.
  • Reputation exists at multiple layers: domain, IP, and sender identity.

The Email Reality Check: "Delivered" ≠ "In Inbox"

250 OK's don't mean much in terms of deliverability. It just means the server said okay to your message.

So when you ask:

"Why didn't my email show up?"

You need to be precise about which stage failed.

Here's the actual set of outcomes:

  1. Not accepted (SMTP rejected)
  2. Accepted (SMTP 250 OK)
  3. Delivered (landed somewhere in the mailbox)
  4. Spam (filtered)
  5. Inbox (placed)
  6. Missing (silently filtered or user rules)

Deliverability lives in stages 2 to 6.

Important: The SMTP sender can "successfully hand off" the message and still lose the deliverability battle after that.

The Deliverability Stack

When you debug deliverability, debugging random symptoms is painful:

  • "Some users get it, some don't."
  • "It works for Outlook but not Gmail."
  • "Marketing emails go to spam but password resets are fine."

Here's the frame of thinking I like to use:

Loading diagram...

Takeaway: If layer 1 is broken, nothing below it matters. Each layer is a gate. Pass all five to reach the inbox.

Let's walk through each layer!

Layer 1: Authentication (SPF, DKIM, DMARC)

These three are the foundation. It's checked first, and if it fails, you're already in trouble.

Fundamentally, it's proving you are who you say you are.

SPF DKIM DMARC answer:

  1. Who is allowed to send for this domain?
  2. Was the message modified in transit?
  3. Is the "visible sender" aligned with the authenticated identity?
  4. What should receivers do when checks fail?

Here's some example logic to put things into perspective:

TypeScript

//THIS ISN'T REAL CODE JUST TO HELP VISUALIZEfunction exampleCheckAuthentication(email: Email): AuthResult {    const spf = checkSPF(email.senderIP, email.mailFrom)    const dkim = verifyDKIM(email.headers, email.body)    const dmarc = getDMARCPolicy(email.fromDomain)    // DMARC requires alignment    const aligned = spf.domain === email.fromDomain || dkim.domain === email.fromDomain    if (!aligned) {        if (dmarc.policy === 'reject') return { action: 'REJECT' }        if (dmarc.policy === 'quarantine') return { action: 'SPAM' }    }    return { action: 'CONTINUE', spf, dkim, dmarc }}

SPF: "Is this IP allowed to send for this domain?"

SPF is a policy published in DNS that says:

If an email claims to be from this domain, these IPs/providers are allowed to send it.

So SPF helps prevent spoofing, but it's not the full story.

DKIM: "Was this message signed and unmodified?"

DKIM attaches a cryptographic signature to the message, that give providers like Gmail and Outlook an easy way to check you are the one that signed this email.

This proves:

  • integrity (message wasn't modified)
  • signing domain identity

Effectively this is to make sure some bad actors didn't tamper with the message while it was in transit.

DMARC: "Do SPF/DKIM align, and what's the policy?"

DMARC is the enforcement layer.

It does two key things:

1. Alignment

It makes sure the authenticated domains (SPF and/or DKIM) align with the visible from: joeshmoe@domain.com someone like you would see.

2. Policy

It tells receivers what to do if alignment/auth fails:

  • p=none (let it go through!) - bad idea
  • p=quarantine (likely spam)
  • p=reject (drop it)

DMARC is basically you telling Gmail what to do if neither SPF nor DKIM passes.

If you're past this spot, great.

Providers like Gmail come to the conclusion you are who you say you are, and this message was authentically sent by you. Now comes the vet: discovering your record (whether its criminal, or spotless)

Layer 2: Reputation (Domain, IP, Sender)

Once providers go "okay, you're ID is identified" the next question is: do we trust you?

A common misconception is:

We set up SPF/DKIM/DMARC, so we should be good.

Authentication only proves identity. Showing up to the DA with a real ID doesn't mean your criminal record is spotless.

Reputation is where mailbox providers decide:

  • do we trust you?
  • do users want your mail?
  • do you behave like a stable sender?

TypeScript

function exampleCalculateReputation(sender: Sender): number {    let score = 50 // start neutral    // Domain history    score += sender.domain.ageInDays > 365 ? 10 : -10    score -= sender.domain.bounceRate * 100    score -= sender.domain.complaintRate * 500    // IP reputation    score += sender.ip.isWarmedUp ? 15 : -20    score -= sender.ip.blacklistCount * 25    // Sender-level signals    score += sender.replyRate * 50    score -= sender.unsubscribeRate * 30    return Math.max(0, Math.min(100, score))}

Domain Reputation

The closest thing people use to this is a credit score. Its built over time, you don't start at a 800.

Example:

  • dookie.com
  • billing.dookie.com
  • support.dookie.com

Signals include:

  • bounce rates
  • complaint rates
  • engagement patterns
  • sending consistency over time

If your domain reputation is bad, you get filtered immediately even if auth passes.

IP Reputation

This is the trust score for the actual machines that send your mail.

Examples of when it matters

  • dedicated IPs
  • newly warmed IPs
  • large volume senders
  • shared IP pools (you can be impacted by neighbors)

If you're using a shared pool, IP reputation is partly out of your hands, but it still affects you. Contact your email provider if this might be a concern.

Sender Reputation

Different providers fuse different models, but generally it refers to reputation attached to the visible sender identity:

  • From name + From address (Support <support@agentmail.com>)
  • patterns of sending from that identity
  • alignment stability

Mailbox providers may differentiate patterns across From addresses, but reputation is primarily domain- and IP-based.”

Layer 3: Sending Behavior (Bounces, Volume, Patterns)

Even with good auth and reputation, how you send matters.

Bounces: Hard vs Soft

Bounces are not just "delivery failures." They're reputation signals.

Think of bounces affecting your deliverability like past-due payments affecting your credit score.

One is not the end of the world, but its history that the email provider(or credit bureau) doesn't forget.

If mailbox providers see you generating lots of bounces, it suggests you're:

  • sending to scraped lists
  • sending to dead mailboxes
  • not maintaining list hygiene
  • behaving like a spammer

Hard Bounces (Permanent)

Hard bounces usually mean the message cannot be delivered.

Common causes:

  • recipient address doesn't exist (user@domain.com invalid)
  • recipient domain doesn't exist
  • blocked as invalid recipient

Soft Bounces (Temporary)

Soft bounces mean "try again later."

Common causes:

  • mailbox is full
  • recipient server is temporarily unavailable
  • rate limiting

Takeaway: Bounces are input into reputation scoring. They are not just "ops logs."

TypeScript

function exampleHandleBounce(bounce: Bounce, sender: Sender) {  if (bounce.type === 'hard') {    // Permanent failure - stop sending immediately    addToSuppressionList(bounce.recipient)    sender.reputation -= 5  } else {    // Soft bounce - retry with backoff    if (bounce.retryCount < 3) {      scheduleRetry(bounce, delay: exponentialBackoff(bounce.retryCount))    } else {      sender.reputation -= 2    }  }  // High bounce rate = red flag  if (sender.bounceRate > 0.05) {    flagForReview(sender, reason: 'HIGH_BOUNCE_RATE')  }}

Volume & Velocity

Mailbox providers watch for:

  • sudden volume spikes
  • sending to lots of brand-new recipients
  • weird patterns (bursts, uniform content, list blasts)

Doing any of the above is not ideal.

Warm up new IPs/domains/inboxes gradually. Segment sends and avoid sudden spikes. In a nutshell warming up means exercising good sending hygeine with providers with email providers like Gmail to build rapport.

Will be releasing a more detailed blog on warming soon.

Layer 4: Content & Message Quality

Once you've passed auth, reputation, and behavior checks, the actual message gets scrutinized:

  • Subject/body patterns - spammy keywords, ALL CAPS, excessive punctuation
  • Link reputation - are you linking to sketchy domains?
  • MIME/HTML correctness - malformed emails look suspicious
  • Attachments - certain file types are red flags

This layer is why two emails from the same sender can have different outcomes. The content matters.

Some of our customers do all the right things but then the content includes words like FREE, 50% OFF, NO CREDIT CARD REQUIRED. As a human reading this, wouldn't these also raise red flags on your part as well?

Best to avoid spammy key words.

Layer 5: Engagement & User Signals

The final layer is the most powerful and hardest to control directly:

  • Opens and replies - good signals
  • Deletes without reading - bad signal
  • "This is spam" complaints - catastrophic

Mailbox providers are constantly asking: "Will this user want this email?"

Your historical engagement data feeds into this prediction.

TypeScript

function examplePredictInboxPlacement(email: Email, recipient: User): Decision {    const history = getEngagementHistory(email.sender, recipient)    // Positive signals    let score = 0    score += history.openRate * 30    score += history.replyRate * 50    score += history.movedToInbox * 20    // Negative signals (these hurt a lot)    score -= history.markedAsSpam * 100    score -= history.deletedWithoutReading * 10    score -= history.unsubscribed * 40    // The million dollar question    if (score > 50) return 'INBOX'    if (score > 20) return 'PROMOTIONS'    return 'SPAM'}

P.S: Having users actually be able to reply to your emails in the same thread and have a back-and-forth conversation with you is the absolute best way to prove to Gmail you deserve a higher deliverability score.

This means their customer is actually engaging with you and your email means something.

This is why transactional marketing email campaigns and service providers tend to be more scrutinized since theres no opportunity to reply to their messages.

Summary

Loading diagram...

Takeaway: Inbox placement is a trust and engagement prediction system.

What's Next (Deep Dives)

This post is just the beginning. Next are the zoom-ins.

Planned deep dives:

  1. SPF Deep Dive (DNS lookup limits, includes, common pitfalls)
  2. DKIM Deep Dive (selectors, rotation, canonicalization)
  3. DMARC Deep Dive (alignment rules, enforcement rollout, reporting)
  4. Domain vs IP Reputation (warmups, dedicated vs shared IP tradeoffs)

If you're building email infrastructure for agents (or just any high-volume product), deliverability is one of those things that feels invisible until it becomes the only thing that matters.

The Only Mental Model You Need

If you remember one sentence:

Deliverability is a trust pipeline, not a boolean.

  • Authentication is how you prove who you are.
  • Reputation is whether anyone believes you.
  • Behavior and engagement are whether you stay believed.

FAQ

Questions, answered.

Because deliverability is not one setting: it's a trust system where mailbox providers continuously score whether you deserve inbox placement. The post's model has five layers evaluated in order: authentication and identity (SPF, DKIM, DMARC), reputation (domain, IP, sender), sending behavior (bounces, volume, patterns), content quality, and engagement signals. If layer 1 is broken, nothing below it matters, and bounces and complaints destroy reputation fast.

SPF is a DNS policy answering "who is allowed to send for this domain"; DKIM attaches a cryptographic signature proving the message wasn't modified and identifying the signing domain; DMARC requires alignment between the visible sender and the authenticated identity and tells receivers what to do on failure (reject, quarantine, or continue).

No. A "250 OK" only means the receiving server accepted the message. The actual outcomes are: not accepted, accepted, delivered somewhere in the mailbox, filtered to spam, placed in the inbox, or silently filtered, and deliverability lives in everything after acceptance. When debugging, be precise about which stage failed.

Bounces are reputation signals, not just delivery failures. High bounce rates suggest you are sending to scraped or unmaintained lists, which damages your domain reputation the same way past-due payments damage a credit score.

Domain reputation is a trust score built over time based on signals like bounce rates, complaint rates, engagement patterns, and sending consistency. It functions like a credit score: you do not start with a perfect record, and a bad reputation will get you filtered even if authentication passes.

Mailbox providers scrutinize the actual message after authentication and reputation checks pass. Spammy keywords, excessive punctuation, sketchy links, malformed HTML, and certain attachment types can all trigger spam filtering even from a trusted sender.

Opens and replies are strong positive signals, while spam complaints are described as catastrophic. Enabling recipients to reply and have a back-and-forth conversation is one of the best ways to demonstrate to providers like Gmail that your emails deserve inbox placement.

If neither SPF nor DKIM aligns with the visible From domain, DMARC instructs the receiving server to either reject the message, quarantine it to spam, or let it through depending on your policy setting. A policy of "p=none" offers no enforcement and is generally a bad idea.

Different mailbox providers use different reputation models and filtering logic, so the same email can have different outcomes across providers. Debugging requires identifying which specific layer of the deliverability stack is failing for each provider rather than treating it as a single problem.

IP warming is the process of gradually building sending volume on a new IP or domain to establish a positive reputation with mailbox providers. Sudden volume spikes or sending to large lists from a cold IP are red flags that can hurt deliverability before a reputation is established.

Blog

Suggested reading

View all posts

News · August 8, 2025

AgentMail: Email Infrastructure for AI Agents

AgentMail is an email infrastructure built for AI agents. Create inboxes, send and receive messages, and search threads programmatically, built for autonomous workflows.

Prompt

Give yourself access to AgentMail by following the guide at:

https://agentmail.to/docs/get-started/agent-signup

and refer to:

https://agentmail.to/llms.txt

for the documentation index.

Start integrating AgentMail into your AI agents today.