Oil painting of a worn second-hand iron key with a stained blank card tag tied to its ring
📮

Self-hosting email in 2026: the deliverability checklist nobody warns you about

Self-hosting email in 2026 isn't impossible, it's a run of separate checks. PTR and FCrDNS, the IPv6 trap, and the checklist in the order to work through it.

"Self-hosting email in 2026 is effectively impossible." It's the kind of line that turns up in self-hosting threads, and the replies tend to split two ways. Some people say they gave up years ago. Others say their Postfix box has delivered flawlessly for a decade.

They're both right, because they're talking about different halves of the job. Inbound mail is easy. Publish an MX record, open port 25, and the world will deliver to you. Outbound is a run of separate checks, and the receivers don't always tell you which one you failed. One of them is the PTR record, and you can't edit it from your domain's DNS panel.

Short answer: you can still send from your own server or app in 2026. But the checklist is longer than the tutorials admit. And a fresh VPS IP can start the race already carrying someone else's reputation.

Why does mail from your own server or a brand-new VPS go straight to spam?

Because the IP may not be new. You're the new tenant, and the address can have a past.

Spamhaus's PBL exists specifically to list ranges that shouldn't be sending direct mail. It's mostly end-user space, and it holds more than 1.4 billion IPv4 addresses, almost 40% of the routable IPv4 space1. And if the previous tenant of your exact IP ran a spam cannon before the provider reclaimed it, you inherit the listings they earned.

None of this shows up when you test. The server says 250 OK, the message leaves, and it lands in spam or vanishes.

What to do: before you configure anything, run the IP through a blocklist check and pull its history with an IP lookup. Our checker can't query Spamhaus2, so look the IP up at check.spamhaus.org too. If the address or its range is already listed, you want to know on day zero, before a week of debugging your own config. A PBL listing just means "this range shouldn't send directly". If it's a static IP that's yours and will run your mail server, with forward and reverse DNS set up, Spamhaus lets you remove that one address yourself at the checker if the network's policy allows it, and the exclusion expires after a year1. Otherwise it's your provider's problem, or a different IP. A leftover SBL listing goes through your provider, because only the network that owns the IP can request SBL removal3. A CSS listing usually expires three days after Spamhaus last sees spam, sometimes longer for chronic abuse, and you can request removal at the same checker4.

What is the PTR record, and why is it the silent gatekeeper?

A PTR record is reverse DNS. It answers "what name does this IP claim?". Forward DNS maps a name to an IP, and the PTR maps the IP back to a name. Receivers can check it the moment you connect, before they've read a single header.

The bar in 2026 isn't just "a PTR exists". It's forward-confirmed reverse DNS, or FCrDNS. The IP resolves to a name, and that name resolves back to the same IP. Both directions have to agree. Google's sender guidelines say it outright: the sending IP must have a PTR record, and the PTR's hostname must resolve back to the sending IP5. Fail that and Gmail may reject, rate-limit or junk your mail, whatever SPF and DKIM say. Gmail's bounce for that failing is 550 5.7.25, and 451 4.7.23 is the rate-limited version6, which we covered in the bounce-reading guide. Microsoft's Exchange Online NDR table lists the same code only for an IPv6 sending address with no reverse DNS record7.

The PTR doesn't live in your DNS. Reverse DNS is delegated to whoever owns the IP block: your VPS provider, your ISP, your cloud8. You can hold every record for your domain and still have no control over the PTR. You have to find the "reverse DNS" field in your hosting panel, or open a ticket. If your host doesn't offer one at all, that alone rules it out for mail.

Two more failure modes hide behind a PTR that technically exists:

192.0.2.4 → ip-192-0-2-4.provider.example   generic PTR: what Yahoo asks you not to use
192.0.2.4 → mail.example.com                custom PTR: what receivers want to see

Yahoo asks for "non-generic" PTRs, and not one that "looks like a dynamically-assigned IP"9. Filters match on the shape of the name. SpamAssassin's RDNS_DYNAMIC fires on rDNS with the IP embedded in it, which is the first line of the block above10. A provider hostname that doesn't spell out the address dodges that particular check.

