payOrRefuse — an x402 payment gate that refuses before a signature exists
git clone https://github.com/kzmttkc/vet402.git && cd vet402 && npm run judge-checkWhat
A gate an AI agent passes through before it pays an x402 endpoint it has not seen before. The question is not "can I pay" but "is there evidence this wallet delivers" — and if there is none, no signature is created.
How
It reads two sources live: vet402's own ledger of real purchases, and The Graph's x402 subgraph on Base. If either source cannot be read, or the evidence is below the caller's floor, it refuses — the signing module is not even loaded. It does not fall back to a cached number.
Proof
On 2026-09-05 the gate read 259 receipts from The Graph's subgraph and paid 0.01 USDC to The Graph's own receiving wallet: block 50898704 on Basescan. Our own engine rated that payee WARN; the record keeps the WARN next to the payment. We did not rewrite our judgement to match the money.
1.Run it yourself — no key, one command
The command under the title, explained. A clean clone. judge-check installs the SDK, the MCP server, the demo and the A/B harness, runs the test suites, and prints one exit code per step. Any API key in your environment is dropped first, so a green run cannot be borrowing our credentials.
Then the walkthrough in SKILL.md — How a judge can run it: the gate refusing offline, the MCP server listing its tool over stdio, and the gate failing closed against the live API with a deliberately wrong key. The last block that actually pays is marked --live and is a human decision, not a default.
2.What to read, in order
- 1.README — §ETHOnline 2026 (Continuity) — the boundary tag, the two git log commands (what we claim / everything on main), the caveat.
- 2.SKILL.md — the gate itself, as commands you can paste. Each block is re-run against production on a schedule, in CI.
- 3.docs/ethonline-2026/DISCLOSURE_2026-09-05.md — the message we sent ETHGlobal before judging, verbatim, and the two corrections we made to it.
- 4.AI_USAGE.md — who wrote which code, by area and representative file, and what the human did.
3.Pre-existing work (Continuity)
vet402 existed before the hackathon. The boundary tag pre-ethonline-2026 is commit c42daca, cut 2026-09-04 00:05:36 UTC. Hacking began at 2026-09-04 16:00 UTC (ETHGlobal's published schedule), so the tag sits 15 h 54 min before the start. Between our application (2026-08-23) and the tag we made 214 commits of ordinary product work. The message we sent ETHGlobal on 2026-09-05 said 207; the disclosure explains why the count here is 214. Three commits in the range we claim were made before 16:00 UTC — their SHAs, times and contents are listed in the disclosure, with the command that lists them. We are not moving the tag: the submission and the disclosure link to it.
4.The Graph
Load-bearing, not decorative. With policy.evidence.source: "subgraph" the gate reads the x402 Base subgraph through the Graph Gateway; if the read fails it refuses with evidence_unavailable + subgraph_evidence_unavailable and does not fall back to our ledger.
Live, and provably so. The evidence row on the decision carries the subgraph's own _meta.block and queriedAt, so a reader can tell a live read from a cached number. Pinned. The caller may name a deploymentId; the response's _meta.deployment must match or the read counts as unavailable.
The payment above ran on exactly this path — The Graph's data, not ours. Details: SKILL.md — Paying on The Graph's own data.
5.Bazantic
Recipe vs no Recipe, 10 trials each, same model, same prompt, same 57 tools. Success (right verdict, and each reason code real) was 5/10 and 5/10 — no difference, and we say so first. What the Recipe did fix is vocabulary: the share of reason codes that are real vet402 identifiers went from 63% to 91% (20/32 → 29/32). That metric is exploratory and labelled so.
One finding for Bazantic itself. $0 routes still answer 402, and paying $0 posts a real 0-USDC transfer on chain: in 20 trials, 110 tool calls, 88 settled, 88 free reads cost 88 facilitator transactions. Each hash is in the raw log. Harness and results: examples/ethonline-2026-ab · BAZANTIC_FEEDBACK.md.
The demo the gate protects is the same one the public uses: verify a payee (no key), the observatory (each purchase we made, settled or not), and the demo CLI (refuse, pay dry-run, judge <url>).