Thassa.

Protocol

Architecture

Thassa markets settle through a proof-of-authority (PoA) oracle pipeline: the markets contract asks the Thassa hub a question, an authorized oracle node answers it against publicly bound sources, a PoA verifier checks the node’s signature onchain, and the hub calls the market back with the outcome. Nothing settles on an unverified answer, and every question is stored onchain in public.

The settlement pipeline

ThassaMarkets

all markets, one contract · oracle client

ThassaHub

oracle request hub · bids & updates

Oracle node (PoA fulfiller)

fetches bound sources · adjudicates · signs

ThassaPoAVerifier

owner-managed signer set · verifies signature

Hub callback → _updateOracle

(marketId, settled, direction) · status → SETTLED

Components

ThassaMarkets

One contract holds all markets — no per-market deployments, which keeps creation gas-free at the protocol level. It extends ThassaOracle, making it an oracle client of the hub: it places settlement bids and receives the hub’s callback. It also runs the entire order book — escrow, matching, fees, redemption.

ThassaHub

The oracle request hub. A settlement request is a hub bid placed via placeBidWithInputData, where inputData = abi.encode(marketId, settlementQuery). The hub holds the bid while the market is SETTLING, accepts a verified update, and invokes the markets contract’s callback. Replay protection comes from hub update digests.

ThassaPoAVerifier

The trust anchor. An owner-managed signer set (addSigner, removeSigner, isSigner, signerCount) verifies each update: the update’s fulfiller must be an authorized signer, and the signature — EIP-191 personal_sign over the hub’s ProofUpdateV2 digest — must recover to that exact fulfiller. Signer changes emit SignerAdded / SignerRemoved.

The oracle node

An offchain fulfiller run by Thassa. For each settlement bid it:

  1. Parses the structured settlement query from bid inputData {question, category, rule, sources}.
  2. Fetches the bound sources itself (ESPN, NWS, news APIs, pricing APIs) — in the node process, before and separate from any LLM call.
  3. Adjudicates only from the fetched evidence — no open web search. For majority-rule queries the node computes concurrence in code, one independent verdict per source.
  4. Signs the response envelope echoing the marketId, or produces no update (_fulfilled=false) when the outcome isn’t determinable yet — sources unavailable, no majority, event not concluded. The bid stays open and the node retries later.

The node’s settlement prompt is hardened against prompt injection: it never follows instructions embedded in a market question and returns strictly the expected shape tuple(marketId, settled, direction).

The callback

The hub delivers the verified update to the markets contract, whose _updateOracle decodes (marketId, settled, direction), requires the market to be SETTLING with settled == true, records the outcome (direction: true = YES), and flips status to SETTLED, emitting MarketSettled. Winners can then redeem $1 per share.

Around the contracts

  • Relayer — batches EIP-712-signed orders into placeOrdersBatch and pays gas. It only ever submits to allowlisted platform contracts and whitelisted methods, and validates every EIP-3009 authorization pays the markets contract before relaying. Never arbitrary calldata.
  • Indexer — subscribes to contract events (OrderPlaced, OrderMatched, MarketSettled, …), maintains the read models the API serves, and pushes WebSocket deltas.
  • Settlement runner — collects the $0.05 settlement fee, calls settleMarket, and watches the hub to flip statuses and notify.

Why PoA?

The canonical settlement path is Thassa’s own node signing response blobs, verified onchain against an explicit signer set. It is a deliberate, transparent trust anchor: the signer set is public, every settlement query is public, and every source is publicly named — see Settlement & sources.