The name your server introduces itself with in the SMTP HELO/EHLO should also be the name the PTR gives. Some receivers check exactly that, and refuse mail when the HELO name has no matching PTR11. On a single-IP server the simple setup is one name for all three: the HELO name, the PTR, and the forward A record.

What to do: set the PTR to your real mail hostname in the provider's panel. Set the forward record to match. Set your MTA's hostname (myhostname in Postfix) to the same name. Postfix sends it as the HELO name by default12. Then check the loop closes with a reverse DNS check.

Why does IPv6 quietly break everything?

Because your server may send over IPv6 when your DNS doesn't cover it.

If your VPS has an IPv6 address, a modern MTA will happily use it when the receiving side offers an AAAA record, and Gmail does13. Postfix defaults to smtp_address_preference = any, which with smtp_balance_inet_protocols = yes (also the default) means about half your deliveries to dual-stack receivers try IPv6 first12. So some of your mail leaves over an address family you never configured. There's no IPv6 PTR, and if the SPF record only lists the IPv4 address, the result is SPF that passes from some places and fails from others. Delivery over IPv4 passes, delivery over IPv6 fails, and the same domain can give you either answer on consecutive messages.

Gmail and Microsoft both single IPv6 out. Microsoft's 5.7.25 bounce is written for IPv6 senders with no reverse DNS7. Google's guidelines require valid reverse DNS on the sending IPv6 address5, and Gmail has a bounce just for it: "This message does not meet IPv6 sending guidelines regarding PTR records and authentication"6.

What to do: pick one on purpose. The default is the option that bites, sending over an address family your DNS has never heard of. Either do IPv6 properly (an IPv6 PTR at the provider, the address in your SPF with ip6:, FCrDNS both ways), or keep receiving on both families and deliver on IPv4 only until you do.

Postfix names this case in its own docs and gives the config. Leave inet_protocols = all in main.cf, and override the outbound transport in master.cf with -o inet_protocols=ipv412. Two recipes you'll find on forums don't give you that. smtp_address_preference = ipv4 only reorders the attempts. A global inet_protocols = ipv4 also stops you receiving over IPv6. Run your record through an SPF check and read which addresses it authorises, not the ones you remember adding.

Isn't SPF, DKIM and DMARC enough?

You need all three, and they aren't enough on their own. Since the Gmail and Yahoo bulk-sender rules landed in February 2024, all three are the entry fee: SPF, DKIM, and at least a p=none DMARC record for anyone sending more than 5,000 messages a day to Gmail accounts, with a complaint rate under 0.3%5. Yahoo's bulk-sender list has the same three records and the same 0.3%9. Outlook.com set its own version of the same rule for high-volume senders, to take effect in May 202514.

Here are the traps that are specific to self-hosting, in the order they bite:

  • SPF must name the address the mail leaves from. Not the web server, not the old office IP. The sending IP, in both families. End it with -all or ~all. Ending a plain list of senders with +all authorises every address on the internet, which is worse than having no record15.
  • DKIM means your server signs. Installing OpenDKIM and publishing the selector is a small job. Don't skip it. DMARC needs at least one aligned pass16, and SPF fails when a forwarder passes your mail on under your original envelope sender15. DKIM generally survives forwarding, as long as nothing changes the signed content17. SPF doesn't.
  • DMARC needs alignment. DMARC doesn't care that SPF passed for some bounce domain. It cares that the passing identity matches the From: domain. With From: example.com, a DKIM signature with d=example.com aligns, and so does SPF on an envelope sender at example.com. Either one passing aligned is enough16.
  • Every green tick above proves identity. It says nothing about reputation. Passing all three and still landing in spam is common enough that we wrote a whole piece on why. It's linked at the end of this one.

Do I really have to "warm up" an IP?

