Skip to content

Debug a 550 rejection

A 550 is a sentence, not a status code. How to read the enhanced code and the text, decide whether it is about you or the recipient, and what to do in each case.

ReceivingIntermediate10 min readUpdated

01The anatomy of a rejection

A rejection is not a status code. It is three fields with three different levels of trustworthiness, delivered in one line, and reading them in the wrong order is how people end up deleting perfectly good addresses.

TL;DR

Read the enhanced status code first, the reply code for one bit of information, and the free text last.

550 5.1.1 <[email protected]>: Recipient address rejected: User unknown
└┬┘ └─┬─┘ └──────────────────────┬────────────────────────┘
                               
                               free text — human-written, no rules
     enhanced status code (RFC 3463) — the reliable field
 reply code — coarse: 5xx permanent, 4xx temporary
FieldHow much to trust itHow the classifier uses it
Reply codeOne bitIt says 5 for permanent and 4 for temporary, and even that is treated with suspicion: a meaningful number of receivers use a 550 loosely for conditions that are plainly transient. A starting point, not a verdict.
Enhanced status codeThe reliable fieldThree dotted numbers — class, subject, detail. A structured field with a specification behind it, so it is checked before the prose is ever looked at, and its answer wins.
Free textA fallback, on purposePlenty of MTAs emit no enhanced code at all, so phrases are matched — mailbox full, over quota, greylist, user unknown, no such user, domain not found, blacklist, reputation. It works, and it is guessing at somebody’s English prose, which is why it never overrides a code that was actually specified.
The provider’s own classificationAbove all threeSES and Resend both pre-classify, and they are trusted when present because they can see things this system cannot — their own suppression lists, feedback loops, and the outcome of previous attempts to the same address from other senders. Everything from the SMTP text is checked against it rather than instead of it.
Subject digitWhat that class of problem is
x.1.xAddressing — the recipient
x.2.xThe mailbox
x.3.xThe mail system
x.7.xSecurity and policy — you

The subject is the middle number and the useful one.

ClassPermanenceSuppression window
hard_invalidPermanentNone — there is nothing to wait for
hard_domainPermanentNone
hard_blockedPermanentNone
soft_mailbox_fullTemporary7 days
soft_throttledTemporary1 day
soft_contentTemporary3 days
soft_temporaryTemporary2 days
unknownNeitherNone — and deliberately not suppressed

The output of all of the above is one of these, and that class — not the number — is what everything downstream acts on.

02Is it about you or about the recipient?

One question splits the whole problem in half, and the two halves have nothing in common. Is this rejection about the recipient — this address, at this domain — or about you: your domain, your IP, your content, your sending pattern?

TL;DR

The subject digit of the enhanced code gets you there fastest: 5.1.x is addressing, 5.7.x is policy.

About the recipient · 5.1.x
  • They are telling you this recipient is wrong
  • List hygiene, and it takes a minute
  • Remove the address and look at where it came from
About you · 5.7.x
  • They are telling you you are wrong, and the recipient may be entirely real and entirely willing
  • Deliverability work, and it takes weeks
  • Everything else — mailbox state, message size, temporary failure — sits in the middle and is usually about the message rather than either party
WHICH SIDE IS THIS REJECTION ABOUT?

5 steps, cheapest first. Ticks are local to this browser tab and are not saved.

03The rejections you will actually see

These are the diagnostics the classifier actually matches, with the class each one produces and the first thing worth changing. Codes come first because they beat text; the text examples are the phrases the fallback matcher looks for when no code is present.

TL;DR

Act on the class in the second column. The number in the first is how you got there, not what you do about it.

