Siftsmith Run on Apify
← All email error fixes

Fix “MTA-STS policy missing” or “not found”

A sending server finds your MTA-STS policy in three steps: a TXT record at _mta-sts, a policy file served from mta-sts. plus your domain, and your MX hosts matched against that policy. “Missing” means one of the first two failed; an MX the policy doesn’t list is the next thing to break. Enter your domain to see which step fails.

Last verified 9 October 2026.

Check where senders lose your MTA-STS policy

Enter the domain that receives the mail. The DNS lookups run in your browser against public DNS; the page also tries to read the policy file, which most hosts don’t allow from a browser.

What this can and can’t tell you: it queries _mta-sts.<domain> TXT, mta-sts.<domain> A, AAAA and CNAME, and the domain’s MX through Cloudflare’s public resolver (Google’s when Cloudflare’s fails). It reads the TXT record against RFC 8461’s grammar, and asks a made-up name on your domain too, so a wildcard isn’t mistaken for your record. When your browser can read the policy file, it parses it and matches every MX host against its mx: lines. A lookup that fails shows as “couldn’t check”, and a file the browser can’t read as “can’t read here”: never as missing.

How senders find an MTA-STS policy

MTA-STS (RFC 8461) lets a domain tell sending servers to deliver its mail only over TLS, to named MX hosts with valid certificates. A sender that supports it does this before delivering:

  1. Look up the TXT record at _mta-sts.<domain>. Records that don’t begin with v=STSv1; are discarded. Exactly one must be left, with an id= of 1 to 32 letters and digits. From §3.1: “If the number of resulting records is not one, or if the resulting record is syntactically invalid, senders MUST assume the recipient domain does not have an available MTA-STS Policy and skip the remaining steps of policy discovery.”
  2. Fetch the policy over HTTPS from https://mta-sts.<domain>/.well-known/mta-sts.txt. The server “MUST present an X.509 certificate that is valid for the "mta-sts" DNS-ID”; “Policies fetched via HTTPS are only valid if the HTTP response code is 200 (OK). HTTP 3xx redirects MUST NOT be followed” (§3.3). Senders “SHOULD validate that the media type is "text/plain"” (§3.2), and §3.3 suggests a 64-kilobyte size limit.
  3. Parse it and match the MX hosts. The file holds version: STSv1, mode (enforce, testing or none), max_age in seconds (at most 31557600) and one mx: line per allowed MX pattern. In enforce mode, senders “MUST NOT deliver the message to hosts that fail MX matching or certificate validation or that do not support STARTTLS” (§5).

If step 2 fails, §3.3 says: “If a valid TXT record is found but no policy can be fetched via HTTPS (for any reason), and there is no valid (non-expired) previously cached policy, senders MUST continue with delivery as though the domain has not implemented MTA-STS.” So a missing policy doesn’t bounce mail; it just leaves it unprotected. In TLS-RPT reports (RFC 8460 §4.3.2.2) the failures show up as sts-policy-fetch-error (“a failure to retrieve an MTA-STS policy, for example, because the policy host is unreachable”), sts-policy-invalid and sts-webpki-invalid (the policy “could not be authenticated using PKIX validation”).

A working setup looks like this:

_mta-sts.example.com.  TXT  "v=STSv1; id=20261009000000"

https://mta-sts.example.com/.well-known/mta-sts.txt  (text/plain)
version: STSv1
mode: enforce
mx: mail.example.com
mx: *.example.net
max_age: 604800

Sources: RFC 8461 §3.1, §3.2, §3.3, §4.1 and §5; RFC 8460 §4.3.2.2 (checked 9 October 2026).

Why senders say the policy is missing

No TXT record at _mta-sts

The most common case: the policy file was uploaded but the TXT record was never added, or was added at the wrong name. It must be named _mta-sts (with the underscore) under the exact domain that receives the mail. For mail to user@mail.example.com, §3.4 says senders “MUST NOT attempt to fetch a policy from the parent zone”, so a subdomain that receives mail needs its own record and host.

Two v=STSv1 records

Adding a new record instead of editing the old one leaves two. With more than one, senders treat the domain as having no policy. Keep one, and change its id= when the policy changes.

An id= with a dash, dot or colon

The id must be 1 to 32 letters and digits. id=2026-10-09 or id=20261009T12:00:00Z make the record invalid, and senders skip it. id=20261009120000 works.

mta-sts.<domain> doesn’t resolve

The TXT record is in place but nobody created the host. Senders can’t connect, so no policy. Add an A or AAAA record, or a CNAME to the service that hosts your policy.

The host answers, but not with the policy

A wildcard DNS record or a default site catches mta-sts.<domain>: the certificate is for another name, the path returns 404, or the server redirects to https://www.. Each makes the fetch fail for senders. Run the curl command the checker gives you and look at the certificate, the status line and any Location: header.

The file is served as HTML or is invalid

Some hosts serve .txt files as text/html or wrap them in a page. The file also needs all of version: STSv1, a valid mode, max_age and, unless the mode is none, at least one mx: line.

An MX host isn’t in the policy

Not “missing”, but the next failure after it: *.example.com covers one label only, so it matches mx1.example.com but not example.com or a.mx1.example.com (§4.1). In enforce mode senders won’t deliver to an MX the policy doesn’t list.

The report is older than your fix

Senders cache a policy for up to max_age and fetch it again when the id= changes. After a failed fetch, §3.3 says they “SHOULD limit further attempts to a period of five minutes or longer per version ID”. Change the id= whenever you change the file.

FAQ

I uploaded the policy file. Why do checkers still say the MTA-STS policy is missing?

Senders never look for the file first. They look up the TXT record at _mta-sts.<domain>, and only if they find exactly one valid v=STSv1 record do they fetch the file from mta-sts.<domain>. A missing TXT record, a second v=STSv1 record, an id= with a dash or dot in it, or a host name that doesn’t resolve all end the search before the file is read.

Why can’t this page read my policy file?

A browser only lets a page read a file from another site when that site sends CORS headers, and most MTA-STS hosts don’t. So when the browser can’t read it, that says nothing about whether the file is there. The page shows the exact URL and a curl command that fetches it the way a sender does, and checks the DNS steps itself.

Does the id= value have to be a date?

No. RFC 8461 only requires 1 to 32 letters and digits, and that it changes whenever the policy does: senders compare it with the id of the policy they cached to decide whether to fetch the file again. A timestamp such as 20261009000000 is a common choice. Dashes, dots, colons and spaces are not allowed.

Is a missing MTA-STS policy a problem for sending mail?

No. MTA-STS protects mail sent to your domain, not mail you send. Without a policy, senders deliver to you as they always have: they may use TLS, but an attacker who can strip it or redirect your MX isn’t stopped. RFC 8461 says that when no policy can be fetched and none is cached, senders continue delivery as though the domain has not implemented MTA-STS.

Checking many domains?

If you manage domains for clients or brands, Email Security Signals fetches each domain’s MTA-STS policy file server-side, the way senders do (certificate checked, no redirects, text/plain, at most 64 KB), and reports its mode, its mx patterns and any MX hosts they miss, alongside SPF, DKIM, DMARC and an A–F grade, one row per domain. $0.02 per graded domain ($20 per 1,000); invalid inputs, domains that don’t exist, DNS lookup failures and duplicates are free.

Check a list on the Apify Store →

Related: fixing Gmail’s 550 5.7.26 bounce, multiple DMARC records, Gmail, Yahoo and Microsoft bulk sender requirements and the free DMARC, SPF and DKIM checker.