Garrett Holmes Denver · replies within one business day

Case file № 006 · Trust design · Verification

A raffle nobody has to take on faith

System
FairDraw
Client
Public tool, self-directed

An online giveaway asks every entrant to trust the host, and an honest host has no way to prove anything. FairDraw seals the entrant list into a link, lets a future Bitcoin block pick the winner, and hands anyone three lines of Python to check the result.

FairDraw: a lottery page showing the sealed roster and the Bitcoin block it is waiting for. Live

The evidence

Screens of the running thing

A FairDraw lottery page showing the sealed entrant list, the target Bitcoin block, and the verification panel.
Exhibit A A draw page. The sealed roster, the block it is waiting for, and the verification steps a stranger can follow, with nothing stored anywhere but the link.

The system

How the parts connect

In
Entrant list pasted, or imported from a thread
Target block height chosen in the future
The system
Sealed link roster + commitment + timestamp proof
Bitcoin block hash two sources that must agree
Out
Ranked result exactly equal odds · runners-up free
Graded certificate proven · witnessed · unproven · failed
Fig. 1 · The list is sealed in the link. The chain picks. Anyone can check.

Before & after

The account, both columns

Before

  • The host of a giveaway says “I used a random number generator.” The entrants take their word for it, or don’t.
  • Even a scrupulous host can’t prove the list wasn’t edited after entries closed, or that the draw wasn’t re-run until a friend came up.
  • Any tool that fixes this by running its own server has only moved the trust: now you are trusting the tool.

After

  • The roster, the prize, and a target block height are compressed into the link itself. Its fingerprint is the commitment; sharing the link freezes the list. There is no server to trust because there is no server.
  • When the target block is mined, its hash is read from two independent sources that must agree, and the draw waits for one more block on top before calling itself confirmed. A chain reorganization replays the draw and says so.
  • Each entrant’s score is a hash of their name and the block. Sorting those scores is a fair shuffle, so runner-up places come free and every entrant’s odds are exactly equal. The test suite runs the three-line Python verifier against the app’s own code and fails the build if they ever disagree.
  • To prove the list existed before the block, the link also carries a timestamp proof from public calendars, in a compact format written for the purpose, and the page verifies it against the chain. A host importing entries from a forum thread can bind the roster to that thread, so anyone can re-derive it from public data.
  • Every draw is graded on a certificate: proven, witnessed, unproven, or failed. The bar for saying “rigged” is deliberately high, because a deleted comment looks identical to an invented name, and a false accusation costs a real person their reputation.

The verdict

The claim was never “fraud is impossible.” It is “any rig leaves visible scars,” and the written threat model says exactly which mechanism proves what, to whom, and where each one degrades. That is trust treated as an operations problem: define what is checkable, make checking cheap, and be honest about the rest.

Bill of materials

What was used, and the job it did

01Svelte + TypeScriptthe whole app; zero runtime dependencies
02Bitcoin block hashesthe randomness, read from two APIs
03OpenTimestampsproof the list came first; implemented from scratch
04Written threat modelwhat each mechanism proves, and to whom
05Cloudflare Pageshosting; the page is the only moving part

Garrett Holmes · The Operations Ledger

Composed by hand in Denver. Replies within one business day.