What you seeClassWhat it meansFirst thing to change
550 5.1.1 <[email protected]>: user unknownhard_invalidThe mailbox does not exist at that domain. The domain answered, and it answered no.Remove it and look at where the address came from — a typo at signup, a scraped list, or a person who left.
550 5.1.3 bad destination mailbox address syntaxhard_invalidThe address is malformed as far as the receiver is concerned, not merely absent.Validate at capture. This one almost always means a form that accepts anything with an @ in it.
550 5.1.6 recipient no longer on serverhard_invalidThe mailbox existed and has been removed. Common on corporate domains after a departure.Remove it. If it was a decision-maker, that is a CRM signal as much as a mail one.
550 5.1.2 host unknown / domain not foundhard_domainThe domain itself does not resolve or has no MX. Nothing at that domain will ever work.Remove every address on that domain, not just this one. Usually gmial.com or a dead company.
552 5.2.2 mailbox full / over quotasoft_mailbox_fullA real person with a real mailbox that has run out of room.Nothing. Suppressed for 7 days and retried. Removing this address loses a live subscriber.
421 4.7.0 too many messages / rate limited / throttledsoft_throttledYou are sending faster than this receiver will take from you right now.Slow down. Suppressed for 1 day. If it is constant, your volume ramp is too steep for a young domain.
451 4.7.1 greylisted, try again latersoft_throttledA deliberate first-contact delay. The receiver wants to see whether you retry like a real MTA.Nothing. This one resolves itself, and it is the case where retrying is correct.
550 5.3.4 message too big for systemsoft_contentSize, not identity. The receiver would have taken a smaller version of this message.Link the attachment instead of embedding it. Suppressed 3 days, which is the wrong lever here.
552 5.2.3 message length exceeds administrative limitsoft_contentThe same thing said by a stricter administrator, often with a much lower ceiling.Shrink the message. Base64 inflates attachments by roughly a third — count that, not the file size.
550 5.7.1 message rejected due to policy / spamhard_blockedThey believe your message is unwanted. The address is very probably fine.Authentication and content, not list hygiene. Resending identical content gets an identical answer.
550 5.7.1 blocked using Spamhaus / listed / poor reputationhard_blockedA reputation decision about your sending IP or domain, not about this recipient.Stop the campaign. One receiving domain rejecting you wholesale is an incident, not a bounce.
451 4.3.0 temporary local problem, try again latersoft_temporarySomething on their side broke. It says nothing about you at all.Nothing. Suppressed 2 days and retried. If it persists for a week, it is not temporary.

Soft classes carry a suppression window rather than a permanent entry, because the underlying conditions clear at different speeds. Hard classes carry no window because there is nothing to wait for.

04When retrying makes it worse

Retrying a permanent rejection is not a neutral act that wastes a little bandwidth. It is a signal, it is recorded, and it is one of the specific behaviours large receivers use to distinguish a legitimate sender from a list that is being sprayed.

TL;DR

A hard class suppresses immediately and without a window — not to save you the send, which costs nothing, but to stop your instance producing the one behavioural signal that is hardest to recover from.

Retrying is correct
  • A 4.7.x deferral on first contact — greylisting — is the receiver checking whether you behave like a real MTA
  • The queue does it for you, backing off rather than hammering
  • The difference between a retry and a retry loop: one respects the interval the receiver implied, the other ignores it
Retrying makes it worse
  • A well-run mail system told this mailbox does not exist removes the address
  • A system that keeps delivering either is not processing bounces or does not care — both describe a list not built from consent
  • The rejection rate against non-existent addresses is a cheap, high-signal proxy for list quality, which is why it is measured. Some receivers seed known-dead addresses specifically to see what you do

Reputation recovers slowly, over weeks of clean sending, and it degrades in an afternoon. If you are looking at a wall of hard_blocked rather than scattered invalid addresses, stop sending before you do anything else, then work through why email goes to spam and re-check your authentication records. Continuing to send while you investigate is the single most expensive thing you can do, because every additional rejection is another data point in the case being built against your domain.

What just happened

You can now read a rejection as three fields of decreasing reliability, place it on the you-or-them axis, and act on the class rather than on the number. The thing most likely to bite you later is the temptation to treat a 5.7.x the way you treat a 5.1.1 — suppress the address and move on. A policy rejection is almost never about that recipient, and quietly suppressing your way through one means you delete a good list while the actual problem, which is what receivers currently think of your domain, keeps getting worse.

Common questions

Read next

YOUR ACCOUNT, YOUR MAIL

Nothing to sign up for. Just deploy it.

Every guide on this site describes software you run yourself.