How the wheel stays fair

Every spin is decided by your browser's cryptographic random number generator before the wheel starts moving. Nothing you type is sent to us. This page explains the method and shows the latest automated audit.

How a winner is picked

The winner is drawn with crypto.getRandomValues, the same cryptographically secure generator browsers use for encryption keys.

Random 32-bit numbers are turned into a position on the wheel by rejection sampling: a number that would make some entries slightly more likely than others is thrown away and drawn again. This removes the small bias of taking a remainder.

The winner is chosen first. The animation then turns the wheel so that it stops inside the winner's segment, at a random point away from its edges.

Weights

An entry written as Pizza*3 is three times as likely to win as an entry with weight 1, and its segment is three times as wide. Weights can be whole numbers or decimals from 0.001 to 1,000,000.

Verifiable draws

For giveaways and raffles, a verifiable draw lets anyone check afterwards that the result was not changed.

  1. Before the spin, the page creates a secret seed and shows a SHA-256 hash of the seed, the entries and the time. Publish the hash, for example in your stream chat, before you spin.
  2. The spin uses a generator built from the secret seed, so the seed and the entries fully decide the winner.
  3. After the spin, the page reveals the seed in a draw receipt. Anyone can paste the receipt into the verify page, which checks the hash and recomputes the winner.

The exact method

The hash is the SHA-256 of this UTF-8 text: a header line, the commitment time, the seed, then one line per entry with its weight, a tab and its label.

weeks-and-random-draw v1
committed_at: 2026-10-16T14:05:09.123Z
seed: 64 hexadecimal characters
3	Pizza
1.5	Sushi
  1. The seed is 32 random bytes from crypto.getRandomValues, written as 64 lowercase hexadecimal characters.
  2. The generator produces 32-bit numbers from SHA-256(seed bytes followed by a 4-byte big-endian counter), for counter 0, 1, 2 and so on, reading each 32-byte hash as eight big-endian numbers.
  3. If every weight is a whole number and the total weight is at most 2^32, the draw takes the next 32-bit number, skips it while it is at least 2^32 − (2^32 mod total), and keeps its remainder after dividing by the total.
  4. Otherwise it takes the next two 32-bit numbers a and b and computes ((a >> 5) × 2^26 + (b >> 6)) ÷ 2^53, a number from 0 up to but not including 1, then multiplies it by the total weight.
  5. The winner is the first entry whose running total of weights is greater than that number.

A verifiable draw proves that the entries and the result were not changed after the hash was published. It cannot stop an organizer from creating several hashes in private and publishing only one they like, so publish the hash before the entries close and make only one.

Verify a draw receipt

Latest audit

Our build runs these tests on every change to the site. Last run: October 19, 2026 18:31.

Every test passed.

Chi-square tests: a test passes when its p-value is above 0.01.
Scenario Spins Chi-square Degrees of freedom p-value Result
2 equal entries 1,000,000 0.86 1 0.3544 Passed
7 equal entries 1,000,000 3.42 6 0.7549 Passed
100 equal entries 1,000,000 125.45 99 0.0375 Passed
1,000 equal entries 1,000,000 1081.73 999 0.0346 Passed
Remove-the-winner mode, 7 entries, every position 999,999 41.72 36 0.2360 Passed
No-repeat mode, 7 entries, every position 999,999 39.90 36 0.3007 Passed
Weighted entries: each entry's share of wins must stay within 0.5 percentage points of its weight.
Weights Spins Largest difference Result
1, 2, 3, 4 1,000,000 0.030 percentage points Passed
0.5, 1.5, 3, 0.25 1,000,000 0.050 percentage points Passed

10,000 of 10,000 drawn spins stopped on the announced winner.

10,000 of 10,000 random draw receipts were recomputed correctly, both in the browser and by an independent implementation.

Wheel engine version: d828d1f5c0c3.