Skip to content

TypeScript SDK ​

@verity-vrf/sdk, built on viem.

ts
import { createPublicClient, createWalletClient, custom, http, parseEther } from 'viem'
import { VerityCoordinator, deployments, pulsechainTestnet, waitForFulfillment, getActivity } from '@verity-vrf/sdk'

const { coordinator, startBlock, keyHashes } = deployments[943]!
const publicClient = createPublicClient({ chain: pulsechainTestnet, transport: http() })
const verity = new VerityCoordinator(coordinator, publicClient, walletClient)
verity.createSubscription({ fund? })Returns the subscription id
verity.fundSubscription(id, amount), addConsumer, removeConsumer, cancelSubscription, owner transferWait for the receipt; throw if the transaction reverted
verity.getSubscription(id)balance, reserved, available, pending requests, owner, consumers
verity.getConfig(), verity.getLanes(), verity.estimateRequestCost(keyHash, gas)
listSubscriptions(client, { coordinator, owner, fromBlock })Live subscriptions owned by an address
getRequestStatus(client, { coordinator, requestId, fromBlock })pending / fulfilled (words, payment, callbackSuccess) / cancelled / unknown
waitForFulfillment(client, opts)Resolves on fulfilment; rejects on cancellation or timeout
getActivity(client, { coordinator, fromBlock })Every request with its fulfilment, delay percentiles and totals
computeRequestId, computePreSeed, deriveWords, keyHashOfPure helpers, identical to the contract
pulsechain, pulsechainTestnet, deploymentsChains and official addresses

When reading logs yourself with viem, call getBlockNumber({ cacheTime: 0 }). The default cache can hide events from the last few seconds.

Indexer API and fallback ​

VerityApi is a typed client for the verity-indexer HTTP API (subscriptions, requests, stats and time series, gas lanes, operators, governance, search) and its live stream. VerityData is what apps should read through: it uses the API when it is reachable and up to date, and otherwise reads the chain directly with the functions above. Every answer says where it came from.

ts
import { VerityApi, VerityData, deployments } from '@verity-vrf/sdk'

const d = deployments[943]!
const api = new VerityApi({ baseUrl: 'https://<indexer>/v1', chainId: 943 })
const data = new VerityData({ publicClient, coordinator: d.coordinator, fromBlock: d.startBlock, api })

const { data: sub, source } = await data.getSubscription(1n) // source: 'api' | 'chain'
sub.details?.lowBalance        // extra fields only the API has (history counters, low-balance hint, ...)
await data.getRequestStatus(requestId)
await data.listSubscriptions(owner)
await data.getActivity({ limit: 25 })

// live updates; onDisabled fires if the server switched the stream off (then poll)
const s = api.subscribe({ subId: 1n, onMessage: (m) => console.log(m.kind, m.data), onDisabled: startPolling })
s.close()

Falls back to the chain on network errors, timeouts, 429, 5xx, an index more than maxLagBlocks (default 20) behind, and 404s for things the index may not have seen yet. Bad input (400) is not retried.

Testnet: PulseChain testnet v4. Unaudited software; do not use on mainnet yet.