Concepts › Verdicts and state
Verdicts and state
Every check comes back as one of four verdicts, never two. The table below is rendered straight from the same record the API and its tests read, so it cannot drift from what the evaluators actually return.
Verdict | Satisfied | Summary | Effect |
|---|---|---|---|
| fail | No | We looked, and the requirement is not met. | Moves the domain to failed. |
| indeterminate | No — but not a failure either | We could not tell. A resolver was unreachable, a query timed out, or an answer could not be validated. | Changes nothing. The domain keeps whatever state it had, last_checked_at moves, and nothing is appended to the timeline. |
| pass | Yes | The requirement is met with nothing to report. | Moves the domain to verified. |
| warn | Yes | The requirement is met, with advice about something that works today. A p=none DMARC policy is the common case. | Moves the domain to verified. |
Why four, not two
pass and warn both satisfy a requirement — warn is advice about
something that works today, like a p=none DMARC policy, not a defect.
fail and indeterminate both leave a requirement unsatisfied, and that is
where the real distinction lives.
indeterminate changes nothing. Not the domain's state, not its
consecutive-failure count — nothing. A resolver that timed out or an answer
that could not be validated is not evidence that a domain is broken, and it is
not evidence that it is healthy either. lastCheckedAt still advances and the
result still records the uncertainty, but the timeline stays silent and the
state machine below does not move.
The state machine
Five states exist in packages/db/src/schema/domains.ts. pending and
verifying are both "not yet known good"; verified, degraded and failed
are the three things a domain can be once something has actually been
observed.
verifying is reserved for a first-verification flow that has not been built
yet — the sweeper's claim query deliberately never sets it, because a check
that could not reach the resolver would otherwise leave the row there forever.
Do not expect to see it on a domain that is already being monitored.
pending ──first pass or warn────────────────────────▶ verified
│ │
│ fail, reaching the degraded threshold fail, reaching the
▼ degraded threshold
degraded ──further fails, reaching the failed threshold──▶ failed
▲ │
└────────────────── pass or warn ─────────────────────┘
indeterminate: no arrow from any state. The counter behind this diagram is
untouched, and the domain keeps whatever state it already had.
A domain can reach degraded straight from pending — the same
consecutive-failure counter drives a first verification and an established
domain's regression, so there is only one state machine to reason about
rather than two. Monitoring and hysteresis covers what
"reaching the threshold" means and why the thresholds are the numbers they
are.
Next
Diagnosis codes covers what a fail or warn verdict
carries beyond the verdict itself.