Appearance
Security Score
Get the email security score for a domain with a detailed breakdown. It's the same score the dashboard shows.
Get Security Score
GET /api/v1/domains/{id}/scorePath Parameters
| Parameter | Type | Description |
|---|---|---|
id | uuid | Domain ID |
Response
json
{
"data": {
"score": 82,
"grade": "B",
"label": "Good",
"usageType": "sends-and-receives",
"lastCheckedAt": "2024-01-15T10:30:00Z",
"points": {
"mx": 10,
"spf": 13,
"dkim": 10,
"dmarc": 22,
"mtaSts": 7,
"tlsRpt": 10,
"bimi": 0,
"dnssec": 10,
"dane": 0
},
"maxima": {
"mx": 10,
"spf": 18,
"dkim": 10,
"dmarc": 25,
"mtaSts": 10,
"tlsRpt": 10,
"bimi": 2,
"dnssec": 10,
"dane": 5
},
"unscored": [],
"deductions": [],
"breakdown": {
"mx": {
"configured": true,
"tlsSupported": true,
"daneSupported": false
},
"spf": {
"valid": true,
"policy": "~all"
},
"dkim": {
"configured": true,
"validSelectors": 2,
"totalSelectors": 2
},
"dmarc": {
"valid": true,
"policy": "quarantine",
"reportingConfigured": true
},
"mtaSts": {
"valid": true,
"mode": "testing"
},
"tlsRpt": {
"valid": true,
"reportingConfigured": true
},
"bimi": {
"configured": false,
"logoValid": false
},
"dnssec": {
"enabled": true,
"valid": true
}
}
}
}Fields
| Field | Description |
|---|---|
score | 0 to 100, or null if the domain hasn't been checked yet |
grade / label | The letter grade and its label (see below) |
points | The points each component earned. The maximum per component depends on the usage type (see below). DKIM shows 0 while it isn't scored yet (see Score Calculation) |
maxima | The most each component can earn for this domain's usage type; 0 means it doesn't apply |
unscored | Components left out of the score because their state isn't known yet, such as dkim before MailShield knows a selector. The score is scaled over the other components |
deductions | Points withheld for a problem the component's own checks don't show, each with a component (mx or dane) and a reason. For example, a mail server whose certificate strict-TLS senders reject earns no MX points |
breakdown | The status of each check the score is based on |
Example
bash
curl -H "Authorization: Bearer ms_your_token" \
https://app.mailshield.app/api/v1/domains/550e8400-e29b-41d4-a716-446655440000/scoreScore Calculation
The score (0-100) is based on the latest checks, weighted by the domain's usage type. The tables below show the maximum points per component. Use points from the response rather than hard-coding these values: the weights can change as scoring improves.
A few rules apply on top of the tables:
- DKIM isn't scored until MailShield knows a selector, from a DMARC report or one you add. Until then
unscoredcontainsdkim,points.dkimis 0, andscoreis scaled over the other components. - A DMARC
pctbelow 100 earns only that share of the step up from the next weaker policy, and ansp=weaker thanp=costs half the difference between the two. - DANE only counts when the TLSA records are in a DNSSEC-signed zone.
- BIMI only counts with DMARC at
p=quarantineorp=rejectand nopctbelow 100, and only the latest BIMI check counts.
Score Grades
| Grade | Score Range | Label |
|---|---|---|
| A | 90-100 | Excellent |
| B | 80-89 | Good |
| C | 70-79 | Fair |
| D | 60-69 | Poor |
| F | 0-59 | Critical |
Sends and Receives (Standard)
For domains that both send and receive email:
| Component | Max points | How points are earned |
|---|---|---|
| MX | 10 | MX records (5) and TLS on the mail servers (5) |
| SPF | 18 | A valid record (10), plus 8 for -all or 3 for ~all |
| DKIM | 10 | A valid selector with a 2048-bit or stronger key (7 for weaker keys) |
| DMARC | 25 | A valid record (5), the policy (reject 10, quarantine 7, none 2), a rua address (5), and reports to this domain's MailShield address or a ruf address (5) |
| MTA-STS | 10 | A valid policy (5), plus 5 in enforce mode or 2 in testing |
| TLS-RPT | 10 | A valid record (5), plus 5 when reports go to MailShield or 3 for another address |
| BIMI | 2 | A valid record with a valid logo |
| DNSSEC | 10 | Enabled and valid |
| DANE | 5 | TLSA records in a DNSSEC-signed zone that match the mail servers' certificates |
Receives Only
For domains that only receive email. DKIM and BIMI aren't scored.
| Component | Max points | How points are earned |
|---|---|---|
| MX | 15 | MX records (10) and TLS on the mail servers (5) |
| SPF | 15 | -all (15) or ~all (8) |
| DMARC | 20 | The policy (reject 10, quarantine 6), a rua address (5), and reports to this domain's MailShield address or a ruf address (5) |
| MTA-STS | 15 | A valid policy (8), plus 7 in enforce mode or 3 in testing |
| TLS-RPT | 10 | A valid record (5), plus 5 when reports go to MailShield or 3 for another address |
| DNSSEC | 15 | Enabled and valid |
| DANE | 10 | TLSA records in a DNSSEC-signed zone that match the mail servers' certificates |
Sends Only
For domains that only send email. MTA-STS, TLS-RPT and DANE aren't scored.
| Component | Max points | How points are earned |
|---|---|---|
| MX | 10 | MX records that accept mail, for bounces (5 if the servers can't be reached) |
| SPF | 22 | A valid record (12), plus 10 for -all or 5 for ~all |
| DKIM | 20 | A valid selector with a 2048-bit or stronger key (14 for weaker keys) |
| DMARC | 25 | A valid record (5), the policy (reject 10, quarantine 7, none 2), a rua address (5), and reports to this domain's MailShield address or a ruf address (5) |
| BIMI | 8 | A valid record with a valid logo |
| DNSSEC | 15 | Enabled and valid |
Parked Domains
For domains that send and receive no email. The points add up to at most 60, and the score is scaled to 100.
| Component | Max points | How points are earned |
|---|---|---|
| MX | 10 | A null MX record (5 if the domain otherwise can't receive mail) |
| SPF | 15 | -all (15) or ~all (8) |
| DMARC | 25 | The policy (reject 15, quarantine 10), a rua address (5), and reports to this domain's MailShield address or a ruf address (5) |
| DNSSEC | 10 | Enabled and valid |
No Score Response
If no DNS checks have been run yet:
json
{
"data": {
"score": null,
"grade": null,
"label": "Not checked",
"message": "No DNS checks have been run yet. Use POST /api/v1/domains/:id/checks to run checks.",
"usageType": "sends-and-receives",
"lastCheckedAt": null
}
}