Inspect an x402 endpoint
Inspect an endpoint before you pay it. Half of the wallets the market study counts as “payers” are indexers and probes,
and three paid tools already grade x402 endpoints from the outside. inspect is ours: one unpaid request, the way a wallet, a directory or a
facilitator makes it, and eleven checks on what comes back: a 402, the v2 header, well-formed accepts with the
token’s signing domain, a price that reads as money, a resource naming the probed URL, a Bazaar extension that
validates against its own schema and declares the probed method, a description, no-store, and Coinbase’s own
validator verdict. The answer is a signed record of what that endpoint declared at that moment. We inspect our own
routes here: one that is a payment challenge, and one free route that simply serves.
Run 2026-10-11 05:26 UTC against api.s2ar.dev 0.1.1 · 3 calls · 1,065 ms · list price $0.01 for a stranger (these ran on the operator's key and cost nothing) · every number on this page re-derived by tools/walkthrough.py before it was written
1. The quote: HTTP 402
curl -s -X POST 'https://api.s2ar.dev/v1/x402/inspect' \
-H 'X-Assay-Quote: 1' \
-H 'content-type: application/json' \
-d '{"resource": "https://api.s2ar.dev/x402/v1/assert"}'
| price_usd | 0.005 |
|---|---|
| rails | ["x402", "credits"] |
| determinism | point-in-time |
| witnesses | ["probe", "cdp-validate"] |
| expected_latency_ms | 4000 |
| free.per_day_keyless | 10 |
| docs | https://s2ar.dev/examples/inspect-an-x402-endpoint.html |
the answer, as JSON
{
"price_usd": 0.005,
"rails": [
"x402",
"credits"
],
"determinism": "point-in-time",
"witnesses": [
"probe",
"cdp-validate"
],
"expected_latency_ms": 4000,
"free.per_day_keyless": 10,
"docs": "https://s2ar.dev/examples/inspect-an-x402-endpoint.html"
}
2. A payment challenge, inspected
Our own assert mirror, probed with GET: eleven checks, the price and the network read off the accepts, the declared method, and Coinbase’s validator agreeing.
curl -s -X POST 'https://api.s2ar.dev/v1/x402/inspect' \
-H "Authorization: Bearer $S2AR_KEY" \
-H 'content-type: application/json' \
-d '{"resource": "https://api.s2ar.dev/x402/v1/assert", "method": "GET"}'
PASS
| status | 402 |
|---|---|
| verdict | pass |
| passed | 11 |
| checks | 11 |
| summary.price_usd | 0.005 |
| summary.networks | ["base"] |
| summary.declared_method | GET |
| results.3.check | accepts_wellformed |
| results.3.ok | true |
| results.10.check | cdp_validate |
| results.10.evidence | {"valid": true, "simulation": "accepted", "failed": []} |
| record.kind | x402-inspection |
| record.replayable | false |
| record_sha256 | a961eb948fcff21b… |
the answer, as JSON
{
"status": 402,
"verdict": "pass",
"passed": 11,
"checks": 11,
"summary.price_usd": 0.005,
"summary.networks": [
"base"
],
"summary.declared_method": "GET",
"results.3.check": "accepts_wellformed",
"results.3.ok": true,
"results.10.check": "cdp_validate",
"results.10.evidence": {
"valid": true,
"simulation": "accepted",
"failed": []
},
"record.kind": "x402-inspection",
"record.replayable": false,
"record_sha256": "a961eb948fcff21b8187ef0bb3889141c0a1939a79e5fed4f2b560f675976e93"
}
| re-derived by the generator | |
|---|---|
| ✓ | receipt sha256:3c14e1ef61e5d196… re-derived: sha256 over the canonical answer, header and body agree |
| ✓ | record a961eb948fcff21b… fetched back from /v1/verify: sealed, signed, and signed by assay-1 (the key at /.well-known/assay.json) |
3. A free route, inspected
The forms list answers 200 to anyone: no challenge, no accepts, nothing for a directory to index. The checks say so, one by one, and the record is still signed: evidence of an absence is evidence.
curl -s -X POST 'https://api.s2ar.dev/v1/x402/inspect' \
-H "Authorization: Bearer $S2AR_KEY" \
-H 'content-type: application/json' \
-d '{"resource": "https://api.s2ar.dev/v1/score/forms", "checks": ["answers_402", "v2_header", "v1_body", "accepts_wellformed", "bazaar_extension"]}'
FAIL
| status | 200 |
|---|---|
| verdict | fail |
| passed | 0 |
| checks | 5 |
| results.0.evidence | {"status": 200, "note": "served without payment"} |
| results.4.evidence | {"reason": "no v2 object"} |
| record_sha256 | 8002a8cc4026de5d… |
the answer, as JSON
{
"status": 200,
"verdict": "fail",
"passed": 0,
"checks": 5,
"results.0.evidence": {
"status": 200,
"note": "served without payment"
},
"results.4.evidence": {
"reason": "no v2 object"
},
"record_sha256": "8002a8cc4026de5d66620ef34f4a4b9c8eb0ae512778f2387c86ff96a34f56d5"
}
| re-derived by the generator | |
|---|---|
| ✓ | receipt sha256:2dbb6c22a8f4832f… re-derived: sha256 over the canonical answer, header and body agree |
| ✓ | record 8002a8cc4026de5d… fetched back from /v1/verify: sealed, signed, and signed by assay-1 (the key at /.well-known/assay.json) |
A probe is a point in time, so the record says replayable: false and carries the sha256 of the response it
judged, and it expires after thirty days. inspect names only what an endpoint publishes to anyone who asks; it
sends no payment, no body and no identity, follows no redirects, and reaches only public hosts on 80 and 443.
What this cannot buy
From the signed proceedings (/.well-known/proceedings.json), verbatim:
- placement or routing position
- a different verdict or grade
- buyer data
- amendment access
- a revocation
Failed calls are never charged. Nothing about a caller is kept. The rules: the charter.