TAPER

Integration

Reading a market

All state is in plain Anchor accounts (see Architecture). To show today's board for NVDAx:

  1. Derive the market: findProgramAddress(["market", NVDAx_mint], program_id).
  2. Derive today's day account: ["day", market, ny_day as i64 little endian], where ny_day is days since 1970-01-01 of the New York date.
  3. Read strikes, sold, cover, vol and close_ts from the day. Calls still for sale: cover - sum(sold).
  4. Price a strike with the formula in Pricing and fees and the pool price (the higher of its price now and its 10-minute mean), or simulate buy_call and read the CallBought event.

Buying a call

// 1. Pass the market's Raydium CLMM pool and its observation ring (the ring key sits at offset 201 of the
//    pool account). The program reads the price itself: the higher of the pool's price now and its
//    10-minute mean.
// 2. Quote: premium x 1.10 for the fee. Pass a cost limit a little above it.
await program.methods
  .buyCall(strikeIndex, new BN(quantity), new BN(maxCost))
  .accounts({ buyer, market, day, ticket, stockMint, priceUpdate, buyerUsdc, usdcVault, usdcMint, tokenProgram, systemProgram })
  .rpc();

quantity is in raw xStock units of cover: 100_000_000 is one token.

Settling

Anyone can settle. After the bell, call settle_day with the pool and its ring; the program takes the pool's mean price over the 15 minutes before the close. Do it within about 25 minutes: once the ring no longer reaches 15:45 the program answers PoolHistoryTooShort, and an hour after the close anyone can void the day instead.

Cranking the burn

burn(amount) takes up to 1,000 USDC of collected fees per call, and at most 0.1% of the pool's USDC side; the swap must return at least 98% of the pool's 30-minute TWAP promise. It needs the Raydium CPMM pool accounts and its observation account for the TWAP check.

Program id

GvkhWyGwq6CBNV3aEt18voh3bj4dah8uQFHWqA7b3AM2 on Solana mainnet. The site's /.well-known/taper.json and /api/health carry it too.