Contract API Reference
Complete reference for every external and public function, event, and custom error across all SBET Protocol contracts. Function signatures use Solidity syntax. Parameters and return values are described in definition lists below each signature.
SBET Core — Trading
trade
Execute trades against one or more maker orders. The taker specifies a maximum trade size and a deadline timestamp. Packed orders contain ABI-packed Order structs with signatures.
- amount
- The taker's maximum trade size (in token base units).
- expiry
- Unix timestamp after which the taker order is invalid.
- matchId
- The match identifier to trade on.
- token
- The ERC-20 settlement token address.
- packedOrders
- Array of ABI-packed Order structs, each a
uint256[5]containing the maker order fields and signature.
matchOrders
Match a left order against multiple right orders. Permissionless — anyone can call. Validates that the spread is crossable (leftPrice + rightPrice >= MAX_PRICE).
- matchId
- The match identifier.
- token
- The ERC-20 settlement token address.
- packedLeftOrder
- ABI-packed Order struct for the left (taker-side) order.
- packedRightOrders
- Array of ABI-packed Order structs for the right (maker-side) orders.
getAndIncrementNonce
Returns the caller's current nonce and atomically increments it. Used during off-chain order construction to obtain a fresh nonce for EIP-712 signing.
- Returns
uint256— The caller's nonce before incrementing.
cancelOrderNonce
Cancel a specific order nonce. Sets nonceCancelled[msg.sender][nonce] = true, preventing any order signed with that nonce from executing.
- nonce
- The order nonce to cancel.
cancelUpTo
Cancel all nonces below the given value. Sets minNonce[msg.sender] = nonce, invalidating every order signed with a nonce less than the specified value.
- nonce
- The nonce threshold. All nonces below this value are cancelled.
cancelAll
Cancel all existing orders for the caller. Sets cancelTimestamps[msg.sender] = block.timestamp, invalidating every order signed before this point in time.
toInt256
Utility function to safely convert a uint256 to int256. Reverts on overflow (values exceeding type(int256).max).
- value
- The unsigned integer to convert.
- Returns
int256— The signed integer representation.
SBET Core — Claims
claim
Claim winnings for a finalized match. Computes the payoff from the caller's position and the final settlement price, then transfers the payout.
- matchId
- The finalized match identifier.
- token
- The ERC-20 settlement token address.
batchClaimPositions
Batch claim across multiple matches and tokens in a single transaction. Arrays must be the same length.
- matchIds
- Array of finalized match identifiers.
- tokens
- Array of corresponding ERC-20 settlement token addresses.
claimMulti
Claim multiple token positions for a single match. Useful when a user has positions in multiple settlement tokens for the same event.
- matchId
- The finalized match identifier.
- targets
- Array of target identifiers encoding the token positions to claim.
computePayoff
Pure function to compute the payoff for a given position size and final settlement price. Returns pos * finalPrice / MAX_PRICE for longs, pos * (MAX_PRICE - finalPrice) / MAX_PRICE for shorts.
- pos
- The user's position size (positive = long, negative = short).
- finalPrice
- The final settlement price (0 to MAX_PRICE).
- Returns
int256— The computed payoff amount.
SBET Core — Pool Betting
createPool
Create a new betting pool with the specified settlement token and number of outcomes. Requires numOutcomes >= 2.
- token
- The ERC-20 settlement token for the pool.
- numOutcomes
- Number of possible outcomes (must be at least 2).
- Returns
uint256— The newly created pool ID.
joinPoolBet
Place a bet in a pool on a specific outcome. Transfers tokens from the caller into the pool.
- poolId
- The pool identifier.
- outcome
- The outcome index to bet on (0-based).
- amount
- The amount of tokens to stake.
finalizePool
Finalize a pool with the winning outcome. Admin-only. After finalization, winners can claim their pro-rata share.
- poolId
- The pool identifier.
- winningOutcome
- The index of the winning outcome.
claimPoolWinnings
Claim the caller's pro-rata share of pool winnings. Payout is calculated as (userOutcomeStake / totalOutcomeStake) * totalStaked.
- poolId
- The finalized pool identifier.
batchClaimPools
Batch claim winnings across multiple finalized pools in a single transaction.
- poolIds
- Array of finalized pool identifiers to claim from.
Pool View Functions
Returns the total number of pools created.
Calculate a user's pro-rata share of winnings in a finalized pool.
- poolId
- The pool identifier.
- user
- The user address to query.
- Returns
uint256— The user's potential payout amount.
Get total amount staked on a specific outcome in a pool.
- poolId
- The pool identifier.
- outcome
- The outcome index (0-based).
- Returns
uint256— Total stake on the outcome.
Get a user's total stake across all outcomes in a pool.
Get a user's stake on a specific outcome in a pool.
Returns the ERC-20 settlement token address for a pool.
Check if a pool has been finalized.
Returns the total amount staked in a pool across all outcomes.
Returns the winning outcome index for a finalized pool.
Returns the number of possible outcomes for a pool.
Check if a pool exists (has been created and has outcomes).
Returns comprehensive pool data in one call.
- poolId
- The pool identifier.
- Returns
finalized— Whether the pool has been finalized.token— The settlement token address.totalStaked— Total amount staked across all outcomes.outcome— The winning outcome index (only valid if finalized).numOutcomes— Number of possible outcomes.
Returns all pool IDs where the user has active stakes within the given range.
- user
- The user address to query.
- startId
- Start pool ID (inclusive).
- endId
- End pool ID (exclusive).
- Returns
uint256[]— Array of pool IDs with active user stakes.
SBET Core — NFT Betting
createBetWithNFT
Create Side A of an NFT bet by staking an ERC-721 or ERC-1155 token. Pays the collection fee if one is configured for the NFT contract.
- matchId
- The match identifier to bet on.
- nftAddress
- The NFT contract address (ERC-721 or ERC-1155).
- nftId
- The token ID of the NFT to stake.
joinBetWithNFT
Join Side B of an existing NFT bet by staking an NFT of comparable value.
- matchId
- The match identifier.
- nftAddress
- The NFT contract address.
- nftId
- The token ID of the NFT to stake.
finalizeMatchNFTs
Finalize NFT bets for a match and distribute staked NFTs to the winners.
- matchId
- The finalized match identifier.
- outcome
- The winning side (
BetSideenum).
finalizeMatchNFTsBatch
Batch finalize NFT bets for a match using an index range. Useful when the number of NFT bets is too large for a single transaction.
- matchId
- The finalized match identifier.
- outcome
- The winning side (
BetSideenum). - fromIdx
- Start index (inclusive) of the NFT bet range.
- toIdx
- End index (exclusive) of the NFT bet range.
setNFTBlacklist
Add or remove an NFT collection from the blacklist. Admin-only. Blacklisted collections cannot be used in NFT bets.
- nftAddress
- The NFT contract address to blacklist or unblacklist.
- blacklisted
trueto blacklist,falseto remove from the blacklist.
Batch update NFT blacklist status for multiple collections in a single transaction. Admin-only.
- nftAddresses
- Array of NFT contract addresses.
- blacklisted
- Array of corresponding blacklist flags.
NFT View Functions
Inspect whether an NFT address supports ERC-721 and/or ERC-1155 via ERC-165 supportsInterface.
- nftAddress
- The NFT contract address to check.
- Returns
is721—trueif the contract supports ERC-721.is1155—trueif the contract supports ERC-1155.
Returns the total number of NFTs staked in a match.
Retrieve details of a specific staked NFT by its index within a match.
- matchId
- The match identifier.
- index
- The index of the NFT stake (0-based).
- Returns
owner— The address that staked the NFT.nftAddress— The NFT contract address.nftId— The token ID.side— The bet side (0 = Side A, 1 = Side B).claimed— Whether the NFT has been claimed after finalization.
Get the two participants of an NFT bet for a match.
Get the total count of staked NFTs for a match (alias for getStakedNFTCount).
Check if a specific NFT is already staked in a match.
Check if an NFT address is safe (not blacklisted) for staking.
Check if an NFT address is blacklisted and cannot be used for staking.
SBET Core — Admin & Views
finalizeWithGraders
Finalize a match using M-of-N grader signatures. The witness encodes the match ID. Graders, quorum, and fee are supplied explicitly and validated against the witness hash. Initiates a 24-hour timelock before execution.
- witness
- A
bytes32hash that encodes matchId, grader set, quorum, and fee. - graderQuorum
- Number of valid grader signatures required (M-of-N).
- graderFee
- Fee amount to distribute among graders.
- graders
- Array of grader addresses. Must match the grader set encoded in
witness. - finalPrice
- The final settlement price (0 to MAX_PRICE).
- sigs
- Array of
uint256[2]grader signatures (r, s components). Must have at leastgraderQuorumvalid entries.
executeFinalization
Execute a pending finalization after the 24-hour timelock has elapsed. Checks oracle staleness before committing the result.
- matchId
- The match identifier with a pending finalization.
claimGraderFees
Claim the caller's grader fee share for a finalized match. The last grader to claim receives the remainder to prevent dust lock.
- matchId
- The finalized match identifier.
- token
- The ERC-20 token in which the grader fee is denominated.
getPositionDirect
Get a user's position for a specific match and token. View function — does not modify state.
- matchId
- The match identifier.
- token
- The ERC-20 settlement token address.
- user
- The user address to query.
- Returns
int256— The user's position (positive = long, negative = short, zero = no position).
hasOpenPosition
Check whether a user has a non-zero position for a given match and token.
- matchId
- The match identifier.
- user
- The user address to check.
- token
- The ERC-20 settlement token address.
- Returns
bool—trueif the user has a non-zero position.
System Administration
Pause the contract. Blocks trading, claims, pool joins, and NFT bets while paused.
Unpause the contract and resume normal operations.
Update the treasury contract address. Validates that the new address is a valid treasury contract.
- _treasury
- The new treasury contract address.
Returns the current treasury contract address.
Oracle & Finalization
Set a Chainlink oracle (aggregator) for a specific match.
- matchId
- The match identifier.
- oracleAddr
- The Chainlink aggregator address.
Set the maximum age of oracle data allowed. Must be between 0 and 24 hours.
- threshold
- Maximum oracle data age in seconds.
Initiate a timelock for match finalization. Starts a 24-hour delay before executeFinalization can be called.
Compute a deterministic match ID from grader oracle configuration. Used by frontends to derive match IDs before bets are placed.
- witness
- Arbitrary witness data for uniqueness.
- graderQuorum
- Number of grader signatures required.
- graderFee
- Fee amount for graders.
- graders
- Array of grader addresses.
- Returns
uint256— The deterministic match ID.
Emergency & Recovery
Activate a 72-hour emergency pause. Blocks trading, claims, pool joins, and NFT bets.
Explicitly clear the emergency state after the 72-hour period has expired.
Required: The notEmergency modifier no longer auto-clears expired emergencies.
The owner must call clearEmergency() manually once the 72-hour window has passed;
until then, all guarded functions remain paused.
Configure recovery parameters for a match that the oracle may never finalize.
- matchId
- The match identifier.
- deadline
- Unix timestamp after which recovery can be triggered.
- cancelPrice
- Fallback settlement price for recovery.
Permissionless function that finalizes a match at the pre-configured cancelPrice after the recovery deadline passes. Allows all participants to claim positions.
Match & Position Views
Get comprehensive match information in one call.
- matchId
- The match identifier.
- Returns
finalized— Whether the match has been finalized.finalPrice— The settlement price (only valid if finalized).sideA/sideB— NFT bet participant addresses.nftCount— Number of NFTs staked.
Check if a match has been finalized.
Returns the final settlement price for a finalized match.
Returns the winning side for NFT-based bets (SideA, SideB, or None for tie).
Batch check which matches are finalized.
Returns recovery configuration for a match (deadline, fallback price, and whether recovery can be triggered now).
Calculate the P/L value of a user's position at a hypothetical price. Useful for risk assessment and UI displays.
- matchId
- The match identifier.
- user
- The user address.
- token
- The ERC-20 settlement token address.
- currentPrice
- The hypothetical settlement price.
- Returns
int256— The computed position value.
Returns the total amount filled for an order identified by its fill hash.
Check if a nonce has been used in a filled order (bitmap-based tracking).
Nonce Views
Returns the minimum valid nonce for a maker. All nonces below this are treated as cancelled.
Returns the next nonce to be assigned to a maker.
Check if a specific nonce has been explicitly cancelled.
Returns the timestamp at which the maker called cancelAll(). Orders with earlier timestamps are invalid.
SBETTreasury
Token Management
Add a token to the treasury allowlist. Restricted to TOKEN_MANAGER_ROLE.
- token
- The ERC-20 token address to allow.
Remove a token from the treasury allowlist. Restricted to TOKEN_MANAGER_ROLE.
- token
- The ERC-20 token address to remove.
Check whether a token is on the treasury allowlist.
- token
- The ERC-20 token address to check.
- Returns
bool—trueif the token is allowed.
Get the full list of allowed token addresses.
- Returns
address[]— Array of all allowed token addresses.
Deposits & Withdrawals
Deposit tokens or ETH into the treasury. Restricted to ADMIN_ROLE. For ETH deposits, pass address(0) as the token and send ETH via msg.value.
- token
- The ERC-20 token address, or
address(0)for ETH. - amount
- The amount to deposit (ignored for ETH; uses
msg.value).
Batch deposit multiple tokens and/or ETH in a single transaction.
- tokens
- Array of token addresses.
- amounts
- Array of corresponding deposit amounts.
Withdraw tokens from the treasury. Subject to daily withdrawal limit checks. Restricted to WITHDRAWER_ROLE.
- token
- The ERC-20 token address to withdraw.
- amount
- The withdrawal amount.
Batch withdraw multiple tokens to multiple recipients in a single transaction.
- tokens
- Array of token addresses.
- amounts
- Array of corresponding withdrawal amounts.
- recipients
- Array of recipient addresses.
Emergency withdrawal that bypasses all daily limits. Restricted to EMERGENCY_ADMIN_ROLE.
- token
- The ERC-20 token address.
- amount
- The emergency withdrawal amount.
Fee Management
Set the protocol fee in basis points. Capped at MAX_PROTOCOL_FEE_BPS. Restricted to ADMIN_ROLE.
- bps
- The fee in basis points (e.g., 100 = 1%).
Accrue a fee for an integrator router. Called internally by the core contracts during trade execution.
- router
- The integrator router address.
- token
- The ERC-20 token address for the fee.
- fee
- The fee amount to accrue.
Pay out all accrued integrator fees for a given router and token.
- router
- The integrator router address.
- token
- The ERC-20 token address.
Emergency & Migration
Pause the treasury for the specified duration. Restricted to EMERGENCY_ADMIN_ROLE.
- duration
- Pause duration in seconds.
Lock or unlock the treasury. When locked, no withdrawals or module funding can occur. Restricted to LOCK_MANAGER_ROLE.
- locked
trueto lock,falseto unlock.
Queue a migration to a new treasury contract. Starts a 2-day timelock. Restricted to ADMIN_ROLE.
- newTreasury
- The address of the new treasury contract.
Execute a previously queued migration after the 2-day timelock has elapsed. Requires the treasury to be continuously locked since the migration was queued.
Module Management
Set the vesting manager module address. Restricted to ADMIN_ROLE.
Set the budget manager module address. Restricted to ADMIN_ROLE.
Set the yield manager module address. Restricted to ADMIN_ROLE.
Set the fee manager module address. Restricted to ADMIN_ROLE.
Set the multi-sig manager module address. Restricted to ADMIN_ROLE.
Set the NFT fee manager module address. Restricted to ADMIN_ROLE.
Set the integrator hub contract address. Restricted to ADMIN_ROLE.
- hub
- The IntegratorHub contract address.
Fund a treasury module contract by transferring tokens from the treasury. Restricted to ADMIN_ROLE.
- module
- The module contract address to fund.
- token
- The ERC-20 token address.
- amount
- The amount to transfer to the module.
Role Management
Grant a treasury role to an account. Restricted to ADMIN_ROLE.
- role
- The role identifier (e.g.,
WITHDRAWER_ROLE,TOKEN_MANAGER_ROLE). - account
- The account to grant the role to.
Revoke a treasury role from an account. Restricted to ADMIN_ROLE.
Check if an account has any treasury role.
Authorize or revoke an accruer address. Accruers can call accrueFeeFor.
Set a payout address as verified for integrator payouts.
Treasury Views
Returns true to verify this is the treasury contract. Used for interface detection.
Check if the treasury is locked (no withdrawals or module funding allowed).
Check if the emergency pause is active.
Get the emergency pause end timestamp.
Get the current protocol fee percentage in basis points.
Get the treasury's balance of a specific token.
Get the remaining daily withdrawal limit for a token.
Batch check if multiple tokens are on the treasury allowlist.
Get metrics (deposits, withdrawals, fees) for multiple tokens in one call.
Get a token metrics report (total deposited, withdrawn, fees collected).
Treasury Configuration
Set the per-token daily withdrawal limit. Restricted to ADMIN_ROLE.
Set the global daily withdrawal limit across all tokens. Restricted to ADMIN_ROLE.
Sweep accidentally sent tokens out of the treasury. Restricted to ADMIN_ROLE.
PredictionMarket
createMarket
Create a new prediction market. The MarketParams struct contains all market configuration.
- params.question
- The market question string.
- params.outcomeLabels
- Array of human-readable outcome labels.
- params.category
- Market category for indexing and display.
- params.resolutionSource
- Description of the data source used for resolution.
- params.resolutionTime
- Unix timestamp when the market can be resolved.
- params.expiryTime
- Unix timestamp after which the market expires and can be voided.
- params.token
- The ERC-20 settlement token address.
- params.creatorFeeBps
- Creator fee in basis points, taken from trading volume.
- params.graderQuorum
- Number of grader signatures required for resolution.
- params.graderFee
- Fee paid to graders upon resolution.
- params.graders
- Array of authorized grader addresses.
- params.initialLiquidity
- Initial liquidity amount deposited by the creator.
- Returns
uint256— The newly created market ID.
resolveMarket
Resolve a prediction market by submitting the winning outcome along with the required quorum of grader signatures.
- marketId
- The market identifier.
- winningOutcome
- The index of the winning outcome.
- graderSigs
- Array of
uint256[2]grader signatures (r, s components).
disputeResolution
Dispute a market resolution. Requires posting a dispute bond via msg.value. The bond is returned if the dispute succeeds.
- marketId
- The resolved market identifier to dispute.
- reason
- Human-readable description of the dispute reason.
resolveDispute
Resolve a dispute with M-of-N dispute council signatures. The dispute council is a separate set of trusted signers.
- marketId
- The disputed market identifier.
- finalOutcome
- The final outcome after dispute resolution.
- disputeCouncilSigs
- Array of
uint256[2]dispute council signatures.
voidMarket
Void a market (admin-only). Refunds all participants their original deposits.
- marketId
- The market identifier to void.
getMarket
Returns full market details including question, outcomes, status, resolution data, and current balances.
- marketId
- The market identifier.
- Returns
MarketView— Struct containing all market details.
PredictionMarket Admin
Set the PredictionAMM contract address. Validates non-zero address.
Update the market creation fee amount.
Update the dispute bond amount required to dispute a resolution.
Update the dispute window duration (time after resolution during which disputes can be filed).
Set the recipient address for protocol fees.
Set the dispute council address (legacy single address mode).
Set a multi-signature dispute council with M-of-N quorum. Validates no zero addresses or duplicate members.
- members
- Array of dispute council member addresses.
- quorum
- Number of signatures required for dispute resolution.
Pause all market operations (creation, resolution, disputes).
Resume market operations.
Withdraw accumulated protocol fees to the fee recipient address.
Finalize a market resolution after the dispute window passes without a dispute. Transitions the market from ResolutionPending to Resolved.
- marketId
- The market identifier in
ResolutionPendingstate.
PredictionMarket Views
Get the total number of markets created.
Paginated query of markets by category. Limited to MAX_BATCH_SIZE per call.
- category
- The category string to filter by.
- offset
- Starting index for pagination.
- limit
- Maximum number of results to return.
- Returns
uint256[]— Array of matching market IDs.
Get a paginated list of markets created by an address.
- creator
- The creator address to filter by.
- offset
- Starting index for pagination.
- limit
- Maximum number of results to return.
- Returns
uint256[]— Array of market IDs created by the address.
Get the SBET match ID for a prediction market outcome. Used for order-book trading on prediction market outcomes.
Check if a market is active and available for trading.
PredictionAMM
seedLiquidity
Seed initial liquidity for a market's LMSR (Logarithmic Market Scoring Rule) pool. Must be called before trading can begin.
- marketId
- The market identifier.
- amount
- The amount of collateral to seed.
- b
- The liquidity parameter controlling price sensitivity. Higher values mean less price impact per trade.
buy
Buy outcome shares via the LMSR pricing function. Cost is computed as C(q + shares) - C(q) where C is the LMSR cost function and q is the current quantity vector. Reverts if cost exceeds maxCost.
- marketId
- The market identifier.
- outcomeIndex
- The outcome to buy shares in (0-based index).
- shares
- Number of shares to buy.
- maxCost
- Maximum acceptable cost (slippage protection).
sell
Sell outcome shares back to the AMM. Payout is computed as C(q) - C(q - shares). Reverts if payout falls below minPayout.
- marketId
- The market identifier.
- outcomeIndex
- The outcome to sell shares of (0-based index).
- shares
- Number of shares to sell.
- minPayout
- Minimum acceptable payout (slippage protection).
redeem
Redeem winning shares after market resolution. Pro-rata distribution of the collateral pool to holders of the winning outcome.
- marketId
- The resolved market identifier.
removeLiquidity
Remove the liquidity provider's remaining collateral after market resolution. Only callable by the original LP.
- marketId
- The resolved market identifier.
getOutcomePrices
Get current LMSR prices for all outcomes. Prices sum to MAX_PRICE and represent the implied probability of each outcome.
- marketId
- The market identifier.
- Returns
uint256[]— Array of prices for each outcome.
getCostToBuy / getPayoutToSell
Preview functions for estimating buy costs and sell payouts without executing a transaction. Useful for building UI previews and slippage calculations.
- marketId
- The market identifier.
- outcomeIndex
- The outcome index (0-based).
- shares
- Number of shares to simulate buying or selling.
- Returns
uint256— The cost to buy or payout from selling the specified shares.
getPool
Get complete LMSR pool state for a market.
- marketId
- The market identifier.
- Returns
token— The collateral token address.b— The liquidity parameter.collateral— Total collateral in the pool.provider— The liquidity provider address.active— Whether the pool is active for trading.quantities— Current share quantities for each outcome.
IntegratorHub
registerMyApp
Self-register an integrator app. Pays a registration fee if one is configured (via msg.value).
- payout
- Address where earned fees will be sent.
- period
- The payout sweep period (
Periodenum: Daily, Weekly, Monthly).
ownerRegister
Admin registers an integrator app without requiring a fee payment.
- router
- The integrator's router address.
- payout
- Address where earned fees will be sent.
- period
- The payout sweep period.
accrue
Accrue fees for an integrator. Only callable by authorized accrual sources (core contracts).
- router
- The integrator's router address.
- token
- The ERC-20 token address for the fee.
- fee
- The fee amount to accrue.
consumeAccrued
Consume accrued fees and split based on the integrator's configured bps. Default split: 95% to integrator, 5% to treasury.
- router
- The integrator's router address.
- token
- The ERC-20 token address.
- Returns
toIntegrator— Amount sent to the integrator's payout address.toTreasury— Amount sent to the protocol treasury.
batchConsume
Batch consume accrued fees for multiple router/token pairs in a single transaction for gas efficiency.
- routers
- Array of integrator router addresses.
- tokens
- Array of corresponding ERC-20 token addresses.
- Returns
toIntegrator— Array of amounts sent to each integrator.toTreasury— Array of amounts sent to the treasury for each pair.
View Functions
Get full app info for a registered integrator, including payout address, period, bps split, and status.
- router
- The integrator's router address.
- Returns
AppView— Struct with full integrator app details.
Get pending amounts due for an integrator and the treasury.
- router
- The integrator's router address.
- token
- The ERC-20 token address.
- Returns
iDue— Amount due to the integrator.tDue— Amount due to the treasury.
Check if an integrator's sweep period has elapsed and fees are ready for consumption.
- router
- The integrator's router address.
- Returns
bool—trueif the sweep period has elapsed.
Get the payout address configured for an integrator.
- router
- The integrator's router address.
- Returns
address— The integrator's payout address.
IntegratorHub Admin
Set the registration fee configuration for app registration.
- feeToken
- The ERC-20 token used for registration fees (or
address(0)for ETH). - amount
- The registration fee amount.
Returns the current registration fee token and amount.
Set the default integrator share percentage (default: 9500 = 95%).
Returns the default integrator basis points.
Authorize or revoke an accrual source (who can call accrue).
Enable or disable accrual processing globally.
Set the minimum threshold for accrual amounts. Amounts below this are rejected.
Set the maximum payout limit per router per sweep period.
Override the integrator share percentage for a specific app.
Activate or deactivate an integrator app.
IntegratorHub Self-Service
Update the caller's own payout address. Only callable by registered routers.
Update the caller's own sweep period (Daily, Weekly, Monthly).
Reactivate the caller's app after deactivation.
IntegratorHub Extended Views
Check if an address is an authorized accrual source.
Get total accrued amounts for a router across all tokens.
Get accrued amount for a specific router/token pair.
Batch query accrued amounts for multiple router/token pairs.
Treasury Modules
TreasuryMultiSig
Propose a single token transfer from the treasury. Returns a proposal ID for voting.
- token
- The ERC-20 token address.
- amount
- The transfer amount.
- recipient
- The recipient address.
- description
- Human-readable description of the proposal.
- Returns
bytes32— The proposal ID.
Propose a batch transfer of multiple tokens to multiple recipients.
- tokens
- Array of ERC-20 token addresses.
- amounts
- Array of transfer amounts.
- recipients
- Array of recipient addresses.
- description
- Human-readable description of the proposal.
- Returns
bytes32— The proposal ID.
Propose adding a new signer to the multi-sig.
- newSigner
- The address of the new signer to add.
- description
- Human-readable description of the proposal.
- Returns
bytes32— The proposal ID.
Propose removing an existing signer from the multi-sig.
- signer
- The address of the signer to remove.
- description
- Human-readable description of the proposal.
- Returns
bytes32— The proposal ID.
Propose changing the signature threshold required for proposal execution.
- newThreshold
- The new required number of signatures.
- description
- Human-readable description of the proposal.
- Returns
bytes32— The proposal ID.
Cast a vote on a proposal. Only callable by registered signers.
- proposalId
- The proposal identifier to vote on.
Cast votes on multiple proposals in a single transaction.
- proposalIds
- Array of proposal identifiers to vote on.
Execute a proposal that has reached the required signature threshold.
- proposalId
- The proposal identifier to execute.
Get the current list of multi-sig signers.
- Returns
address[]— Array of signer addresses.
Get full details for a proposal including votes, status, and payload.
Check if a proposal has reached the required threshold and is ready for execution.
Cancel a pending proposal. Only the proposer or a MULTISIG_ADMIN can cancel.
Get all pending (not yet executed or cancelled) proposal IDs.
Get all executed proposal IDs.
Get all cancelled proposal IDs.
Get all addresses that voted on a proposal.
Deposit tokens into the multi-sig contract. Emits Deposit. Amount must be > 0.
Emergency withdrawal by admin. Updates totalWithdrawn metrics.
TreasuryVesting
Create a new vesting schedule for a beneficiary.
- beneficiary
- The address receiving the vested tokens.
- token
- The ERC-20 token address.
- amount
- Total amount of tokens to vest.
- duration
- Total vesting duration in seconds.
- cliff
- Cliff period in seconds. No tokens vest before the cliff.
- revocable
trueif the admin can revoke unvested tokens.- Returns
uint256— The vesting schedule ID.
Release vested tokens to the beneficiary. Transfers all currently vested and unreleased tokens.
- vestingId
- The vesting schedule identifier.
Revoke a vesting schedule (admin-only). Returns unvested tokens to the treasury. Only works on revocable schedules.
- vestingId
- The vesting schedule identifier.
Batch release vested tokens across multiple vesting schedules.
- vestingIds
- Array of vesting schedule identifiers.
Get the total amount that has vested so far for a schedule.
Get the amount that is currently vested but not yet released.
Get all vesting schedule IDs for a beneficiary.
Get all active (non-revoked) vesting schedule IDs for a beneficiary.
Get total vested amount across all schedules for a beneficiary.
Deposit tokens to fund vesting schedules. Tokens need to be approved first. Emits VestingDeposit.
- token
- The ERC-20 token address (or
address(0)for ETH). - amount
- Amount to deposit. Must be > 0.
Emergency withdrawal by admin. Reduces totalVestedByToken to keep accounting consistent.
Pause all vesting releases (admin-only). Emits VestingIsPaused.
Unpause vesting releases (admin-only). Emits VestingUnpaused.
TreasuryBudgets
Create a new budget with a spending limit over a duration.
- name
- Human-readable budget name.
- token
- The ERC-20 token address for the budget.
- amount
- Total budget amount.
- duration
- Budget period duration in seconds.
- Returns
bytes32— The budget identifier.
Allocate a portion of a budget to a specific department address.
- budgetId
- The budget identifier.
- department
- The department address.
- amount
- Amount to allocate from the budget.
Spend from a department’s budget allocation. Requires BUDGET_SPENDER_ROLE or a spending approval. Emits utilization alert at 75%.
- budgetId
- The budget identifier.
- department
- The department address.
- amount
- Amount to spend.
- recipient
- The recipient address.
- description
- Human-readable description of the expenditure.
Approve a spender to withdraw up to a specified amount from a department’s budget.
- budgetId
- The budget identifier.
- department
- The department address.
- spender
- The address being granted spending approval.
- amount
- Maximum amount the spender can withdraw.
Deactivate a budget (admin-only). Prevents further spending.
Reactivate a previously deactivated budget (admin-only).
Extend a budget’s end time (admin-only). Additional time must be > 0 and ≤ MAX_BUDGET_DURATION.
Transfer budget ownership to a new address (admin-only).
Deposit tokens to fund budgets. Amount must be > 0. Emits BudgetDeposit.
Emergency withdrawal by admin. Reduces totalBudgetedByToken to keep accounting consistent.
Get budget utilization as basis points (0–10000).
Get all department addresses allocated under a budget.
Get the remaining unspent allocation for a department within a budget.
Get all budget IDs ever created.
Check whether a budget has passed its end time.
Get all budget IDs that have allocations for a specific department.
Get the total amount allocated across all departments for a budget.
TreasuryYield
Add a new yield strategy for a token. Admin-only.
- token
- The ERC-20 token address.
- strategy
- The yield strategy contract address.
- targetAllocation
- Target allocation percentage for this strategy (basis points).
Remove a yield strategy for a token. Withdraws all funds from the strategy first.
- token
- The ERC-20 token address.
- strategy
- The yield strategy contract address to remove.
Deploy funds from the treasury to a specific yield strategy.
- token
- The ERC-20 token address.
- strategy
- The yield strategy contract address.
- amount
- Amount to deploy.
Withdraw funds from a yield strategy back to the treasury.
- token
- The ERC-20 token address.
- strategy
- The yield strategy contract address.
- amount
- Amount to withdraw.
Harvest yield from a specific strategy and return it to the treasury.
- token
- The ERC-20 token address.
- strategy
- The yield strategy contract address.
Harvest yield from all active strategies for a given token.
- token
- The ERC-20 token address.
Rebalance allocations across all strategies for a token to match target allocations. Includes slippage checks on both withdraw and deposit sides.
- token
- The ERC-20 token address.
Emergency withdrawal from a strategy (admin-only). Accounts based on actual received tokens rather than requested amount.
- token
- The ERC-20 token address.
- strategy
- The yield strategy contract address.
- amount
- Amount to withdraw.
Update the treasury address (admin-only). Emits TreasuryUpdated.
Update a yield strategy's parameters (active status and target allocation).
- token
- The ERC-20 token address.
- strategy
- The yield strategy contract address.
- active
- Whether the strategy is active.
- targetAllocation
- New target allocation in basis points.
Set the maximum deposit cap for a specific strategy.
Set the harvest cooldown period for a token's strategies.
Send tokens from the yield manager back to the treasury.
Deposit tokens from the treasury into the yield manager for deployment.
Get detailed information about a specific yield strategy.
Get total amount deposited across all strategies for a token.
Get total yield harvested across all strategies for a token.
Get all strategy addresses for a token.
Get detailed information for all strategies of a token.
TreasuryFeeManager
Queue a new fee recipient to be added after a timelock period.
- recipient
- The address to receive protocol fees.
- percentage
- The percentage of fees allocated to this recipient (basis points).
- description
- Human-readable description of the fee recipient.
- Returns
bytes32— The queued operation ID.
Execute a queued fee operation after the timelock has elapsed.
- id
- The queued operation identifier.
Distribute accumulated fees for a token to all configured fee recipients based on their percentage allocations.
- token
- The ERC-20 token address.
Accumulate fees for later distribution. Called by core contracts during fee collection.
- token
- The ERC-20 token address (or
address(0)for ETH). - amount
- The fee amount to accumulate.
Queue an update to an existing fee recipient. Subject to timelock.
- index
- The index of the fee recipient to update.
- newRecipient
- The new recipient address.
- newPercentage
- The new percentage allocation in basis points.
- Returns
bytes32— The queued operation ID.
Queue removal of a fee recipient. Subject to timelock.
Queue freezing or unfreezing fee recipient changes. When frozen, no recipients can be added, updated, or removed.
Cancel a queued fee operation before execution.
Set the timelock delay for fee operations.
Set the minimum accumulated fee amount required before distribution is allowed.
Toggle a fee recipient's active status. Inactive recipients are skipped during distribution.
Get the total number of configured fee recipients.
Get all fee recipients with their configuration.
Get only active fee recipients.
Get the total accumulated fees for a specific token awaiting distribution.
Get the total amount a recipient has received for a token across all distributions.
Emergency withdrawal by admin. Reduces accumulated fee tracking.
TreasuryNFTFees
Configure fee settings for an NFT collection. Supports both fixed and percentage-based fees with min/max bounds.
- collection
- The NFT collection contract address.
- enabled
trueto enable fee collection for this collection.- fixedAmount
- Fixed fee amount (used when
usePercentageisfalse). - feeToken
- The ERC-20 token used for fee payment.
- percentageFee
- Percentage fee in basis points (used when
usePercentageistrue). - usePercentage
truefor percentage-based fees,falsefor fixed fees.- minFee
- Minimum fee floor (for percentage mode).
- maxFee
- Maximum fee cap (for percentage mode).
Collect the configured fee for an NFT bet. Called by the NFT betting contract during bet creation.
- from
- The address paying the fee.
- nftCollection
- The NFT collection contract address.
- betValue
- The bet value (used for percentage-based fee calculation).
Preview the fee that would be charged for an NFT bet.
- nftCollection
- The NFT collection contract address.
- betValue
- The bet value for percentage calculation.
- Returns
amount— The computed fee amount.token— The ERC-20 token in which the fee is denominated.
Permanently exempt or un-exempt a user from NFT fees.
- user
- The user address.
- exempt
trueto exempt,falseto remove exemption.
Grant a temporary fee exemption to a user for the specified duration.
- user
- The user address.
- duration
- Exemption duration in seconds.
Set the default fee configuration applied to collections without a specific config.
- amount
- Default fixed fee amount.
- token
- Default fee token address.
- percentage
- Default percentage fee in basis points.
- usePercentage
truefor percentage-based,falsefor fixed.
Set a tiered fee schedule for a collection. Each threshold defines a bet-value bracket with a corresponding fee.
- collection
- The NFT collection contract address.
- thresholds
- Array of bet-value thresholds (must be ascending).
- fees
- Array of fee amounts corresponding to each threshold bracket.
Set a fee configuration for an entire NFT category (e.g., “gaming”, “sports”).
- category
- The category name.
- config
- The
NFTFeeConfigstruct with fee parameters.
Assign an NFT collection to a fee category. The collection inherits the category’s fee config.
- collection
- The NFT collection contract address.
- category
- The category name to assign.
Withdraw collected fees for a specific token to the fee recipient. Requires FEE_MANAGER_ROLE.
- token
- The token to withdraw.
- amount
- The amount to withdraw.
Set the primary fee recipient address for withdrawFees.
- recipient
- The new fee recipient address.
Set multiple fee distribution recipients with BPS-weighted shares. Used by distributeFees.
- wallets
- Array of recipient wallet addresses.
- bps
- Array of basis-point shares (must sum to 10,000).
Accumulate fees for later distribution via distributeFees. Requires ACCRUER_ROLE. Reverts on zero amount.
- token
- The token being accumulated.
- amount
- The fee amount to accumulate (must be > 0).
Distribute accumulated fees for a token among BPS-weighted recipients. The last recipient receives the remainder to eliminate rounding dust.
- token
- The token whose accumulated fees should be distributed.
Emergency withdrawal by admin. Reduces accumulatedFeesByToken and internal accrued tracking.
- token
- The token to withdraw.
- amount
- The amount to withdraw.
Update the treasury address. Emits TreasuryUpdated. Admin-only.
- _treasury
- The new treasury contract address.
Get the tiered fee schedule for a collection.
- collection
- The NFT collection contract address.
- Returns
thresholds— Bet-value threshold array.fees— Corresponding fee amounts.
Batch set fee configurations for multiple NFT collections. Requires NFT_FEE_MANAGER_ROLE.
Check if a user is currently exempted from NFT fees (permanent or temporary).
TreasuryNFTManager
Manages NFT deposits and withdrawals through the NFT vault on behalf of the treasury. Uses AccessControl with NFT_MANAGER_ROLE.
Deposit a single NFT into the vault. Requires NFT_MANAGER_ROLE.
- nft
- The NFT contract address (must be an allowed token).
- tokenId
- The token ID to deposit.
- amount
- Amount (1 for ERC-721, variable for ERC-1155).
Withdraw a single NFT from the vault. Requires NFT_MANAGER_ROLE.
- nft
- The NFT contract address (must be an allowed token).
- tokenId
- The token ID to withdraw.
- amount
- Amount to withdraw.
Batch deposit multiple NFTs into the vault. Maximum 50 items per batch.
Batch withdraw multiple NFTs from the vault. Maximum 50 items per batch.
Update the NFT vault address. Requires DEFAULT_ADMIN_ROLE. Rejects zero address.
- vault
- The new vault contract address (must be non-zero).
Get all token IDs held in the vault for a specific NFT contract.
- nft
- The NFT contract address.
- Returns
uint256[]— Array of token IDs held in the vault.
DonationManager
Manages charitable organizations and donation flows. Supports ERC-20 and ETH donations to verified organizations, cause-based distribution, and donation-from-winnings.
Register a new organization. Requires DONATION_MANAGER_ROLE. Limited to MAX_ORGANIZATIONS (500).
- name
- Organization name (non-empty).
- cause
- Cause category (non-empty).
- description
- Organization description (non-empty).
- imgUrl
- Image URL (non-empty).
- wallet
- Wallet address to receive donations (non-zero).
Verify or unverify an organization. Owner-only. Rejects redundant state changes.
Donate ERC-20 tokens to a verified organization. Validates token address is non-zero.
Donate ETH to a verified organization. Forwards ETH via call to org wallet.
Distribute a donation evenly among all verified organizations for a cause. Last org receives remainder.
Donate a portion of winnings on behalf of a user. Requires DONATION_MANAGER_ROLE.
Supporting Contracts
SBETQuery
Diagnostic query contract providing read-only access to protocol state. All functions are view or pure. Wraps calls to the main SBET contract for convenient frontend consumption.
User Position Queries
Get a user's position for a specific match and token.
Get a user's positions across multiple matches in a single call.
Calculate the potential payoff for a position at the current final price.
- Returns
payoff— The computed payoff amount.isFinalized— Whether the match has been finalized.
Get a user's total exposure across multiple matches.
Check which matches have claimable positions for a user. Returns only finalized matches with positive payoffs.
Match Queries
Get comprehensive match details including finalization status, oracle, and timelock.
Get open (unfinalized) matches where a user has positions.
Check if a match is ready for finalization (timelock elapsed).
Batch query finalization status and final prices for multiple matches.
Pool Queries
Get basic pool information.
Get detailed pool information including per-outcome stakes.
Get a user's pool participation details including stake per outcome and potential payout.
Simulate potential winnings for each outcome. Returns an array where each element is the user's payout if that outcome wins.
Filter pool IDs to only those where the user has participated.
NFT Queries
Comprehensive check of NFT availability for staking. Returns blacklist status, ownership, approval, and token standard.
Get all NFTs staked in a match with full details.
Get NFT bet participants and whether both sides are filled.
Order & Nonce Queries
Check if a nonce is available for use (not used, not cancelled, above minNonce).
Get the next available nonce for a maker's order signing.
Get complete nonce status for a maker.
System State Queries
Get current system status including pause state, emergency state, and treasury info.
Check if a token is allowed for trading.
Get the current protocol fee percentage.
Get all allowed tokens from the treasury.
Check if the system is fully operational. Returns a reason string if not.
Token Balance Queries
Get a user's token balances and allowances for the SBET contract in one call.
Aggregated Queries
Get a user's complete portfolio summary: active matches, positions, pool stakes, and total exposure.
Estimate gas for a trade with the given parameters.
Get comprehensive match analytics.
SBETMath
Internal math library used across SBET contracts. All functions are pure and internal.
max(int256 a, int256 b) → int256— Return the larger of two signed integers.min(int256 a, int256 b) → int256— Return the smaller of two signed integers.minu(uint256 a, uint256 b) → uint256— Return the smaller of two unsigned integers.priceDivide(int256 amount, int256 price) → int256— Multiplyamountbyprice / MAX_PRICE. Reverts if amount < 0 or price ≤ 0.safeSub(uint256 a, uint256 b) → uint256— Subtract with underflow protection. Reverts withSafeSubUnderflowif b > a.safeSub(int256 a, int256 b) → int256— Signed subtract with overflow checks. Reverts withBalanceDeltaOverflow.safeAdd(int256 a, int256 b) → int256— Signed add with overflow checks. Reverts withBalanceDeltaOverflow.safeMin(int256 a, int256 b) → int256— Return the smaller of two signed integers (safe variant).safeMax(int256 a, int256 b) → int256— Return the larger of two signed integers (safe variant).exposureDelta(int256 longBalDelta, int256 shortBalDelta, int256 oldLongPos, int256 newLongPos, int256 oldShortPos, int256 newShortPos) → int256— Compute the net change in collateral exposure from long/short position updates.effectiveBalance(uint256 balance, int256 position, uint256 price, bool isLong) → uint256— Compute the effective collateral for a position at a given price, accounting for opposing-side offsets.safeAddPosition(int256 a, int256 b) → int256— Add to a position with overflow checks. Reverts withPositionOverflow.safeSubPosition(int256 a, int256 b) → int256— Subtract from a position with underflow checks. Reverts withPositionOverflow.isPositionValid(int256 position) → bool— Check if a position magnitude is withinMAX_POSITION_MAGNITUDE(1e27).
NFTVault
Escrow contract for NFTs used in betting. Holds ERC-721 and ERC-1155 tokens on behalf of the protocol.
Deposit an NFT from a user into the vault. Called by the NFT betting contract.
- user
- The depositor address.
- nft
- The NFT contract address.
- tokenId
- The token ID to deposit.
- amount
- Amount (1 for ERC-721, variable for ERC-1155).
Withdraw an NFT from the vault to a recipient. Called by the NFT betting contract after match finalization.
- nft
- The NFT contract address.
- tokenId
- The token ID to withdraw.
- amount
- Amount to withdraw.
- to
- The recipient address.
Batch deposit multiple NFTs into the vault in a single transaction.
Batch withdraw multiple NFTs from the vault in a single transaction.
Get all token IDs held in the vault for a specific NFT contract.
- nft
- The NFT contract address.
- Returns
uint256[]— Array of token IDs held in the vault.
Get the vault's balance of a specific NFT token ID.
- nft
- The NFT contract address.
- tokenId
- The token ID to query.
- Returns
uint256— The balance held in the vault.
Emergency transfer of an NFT out of the vault. Admin-only, requires vault to be locked. Updates _holdings and validates to != address(0). For ERC-721, transfers the token; for ERC-1155, transfers the full balance.
- nft
- The NFT contract address.
- tokenId
- The token ID.
- to
- The recipient address (must be non-zero).
NFTVault Admin
Update the treasury address for the vault.
Allowlist or blocklist an NFT contract for deposit and withdrawal.
- nft
- The NFT contract address.
- allowed
trueto allow,falseto block.
Lock or unlock the vault. When locked, only emergency transfers are allowed.
Returns the NFT standard type (“ERC721” or “ERC1155”) for a given address.
Special Functions
Solidity receive() and fallback() handlers defined across the protocol.
SBET
The main SBET contract explicitly rejects direct ETH transfers and calls to undefined function selectors.
Reverts with DirectETHNotAccepted(). The contract does not accept plain ETH payments.
Reverts with DirectCallNotSupported(). Rejects any call that does not match a defined function selector.
SBETTreasury
Accepts ETH deposits. Validates the contract is not paused or locked. Updates tokenMetrics for ETH_ADDRESS and emits DepositETH.
TreasuryFeeManager
Accepts ETH and accumulates it as fees. Increments accumulatedFees[ETH_ADDRESS] and emits FeesAccumulated.
TreasuryVesting
Accepts ETH for vesting deposits. Emits VestingDeposit.
TreasuryBudgets
Accepts ETH for budget deposits. Emits BudgetDeposit.
TreasuryMultiSig
Accepts ETH deposits to the multi-sig. Emits Deposit.
TreasuryNFTFees
Accepts ETH. Emits EthReceived.
IntegratorHub
Reverts with UnexpectedETH(). The IntegratorHub does not accept direct ETH transfers.
Public State Variables
Solidity automatically generates getter functions for all public state variables.
The most important ones are listed below, grouped by contract.
Constant and immutable variables are covered in the Constants section.
SBET
Whether the contract is in emergency-pause mode (blocks all trading and claims).
Unix timestamp when the emergency pause expires (0 if not paused).
Maximum age (seconds) before an oracle price is considered stale.
Returns the oracle address assigned to finalize the given match.
Returns the timelock timestamp for a pending finalization.
SBETStorage
The treasury contract used for fee collection and payouts.
SBETTreasury
Protocol fee in basis points (e.g., 250 = 2.5%).
Address of the IntegratorHub module.
Whether an address is authorized to accrue fees.
Per-address daily withdrawal cap.
Global daily withdrawal cap across all addresses.
Cumulative deposit, withdrawal, and fee metrics for a given ERC-20 token.
Whether an address is verified for payouts.
Target address for a pending treasury migration (zero if none).
Unix timestamp when the pending migration can be executed.
IntegratorHub
Global toggle for fee accrual processing.
Minimum fee amount required before an accrual is recorded.
Whether an address is an authorized accrual source.
TreasuryFeeManager
Sum of all fee recipient basis points (must not exceed 10 000).
Timelock delay (seconds) for queued fee operations.
Whether the fee recipient list is permanently frozen.
Total amount distributed for a given token across all recipients.
Unix timestamp of the most recent fee distribution.
Undistributed fees accumulated for a given token.
TreasuryVesting
Whether all vesting releases are paused.
Auto-incrementing ID for the next vesting schedule.
Total amount of a token locked across all active vesting schedules.
Total amount of a token released to beneficiaries across all completed or partially vested schedules.
TreasuryYield
Maximum deposit cap for a given yield strategy (shared across all tokens).
Minimum seconds between harvests for a given token.
Cumulative amount of a token deposited across all strategies since deployment.
Cumulative yield of a token harvested across all strategies since deployment.
TreasuryBudgets
Total amount budgeted across all departments for a given token.
Total amount spent across all departments for a given token.
TreasuryMultiSig
Number of votes a proposal has received.
Whether a specific address has voted on a proposal.
TreasuryNFTFees
Default fee amount charged for NFT operations when no custom config is set.
Default token used for NFT fee payments.
Address of the NFTVault contract used for NFT custody.
NFTVault
Whether the vault is locked (only emergency transfers allowed).
Whether a given NFT contract is allowed for deposits.
Inherited Functions (OpenZeppelin)
The following functions are inherited from OpenZeppelin base contracts and are callable on the relevant SBET contracts.
Ownable (SBET, PredictionMarket, PredictionAMM, IntegratorHub, NFTVault, DonationManager)
Returns the address of the current contract owner.
Transfer ownership of the contract to a new address. The new owner cannot be address(0).
Permanently renounce ownership. The contract will have no owner and owner-only functions become uncallable. This action is irreversible.
Pausable (SBET, PredictionMarket)
Returns true if the contract is currently paused.
AccessControl (SBETTreasury, Treasury Modules, DonationManager)
Check if an account has a specific role.
Returns the admin role that controls the given role.
Revoke a role from the caller. The caller must be account (can only renounce own roles).
Types (Structs & Enums)
Solidity struct and enum definitions used in function signatures, return values, and events across the protocol.
Core Types (ISBETInterfaces)
enum TradeStatus {
INVALID,
OK,
TAKER_NO_BALANCE,
TRADE_EXPIRED,
MATCH_FINALIZED,
TRADE_TOO_SMALL,
ORDER_NO_BALANCE,
ORDER_EXPIRED,
ORDER_CANCELLED,
AMOUNT_MALFORMED,
SELF_TRADE,
INVALID_SIGNATURE,
INVALID_NONCE,
INVALID_PRICE_DIR,
INVALID_TAKER
}
Status codes returned during trade execution. OK indicates success; all others are rejection reasons logged in LogTradeError.
enum BetSide {
None, // 0: No side / tie
SideA, // 1: First participant
SideB // 2: Second participant
}
Used in NFT betting to identify which side of a bet a participant is on.
struct Order {
address maker;
address taker; // address(0) = open to anyone
address token; // ERC-20 settlement token
uint256 matchId;
uint256 amount;
uint32 price; // 0 to MAX_PRICE (1e9)
uint8 direction; // 0 = buy, 1 = sell
uint256 expiry; // Unix timestamp
uint256 timestamp; // Signing timestamp
uint256 orderGroup; // Grouping identifier
uint256 fillHash; // Unique fill tracking hash
uint256 nonce; // EIP-712 nonce
bool isNFT; // NFT-collateralized order
address nftAddress; // NFT contract (if isNFT)
uint256 nftId; // NFT token ID (if isNFT)
}
The EIP-712 typed order struct signed off-chain by makers. Packed into uint256[5] arrays for on-chain submission.
struct NFTStake {
address owner;
address nftAddress;
uint256 nftId;
BetSide side;
bool claimed;
}
Represents a single NFT staked in a match bet. Returned by getStakedNFT().
struct TokenMetrics {
uint256 totalDeposited;
uint256 totalWithdrawn;
uint256 totalFees;
uint256 lastUpdated;
}
Treasury per-token accounting metrics. Returned by getTokenReport() and getMultipleTokenMetrics().
Prediction Market Types (IPredictionMarket)
enum MarketStatus { Active, Paused, ResolutionPending, Resolved, Disputed, Voided }
Lifecycle states for a prediction market.
enum MarketType { Binary, MultiOutcome }
Binary for two-outcome markets; MultiOutcome for three or more outcomes.
struct MarketParams {
string question;
string[] outcomeLabels;
string category;
string resolutionSource;
uint256 resolutionTime;
uint256 expiryTime;
address token;
uint256 creatorFeeBps;
uint256 graderQuorum;
uint256 graderFee;
address[] graders;
uint256 initialLiquidity;
}
Input parameter for createMarket(). Contains all market configuration.
struct MarketView {
uint256 marketId;
address creator;
MarketType marketType;
MarketStatus status;
string question;
string[] outcomeLabels;
string category;
string resolutionSource;
uint256 resolutionTime;
uint256 expiryTime;
address token;
uint256 creatorFeeBps;
uint256 numOutcomes;
uint256[] subMarketMatchIds;
uint256 totalVolume;
uint256 createdAt;
uint256 resolvedAt;
uint256 winningOutcome;
}
Returned by getMarket(). Contains the full state of a prediction market.
Integrator Types (IIntegratorHub)
enum Period {
None, // 0: Manual payout only
Daily, // 1: 24-hour intervals
Weekly, // 2: 7-day intervals
Monthly // 3: 30-day intervals
}
Payout sweep period for integrator apps. Determines how often accrued fees can be consumed.
struct AppView {
address payout; // Fee payout address
uint16 bps; // Integrator share (0 => use defaultBps)
Period period; // Payout sweep period
uint64 lastSweep; // Last sweep timestamp
bool active; // Whether the app can accrue fees
bool paid; // Whether the app has ever received payment
}
Returned by appOf(). Full integrator app configuration and status.
Treasury Types (ITreasuryInterfaces)
struct FeeRecipient {
address recipient;
uint256 percentage; // Basis points
string description;
bool active;
}
Used by TreasuryFeeManager. Returned by getAllFeeRecipients().
struct VestingSchedule {
address beneficiary;
address token;
uint256 totalAmount;
uint256 released;
uint256 startTime;
uint256 duration;
uint256 cliffDuration;
bool revocable;
bool revoked;
}
Used by TreasuryVesting. Created via createVesting().
struct Budget {
string name;
address token;
uint256 totalAmount;
uint256 spent;
uint256 startTime;
uint256 endTime;
bool active;
address creator;
address owner;
}
Used by TreasuryBudgets. Created via createBudget().
struct DepartmentAllocation {
uint256 allocated;
uint256 spent;
bool exists;
}
Per-department allocation within a budget.
struct StrategyInfo {
address strategy;
bool active;
uint256 deposited;
uint256 totalHarvested;
uint256 lastHarvestTime;
uint256 targetAllocation; // Basis points
}
Used by TreasuryYield. Returned by getStrategyInfo() and getStrategiesDetailed().
struct NFTFeeConfig {
bool enabled;
uint256 fixedFeeAmount;
address feeToken;
uint256 percentageFee; // Basis points
bool usePercentage;
uint256 minFee;
uint256 maxFee;
}
Used by TreasuryNFTFees. Passed to setNFTFeeConfig() and setCategoryFee().
MultiSig Types (TreasuryMultiSig)
enum ProposalType {
Transfer,
BatchTransfer,
AddSigner,
RemoveSigner,
ChangeThreshold,
CancelProposal
}
The type of operation a multi-sig proposal represents.
struct Proposal {
ProposalType proposalType;
address proposer;
address token;
uint256 amount;
address recipient;
uint256 createdAt;
uint256 executedAt;
bool executed;
bool cancelled;
string description;
bytes data; // Encoded payload for batch transfers
}
Returned by getProposalDetails(). The data field contains ABI-encoded BatchTransferData for batch transfer proposals.
struct BatchTransferData {
address[] tokens;
uint256[] amounts;
address[] recipients;
}
ABI-encoded in the Proposal.data field for BatchTransfer proposals. Decoded by the multi-sig during execution.
AMM Types (PredictionAMM)
struct Pool {
uint256 marketId;
address token;
uint256 b; // LMSR liquidity parameter (1e18 scale)
int256[] quantities; // Shares outstanding per outcome (1e18 scale)
uint256 collateral; // Total collateral deposited
address provider; // Liquidity provider
bool active;
}
Internal representation of an LMSR pool. Returned (destructured) by getPool().
Donation Types (DonationManager)
struct Organization {
string name;
string cause;
string imgUrl;
string description;
uint256 fundsRaised; // Total across all tokens
address wallet;
bool verified;
}
Registered charity or cause. Created via registerOrganization(). The verified flag is set by the donation manager role.
Fee Manager Types (TreasuryFeeManager)
enum FeeOpType {
Add,
Update,
Remove,
Freeze,
Unfreeze,
UpdateTimelock
}
The type of queued fee operation. All fee changes go through a timelock.
struct FeeOp {
FeeOpType op;
uint256 index;
address recipient;
uint256 percentage; // Basis points
string description;
bool freeze;
uint256 eta; // Execution time (block.timestamp + delay)
bool executed;
address proposer;
}
A queued fee operation. Created by queueAddFeeRecipient(), queueUpdateFeeRecipient(), etc. Executed after timelock via executeQueuedFeeOp().
Constants
Protocol-wide constants and access control role identifiers. These values are immutable and set at compile time (or deployment for immutable variables).
Core Protocol (SBETStorage / SBET)
uint256 constant MAX_PRICE = 1e9; // Price ceiling (100%)
uint256 constant MAX_POSITION_MAGNITUDE = 1e27; // Maximum position size
uint256 constant MIN_SANE_AMOUNT = 2; // Minimum trade amount
uint256 constant MAX_SANE_AMOUNT = type(uint128).max; // Maximum trade amount
uint256 constant MAX_FEE_BPS = 1_000; // 10% fee cap
uint256 constant FINALIZATION_DELAY = 24 hours; // Match finalization timelock
Prediction Market
uint256 constant MAX_OUTCOMES = 20; // Maximum market outcomes
uint256 constant MIN_OUTCOMES = 2; // Minimum market outcomes
uint256 constant MAX_CREATOR_FEE_BPS = 50; // 0.5% max creator fee
uint256 constant MAX_BATCH_SIZE = 100; // Paginated query limit
uint256 constant MAX_PRICE = 1e9; // Price ceiling
Treasury Roles (SBETTreasury)
bytes32 constant ADMIN_ROLE = keccak256("ADMIN_ROLE");
bytes32 constant TOKEN_MANAGER_ROLE = keccak256("TOKEN_MANAGER_ROLE");
bytes32 constant WITHDRAWER_ROLE = keccak256("WITHDRAWER_ROLE");
bytes32 constant EMERGENCY_ADMIN_ROLE = keccak256("EMERGENCY_ADMIN_ROLE");
bytes32 constant LOCK_MANAGER_ROLE = keccak256("LOCK_MANAGER_ROLE");
uint256 constant MAX_PROTOCOL_FEE_BPS = 1_000; // 10% max protocol fee
uint256 constant MIGRATION_DELAY = 2 days; // Migration timelock
Treasury Module Roles
// TreasuryFeeManager
bytes32 constant FEE_ADMIN_ROLE = keccak256("FEE_ADMIN_ROLE");
bytes32 constant FEE_MANAGER_ROLE = keccak256("FEE_MANAGER_ROLE");
bytes32 constant FEE_DISTRIBUTOR_ROLE = keccak256("FEE_DISTRIBUTOR_ROLE");
// TreasuryVesting
bytes32 constant VESTING_ADMIN_ROLE = keccak256("VESTING_ADMIN_ROLE");
bytes32 constant VESTING_MANAGER_ROLE = keccak256("VESTING_MANAGER_ROLE");
// TreasuryYield
bytes32 constant YIELD_ADMIN_ROLE = keccak256("YIELD_ADMIN_ROLE");
bytes32 constant YIELD_MANAGER_ROLE = keccak256("YIELD_MANAGER_ROLE");
bytes32 constant YIELD_HARVESTER_ROLE = keccak256("YIELD_HARVESTER_ROLE");
// TreasuryBudgets
bytes32 constant BUDGET_ADMIN_ROLE = keccak256("BUDGET_ADMIN_ROLE");
bytes32 constant BUDGET_MANAGER_ROLE = keccak256("BUDGET_MANAGER_ROLE");
bytes32 constant BUDGET_SPENDER_ROLE = keccak256("BUDGET_SPENDER_ROLE");
// TreasuryMultiSig
bytes32 constant MULTISIG_ADMIN_ROLE = keccak256("MULTISIG_ADMIN_ROLE");
bytes32 constant SIGNER_ROLE = keccak256("SIGNER_ROLE");
// TreasuryNFTFees
bytes32 constant NFT_FEE_ADMIN_ROLE = keccak256("NFT_FEE_ADMIN_ROLE");
bytes32 constant NFT_FEE_MANAGER_ROLE = keccak256("NFT_FEE_MANAGER_ROLE");
bytes32 constant FEE_COLLECTOR_ROLE = keccak256("FEE_COLLECTOR_ROLE");
// TreasuryNFTManager
bytes32 constant NFT_MANAGER_ROLE = keccak256("NFT_MANAGER_ROLE");
// DonationManager
bytes32 constant DONATION_MANAGER_ROLE = keccak256("DONATION_MANAGER_ROLE");
Limits & Timelocks
// TreasuryMultiSig
uint256 constant MIN_SIGNERS = 2;
uint256 constant MAX_SIGNERS = 10;
uint256 constant PROPOSAL_EXPIRY = 7 days;
uint256 constant MAX_PENDING_PROPOSALS = 50;
// TreasuryFeeManager
uint256 constant MAX_FEE_RECIPIENTS = 10;
uint256 constant MIN_TIMELOCK_DELAY = 12 hours;
uint256 constant MAX_TIMELOCK_DELAY = 30 days;
uint256 constant OP_EXPIRY_WINDOW = 14 days;
// TreasuryVesting
uint256 constant MAX_DURATION = 10 * 365 days; // 10-year max vesting
uint256 constant MIN_DURATION = 1 days;
// TreasuryBudgets
uint256 constant MAX_BUDGET_DURATION = 365 days;
uint256 constant MIN_BUDGET_DURATION = 1 days;
uint256 constant MAX_DEPARTMENTS = 100;
// TreasuryYield
uint256 constant MAX_STRATEGIES_PER_TOKEN = 5;
uint256 constant MAX_SLIPPAGE_BPS = 500; // 5% max slippage
// DonationManager
uint256 constant MAX_ORGANIZATIONS = 500;
// Shared batch limits
uint256 constant MAX_BATCH_SIZE = 50; // Treasury, NFT, Integrator ops
Events
SBET Events
event MatchCreated(uint256 indexed matchId, address creator, address oracle);
event OracleSet(uint256 indexed matchId, address oracle);
event LogFinalizeMatch(uint256 indexed matchId, uint32 finalPrice);
event FinalizationRequested(uint256 indexed matchId, uint256 unlockTime);
event GraderFinalized(uint256 indexed matchId, uint32 finalPrice, uint256 graderFee, uint256 sigCount);
event GraderFeesWithdrawn(uint256 indexed matchId, address indexed token, address indexed grader, uint256 amount);
event RecoveryConfigured(uint256 indexed matchId, uint256 deadline, uint32 cancelPrice);
event FundsRecovered(uint256 indexed matchId, uint32 cancelPrice, address indexed triggeredBy);
event TreasuryUpdated(address indexed previousTreasury, address indexed newTreasury);
event EmergencyTriggered(uint256 endTime);
event EmergencyCleared();
SBETTrading Events
event LogRequestTrade(address indexed sender);
event LogTrade(
address indexed takerAccount, address indexed makerAccount, uint256 indexed matchId,
address token, uint256 orderFillHash, uint8 orderDirection, uint32 price,
uint256 longAmount, int256 newLongPosition, uint256 shortAmount, int256 newShortPosition,
int256 longBalanceDelta, int256 shortBalanceDelta
);
event LogETHBalanceUpdate(
address indexed longAddr, address indexed shortAddr, uint256 matchId,
address token, uint8 orderDirection, uint32 price,
int256 longBalanceDelta, int256 shortBalanceDelta
);
event LogTradeError(
address indexed takerAccount, address indexed makerAccount, uint256 indexed matchId,
address token, uint256 orderFillHash, uint16 status
);
event LogCancel(address indexed account, address token, uint256 amount, uint256 orderGroup);
event LogCancelAll(address indexed account, uint256 timestamp);
event ExposureAdjustment(
uint256 indexed matchId, address indexed token, address longAddr, address shortAddr,
int256 exposureDelta, uint8 adjustmentType
);
event SignatureRejected(address indexed maker, uint256 fillHash);
event NonceIncremented(address indexed maker, uint256 newNonce);
event NonceCancelled(address indexed maker, uint256 nonce);
event NonceCancelledUpTo(address indexed maker, uint256 nonce);
event LargePosition(address indexed user, uint256 matchId, uint256 size);
event LogMatchOrders(
address indexed caller, uint256 indexed matchId, address token,
uint256 leftFilled, uint256 rightFilled, int256 callerDelta
);
SBETClaim Events
event LogClaim(address indexed account, uint256 indexed matchId, address indexed token, uint256 amount, uint256 graderFee);
event LogClaimFor(address indexed account, uint256 indexed matchId, address indexed token, int256 payoff);
SBETNFT Events
event NFTStaked(address indexed user, address indexed nftAddress, uint256 nftId);
event NFTReturned(address indexed user, address indexed nftAddress, uint256 nftId);
event NFTBlacklistUpdated(address indexed nftAddress, bool blacklisted);
SBETPool Events
event PoolCreated(uint256 indexed poolId, address indexed token, uint256 numOutcomes);
event PoolJoined(uint256 indexed poolId, address indexed user, uint256 outcome, uint256 amount);
event PoolFinalized(uint256 indexed poolId, uint256 winningOutcome);
event PoolVoided(uint256 indexed poolId);
event PoolClaimed(uint256 indexed poolId, address indexed user, uint256 share);
PredictionMarket Events
event MarketCreated(uint256 indexed marketId, address indexed creator, string question, uint256 numOutcomes);
event MarketResolved(uint256 indexed marketId, uint256 winningOutcome);
event MarketVoided(uint256 indexed marketId);
event MarketDisputed(uint256 indexed marketId, address indexed disputer, string reason);
event DisputeResolved(uint256 indexed marketId, uint256 finalOutcome);
event AMMSet(address indexed amm);
event CreationFeeUpdated(uint256 newFee);
event DisputeBondUpdated(uint256 newBond);
event DisputeWindowUpdated(uint256 newWindow);
event FeeRecipientUpdated(address indexed newRecipient);
PredictionAMM Events
event LiquiditySeeded(uint256 indexed marketId, address indexed provider, uint256 amount, uint256 b);
event SharesBought(uint256 indexed marketId, uint256 outcomeIndex, address indexed buyer, uint256 shares, uint256 cost);
event SharesSold(uint256 indexed marketId, uint256 outcomeIndex, address indexed seller, uint256 shares, uint256 payout);
event SharesRedeemed(uint256 indexed marketId, address indexed user, uint256 payout);
event LiquidityRemoved(uint256 indexed marketId, address indexed provider, uint256 amount);
SBETTreasury Events
event AllowedTokenAdded(address indexed token);
event AllowedTokenRemoved(address indexed token);
event LockStatusChanged(bool isLocked);
event DepositETH(address indexed sender, uint256 amount);
event DepositERC20(address indexed token, address indexed sender, uint256 amount);
event Withdraw(address indexed token, address indexed recipient, uint256 amount);
event EmergencyWithdraw(address indexed token, address indexed account, uint256 amount);
event RoleWasGranted(bytes32 indexed role, address indexed account, address owner);
event RoleWasRevoked(bytes32 indexed role, address indexed account, address owner);
event WithdrawalLimitUpdated(uint256 oldLimit, uint256 newLimit);
event ProtocolFeeBpsSet(uint256 oldBps, uint256 newBps);
event IntegratorHubUpdated(address indexed prev, address indexed curr);
event AccruerUpdated(address indexed accr, bool allowed);
event IntegratorPayout(address indexed router, address indexed token, address indexed payout, uint256 toIntegrator, uint256 toTreasury);
event PayoutAddressVerified(address indexed payout, bool verified);
event ModuleUpdated(string indexed module, address indexed oldAddress, address indexed newAddress);
event YieldStrategySet(address indexed token, address indexed strategy);
event TokenSwept(address indexed token, address indexed to, uint256 amount);
event BatchDeposit(address indexed sender, uint256 tokensCount, uint256 totalValue);
event MigrationQueued(address indexed newTreasury, uint256 eta);
event MigrationExecuted(address indexed newTreasury);
IntegratorHub Events
event RegistrationFeeSet(address indexed token, uint256 amount);
event DefaultBpsSet(uint16 oldBps, uint16 newBps);
event AccrualSourceSet(address indexed caller, bool allowed);
event AccrualsStatusChanged(bool enabled);
event MinAccrualAmountSet(uint256 amount);
event MaxPayoutLimitSet(address indexed router, uint256 limit);
event AppRegistered(address indexed router, address indexed payout, IH.Period period);
event AppUpdated(address indexed router, address payout, uint16 bps, IH.Period period, bool active);
event Accrued(address indexed router, address indexed token, uint256 amount);
event Consumed(address indexed router, address indexed token, uint256 toIntegrator, uint256 toTreasury);
event LastSweepUpdated(address indexed router, uint64 when);
NFTVault Events
event TreasurySet(address indexed prev, address indexed curr);
event TokenAllowed(address indexed nft, bool allowed);
event Locked(bool locked);
event Deposit(address indexed nft, uint256 indexed tokenId, uint256 amount, address indexed from);
event Withdraw(address indexed nft, uint256 indexed tokenId, uint256 amount, address indexed to);
event EmergencyTransfer(address indexed nft, uint256 indexed tokenId, address indexed to);
event VaultMigration(address indexed newVault);
Treasury Module Events
// TreasuryVesting
event VestingCreated(uint256 indexed vestingId, address indexed beneficiary, address indexed token, uint256 amount, uint256 startTime, uint256 duration, uint256 cliff, bool revocable);
event VestingReleased(uint256 indexed vestingId, address indexed beneficiary, address indexed token, uint256 amount);
event VestingScheduleRevoked(uint256 indexed vestingId, address indexed beneficiary, uint256 amountUnvested);
event VestingDeposit(address indexed token, address indexed depositor, uint256 amount);
event VestingIsPaused();
event VestingUnpaused();
event VestingExtended(uint256 indexed vestingId, uint256 newDuration);
// TreasuryYield
event StrategyAdded(address indexed token, address indexed strategy, uint256 targetAllocation);
event StrategyRemoved(address indexed token, address indexed strategy);
event StrategyUpdated(address indexed token, address indexed strategy, bool active, uint256 targetAllocation);
event Deposited(address indexed token, address indexed strategy, uint256 amount);
event Withdrawn(address indexed token, address indexed strategy, uint256 amount);
event Harvested(address indexed token, address indexed strategy, uint256 amount);
event EmergencyWithdrawn(address indexed token, address indexed strategy, uint256 amount);
event MaxDepositSet(address indexed strategy, uint256 amount);
event HarvestCooldownSet(address indexed token, uint256 cooldown);
event Rebalanced(address indexed token, uint256 totalAmount);
event TreasuryUpdated(address indexed oldTreasury, address indexed newTreasury);
// TreasuryFeeManager
event FeeRecipientAdded(uint256 indexed index, address indexed recipient, uint256 percentage, string description);
event FeeRecipientUpdated(uint256 indexed index, address indexed oldRecipient, address indexed newRecipient, uint256 oldPct, uint256 newPct);
event FeeRecipientRemoved(uint256 indexed index, address indexed recipient, uint256 percentage);
event FeeRecipientStatusChanged(uint256 indexed index, bool active);
event FeeRecipientsFrozenStateChanged(bool frozen);
event FeeOpQueued(bytes32 indexed id, FeeOpType op, uint256 eta, address proposer);
event FeeOpExecuted(bytes32 indexed id, FeeOpType op);
event FeeOpCancelled(bytes32 indexed id);
event FeesDistributed(address indexed token, uint256 totalAmount, uint256 recipientCount);
event FeeDistributed(address indexed token, address indexed recipient, uint256 amount);
event TimelockDelayUpdated(uint256 oldDelay, uint256 newDelay);
event MinDistributionSet(address indexed token, uint256 amount);
event FeesAccumulated(address indexed token, uint256 amount);
// TreasuryBudgets
event BudgetCreated(bytes32 indexed budgetId, string name, address indexed token, uint256 amount, uint256 startTime, uint256 endTime, address indexed creator);
event DepartmentAllocated(bytes32 indexed budgetId, address indexed department, uint256 amount);
event BudgetSpent(bytes32 indexed budgetId, address indexed department, address indexed spender, uint256 amount, string description);
event SpendingApprovalSet(bytes32 indexed budgetId, address indexed department, address indexed spender, uint256 amount);
event BudgetDeactivated(bytes32 indexed budgetId);
event BudgetReactivated(bytes32 indexed budgetId);
event BudgetExtended(bytes32 indexed budgetId, uint256 newEndTime);
event BudgetOwnershipTransferred(bytes32 indexed budgetId, address indexed newOwner);
event BudgetUtilizationAlert(bytes32 indexed budgetId, uint256 percentUsed);
event BudgetDeposit(address indexed token, address indexed depositor, uint256 amount);
// TreasuryMultiSig
event ProposalCreated(bytes32 indexed proposalId, ProposalType indexed proposalType, address indexed proposer, string description);
event ProposalVoted(bytes32 indexed proposalId, address indexed voter, uint256 votes);
event ProposalExecuted(bytes32 indexed proposalId, address indexed executor);
event ProposalCancelled(bytes32 indexed proposalId, address indexed canceller);
event Transfer(address indexed token, address indexed recipient, uint256 amount);
event SignerAdded(address indexed signer);
event SignerRemoved(address indexed signer);
event ThresholdChanged(uint256 oldThreshold, uint256 newThreshold);
event Deposit(address indexed token, address indexed depositor, uint256 amount);
// TreasuryNFTFees
event NFTFeeConfigSet(address indexed nftCollection, bool enabled, uint256 fixedFeeAmount, address feeToken, uint256 percentageFee, bool usePercentage);
event DefaultFeeSet(uint256 amount, address token, uint256 percentage, bool usePercentage);
event NFTFeeCollected(address indexed from, address indexed nftCollection, uint256 amount, address token, uint256 betValue);
event CategoryFeeSet(string indexed category, NFTFeeConfig config);
event CollectionCategorized(address indexed collection, string category);
event FeeExemptionSet(address indexed user, bool exempt);
event TemporaryExemptionSet(address indexed user, uint256 expiryTime);
event FeeScheduleSet(address indexed collection, uint256[] thresholds, uint256[] fees);
event FeesWithdrawn(address indexed token, uint256 amount, address recipient);
event FeeRecipientSet(address indexed oldRecipient, address indexed newRecipient);
event TreasuryUpdated(address indexed oldTreasury, address indexed newTreasury);
event EthReceived(address indexed sender, uint256 amount);
// TreasuryNFTManager
event NFTVaultUpdated(address indexed oldVault, address indexed newVault);
event NFTDeposited(address indexed caller, address indexed nft, uint256 tokenId, uint256 amount);
event NFTWithdrawn(address indexed caller, address indexed nft, uint256 tokenId, uint256 amount);
event BatchNFTDeposited(address indexed caller, address[] nfts, uint256[] tokenIds, uint256[] amounts);
event BatchNFTWithdrawn(address indexed caller, address[] nfts, uint256[] tokenIds, uint256[] amounts);
// DonationManager
event OrganizationAdded(uint256 indexed id, string name, string cause, address wallet);
event OrganizationVerified(uint256 indexed id, bool verified);
event DonationMade(uint256 indexed orgId, address indexed donor, uint256 amount, address token);
event DonationMadeByCause(string cause, address indexed donor, uint256 totalAmount, address token);
event DonationFromWinnings(uint256 indexed orgId, address indexed donor, uint256 donationAmount, address token, uint256 totalWinnings);
event EthDonation(uint256 indexed orgId, address indexed donor, uint256 ethAmount);
Errors
SBET Core Errors (ISBETInterfaces + SBET.sol)
// SBET.sol
error InvalidThreshold();
// Trading & Order Errors
error DirectCallNotSupported();
error DirectETHNotAccepted();
error InvalidOrderSignature();
error InvalidTaker();
error InvalidPrice();
error InvalidDirection();
error EmptyPackedOrders();
error SelfTrade();
error TradeExpired();
error InvalidNonce();
error OrderCancelled();
error TradeNotOK();
error AmountMalformed();
error AmountTooSmall(uint256 amount);
error AmountTooLarge(uint256 amount);
error InvalidPriceRange(uint32 price);
error InvalidCancelPrice();
error PositionTooLarge();
error InvalidRecipient();
error LengthMismatch();
error InvalidBatchSize();
error EmptyArray();
error OrderNotFound();
// Match & Finalization Errors
error InvalidMatchId();
error MatchNotFinalized();
error MatchIsFinalized();
error MatchAlreadyFinalized(uint256 matchId);
error BadFinalPrice();
error MatchIdMismatch();
// Claim Errors
error NoPositionToClaim();
error NegativeETHDeltaNotSupported();
error ContractRecipientNotAllowed();
// Grader Oracle Errors
error InvalidGraderQuorum();
error InsufficientSignatures();
error TooManySignatures();
error DuplicateGraderSignature();
error NoGraderFees();
error NotReportingGrader();
error GraderFeesAlreadyClaimed();
// Token & Treasury Errors
error TokenNotAllowed();
error InvalidToken();
error ETHTransferFailed();
error TreasuryUnset();
error NotTreasury();
error ZeroTreasury();
// Oracle Errors
error InvalidOracleAddress();
error OracleNotSet();
error StaleOracleData();
error InvalidRange();
// Emergency & System Errors
error EmergencyActive();
error EmergencyNotActive();
error FeeTooHigh();
error NotReady();
error ArithmeticOverflow();
error RecoveryNotReady();
error RecoveryNotConfigured();
error InvalidRecoveryDeadline();
SBETPool Errors
error InvalidPoolId();
error PoolIsFinalized();
error PoolNotFinalized();
error PoolDoesNotExist();
error InvalidOutcome();
error NeedAtLeastTwoOutcomes();
error TooManyOutcomes();
error BetTooSmall();
error NoWinningStake();
error EndExceedsPoolCount();
SBETNFT Errors
error UnsupportedNFTType();
error InvalidNFTAddress();
error InvalidFrom();
error InvalidBetSide();
error CallerNotNFTOwner();
error NFTBlacklisted(address nftAddress);
error NotNFTOwner(address claimed, address actual);
error NFTNotApproved();
error InsufficientNFTBalance();
error NFTAlreadyStaked();
error NoNFTStaked();
error NFTNotStaked();
error BetAlreadyStarted();
error NoBetCreated();
error SideBAlreadyFilled();
error CannotSelfBet();
error InsufficientETHForNFTFee(uint256 required, uint256 sent);
SBETMath Errors
error InvalidPriceDivideArgs();
error InvalidEffectiveBalancePrice();
error SafeSubUnderflow();
error PositionOverflow();
error BalanceDeltaOverflow();
SBETQuery Errors
error InvalidSBETAddress();
error PoolQueryFailed();
PredictionMarket Errors
error TooFewOutcomes();
error TooManyOutcomes();
error InsufficientCreationFee();
error PastResolutionTime();
error ExpiryBeforeResolution();
error InvalidGraderQuorum();
error CreatorFeeTooHigh();
error MarketNotActive();
error MarketNotResolutionPending();
error MarketNotDisputed();
error ResolutionTooEarly();
error MarketNotExpired();
error MarketAlreadyResolved();
error DisputeWindowPassed();
error DisputeWindowNotPassed();
error InsufficientDisputeBond();
error InvalidOutcomeIndex();
error ZeroAddress();
error LabelsMismatch();
error MarketDoesNotExist();
error InvalidQuorum();
error DuplicateCouncilMember();
error EthTransferFailed();
error InvalidDisputeCouncilSig();
error DisputeCouncilNotSet();
PredictionAMM Errors
error PoolAlreadySeeded();
error PoolNotActive();
error PoolNotResolved();
error InsufficientShares();
error CostExceedsMaxCost();
error PayoutBelowMinPayout();
error InvalidShares();
error InvalidLiquidityParam();
error NotPoolProvider();
error MarketNotResolved();
error NoWinningShares();
error OnlyPredictionMarket();
error ZeroAddress();
error InsufficientLiquidity();
error WinningSharesPending();
SBETTreasury Errors
error TokenAlreadyAllowed();
error TokenNotAllowed(address token);
error TokenAddFailed();
error ContractIsLocked();
error TokenIsManaged(address token);
error DepositAmountMustBeGreaterThanZero();
error IncorrectETHValue();
error ProjectTokenCannotBeRemoved();
error ZeroAddressNotAccepted();
error AccountAlreadyHasRole(bytes32 role, address account);
error AccountDoesNotHaveRole(bytes32 role, address account);
error InvalidAddress();
error ContractPaused();
error BpsTooHigh();
error NoIntegratorHub();
error NotAccruer();
error EthTransferFailed();
error InvalidPayoutAddress();
error PayoutAddressNotVerified();
error CannotSendToSelf();
error DailyLimitExceeded(uint256 attempted, uint256 remaining);
error LengthMismatch();
error BatchSizeTooLarge();
error InvalidDuration();
error InvalidAccount();
error AccountNotAdmin(address account);
error TreasuryNotLocked();
error MigrationNotReady();
error MigrationNotSet();
error MigrationLockInterrupted();
IntegratorHub Errors
error FeeTooHigh();
error NotAccruer();
error NotTreasury();
error AlreadyRegistered();
error RegistrationFeeNotSet();
error RegistrationFeeMismatch();
error UnsupportedPeriod();
error NotRegistered();
error InactiveApp();
error AccrualsPaused();
error AlreadyActive();
error NotActive();
error UnexpectedETH();
error AmountTooSmall();
error ETHTransferFailed();
error InvalidFeeToken();
error FeeTokenNotERC20();
error LengthMismatch();
error ZeroAddress();
error BatchTooLarge();
Treasury Module Errors
// TreasuryMultiSig
error InvalidTreasury();
error InvalidThreshold();
error TooManySigners();
error TooFewSigners();
error NotEnoughSigners();
error InvalidProposal();
error ProposalNotFound();
error ProposalExpired();
error ProposalAlreadyExecuted();
error ProposalAlreadyCancelled();
error AlreadyVoted();
error NotEnoughVotes(uint256 have, uint256 need);
error InvalidRecipient();
error InvalidAmount();
error InvalidToken();
error TokenNotAllowed();
error BatchLengthMismatch();
error TooManyPendingProposals();
error NotProposer();
error NotSigner();
error SignerAlreadyExists();
error SignerDoesNotExist();
error CannotRemoveLastSigner();
error ContractPaused();
error EthTransferFailed();
error InvalidData();
// TreasuryVesting
error InvalidBeneficiary();
error InvalidToken();
error InvalidDuration();
error InvalidAmount();
error VestingNotRevocable();
error VestingAlreadyRevoked();
error CliffNotReached(uint256 cliffEndTs, uint256 nowTs);
error NothingToRelease();
error NotBeneficiary();
error TokenNotAllowed();
error ContractPaused();
error EthTransferFailed();
error ScheduleDoesNotExist();
error DurationTooLong();
error CliffExceedsDuration();
error VestingPaused();
error InsufficientVestingBalance(address token, uint256 required, uint256 available);
// TreasuryBudgets
error InvalidTreasury();
error BudgetAlreadyExists();
error BudgetDoesNotExist();
error BudgetNotFound();
error BudgetNotActive();
error BudgetExpired();
error BudgetNotStarted();
error InvalidDuration();
error InvalidAmount();
error InvalidToken();
error TokenNotAllowed();
error DepartmentNotAllocated();
error InsufficientAllocation();
error InsufficientApproval();
error AllocationExceedsBudget();
error TooManyDepartments();
error InvalidDepartment();
error ContractPaused();
error EthTransferFailed();
error InvalidName();
error ZeroAddress();
error Unauthorized();
error InsufficientBudgetBalance(address token, uint256 required, uint256 available);
// TreasuryYield
error NoStrategies();
error InvalidTreasury();
error TokenNotAllowed();
error StrategyAlreadyExists();
error TooManyStrategies();
error AllocationExceeded();
error DepositTooSmall();
error InvalidAmount();
error InsufficientBalance();
error StrategyNotActive();
error StrategyNotRegistered();
error HarvestCooldownActive();
error SlippageTooHigh();
error ContractPaused();
error NotTreasury();
error StrategyNotSet(address token);
// TreasuryFeeManager
error InvalidTreasury();
error InvalidRecipient();
error InvalidPercentage();
error RecipientLimitReached();
error FeeCapExceeded(uint256 newTotalBps);
error FeeRecipientsFrozen();
error IndexOutOfBounds();
error BadFeeArgs();
error NotReady(uint256 eta, uint256 currentTime);
error AlreadyExecuted();
error OpDoesNotExist();
error NoFeesToDistribute();
error BadDelay();
error TokenNotAllowed();
error ContractPaused();
error EthTransferFailed();
error RecipientAlreadyExists();
error RecipientNotActive();
error DistributionTooSoon();
error InsufficientAccumulatedFees();
error OpExpired(bytes32 id);
// TreasuryNFTFees
error InvalidNFTAddress();
error InvalidTreasury();
error InvalidAddress();
error InvalidAmount();
error InvalidFeeConfiguration();
error InvalidRecipientsBps();
error TokenNotAllowed();
error NotAccruer();
error EthTransferFailed();
error InvalidFeeToken();
error FeeExceedsMaximum();
error BatchSizeTooLarge();
error LengthMismatch();
error ContractPaused();
error CollectionNotConfigured();
error InvalidCategory();
error InvalidSchedule();
error UserExempted();
error ZeroAddress();
error NoFees();
TreasuryNFTManager Errors
error NftVaultUnset();
error ContractIsLocked();
error TokenNotAllowed(address token);
error LengthMismatch();
error BatchTooLarge();
error ContractPaused();
error OnlyTreasury();
error ZeroAddress();
NFTVault Errors
error NotTreasury();
error InvalidAddress();
error UnsupportedNFTType();
error ERC721InvalidAmount();
error TokenNotAllowed(address token);
error ContractLocked();
error LengthMismatch();
error InvalidAmount();
error MustBeLocked();
error BatchTooLarge();
DonationManager Errors
error InvalidOrganizationName();
error InvalidOrganizationCause();
error InvalidImageUrl();
error InvalidDescription();
error InvalidWalletAddress();
error InvalidOrganizationId();
error OrganizationAlreadyVerified();
error OrganizationNotVerified();
error InvalidDonationAmount();
error NoVerifiedOrganizationsForCause();
error EthTransferFailed();
error TooManyOrganizations();
error InvalidTokenAddress();