Rules v1 · published 2026-10-03

How a ticket is decided

A ticket is 3 to 10 calls on different markets with one shared clock. Every call has to touch its target before the clock runs out. One miss and the whole ticket is lost. The server decides from recorded prices, never from your browser or the chart.

01

What counts as a hit

Up leg: hit when a recorded price is at or above the target. Down leg: hit when a recorded price is at or below the target. The target is fixed when the ticket is accepted, as an absolute price: start price × (1 ± your move). Up targets round up and Down targets round down, so rounding never makes a target easier.

A leg needs to touch once. It doesn't have to stay there, and the closing price doesn't matter. Once hit, a leg stays hit.

targetaccepteddeadlinerecorded touch = hit
Dots are recorded observations. The lime dot is the first one at or beyond the target, so the leg is hit from that moment on.
02

Which prices count

  • The window is after acceptance, up to and including the deadline. A price stamped exactly at the deadline counts; one stamped a millisecond later does not.
  • Only recorded observations count. The server records a price from Hyperliquid about every 2s. If the price crosses a target and comes back between two observations, that touch is not seen. Charts draw the same recorded points.
  • Observations are ordered by the provider's timestamp, not by when they arrived. Duplicates are stored once; a duplicate that disagrees is kept aside for audit and ignored.
  • Live feeds: a price that arrives more than 30s after the deadline is ignored for that ticket, and a loss is only declared after that grace. The simulator is replayable, so its prices for a moment are the same whenever they are recorded.
  • A single tick that jumps more than 25% from the previous accepted price is treated as a bad print and skipped.
03

Won, lost or refunded

WonEvery leg hit. Settles the moment the last leg touches, even before the deadline. You receive stake × multiplier.
LostThe deadline passed and at least one leg that didn't hit had complete price coverage, so the miss is proven. The stake goes to the collateral pool.
RefundedEvery leg that didn't hit has a hole in its data: no recorded price for more than 10s (feed outage, trading halt, market became unavailable). Nothing proves a miss, so the stake comes back in full.

Example: BTC hit, ETH hit, NVDA had a 40-second halt and never touched → refunded. Same ticket, but SOL also missed with full coverage → lost, because SOL proves the ticket missed regardless of NVDA.

04

Stocks and trading hours

Stock legs follow their market calendar: 24/5 · Sun 8pm – Fri 8pm ET for tokenized stocks, NYSE hours · 9:30am – 4pm ET for ETFs, closed on NYSE holidays. A stock can join a ticket only if the whole window plus the 30s grace fits inside one open session; otherwise the quote is refused. Halts during a ticket show up as missing data and fall under the refund rule above.

05

Quotes and multipliers

  • Quotes are computed on the server and are valid for 20s (120s for onchain tickets, which need wallet confirmations). A quote is tied to its exact legs, clock and stake and can be used once.
  • The model simulates correlated paths for all legs together (a shared market factor plus a crypto or equity factor), counts the chance that every leg touches on the feed's observation grid, and adds a buffer for simulation noise. Multiplying single-leg odds would be wrong: BTC and ETH tend to move together.
  • Offered multiplier = (1 − 7% margin) ÷ (modelled chance + 2 standard errors), capped between 1.10x and 1,000x.
  • A single ticket may reserve at most 5% of the free collateral pool and at most $50,000 of payout. Stake range: $1 to $500.
  • At acceptance the server checks again: prices fresh, markets open, no target already crossed, and no leg moved more than 35% of the way to its target since the quote. Otherwise you get a fresh quote.
06

Money

In this build every balance is test tUSD. Accepting a ticket moves your stake from available to reserved and reserves the house's side of the payout in the same database transaction. Every movement is a balanced, idempotent ledger journal; a ticket can be settled and paid once. Retrying a request with the same idempotency key returns the same ticket.

07

Onchain tickets and trust

Locally, tickets can settle through the STREAK escrow contract. The escrow holds the stake, reserves the full payout from its pool before accepting, accepts each server-signed quote once, settles each ticket once, and keeps settlement and refunds open even when new tickets are paused.

It is not trustless: a trusted quote signer prices tickets and a trusted settlement signer reports outcomes from off-chain price data. If the settlement signer doesn't settle within 60 minutes after the deadline, the player can reclaim the stake directly from the contract. Onchain windows start when the transaction lands; if a target was already crossed by then, the ticket is refunded.

  • Local Anvillocal chain is not running for this deployment
  • Robinhood Chain Testnetescrow not deployed on testnet yet (needs RH_TESTNET_ESCROW, RH_TESTNET_TOKEN and dedicated signer keys)
  • Robinhood Chainreal-money mode is locked in this build
  • Solana DevnetSolana escrow program is not built yet; Solana wallets play on the test ledger
  • Solanareal-money mode is locked in this build
08

Modes

Simulation: seeded simulated prices and test funds. Live prices: real market prices from Hyperliquid's public data, still test funds. Real money: locked in this build until a validated pricing model, verifiable payout collateral, an audited contract and a settlement-grade price source are in place. The app always shows the current mode in the header.

09

Versions

Each ticket stores the rules version it was accepted under and is always settled by that version. New versions never change open tickets. Back to markets