Quests & Leaderboards
StellarCade tracks quest progress and XP per player, with completed quests eligible for on-chain rewards via the quest-ledger-v2 and achievement-badge contracts (both marked Implemented with real test coverage — see Soroban Smart Contracts). The SDK's QuestsClient and LeaderboardClient read this state through the gateway.
Reading and Claiming Quests
typescriptimport { StellarCadeClient, createConfig } from "@stellarcade/sdk"; const client = new StellarCadeClient(createConfig({ network: "testnet", gatewayUrl: "https://gateway.stellarcade.example", arbiterUrl: "https://arbiter.stellarcade.example", contracts: { /* ...contract addresses... */ }, })); const quests = await client.quests.listForPlayer(playerAddress); quests.forEach((q) => { console.log(`${q.questId}: ${q.progress}/${q.target}${q.claimed ? " (claimed)" : ""}`); if (q.streak > 0) console.log(` Streak: ${q.streak}`); }); // Claim a completed quest const completed = quests.find((q) => q.progress >= q.target && !q.claimed); if (completed) { const result = await client.quests.claim(completed.questId, playerAddress); await client.waitForTx(result.hash); }
QuestProgress is { questId, playerAddress, progress, target, claimed, streak } — there's no separate title/category/milestones structure or XP-reward field in the SDK's types; that level of detail, if you need it, comes from whatever the gateway's quest-listing response includes beyond this typed shape.
Leaderboard
typescriptconst overall = await client.leaderboard.get({ limit: 10 }); const coinFlipOnly = await client.leaderboard.get({ gameId: "coin-flip", limit: 10 }); overall.forEach((entry) => { console.log(`#${entry.rank} — ${entry.playerAddress.slice(0, 8)}… — ${entry.score}`); });
LeaderboardQuery only supports gameId and limit — there's no timeframe ("daily"/"weekly"/"all_time") parameter in the current SDK; ranking windows, if the gateway supports them, aren't exposed through this client yet.