Re-check a page against an earlier receipt
Last updated: 2026-10-12
POST /v1/recheck fetches the page named in an earlier receipt again and tells you whether its text changed: unchanged, changed, gone or unreadable, the fields that differ, and a signed receipt naming both the old and the new hashes. Price: US$0.003 per call.
When to use it
- For page change detection without storing anything: keep the receipt, recheck when you need to know.
- Before reusing a quote or a citation you checked days ago.
- To keep a dated chain of evidence that a page stayed the same (each receipt names the one before).
Request
Send exactly one of the two baseline forms. The receipt from an earlier call:
{ "receipt": "eyJhbGciOiJFZERTQSIs…", "return_text": false }
Or a URL and the content_sha256 from our own fetch of it:
{ "url": "https://www.iana.org/help/example-domains", "content_sha256": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", "return_text": false }
| Field | Required | Meaning |
|---|---|---|
receipt | one of the two forms | compact JWS receipt from an earlier /v1/fetch, /v1/verify/quote or /v1/recheck call of this service, paid or trial (not a sample), at most 160 KB |
url | one of the two forms | only without receipt: http or https URL, at most 2,048 characters |
content_sha256 | with url | the page.content_sha256 from our own fetch, 64 hex characters; other tools hash other text, so their hashes will not match |
return_text | no | also return up to 20,000 characters of the new clean text; default false |
The page fetched is the baseline's url (the URL first asked for, not the final URL), so redirects are followed again. The body may be up to 168 KB, so a long receipt fits.
Answer
From the free sample (GET /v1/sample/recheck), shortened:
{
"change": "unchanged",
"changed": false,
"differences": [],
"baseline": {
"source": "caller",
"receipt_sha256": null,
"url": "https://vehcdj664efetfrsolne5umanq.srv.us/v1/sample/page",
"content_sha256": "0e429607…"
},
"elapsed_seconds": null,
"page": {
"final_url": "https://vehcdj664efetfrsolne5umanq.srv.us/v1/sample/page",
"http_status": 200,
"content_kind": "real",
"content_sha256": "0e429607…",
"raw_sha256": "179b9ac4…"
},
"text": null,
"injection_flags": [],
"advice": "The page's text is the same as in the baseline (byte for byte on the clean text). Markup or other bytes may still have moved; see differences.",
"receipt": "eyJhbGciOiJFZERTQSIs…",
"tier": "paid",
"rail": "x402",
"network": "eip155:8453"
}
change | changed | Meaning |
|---|---|---|
unchanged | false | The page's text is the same as in the baseline. A page already gone in the baseline and still gone is unchanged too. |
changed | true | The page's text differs from the baseline. Fetch it again or check your quote before you rely on it. |
gone | true | The page no longer exists (404 or 410, or the site's name no longer resolves). |
unreadable | null | We could not read the page this time (page.content_kind says why), so we cannot say whether it changed. Try again later. |
differenceslists every compared field that differs, whatever the verdict:content_sha256,raw_sha256,http_status,final_url,content_kind, and with a receipt baseline alsoserver_ipandtls.cert_sha256when both sides have them.baselineis what was compared against. With theurlform,sourceiscallerand the fields only a receipt carries are null.elapsed_secondsis the time since the baseline was fetched (null with theurlform).page,textandinjection_flagsare the new fetch, as [/v1/fetch](/docs/fetch) gives them.
What "changed" means
The comparison is byte for byte on the clean text we extract (content_sha256). Markup-only changes are not changes: raw_sha256 may differ while the answer is unchanged. A page with a date, a counter or rotating text reads as changed on every visit. A content_sha256 from another tool will not match ours: use the hash from our own fetch.
Chaining
The recheck receipt is itself a valid baseline: send it to the next call. Its result.baseline.receipt_sha256 is the SHA-256 of the receipt you sent, so a chain can be checked offline with verify-receipt.mjs.
Charges and errors
The call is charged like /v1/fetch whenever it answers, gone and unreadable included: the fetch was done and the receipt is evidence of it. Every baseline problem is a 400 before payment, never charged:
bad_request: neither or both baseline forms, orcontent_sha256withouturl.baseline_invalid: the receipt does not verify against this service's keys, is not a fetch, verify/quote or recheck receipt, is a sample, or names no URL;details.reasonsays which.
The other errors are those of /v1/fetch; see Errors. On the edge, a PDF page answers 501 not_on_edge, uncharged.
Compared with a hosted watch
No schedule, no webhook, nothing stored: you call when you want to know, and pay US$0.003 per check.