@fulltime/settle · settlement SDK

Settle match outcomes by proof.
No operator.

An installable Solana settlement engine powered by TxLINE proofs. This app is one thing built on it.

Parametric match-stat conditions — a single-stat threshold or a two-stat predicate over one fixture's TxLINE data. Not general-purpose settlement.

Get itnot on npm yet
$ git clone https://github.com/A91y/full-time

Not published to a registry — build @fulltime/settle from packages/settle.

settleByProof is the whole point — the proof decides, not a signer.
settle.ts
import { SettleClient } from "@fulltime/settle";

const client = new SettleClient({ rpcUrl, txlineOrigin, jwt, apiToken, keypair });

const { market } = await client.createMarket({
  fixtureId, spec, deadline, graceWindow, contestWindow, feeBps,
  feeRecipient: client.wallet,
});

await client.placeBet(market, true, 1_000_000n);      // escrow 1 USDC on YES
await client.settleByProof(market, fixtureId, spec);  // proof → validate_stat → resolve
await client.claim(market);                           // pay out by proof

How it works

The data path is a centralized convenience; the verification path is not. A forged score produces a mismatched root and fails.

Off-chain · fetched
TxLINE REST
SettleClient
On-chain · trusted
settle
CPI validate_stat
daily_scores_merkle_roots

No privileged signer

settle takes no authority signer. Anyone can call it; nobody can settle a false outcome.

Verified on-chain

The proof is recomputed against an anchored Merkle root, not trusted from an oracle key.

Bring your own token

Node-native, no framework. Runs on a free TxLINE World Cup tier token you supply.

Runs headless

no privileged key

Settlement doesn't need a browser. The keeper is an independent process — any keypair, no authority signer — that polls open markets and settles each the moment its match finalises.

keeper · decision loop
every tick:
  for each Open market:
    proof = fetch(fixtureId, statKey)   // TxLINE game_finalised?
    if      (proof)   settle(market, proof)   // CPI validate_stat → Resolved
    else if (expired) refund(market)          // deadline + grace passed
    else              wait                     // still in window
settle

game_finalised proof exists → CPI validate_stat → market Resolved.

refund

never finalised past deadline + grace → funds returnable by anyone.

wait

still inside the window → do nothing this tick, re-check next poll.

Independent of this app and the SDK. keeper source

The market app you're using is a consumer of this SDK — the same interface a third party would use, importing the client, builders, and constants from the package.

Open the reference app

Read the source

Built and verified on Solana devnet — one full create → place → settle → claim lifecycle. Not published to a registry yet.