Stork Oracle
Overview
Section titled “Overview”Stork is a decentralized oracle that provides signed price data on-chain. Quasdaq uses Stork to:
- Display live prices on the frontend via the REST API
- Resolve markets by submitting signed oracle data to the contract
Feed IDs
Section titled “Feed IDs”Each asset has a feed ID string (e.g. "BTCUSD") that is hashed with keccak256 to produce the bytes32 value stored on-chain.
import { keccak256, toUtf8Bytes } from "quais";
// The feed ID must match exactly — case-sensitiveconst feedIdHash = keccak256(toUtf8Bytes("BTCUSD"));Available Feeds
Section titled “Available Feeds”Not all assets in the catalog have a live Stork subscription. Query the Feed API with ?storkOnly=true to see only resolvable feeds:
curl "https://quasdaq.com/api/feeds?storkOnly=true"Assets with hasStorkFeed: true include: BTC, ETH, SOL, BNB, SPY, and others.
Resolution Process
Section titled “Resolution Process”1. Fetch signed price data
Section titled “1. Fetch signed price data”const res = await fetch( `https://quasdaq.com/api/stork?feedId=BTCUSD`);const storkData = await res.json();2. Get oracle update fee
Section titled “2. Get oracle update fee”const storkContract = new Contract(storkAddress, [ "function getUpdateFeeV1(tuple(tuple(uint64,int192),bytes32,bytes32,bytes32,bytes32,bytes32,uint8)[]) view returns (uint256)"], provider);
const fee = await storkContract.getUpdateFeeV1(updateData);3. Call resolve on the market
Section titled “3. Call resolve on the market”const market = new Contract(marketAddress, [ "function resolve(tuple(tuple(uint64,int192),bytes32,bytes32,bytes32,bytes32,bytes32,uint8)[]) payable"], signer);
await market.resolve(updateData, { value: fee, gasLimit: 500000n });Stork API Response Structure
Section titled “Stork API Response Structure”The Stork API returns data nested under:
stork_signed_price ├── timestamped_signature │ └── signature │ ├── r (bytes32) │ ├── s (bytes32) │ └── v (uint8) ├── timestamp (uint64, nanoseconds) └── price (quantized int192)TemporalNumericValueInput Struct
Section titled “TemporalNumericValueInput Struct”The on-chain struct ordering matters:
struct TemporalNumericValueInput { TemporalNumericValue temporalNumericValue; // MUST be first bytes32 id; bytes32 publisherMerkleRoot; bytes32 valueComputeAlgHash; bytes32 r; bytes32 s; uint8 v;}