🚧 SportsPerp is currently live on devnet. Mainnet target: before Jun 12, 2026 (World Cup kickoff).
TradingMarkets

Markets

SportsPerp launches with 68 markets — 20 EPL teams and 48 rostered players. Every market is a perpetual future priced against the composite OBV Index, collateralized in USDC, and settled on Solana.

Market types

TypeID rangeCountNotes
Team0–1920Contiguous — one market per EPL club, alphabetically assigned
Player20–9948Sparse — IDs are permanent even as players transfer, get injured, or drop out of roster

The market_type field on MarketConfig is 0 for teams, 1 for players. Market IDs are stored as u16 and used as PDA seeds.

Why stable, sparse IDs

A traditional listing system would re-index markets whenever the player roster changes — new signings get the next available slot, dropped players free their ID, existing markets shift. That’s a disaster for a perp protocol:

  • Open positions reference market IDs. Reassigning an ID would either silently reassign positions (destructive) or force-close them (user-hostile).
  • Historical candles are keyed by market ID. A reassignment severs the price history.

SportsPerp instead uses stable, sparse IDs in the 20–99 range for players. When a player leaves the roster, their market is paused and eventually sunset (see Market Lifecycle); their ID is never reused. A player who returns keeps their original market, price history, and any open positions.

The roster as single source of truth

roster.json at the repo root defines every market: ID, name, team affiliation, canonical source ID, position group, and metadata. The file is:

  • File-watched. The engine hot-reloads when roster.json changes — no service restart required.
  • Consumed by every service. Crank, oracle pusher, keeper, liquidator, frontend, and init scripts all read from the same file. No drift.
  • Versioned. Currently v4 (every player entry carries an sb_player_id for stable identity across roster rotations). Changes are backed up automatically before being applied.

Roster updates are generated by a script that pulls the current EPL player pool from the data partner’s REST feed, applies the selection algorithm described in the next section, and fuzzy-matches against the existing roster to preserve market IDs.

Player selection algorithm

To keep player markets tradable, the roster algorithm enforces quality and diversity constraints:

  1. Fetch all EPL players (~535) from the data partner’s REST feed.
  2. Filter by minimum playing time: minutes ≥ 900 (~319 eligible).
  3. Rank each player by their composite z-score within position group (OBV 55% + Form 30% + Minutes 15%).
  4. Select the top 48 subject to:
    • Position floors: ≥ 8 FW, ≥ 15 MF, ≥ 10 DF, ≥ 3 GK
    • Team cap: ≤ 5 players per club (prevents stacking on the best teams)
  5. Fuzzy-match against existing roster names to preserve stable IDs.
  6. Back up the previous roster before writing.

The cap on players-per-team is deliberate: a trader wanting leveraged exposure to the top club gets the team market (ID 0–19); player markets are for speculating on individual performance, not dodging the team-market liquidity.

Market volatility characteristics

Teams and players have different risk profiles:

DimensionTeam marketsPlayer markets
Signal windowWhole club across 38 matchesIndividual across 24–38 appearances
Volatility driversResults, manager changes, European fixturesInjuries, transfers, rotations, suspensions
Confidence intervalTighter (300–800 bps)Wider (400–1000 bps)
Default max leverage5x5x (same base; confidence scaling narrows in practice)

Player markets are inherently more volatile. A transfer rumor, a minor injury, or a manager’s rotation decision can move the index sharply before any on-pitch impact is observed. The wider confidence interval triggers automatic leverage reduction during high-uncertainty windows (Margin).

Current state

  • Program ID: 6d4fSCD7mNy7aDNS2mXUxYpZjFFQKBKwAsM5kojKQA6h (devnet)
  • Markets deployed: 20 teams + 48 players = 68 active
  • Next update: weekly roster regeneration as the EPL season progresses

Further reading