If you plan to send volume, yes. A new IP that goes from zero to thousands of messages a day is the spike Google tells senders with no history to avoid, because it "could result in rate limiting or reputation drops"5.

Gmail's 421 4.7.28 deferral is the polite version: "an unusual rate of email originating from your IP address", temporarily rate limited6. Read it as "you are new, slow down, earn it". Google's advice isn't to wait. Cut the volume until the deferrals drop, then increase slowly again, starting with engaged recipients5.

For a personal or small-business server sending a few dozen messages a day, warm-up is a much smaller problem. Google's guidelines say "The more email that you send, the more slowly you should increase sending volume"5. The trap is the app that launches with a mailing list. Day one, ten thousand onboarding emails from an IP with no history. There the sending pattern is the problem, not the DNS.

Our take: always split transactional from bulk. Yahoo says the same9. Password resets and receipts from your own server are a fight you can win: low volume, high engagement, recipients who want the mail. Send newsletters and campaigns from the same IP and the transactional mail gets dragged down with the bulk reputation. If you send real volume, put the bulk stream through a relay with an established reputation, and keep your own box for the mail that must arrive.

The checklist, in the order to work through it

No receiver publishes the order it scores these in. This is the order we'd configure and debug them in.

  1. IP history. Blocklist check and IP reputation on the address before you build on it. A listed range means a new IP or a new host, unless it's only the PBL and your static IP qualifies for self-removal.
  2. PTR set and FCrDNS closed, for IPv4 and IPv6, or outbound IPv6 switched off in the MTA. Check it with a reverse DNS lookup.
  3. HELO hostname = PTR name = forward A/AAAA. Three records, one name.
  4. SPF names the real sending addresses, both families, ending ~all or -all.
  5. DKIM signing on, selector published, 2048-bit key, which Google recommends if your DNS provider supports it5, d= aligned with your From: domain.
  6. DMARC published, p=none with rua= while you watch the reports. Move to enforcement only once every legitimate stream passes aligned, and sign with DKIM before p=reject. If your users post to mailing lists, RFC 9989 says you shouldn't publish p=reject, and if you do, to spend at least a month at p=none and as long again at p=quarantine first16.
  7. Port 25 outbound actually open. AWS blocks it by default and lifts it on request18. Google Cloud blocks it, though some projects are exempt19. Azure blocks it by default on everything but Enterprise Agreement and MCA-E subscriptions20. Google Cloud and Azure both point you at a relay or an outside mail service instead.
  8. TLS on the outbound connection. Gmail requires it of every sender5, and its 421 4.7.29 deferral rate-limits mail that arrives without it6.
  9. MX sanity. Your MX records don't affect outbound authentication. But Outlook.com asks high-volume senders for a From or Reply-To address that can receive replies14.
  10. Warm up before volume, and split transactional from bulk before the first campaign.
  11. Monitor after go-live: DMARC reports, Google Postmaster Tools once you send enough for its dashboards to fill21, and a periodic blocklist re-check. Reputation moves, and which listings matter is its own subject.

Our take: "effectively impossible" is wrong, and so is "works fine, just read the docs". Receiving your own mail is as easy as it ever was. Sending has turned into a checklist, and it favours people who work through it in order. The economics are real: a mailbox provider handles most of the eleven items for money. The case for owning your mail is real too.

Try it: run your sending IP through the reverse DNS checker to see whether the PTR and FCrDNS loop closes, then put your domain through the SPF checker to confirm the record authorises the addresses you really send from, IPv6 included.

If the checks come back clean and mail still folders, the problem has moved from identity to reputation, and that's a different article. Everything "passes" and the mail still lands in spam covers the signals that decide placement after authentication. The blocklist guide covers which of the lists on a checker's output can hurt you.

Check your reverse DNS for free.

Sources checked

