Robinhood Chain
LIVE PULLS
Loading latest pulls…
Provably fair

Committed before you rip.

Don't trust us — check us. Every pack ever opened on RipX can be re-drawn here, in your own browser.

How it works

  1. We lock in a secret

    Before your balance is charged, the server creates a random 32-byte secret (the server seed) for every pack in your order and shows you only its fingerprint: sha256(seed). That fingerprint is the commitment — it can't be changed afterwards without you noticing.

  2. You add your own seed

    Your browser generates a random client seed for every order (see it under “Advanced” in the buy panel — you can type your own). It is sent with the order, after our commitment already exists, so we can't pick a server seed that suits it.

  3. Every card is math

    For card i we compute HMAC-SHA256(serverSeed, "clientSeed:openingId:i:rarity") → a number between 0 and 1 → a rarity using the published odds. A second hash (":card") picks the card inside that rarity by weight. The draw happens once, before any animation; replaying or skipping never re-draws.

  4. You check our work

    After the reveal we publish the server seed. This page hashes it, compares it with the commitment, then re-runs the whole draw in your browser. If a single byte had been changed, the fingerprint — or the cards — wouldn't match.

Worked example · one card

  1. Messagek3Yq…9fA:5d0c…e1:0:rarityclient seed : opening id : card index : step
  2. HMAC-SHA256e6b1 04c9 7a2f 83…keyed with the revealed server seed; we keep the first 6 bytes
  3. ÷ 2⁴⁸u = 0.90114…a uniform number between 0 and 1
  4. Core odds73% · 93% · 98.6% · 99.85% · 100%cumulative: common, uncommon, rare, epic, mythic → 0.901 lands in Uncommon
  5. Second hash…:0:card → u = 0.412picks the card inside Uncommon by its published weight

Odds and weights for every pack are public on its What's inside page, so every number above can be reproduced.

Why a client seed?

A commitment alone proves we didn't change the seed after you bought. The client seed closes the other gap: because your browser's random value is mixed into every hash, we can't pre-compute which server seeds would be cheap for us. Neither side controls the result alone. Openings from before client seeds existed verify with an empty seed.

Verify offline (Node.js)
// Node 18+ — verify a RipX opening offline
const { createHash, createHmac } = require("node:crypto");
const seed = Buffer.from(SERVER_SEED, "hex");
console.log(createHash("sha256").update(seed).digest("hex") === COMMITMENT);
const u = (msg) => createHmac("sha256", seed).update(msg).digest().readUIntBE(0, 6) / 2 ** 48;
// card i: rarity from u(`${CLIENT_SEED}:${OPENING_ID}:${i}:rarity`) against the pack's odds,
//         then the card from u(`...:${i}:card`) by weight inside that rarity.

Verify an opening

Your recent rips

Connect to list your own openings and verify any of them in one click. No wallet needed to verify an id someone shared with you.