Verify the dice of a game
Before the first roll, the app shows a commitment: the SHA-256 hash of a secret seed. Every roll is derived from that seed. When the game ends the seed is revealed. This page checks both, without trusting the app: it hashes the seed, compares it with the commitment, and replays every roll.
Everything runs in your browser. Nothing is sent anywhere; you can read the whole computation below (view source), and a Python script does the same.
Paste the record
In the app: tap Fair dice during or after a game and choose Share record, then paste the text here. You can also fill in the fields by hand.
How the rolls are derived
The seed is 32 random bytes. The commitment is SHA-256(seed), shown as hex. Roll number i (counting from 0) is derived from h = HMAC-SHA256(key = seed, message = "roll:" + i): walk the bytes of h in order, skip any byte of value 252 or more (so all six faces stay exactly equally likely), and take 1 + byte mod 6 for the first die and then again for the second. The opening roll uses the first index whose two dice differ; the earlier ones are the "skipped opening ties". Online, the server draws the seed and reveals it when the game ends; offline, the app does the same before the first move.
Licence: the script on this page and the Python script are released under the MIT licence; copy them freely.