MTA-STS (Mail Transfer Agent Strict Transport Security)
MTA-STS is a security standard that enforces TLS encryption for email delivery between mail servers.
How MTA-STS Works
The Problem
Email servers communicate using SMTP, which supports optional TLS via STARTTLS. However:
- STARTTLS is opportunistic (optional)
- Attackers can strip STARTTLS (downgrade attack)
- No certificate validation by default
- Man-in-the-middle attacks are possible
The Solution
MTA-STS tells sending servers:
- TLS is required (not optional)
- Which mail servers to accept
- Certificates must be valid
Sender's Server Your Mail Server
│ │
│ 1. Look up MTA-STS policy │
│ (DNS + HTTPS) │
│ │
│ 2. Policy says: TLS required │
│ │
│ 3. Connect with TLS ──────────> │
│ (or refuse to deliver) │
│ │MTA-STS Components
MTA-STS requires two components:
1. DNS TXT Record
Location: _mta-sts.example.com
v=STSv1; id=20240115120000| Field | Description |
|---|---|
v | Version (STSv1) |
id | Policy ID (changes when policy updates) |
2. Policy File
Location: https://mta-sts.example.com/.well-known/mta-sts.txt
version: STSv1
mode: enforce
mx: mail.example.com
mx: mail2.example.com
max_age: 604800Policy Fields
| Field | Required | Description |
|---|---|---|
version | Yes | Always STSv1 |
mode | Yes | testing or enforce |
mx | Yes | Allowed MX hosts (one per line) |
max_age | Yes | Cache duration in seconds |
Mode
| Mode | Behavior |
|---|---|
testing | Report failures but still deliver |
enforce | Require TLS or reject delivery |
MX Hosts
List all valid mail servers:
mx: mail.example.com
mx: mail2.example.com
mx: *.mail.example.comNote: Wildcards are supported (*.example.com)
Max Age
How long senders cache the policy:
| Duration | Seconds | Use Case |
|---|---|---|
| 1 day | 86400 | Testing |
| 1 week | 604800 | Standard |
| 1 month | 2592000 | Stable config |
Implementation Steps
Step 1: Verify Prerequisites
Before enabling MTA-STS:
- ✅ All MX servers support TLS
- ✅ Valid certificates on all MX servers
- ✅ Certificates match MX hostnames
Step 2: Create Policy File
Create the policy file at:
https://mta-sts.example.com/.well-known/mta-sts.txtRequirements:
- Must be served over HTTPS
- Valid SSL certificate
- Content-Type: text/plain
- Accessible publicly
Example:
version: STSv1
mode: testing
mx: mail.example.com
max_age: 86400Step 3: Add DNS Record
Add TXT record at _mta-sts.example.com:
v=STSv1; id=20240115The ID should:
- Be unique for each policy version
- Change when policy is updated
- Common format: timestamp or version number
Step 4: Test
- Wait for DNS propagation
- Verify policy is accessible
- Monitor TLS-RPT reports
Step 5: Enforce
After confirming no issues:
- Change mode to
enforce - Update policy ID in DNS
- Increase max_age
Testing vs. Enforce
Testing Mode
mode: testing- Senders log failures but deliver anyway
- Use TLS-RPT to see issues
- No impact on email delivery
- Start here
Enforce Mode
mode: enforce- Senders reject if TLS fails
- Full protection against downgrade attacks
- May block email if misconfigured
- After thorough testing
Common Issues
Policy Not Accessible
Symptoms:
- MTA-STS check fails
- Senders can't fetch policy
Causes:
- Wrong subdomain (
mta-stsnotwww) - Missing SSL certificate
- Firewall blocking access
- Wrong path (must be
/.well-known/mta-sts.txt)
Certificate Errors
Symptoms:
- TLS-RPT reports certificate failures
Causes:
- Expired certificate
- Wrong hostname in certificate
- Self-signed certificate (not allowed)
- Certificate chain incomplete
MX Mismatch
Symptoms:
- Delivery failures in enforce mode
Causes:
- Policy MX hosts don't match DNS MX records
- Missing wildcard for subdomains
- Typos in hostnames
Policy ID Not Updated
Symptoms:
- Policy changes not taking effect
Cause:
- Senders cache based on policy ID
- ID must change when policy changes
Solution:
- Update DNS record with new ID
- Use timestamp-based IDs
MTA-STS and TLS-RPT
MTA-STS works best with TLS-RPT:
- MTA-STS - Defines the policy
- TLS-RPT - Reports on policy enforcement
Always configure both:
_mta-sts.example.com TXT "v=STSv1; id=20240115"
_smtp._tls.example.com TXT "v=TLSRPTv1; rua=mailto:tls@example.com"Hosting Options
Self-Hosted
Run your own web server:
- Full control
- Requires maintenance
- Need HTTPS certificate
MailShield Hosted
MailShield can host your policy:
- No web server needed
- Automatic HTTPS
- Easy management
CDN/Static Hosting
Use services like:
- Cloudflare Pages
- GitHub Pages
- AWS S3 + CloudFront
Best Practices
Do
✅ Start with mode: testing
✅ Configure TLS-RPT for visibility
✅ Test thoroughly before enforcing
✅ Include all MX hosts in policy \ ✅ Use wildcards carefully \
Don't
❌ Start with mode: enforce
❌ Forget to update policy ID
❌ Use mismatched MX hosts
❌ Skip TLS-RPT configuration
❌ Use very short max_age in production
Example Configurations
Basic Testing
DNS:
_mta-sts.example.com TXT "v=STSv1; id=2024011501"Policy:
version: STSv1
mode: testing
mx: mail.example.com
max_age: 86400Full Enforcement
DNS:
_mta-sts.example.com TXT "v=STSv1; id=2024011502"Policy:
version: STSv1
mode: enforce
mx: mail.example.com
mx: mail2.example.com
max_age: 604800Multiple MX with Wildcards
version: STSv1
mode: enforce
mx: mail.example.com
mx: backup.example.com
mx: *.mail.example.com
max_age: 604800