Each claim above was checked against the source named here on 24 October 2026. Vendor pages and DNS records change, so re-run the commands rather than trusting the date on this page.

  1. “The Policy Blocklist is a dataset containing end-user IP address ranges from which email should never be sent directly to the final destination.” “This dataset provides valuable protection by containing more than 1.4 billion IPv4s, corresponding to almost 40% of the routable IPv4 space.” “If the Policy for a particular network allows it, end users can have their IP excluded from PBL.” Single-IP removal: “It is quick and easy for mail server administrators to exclude their static IP address from a PBL Zone Listing”, and the IP must be static, an outbound mail server, “Configured with appropriate forward (A record) and reverse DNS (rDNS)” and “Assigned to the individual or company performing the removal”. “End-user single-IP exclusions from PBL Zone Listings expire after one year, and will be immediately reversed if spam is detected from them.” Source: Spamhaus: Policy Blocklist (PBL) ↩
  2. Our own code: “Spamhaus (ZEN, PBL, DBL, and CBL, which Spamhaus serves from the same nameservers) removed 2026-09-18. It refuses queries from shared hosting and public resolvers”. The checker queries 11 IP lists and 3 domain lists, none of them Spamhaus. Source: app/lib/BlacklistChecker.php, IP_RBLS and DOMAIN_LISTS ↩
  3. “Removal requests must be sent by the Internet Service Provider in charge of the listed IP address(es).” “Due to the technical nature of these listings, only these companies can deal with SBL removals.” Source: Spamhaus: Spamhaus Blocklist (SBL) ↩
  4. “CSS listings expire quickly: normally, three days after last spam detection. In some cases of chronic abuse, the listings can last longer.” Removal: “you should visit https://check.spamhaus.org … the only place where CSS removals are handled.” “Whatever caused the problem MUST be identified and corrected before removing an IP from CSS.” Source: Spamhaus: Combined Spam Sources (CSS) ↩
  5. Every sender: “Ensure that sending domains or IPs have valid forward and reverse DNS records”, “Use a TLS connection for transmitting email” and “Keep spam rates reported in Postmaster Tools below 0.3%”, “Starting February 1, 2024”. Over 5,000 a day: “Set up SPF and DKIM email authentication for your domain” and “Your DMARC enforcement policy can be set to none.” PTR: “The public IP address of a sending SMTP server must have a corresponding PTR record that resolves to a hostname … The same hostname must also have an A (for IPv4) or AAAA (for IPv6) record that resolves to the same public IP address used by the sending server.” Consequence: “your email might not be delivered as expected, or might be marked as spam.” DKIM: “we recommend using a 2048-bit key if your domain provider supports this.” Volume: “The more email that you send, the more slowly you should increase sending volume”; “Start with a low sending volume to engaged users, and slowly increase the volume over time”; “Avoid introducing sudden volume spikes if you do not have a history of sending large volumes. For example, immediately doubling previously sent volumes suddenly could result in rate limiting or reputation drops”; “If messages start bouncing or start being deferred, reduce the sending volume until the SMTP error rate decreases. Then, increase slowly again.” Source: Google: Email sender guidelines ↩
  6. 550 5.7.25: “This message was blocked because the sending IP address doesn’t have a PTR record, or the forwarding DNS entry doesn’t reference the sending IP address. Gmail requires that sending IP addresses have a PTR record.” 451 4.7.23: “The sending IP address for this message doesn’t have a PTR record, or the PTR record’s forward DNS entry doesn’t match the sending IP address. To protect users from spam, your email has been temporarily rate limited.” 550 5.7.1: “This message does not meet IPv6 sending guidelines regarding PTR records and authentication.” 421 4.7.28: “Gmail has detected an unusual rate of email originating from your IP address … email sent from your IP address has been temporarily rate limited.” 421 4.7.29: “Your email has been rate limited because you’re not using a TLS connection.” Source: Google: Gmail SMTP errors and codes ↩
  7. Exchange Online NDR table, 5.7.25: “Access denied, the sending IPv6 address [2a01:111:f200:2004::240] must have a reverse DNS record”, with “The sending IPv6 address must have a reverse DNS record to send email over IPv6.” No IPv4 entry for the code. Source: Microsoft Learn: Email NDRs and SMTP errors in Exchange Online ↩
  8. The reverse zone for an address block is served by the block’s holder, not by whoever owns the domain in the PTR. As it resolved on 24 October 2026: 8.in-addr.arpa is delegated to ARIN’s servers (r.arin.net, u.arin.net, …), 8.8.8.in-addr.arpa to ns1.google.com to ns4.google.com, and 8.8.8.8 answers PTR dns.google. Source: dig +short NS 8.in-addr.arpa, dig +short NS 8.8.8.in-addr.arpa, dig +short -x 8.8.8.8 ↩
  9. “Publish valid, meaningful, non-generic reverse DNS (PTR) records for all of your sending IPs.” “Do not use a reverse DNS that looks like a dynamically-assigned IP instead of a static mail server.” Bulk senders: “Implement both SPF & DKIM”, “Publish a valid DMARC policy with at least p=none”, “Keep your spam rate below 0.3%”, under “Beginning in February 2024”. “Don’t send bulk/marketing email from the same IPs you use to send user mail, transactional mail, alerts, etc.” The page does not define a bulk sender by a daily count. Source: Yahoo: Sender Best Practices ↩
  10. RDNS_DYNAMIC, “Delivered to internal network by host with dynamic-looking rDNS”, is a meta rule over sub-rules including __RDNS_DYNAMIC_IPADDR, which matches an rDNS name carrying four digit groups (the IP) unless the name contains a static label. The rule only fires when the last external relay did not use SMTP authentication. Tested on 24 October 2026: the regex matches ip-192-0-2-4.provider.example and not mail.example.com. Source: Apache SpamAssassin rules: 20_dynrdns.cf ↩
  11. On mail from Microsoft 365 being refused: “The recipient server requires that the server name that’s contained in the message HELO string have a corresponding pointer (PTR) resource record (reverse IP lookup).” Source: Microsoft Learn: Cannot send emails to an external recipient ↩
  12. smtp_helo_name “(default: $myhostname) The hostname to send in the SMTP HELO or EHLO command.” smtp_address_preference “(default: any)”, the address type “that the Postfix SMTP client will try first”; “With this, and ‘smtp_balance_inet_protocols = yes’ (the default), only half of deliveries will suffer delays if there is an outage that affects IPv6 or IPv4”. “The setting ‘smtp_address_preference = ipv4’ is not a solution for remote servers that flag email received over IPv6 as more ‘spammy’ (the client IPv6 address has a bad or missing PTR or AAAA record, bad network neighbors, etc.). Instead, configure Postfix to receive mail over both IPv4 and IPv6, and to deliver mail over only IPv4”, with inet_protocols = all in main.cf and smtp … smtp -o inet_protocols=ipv4 in master.cf. inet_protocols: “The Internet protocols Postfix will attempt to use when making or accepting connections.” Source: Postfix postconf(5) ↩
  13. Gmail’s primary MX has an AAAA record. As it resolved on 24 October 2026: gmail.com MX 5 gmail-smtp-in.l.google.com, which has AAAA 2a00:1450:4009:c0f::1b (the address varies by resolver location and between queries; an earlier query the same day returned 2a00:1450:4009:c19::1b). Source: dig +short MX gmail.com and dig +short AAAA gmail-smtp-in.l.google.com ↩
  14. “This applies to Outlook.com - our consumer service, which is supporting hotmail.com live.com and outlook.com consumer domain addresses.” “For domains sending over 5,000 emails per day, Outlook will soon require compliance with SPF, DKIM, DMARC”, DMARC “At least p=none”. Updated text: rejected messages get “550; 5.7.515 Access denied, sending domain [SendingDomain] does not meet the required authentication level.” “This change will state taking effect on May 5th as originally stated.” The earlier junk-folder paragraph is struck through on the page. Recommended for large senders: “Ensure the “From” or “Reply-To” address is valid, reflects the true sending domain, and can receive replies.” Source: Microsoft Defender for Office 365 Blog: Outlook’s new requirements for high-volume senders ↩
  15. “The qualifier is optional and defaults to ‘+’” (§4.6.2); “The ‘all’ mechanism is a test that always matches” (§5.1); “A ‘pass’ result is an explicit statement that the client is authorized to inject mail with the given identity” (§2.6.3), where no record gives “none” (§2.6.1). The RFC’s own example: “v=spf1 +all … any <ip> passes” (Appendix A.1). So +all after a plain list of senders authorises every IP on the internet, and with DMARC (source 16, §4.4.2) a forger using your domain as the envelope sender gets an aligned SPF pass. (Appendix A.4 shows a record built from -include terms where a trailing +all “can be very restrictive”, which is why the sentence says a plain list.) Forwarding: “Because SPF evaluation is based on the IP address of the ‘last’ sending SMTP server, the address of the mediator will be used … If the address is the same as for the original message, and the original message had an associated SPF record, then the SPF evaluation will fail unless mitigations such as those described in Appendix D are used” (§10.3). Source: RFC 7208 §2.6, §4.6.2, §5.1 and §10.3 ↩
  16. “If one or more of the Authenticated Identifiers align with the Author Domain, the message is considered to pass the DMARC mechanism check” (§5.3.5). Alignment is a shared Organizational Domain (relaxed) or an identical name (strict) between the From: domain and the DKIM d= or SPF MAIL FROM domain (§4.4, §4.4.1, §4.4.2). Rollout: start at p=none with rua (§5.1.4); unaligned legitimate streams “MUST be addressed prior to any attempt by the Domain Owner to publish a Domain Owner Assessment Policy … of Enforcement” (§5.1.6). “domains that publish ‘p=reject’ MUST NOT rely solely on SPF to secure a DMARC pass and MUST apply valid DKIM signatures to their messages”; “domains that host users who might post messages to mailing lists SHOULD NOT publish Domain Owner Assessment Policies of ‘p=reject’”; such domains wanting p=reject SHOULD first publish “‘p=none’ for at least a month, followed by publishing ‘p=quarantine’ for an equally long period of time” (§7.4). In relayed mail, “DKIM signatures will generally remain valid” (§7.4). RFC 9989 obsoletes RFC 7489. Source: RFC 9989 §4.4, §5.1, §5.3.5 and §7.4 ↩
  17. Plain forwarding: “the recipient at the final address’ mailbox is likely to be able to verify the original signature since the signed content has not changed” (B.2.2). “A Forwarder that does not modify the body or signed header fields of a message is likely to maintain the validity of the existing signature”, while mailing lists that add footers or change the Subject can invalidate it (B.2.3). Source: RFC 6376 Appendix B.2.2 and B.2.3 ↩
  18. “By default, AWS blocks outbound traffic on port 25 for all EC2 instances and Lambda functions on elastic network interfaces.” “To remove the restriction on port 25, you must submit a request to AWS.” Source: AWS re:Post: remove the restriction on port 25 ↩
  19. “Due to the risk of abuse, connections to destination TCP Port 25 are blocked when the destination is external to your VPC network. … However, some projects do not have this restriction and do allow external SMTP egress on port 25.” The page then points to third-party mail providers or a Google Workspace relay. It describes no request to lift the block. Source: Google Cloud: Sending email from an instance ↩
  20. Enterprise Agreement and MCA-E subscriptions: “the outbound SMTP connections on TCP port 25 aren’t blocked.” Enterprise Dev/Test: “port 25 is blocked by default. It’s possible to have this block removed.” All other subscription types: “The Azure platform blocks outbound SMTP connections on TCP port 25 for deployed VMs”, and “we encourage you to use an authenticated SMTP relay service”. Source: Microsoft Learn: Troubleshoot outbound SMTP connectivity in Azure ↩
  21. “Data might be missing if the total number of messages for a given day is too low. This is to protect users’ privacy.” “Check the dashboards again when your email sending volume increases enough to populate the dashboards.” Source: Google: Set up Postmaster Tools ↩
← Back to all articles