@provable-games/budokan-sdk 0.1.3 → 0.1.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +44 -24
- package/dist/{client-BtC3ngNe.d.cts → client-eg3Ink5N.d.cts} +31 -20
- package/dist/{client-BtC3ngNe.d.ts → client-eg3Ink5N.d.ts} +31 -20
- package/dist/index.cjs +382 -113
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +4 -2
- package/dist/index.d.ts +4 -2
- package/dist/index.js +383 -114
- package/dist/index.js.map +1 -1
- package/dist/react.cjs +407 -113
- package/dist/react.cjs.map +1 -1
- package/dist/react.d.cts +3 -1
- package/dist/react.d.ts +3 -1
- package/dist/react.js +408 -114
- package/dist/react.js.map +1 -1
- package/package.json +1 -1
package/dist/react.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { createContext, useMemo, useRef, useEffect, useContext, useState, useCallback } from 'react';
|
|
2
|
-
import { num } from 'starknet';
|
|
2
|
+
import { CairoCustomEnum, num } from 'starknet';
|
|
3
3
|
import { jsx } from 'react/jsx-runtime';
|
|
4
4
|
|
|
5
5
|
// src/react/context.tsx
|
|
@@ -199,12 +199,8 @@ function snakeToCamel(obj) {
|
|
|
199
199
|
// src/api/tournaments.ts
|
|
200
200
|
function normalizeTournament(raw) {
|
|
201
201
|
const t = snakeToCamel(raw);
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
} else if (t.tournamentId && !t.id) {
|
|
205
|
-
t.id = t.tournamentId;
|
|
206
|
-
}
|
|
207
|
-
return t;
|
|
202
|
+
const id = t.id ?? t.tournamentId;
|
|
203
|
+
return { ...t, id, tournamentId: id };
|
|
208
204
|
}
|
|
209
205
|
function fetchOpts(ctx) {
|
|
210
206
|
return {
|
|
@@ -337,11 +333,12 @@ async function getPlayerTournaments(baseUrl, address, params, ctx) {
|
|
|
337
333
|
game_token_ids: params?.gameTokenIds?.join(",")
|
|
338
334
|
});
|
|
339
335
|
const result = await apiFetch(`${baseUrl}/players/${normalized}/tournaments${qs}`, fetchOpts2(ctx));
|
|
336
|
+
const { total, limit: resLimit, offset: resOffset } = extractPagination(result, { limit: params?.limit, offset: params?.offset });
|
|
340
337
|
return {
|
|
341
338
|
data: result.data.map((item) => snakeToCamel(item)),
|
|
342
|
-
total
|
|
343
|
-
limit:
|
|
344
|
-
offset:
|
|
339
|
+
total,
|
|
340
|
+
limit: resLimit,
|
|
341
|
+
offset: resOffset
|
|
345
342
|
};
|
|
346
343
|
}
|
|
347
344
|
async function getPlayerStats(baseUrl, address, ctx) {
|
|
@@ -370,11 +367,12 @@ async function getGameTournaments(baseUrl, gameAddress, params, ctx) {
|
|
|
370
367
|
offset: params?.offset
|
|
371
368
|
});
|
|
372
369
|
const result = await apiFetch(`${baseUrl}/games/${normalized}/tournaments${qs}`, fetchOpts3(ctx));
|
|
370
|
+
const { total, limit: resLimit, offset: resOffset } = extractPagination(result, { limit: params?.limit, offset: params?.offset });
|
|
373
371
|
return {
|
|
374
372
|
data: result.data.map((item) => snakeToCamel(item)),
|
|
375
|
-
total
|
|
376
|
-
limit:
|
|
377
|
-
offset:
|
|
373
|
+
total,
|
|
374
|
+
limit: resLimit,
|
|
375
|
+
offset: resOffset
|
|
378
376
|
};
|
|
379
377
|
}
|
|
380
378
|
async function getGameStats(baseUrl, gameAddress, ctx) {
|
|
@@ -403,11 +401,12 @@ async function getActivity(baseUrl, params, ctx) {
|
|
|
403
401
|
offset: params?.offset
|
|
404
402
|
});
|
|
405
403
|
const result = await apiFetch(`${baseUrl}/activity${qs}`, fetchOpts4(ctx));
|
|
404
|
+
const { total, limit: resLimit, offset: resOffset } = extractPagination(result, { limit: params?.limit, offset: params?.offset });
|
|
406
405
|
return {
|
|
407
406
|
data: result.data.map((item) => snakeToCamel(item)),
|
|
408
|
-
total
|
|
409
|
-
limit:
|
|
410
|
-
offset:
|
|
407
|
+
total,
|
|
408
|
+
limit: resLimit,
|
|
409
|
+
offset: resOffset
|
|
411
410
|
};
|
|
412
411
|
}
|
|
413
412
|
async function getActivityStats(baseUrl, ctx) {
|
|
@@ -583,19 +582,15 @@ var CHAINS = {
|
|
|
583
582
|
rpcUrl: "https://api.cartridge.gg/x/starknet/mainnet/rpc/v0_10",
|
|
584
583
|
apiBaseUrl: "https://budokan-api-production.up.railway.app",
|
|
585
584
|
wsUrl: "wss://budokan-api-production.up.railway.app/ws",
|
|
586
|
-
budokanAddress: "",
|
|
587
|
-
|
|
588
|
-
viewerAddress: ""
|
|
589
|
-
// TODO: set after mainnet deployment
|
|
585
|
+
budokanAddress: "0x06137ee50f57d08e1d0d758045e45982e2f5ef4826091ed4db136e7afbafecce",
|
|
586
|
+
viewerAddress: "0x075d1b9f1a9751e6b8f8b5a4ca8e721f10c58d87607e703cda062e512a434443"
|
|
590
587
|
},
|
|
591
588
|
sepolia: {
|
|
592
589
|
rpcUrl: "https://starknet-sepolia.public.blastapi.io",
|
|
593
590
|
apiBaseUrl: "https://budokan-api-sepolia.up.railway.app",
|
|
594
591
|
wsUrl: "wss://budokan-api-sepolia.up.railway.app/ws",
|
|
595
|
-
budokanAddress: "",
|
|
596
|
-
|
|
597
|
-
viewerAddress: ""
|
|
598
|
-
// TODO: set after sepolia deployment
|
|
592
|
+
budokanAddress: "0x0072a26c29ba5021508bbbb8487663a2a536b8a926acf388d3d772961bd063e0",
|
|
593
|
+
viewerAddress: "0x06bef644110a02c1b075b539953c707cd03b4bb32b42f5f1b0b0090b5139529f"
|
|
599
594
|
}
|
|
600
595
|
};
|
|
601
596
|
function getChainConfig(chain) {
|
|
@@ -775,7 +770,6 @@ async function withFallback(primary, fallback, health) {
|
|
|
775
770
|
|
|
776
771
|
// src/rpc/provider.ts
|
|
777
772
|
var starknetModule = null;
|
|
778
|
-
var useObjectConstructor = null;
|
|
779
773
|
async function getStarknet() {
|
|
780
774
|
if (!starknetModule) {
|
|
781
775
|
starknetModule = await import('starknet');
|
|
@@ -793,30 +787,7 @@ async function createContract(abi, address, provider) {
|
|
|
793
787
|
resolvedAbi = abi.default;
|
|
794
788
|
}
|
|
795
789
|
const starknet = await getStarknet();
|
|
796
|
-
|
|
797
|
-
if (useObjectConstructor === null) {
|
|
798
|
-
try {
|
|
799
|
-
const contract = new StarknetContract({
|
|
800
|
-
abi: resolvedAbi,
|
|
801
|
-
address,
|
|
802
|
-
providerOrAccount: provider
|
|
803
|
-
});
|
|
804
|
-
useObjectConstructor = true;
|
|
805
|
-
return contract;
|
|
806
|
-
} catch {
|
|
807
|
-
useObjectConstructor = false;
|
|
808
|
-
return new StarknetContract(resolvedAbi, address, provider);
|
|
809
|
-
}
|
|
810
|
-
}
|
|
811
|
-
if (useObjectConstructor) {
|
|
812
|
-
return new StarknetContract({
|
|
813
|
-
abi: resolvedAbi,
|
|
814
|
-
address,
|
|
815
|
-
providerOrAccount: provider
|
|
816
|
-
});
|
|
817
|
-
} else {
|
|
818
|
-
return new StarknetContract(resolvedAbi, address, provider);
|
|
819
|
-
}
|
|
790
|
+
return new starknet.Contract({ abi: resolvedAbi, address, providerOrAccount: provider });
|
|
820
791
|
}
|
|
821
792
|
function wrapRpcCall(fn, contractAddress) {
|
|
822
793
|
return fn().catch((error) => {
|
|
@@ -864,16 +835,22 @@ function decodeByteArray(value) {
|
|
|
864
835
|
}
|
|
865
836
|
return result;
|
|
866
837
|
}
|
|
838
|
+
var PHASE_VARIANTS = ["Scheduled", "Registration", "Staging", "Live", "Submission", "Finalized"];
|
|
839
|
+
var PHASE_NAME_MAP = {
|
|
840
|
+
scheduled: "Scheduled",
|
|
841
|
+
registration: "Registration",
|
|
842
|
+
staging: "Staging",
|
|
843
|
+
live: "Live",
|
|
844
|
+
submission: "Submission",
|
|
845
|
+
finalized: "Finalized"
|
|
846
|
+
};
|
|
867
847
|
function phaseToRpcArg(phase) {
|
|
868
|
-
const
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
finalized: "Finalized"
|
|
875
|
-
};
|
|
876
|
-
return { [map[phase]]: {} };
|
|
848
|
+
const activeVariant = PHASE_NAME_MAP[phase];
|
|
849
|
+
const variants = {};
|
|
850
|
+
for (const v of PHASE_VARIANTS) {
|
|
851
|
+
variants[v] = v === activeVariant ? {} : void 0;
|
|
852
|
+
}
|
|
853
|
+
return new CairoCustomEnum(variants);
|
|
877
854
|
}
|
|
878
855
|
function parseTournament(raw, entryCount) {
|
|
879
856
|
const obj = raw;
|
|
@@ -891,11 +868,16 @@ function parseTournament(raw, entryCount) {
|
|
|
891
868
|
const gameEndDelay = Number(sched?.game_end_delay ?? 0);
|
|
892
869
|
const submissionDuration = Number(sched?.submission_duration ?? 0);
|
|
893
870
|
const createdAtStr = String(createdAt);
|
|
894
|
-
const
|
|
895
|
-
const
|
|
896
|
-
const
|
|
897
|
-
const
|
|
898
|
-
const
|
|
871
|
+
const regStart = createdAt + registrationStartDelay;
|
|
872
|
+
const regEnd = regStart + registrationEndDelay;
|
|
873
|
+
const gameStart = createdAt + gameStartDelay;
|
|
874
|
+
const gameEnd = gameStart + gameEndDelay;
|
|
875
|
+
const subEnd = gameEnd + submissionDuration;
|
|
876
|
+
const registrationStartTime = String(regStart);
|
|
877
|
+
const registrationEndTime = String(regEnd);
|
|
878
|
+
const gameStartTime = String(gameStart);
|
|
879
|
+
const gameEndTime = String(gameEnd);
|
|
880
|
+
const submissionEndTime = String(subEnd);
|
|
899
881
|
const gc = obj.game_config;
|
|
900
882
|
const gameAddress = gc ? num.toHex(gc.game_address) : "";
|
|
901
883
|
const settingsId = Number(gc?.settings_id ?? 0);
|
|
@@ -924,7 +906,7 @@ function parseTournament(raw, entryCount) {
|
|
|
924
906
|
distributionCount: Number(ef.distribution_count ?? 0)
|
|
925
907
|
};
|
|
926
908
|
}
|
|
927
|
-
const entryRequirement = parseOption(obj.entry_requirement)
|
|
909
|
+
const entryRequirement = parseOption(obj.entry_requirement);
|
|
928
910
|
const hasEntryRequirement = entryRequirement !== null;
|
|
929
911
|
return {
|
|
930
912
|
id,
|
|
@@ -1014,35 +996,30 @@ function parsePrize(raw) {
|
|
|
1014
996
|
let distributionCount = null;
|
|
1015
997
|
let payoutPosition = 0;
|
|
1016
998
|
if (tokenTypeData) {
|
|
1017
|
-
|
|
1018
|
-
|
|
999
|
+
const activeVariant = typeof tokenTypeData.activeVariant === "function" ? tokenTypeData.activeVariant() : tokenTypeData.erc20 !== void 0 ? "erc20" : tokenTypeData.erc721 !== void 0 ? "erc721" : null;
|
|
1000
|
+
const variantData = tokenTypeData.variant;
|
|
1001
|
+
const unwrap = (name) => variantData?.[name] ?? tokenTypeData[name];
|
|
1002
|
+
if (activeVariant === "erc20") {
|
|
1003
|
+
const erc20 = unwrap("erc20");
|
|
1019
1004
|
tokenType = "erc20";
|
|
1020
|
-
amount = String(erc20
|
|
1021
|
-
const
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
tokenId = String(erc721.id ?? "0");
|
|
1031
|
-
} else if ("variant" in tokenTypeData) {
|
|
1032
|
-
const variant = tokenTypeData.variant?.toLowerCase();
|
|
1033
|
-
if (variant === "erc20") {
|
|
1034
|
-
tokenType = "erc20";
|
|
1035
|
-
amount = String(tokenTypeData.amount ?? "0");
|
|
1036
|
-
const dist = tokenTypeData.distribution;
|
|
1037
|
-
if (dist) {
|
|
1038
|
-
distributionType = String(dist.type ?? null);
|
|
1039
|
-
distributionWeight = dist.weight != null ? Number(dist.weight) : null;
|
|
1005
|
+
amount = String(erc20?.amount ?? "0");
|
|
1006
|
+
const distOption = erc20?.distribution;
|
|
1007
|
+
const distInner = distOption?.Some;
|
|
1008
|
+
if (distInner) {
|
|
1009
|
+
const distVariant = distInner.variant ?? distInner;
|
|
1010
|
+
const distType = Object.keys(distVariant).find((k) => distVariant[k] !== void 0);
|
|
1011
|
+
if (distType) {
|
|
1012
|
+
distributionType = distType.toLowerCase();
|
|
1013
|
+
const distValue = distVariant[distType];
|
|
1014
|
+
distributionWeight = distValue != null ? Number(distValue) : null;
|
|
1040
1015
|
}
|
|
1041
|
-
distributionCount = tokenTypeData.distribution_count != null ? Number(tokenTypeData.distribution_count) : null;
|
|
1042
|
-
} else if (variant === "erc721") {
|
|
1043
|
-
tokenType = "erc721";
|
|
1044
|
-
tokenId = String(tokenTypeData.id ?? "0");
|
|
1045
1016
|
}
|
|
1017
|
+
const countOption = erc20?.distribution_count;
|
|
1018
|
+
distributionCount = countOption?.Some != null ? Number(countOption.Some) : null;
|
|
1019
|
+
} else if (activeVariant === "erc721") {
|
|
1020
|
+
const erc721 = unwrap("erc721");
|
|
1021
|
+
tokenType = "erc721";
|
|
1022
|
+
tokenId = String(erc721?.id ?? "0");
|
|
1046
1023
|
}
|
|
1047
1024
|
}
|
|
1048
1025
|
return {
|
|
@@ -1106,9 +1083,24 @@ async function viewerTournamentsByCreator(contract, creator, offset, limit) {
|
|
|
1106
1083
|
return parseFilterResult(result);
|
|
1107
1084
|
}, contract.address);
|
|
1108
1085
|
}
|
|
1086
|
+
var PHASE_GROUPS = {
|
|
1087
|
+
scheduled: ["scheduled", "registration", "staging"],
|
|
1088
|
+
registration: ["registration"],
|
|
1089
|
+
staging: ["staging"],
|
|
1090
|
+
live: ["live", "submission"],
|
|
1091
|
+
submission: ["submission"],
|
|
1092
|
+
finalized: ["finalized"]
|
|
1093
|
+
};
|
|
1109
1094
|
async function viewerTournamentsByPhase(contract, phase, offset, limit) {
|
|
1095
|
+
const phases = PHASE_GROUPS[phase];
|
|
1096
|
+
if (phases.length === 1) {
|
|
1097
|
+
return wrapRpcCall(async () => {
|
|
1098
|
+
const result = await contract.call("tournaments_by_phase", [phaseToRpcArg(phase), offset, limit]);
|
|
1099
|
+
return parseFilterResult(result);
|
|
1100
|
+
}, contract.address);
|
|
1101
|
+
}
|
|
1110
1102
|
return wrapRpcCall(async () => {
|
|
1111
|
-
const result = await contract.call("
|
|
1103
|
+
const result = await contract.call("tournaments_by_phases", [phases.map(phaseToRpcArg), offset, limit]);
|
|
1112
1104
|
return parseFilterResult(result);
|
|
1113
1105
|
}, contract.address);
|
|
1114
1106
|
}
|
|
@@ -1150,6 +1142,31 @@ async function viewerPrizes(contract, tournamentId) {
|
|
|
1150
1142
|
return result.map(parsePrize);
|
|
1151
1143
|
}, contract.address);
|
|
1152
1144
|
}
|
|
1145
|
+
async function viewerRewardClaims(contract, tournamentId, offset, limit) {
|
|
1146
|
+
return wrapRpcCall(async () => {
|
|
1147
|
+
const result = await contract.call("tournament_reward_claims", [tournamentId, offset, limit]);
|
|
1148
|
+
const obj = result;
|
|
1149
|
+
const claims = obj.claims?.map((raw) => {
|
|
1150
|
+
const claim = raw;
|
|
1151
|
+
return {
|
|
1152
|
+
rewardType: claim.reward_type,
|
|
1153
|
+
claimed: Boolean(claim.claimed)
|
|
1154
|
+
};
|
|
1155
|
+
}) ?? [];
|
|
1156
|
+
return {
|
|
1157
|
+
claims,
|
|
1158
|
+
total: Number(obj.total ?? 0),
|
|
1159
|
+
totalClaimed: Number(obj.total_claimed ?? 0),
|
|
1160
|
+
totalUnclaimed: Number(obj.total_unclaimed ?? 0)
|
|
1161
|
+
};
|
|
1162
|
+
}, contract.address);
|
|
1163
|
+
}
|
|
1164
|
+
async function viewerPlayerTournaments(contract, playerAddress, offset, limit) {
|
|
1165
|
+
return wrapRpcCall(async () => {
|
|
1166
|
+
const result = await contract.call("player_tournaments", [playerAddress, offset, limit]);
|
|
1167
|
+
return parseFilterResult(result);
|
|
1168
|
+
}, contract.address);
|
|
1169
|
+
}
|
|
1153
1170
|
|
|
1154
1171
|
// src/rpc/abis/budokanViewer.json
|
|
1155
1172
|
var budokanViewer_default = [
|
|
@@ -1435,16 +1452,6 @@ var budokanViewer_default = [
|
|
|
1435
1452
|
}
|
|
1436
1453
|
]
|
|
1437
1454
|
},
|
|
1438
|
-
{
|
|
1439
|
-
type: "struct",
|
|
1440
|
-
name: "core::array::Span::<core::starknet::contract_address::ContractAddress>",
|
|
1441
|
-
members: [
|
|
1442
|
-
{
|
|
1443
|
-
name: "snapshot",
|
|
1444
|
-
type: "@core::array::Array::<core::starknet::contract_address::ContractAddress>"
|
|
1445
|
-
}
|
|
1446
|
-
]
|
|
1447
|
-
},
|
|
1448
1455
|
{
|
|
1449
1456
|
type: "struct",
|
|
1450
1457
|
name: "core::array::Span::<core::felt252>",
|
|
@@ -1457,7 +1464,7 @@ var budokanViewer_default = [
|
|
|
1457
1464
|
},
|
|
1458
1465
|
{
|
|
1459
1466
|
type: "struct",
|
|
1460
|
-
name: "
|
|
1467
|
+
name: "metagame_extensions_interfaces::extension::ExtensionConfig",
|
|
1461
1468
|
members: [
|
|
1462
1469
|
{
|
|
1463
1470
|
name: "address",
|
|
@@ -1477,13 +1484,9 @@ var budokanViewer_default = [
|
|
|
1477
1484
|
name: "token",
|
|
1478
1485
|
type: "core::starknet::contract_address::ContractAddress"
|
|
1479
1486
|
},
|
|
1480
|
-
{
|
|
1481
|
-
name: "allowlist",
|
|
1482
|
-
type: "core::array::Span::<core::starknet::contract_address::ContractAddress>"
|
|
1483
|
-
},
|
|
1484
1487
|
{
|
|
1485
1488
|
name: "extension",
|
|
1486
|
-
type: "
|
|
1489
|
+
type: "metagame_extensions_interfaces::extension::ExtensionConfig"
|
|
1487
1490
|
}
|
|
1488
1491
|
]
|
|
1489
1492
|
},
|
|
@@ -1743,6 +1746,92 @@ var budokanViewer_default = [
|
|
|
1743
1746
|
}
|
|
1744
1747
|
]
|
|
1745
1748
|
},
|
|
1749
|
+
{
|
|
1750
|
+
type: "enum",
|
|
1751
|
+
name: "game_components_interfaces::prize::PrizeType",
|
|
1752
|
+
variants: [
|
|
1753
|
+
{
|
|
1754
|
+
name: "Single",
|
|
1755
|
+
type: "core::integer::u64"
|
|
1756
|
+
},
|
|
1757
|
+
{
|
|
1758
|
+
name: "Distributed",
|
|
1759
|
+
type: "(core::integer::u64, core::integer::u32)"
|
|
1760
|
+
}
|
|
1761
|
+
]
|
|
1762
|
+
},
|
|
1763
|
+
{
|
|
1764
|
+
type: "enum",
|
|
1765
|
+
name: "budokan_interfaces::budokan::EntryFeeRewardType",
|
|
1766
|
+
variants: [
|
|
1767
|
+
{
|
|
1768
|
+
name: "Position",
|
|
1769
|
+
type: "core::integer::u32"
|
|
1770
|
+
},
|
|
1771
|
+
{
|
|
1772
|
+
name: "TournamentCreator",
|
|
1773
|
+
type: "()"
|
|
1774
|
+
},
|
|
1775
|
+
{
|
|
1776
|
+
name: "GameCreator",
|
|
1777
|
+
type: "()"
|
|
1778
|
+
},
|
|
1779
|
+
{
|
|
1780
|
+
name: "Refund",
|
|
1781
|
+
type: "core::felt252"
|
|
1782
|
+
}
|
|
1783
|
+
]
|
|
1784
|
+
},
|
|
1785
|
+
{
|
|
1786
|
+
type: "enum",
|
|
1787
|
+
name: "budokan_interfaces::budokan::RewardType",
|
|
1788
|
+
variants: [
|
|
1789
|
+
{
|
|
1790
|
+
name: "Prize",
|
|
1791
|
+
type: "game_components_interfaces::prize::PrizeType"
|
|
1792
|
+
},
|
|
1793
|
+
{
|
|
1794
|
+
name: "EntryFee",
|
|
1795
|
+
type: "budokan_interfaces::budokan::EntryFeeRewardType"
|
|
1796
|
+
}
|
|
1797
|
+
]
|
|
1798
|
+
},
|
|
1799
|
+
{
|
|
1800
|
+
type: "struct",
|
|
1801
|
+
name: "budokan_interfaces::viewer::RewardClaimView",
|
|
1802
|
+
members: [
|
|
1803
|
+
{
|
|
1804
|
+
name: "reward_type",
|
|
1805
|
+
type: "budokan_interfaces::budokan::RewardType"
|
|
1806
|
+
},
|
|
1807
|
+
{
|
|
1808
|
+
name: "claimed",
|
|
1809
|
+
type: "core::bool"
|
|
1810
|
+
}
|
|
1811
|
+
]
|
|
1812
|
+
},
|
|
1813
|
+
{
|
|
1814
|
+
type: "struct",
|
|
1815
|
+
name: "budokan_interfaces::viewer::RewardClaimResult",
|
|
1816
|
+
members: [
|
|
1817
|
+
{
|
|
1818
|
+
name: "claims",
|
|
1819
|
+
type: "core::array::Array::<budokan_interfaces::viewer::RewardClaimView>"
|
|
1820
|
+
},
|
|
1821
|
+
{
|
|
1822
|
+
name: "total",
|
|
1823
|
+
type: "core::integer::u32"
|
|
1824
|
+
},
|
|
1825
|
+
{
|
|
1826
|
+
name: "total_claimed",
|
|
1827
|
+
type: "core::integer::u32"
|
|
1828
|
+
},
|
|
1829
|
+
{
|
|
1830
|
+
name: "total_unclaimed",
|
|
1831
|
+
type: "core::integer::u32"
|
|
1832
|
+
}
|
|
1833
|
+
]
|
|
1834
|
+
},
|
|
1746
1835
|
{
|
|
1747
1836
|
type: "interface",
|
|
1748
1837
|
name: "budokan_interfaces::viewer::IBudokanViewer",
|
|
@@ -1839,6 +1928,30 @@ var budokanViewer_default = [
|
|
|
1839
1928
|
],
|
|
1840
1929
|
state_mutability: "view"
|
|
1841
1930
|
},
|
|
1931
|
+
{
|
|
1932
|
+
type: "function",
|
|
1933
|
+
name: "tournaments_by_phases",
|
|
1934
|
+
inputs: [
|
|
1935
|
+
{
|
|
1936
|
+
name: "phases",
|
|
1937
|
+
type: "core::array::Array::<budokan_interfaces::budokan::Phase>"
|
|
1938
|
+
},
|
|
1939
|
+
{
|
|
1940
|
+
name: "offset",
|
|
1941
|
+
type: "core::integer::u64"
|
|
1942
|
+
},
|
|
1943
|
+
{
|
|
1944
|
+
name: "limit",
|
|
1945
|
+
type: "core::integer::u64"
|
|
1946
|
+
}
|
|
1947
|
+
],
|
|
1948
|
+
outputs: [
|
|
1949
|
+
{
|
|
1950
|
+
type: "budokan_interfaces::viewer::TournamentFilterResult"
|
|
1951
|
+
}
|
|
1952
|
+
],
|
|
1953
|
+
state_mutability: "view"
|
|
1954
|
+
},
|
|
1842
1955
|
{
|
|
1843
1956
|
type: "function",
|
|
1844
1957
|
name: "count_tournaments",
|
|
@@ -1898,6 +2011,22 @@ var budokanViewer_default = [
|
|
|
1898
2011
|
],
|
|
1899
2012
|
state_mutability: "view"
|
|
1900
2013
|
},
|
|
2014
|
+
{
|
|
2015
|
+
type: "function",
|
|
2016
|
+
name: "count_tournaments_by_phases",
|
|
2017
|
+
inputs: [
|
|
2018
|
+
{
|
|
2019
|
+
name: "phases",
|
|
2020
|
+
type: "core::array::Array::<budokan_interfaces::budokan::Phase>"
|
|
2021
|
+
}
|
|
2022
|
+
],
|
|
2023
|
+
outputs: [
|
|
2024
|
+
{
|
|
2025
|
+
type: "core::integer::u64"
|
|
2026
|
+
}
|
|
2027
|
+
],
|
|
2028
|
+
state_mutability: "view"
|
|
2029
|
+
},
|
|
1901
2030
|
{
|
|
1902
2031
|
type: "function",
|
|
1903
2032
|
name: "tournament_detail",
|
|
@@ -1993,6 +2122,54 @@ var budokanViewer_default = [
|
|
|
1993
2122
|
}
|
|
1994
2123
|
],
|
|
1995
2124
|
state_mutability: "view"
|
|
2125
|
+
},
|
|
2126
|
+
{
|
|
2127
|
+
type: "function",
|
|
2128
|
+
name: "tournament_reward_claims",
|
|
2129
|
+
inputs: [
|
|
2130
|
+
{
|
|
2131
|
+
name: "tournament_id",
|
|
2132
|
+
type: "core::integer::u64"
|
|
2133
|
+
},
|
|
2134
|
+
{
|
|
2135
|
+
name: "offset",
|
|
2136
|
+
type: "core::integer::u32"
|
|
2137
|
+
},
|
|
2138
|
+
{
|
|
2139
|
+
name: "limit",
|
|
2140
|
+
type: "core::integer::u32"
|
|
2141
|
+
}
|
|
2142
|
+
],
|
|
2143
|
+
outputs: [
|
|
2144
|
+
{
|
|
2145
|
+
type: "budokan_interfaces::viewer::RewardClaimResult"
|
|
2146
|
+
}
|
|
2147
|
+
],
|
|
2148
|
+
state_mutability: "view"
|
|
2149
|
+
},
|
|
2150
|
+
{
|
|
2151
|
+
type: "function",
|
|
2152
|
+
name: "player_tournaments",
|
|
2153
|
+
inputs: [
|
|
2154
|
+
{
|
|
2155
|
+
name: "player_address",
|
|
2156
|
+
type: "core::starknet::contract_address::ContractAddress"
|
|
2157
|
+
},
|
|
2158
|
+
{
|
|
2159
|
+
name: "offset",
|
|
2160
|
+
type: "core::integer::u64"
|
|
2161
|
+
},
|
|
2162
|
+
{
|
|
2163
|
+
name: "limit",
|
|
2164
|
+
type: "core::integer::u64"
|
|
2165
|
+
}
|
|
2166
|
+
],
|
|
2167
|
+
outputs: [
|
|
2168
|
+
{
|
|
2169
|
+
type: "budokan_interfaces::viewer::TournamentFilterResult"
|
|
2170
|
+
}
|
|
2171
|
+
],
|
|
2172
|
+
state_mutability: "view"
|
|
1996
2173
|
}
|
|
1997
2174
|
]
|
|
1998
2175
|
},
|
|
@@ -2277,6 +2454,41 @@ var BudokanClient = class {
|
|
|
2277
2454
|
let data = [];
|
|
2278
2455
|
if (filterResult.tournamentIds.length > 0) {
|
|
2279
2456
|
data = await viewerTournamentsBatch(contract, filterResult.tournamentIds);
|
|
2457
|
+
if (params?.includePrizeSummary) {
|
|
2458
|
+
const prizePromises = data.map(
|
|
2459
|
+
(t) => viewerPrizes(contract, t.id).catch(() => [])
|
|
2460
|
+
);
|
|
2461
|
+
const allPrizes = await Promise.all(prizePromises);
|
|
2462
|
+
data = data.map((t, i) => {
|
|
2463
|
+
const prizes = allPrizes[i];
|
|
2464
|
+
if (prizes.length === 0) return t;
|
|
2465
|
+
const tokenMap = /* @__PURE__ */ new Map();
|
|
2466
|
+
for (const p of prizes) {
|
|
2467
|
+
const key = p.tokenAddress;
|
|
2468
|
+
const existing = tokenMap.get(key);
|
|
2469
|
+
if (existing) {
|
|
2470
|
+
existing.totalAmount += BigInt(p.amount ?? "0");
|
|
2471
|
+
if (p.tokenType === "erc721") existing.nftCount += 1;
|
|
2472
|
+
} else {
|
|
2473
|
+
tokenMap.set(key, {
|
|
2474
|
+
tokenAddress: p.tokenAddress,
|
|
2475
|
+
tokenType: p.tokenType,
|
|
2476
|
+
totalAmount: BigInt(p.amount ?? "0"),
|
|
2477
|
+
nftCount: p.tokenType === "erc721" ? 1 : 0
|
|
2478
|
+
});
|
|
2479
|
+
}
|
|
2480
|
+
}
|
|
2481
|
+
return {
|
|
2482
|
+
...t,
|
|
2483
|
+
prizeAggregation: Array.from(tokenMap.values()).map((v) => ({
|
|
2484
|
+
tokenAddress: v.tokenAddress,
|
|
2485
|
+
tokenType: v.tokenType,
|
|
2486
|
+
totalAmount: v.totalAmount.toString(),
|
|
2487
|
+
nftCount: v.nftCount
|
|
2488
|
+
}))
|
|
2489
|
+
};
|
|
2490
|
+
});
|
|
2491
|
+
}
|
|
2280
2492
|
}
|
|
2281
2493
|
return { data, total: filterResult.total, limit, offset };
|
|
2282
2494
|
};
|
|
@@ -2367,10 +2579,32 @@ var BudokanClient = class {
|
|
|
2367
2579
|
// ---- Player Queries (API-only, no on-chain equivalent) ----
|
|
2368
2580
|
/**
|
|
2369
2581
|
* Fetch tournaments that a player has registered for.
|
|
2370
|
-
*
|
|
2582
|
+
* Supports RPC fallback via viewer contract.
|
|
2371
2583
|
*/
|
|
2372
2584
|
async getPlayerTournaments(address, params) {
|
|
2373
|
-
|
|
2585
|
+
const rpcFallback = async () => {
|
|
2586
|
+
const contract = await this.getViewerContract();
|
|
2587
|
+
const offset = params?.offset ?? 0;
|
|
2588
|
+
const limit = params?.limit ?? 20;
|
|
2589
|
+
const filterResult = await viewerPlayerTournaments(contract, address, offset, limit);
|
|
2590
|
+
let data = [];
|
|
2591
|
+
if (filterResult.tournamentIds.length > 0) {
|
|
2592
|
+
const tournaments = await viewerTournamentsBatch(contract, filterResult.tournamentIds);
|
|
2593
|
+
data = tournaments.map((t) => ({
|
|
2594
|
+
...t,
|
|
2595
|
+
tournamentId: t.id
|
|
2596
|
+
}));
|
|
2597
|
+
}
|
|
2598
|
+
return { data, total: filterResult.total, limit, offset };
|
|
2599
|
+
};
|
|
2600
|
+
if (this.resolvedConfig.primarySource === "rpc") {
|
|
2601
|
+
return rpcFallback();
|
|
2602
|
+
}
|
|
2603
|
+
return withFallback(
|
|
2604
|
+
() => getPlayerTournaments(this.resolvedConfig.apiBaseUrl, address, params, this.apiCtx),
|
|
2605
|
+
rpcFallback,
|
|
2606
|
+
this.connectionStatus
|
|
2607
|
+
);
|
|
2374
2608
|
}
|
|
2375
2609
|
/**
|
|
2376
2610
|
* Fetch stats for a player.
|
|
@@ -2412,20 +2646,55 @@ var BudokanClient = class {
|
|
|
2412
2646
|
async getGameStats(gameAddress) {
|
|
2413
2647
|
return getGameStats(this.resolvedConfig.apiBaseUrl, gameAddress, this.apiCtx);
|
|
2414
2648
|
}
|
|
2415
|
-
// ---- Reward Claims & Qualifications
|
|
2649
|
+
// ---- Reward Claims & Qualifications ----
|
|
2416
2650
|
/**
|
|
2417
2651
|
* Fetch reward claims for a tournament.
|
|
2418
|
-
*
|
|
2652
|
+
* Supports RPC fallback via viewer contract.
|
|
2419
2653
|
*/
|
|
2420
2654
|
async getTournamentRewardClaims(tournamentId, params) {
|
|
2421
|
-
|
|
2655
|
+
const rpcFallback = async () => {
|
|
2656
|
+
const contract = await this.getViewerContract();
|
|
2657
|
+
const offset = params?.offset ?? 0;
|
|
2658
|
+
const limit = params?.limit ?? 100;
|
|
2659
|
+
const result = await viewerRewardClaims(contract, tournamentId, offset, limit);
|
|
2660
|
+
const data = result.claims.map((c) => ({
|
|
2661
|
+
tournamentId,
|
|
2662
|
+
rewardType: c.rewardType,
|
|
2663
|
+
claimed: c.claimed
|
|
2664
|
+
}));
|
|
2665
|
+
return { data, total: result.total, limit, offset };
|
|
2666
|
+
};
|
|
2667
|
+
if (this.resolvedConfig.primarySource === "rpc") {
|
|
2668
|
+
return rpcFallback();
|
|
2669
|
+
}
|
|
2670
|
+
return withFallback(
|
|
2671
|
+
() => getTournamentRewardClaims(this.resolvedConfig.apiBaseUrl, tournamentId, params, this.apiCtx),
|
|
2672
|
+
rpcFallback,
|
|
2673
|
+
this.connectionStatus
|
|
2674
|
+
);
|
|
2422
2675
|
}
|
|
2423
2676
|
/**
|
|
2424
2677
|
* Fetch reward claims summary for a tournament.
|
|
2425
|
-
*
|
|
2678
|
+
* Supports RPC fallback via viewer contract.
|
|
2426
2679
|
*/
|
|
2427
2680
|
async getTournamentRewardClaimsSummary(tournamentId) {
|
|
2428
|
-
|
|
2681
|
+
const rpcFallback = async () => {
|
|
2682
|
+
const contract = await this.getViewerContract();
|
|
2683
|
+
const result = await viewerRewardClaims(contract, tournamentId, 0, 0);
|
|
2684
|
+
return {
|
|
2685
|
+
totalPrizes: result.total,
|
|
2686
|
+
totalClaimed: result.totalClaimed,
|
|
2687
|
+
totalUnclaimed: result.totalUnclaimed
|
|
2688
|
+
};
|
|
2689
|
+
};
|
|
2690
|
+
if (this.resolvedConfig.primarySource === "rpc") {
|
|
2691
|
+
return rpcFallback();
|
|
2692
|
+
}
|
|
2693
|
+
return withFallback(
|
|
2694
|
+
() => getTournamentRewardClaimsSummary(this.resolvedConfig.apiBaseUrl, tournamentId, this.apiCtx),
|
|
2695
|
+
rpcFallback,
|
|
2696
|
+
this.connectionStatus
|
|
2697
|
+
);
|
|
2429
2698
|
}
|
|
2430
2699
|
/**
|
|
2431
2700
|
* Fetch qualifications for a tournament.
|
|
@@ -2528,12 +2797,22 @@ function useBudokanClient() {
|
|
|
2528
2797
|
}
|
|
2529
2798
|
return client;
|
|
2530
2799
|
}
|
|
2800
|
+
function useResetOnClient(client, ...resetters) {
|
|
2801
|
+
useEffect(() => {
|
|
2802
|
+
for (const reset of resetters) {
|
|
2803
|
+
reset(null);
|
|
2804
|
+
}
|
|
2805
|
+
}, [client]);
|
|
2806
|
+
}
|
|
2807
|
+
|
|
2808
|
+
// src/react/useTournaments.ts
|
|
2531
2809
|
function useTournaments(params) {
|
|
2532
2810
|
const client = useBudokanClient();
|
|
2533
2811
|
const [tournaments, setTournaments] = useState(null);
|
|
2534
2812
|
const [loading, setLoading] = useState(!!params);
|
|
2535
2813
|
const [error, setError] = useState(null);
|
|
2536
2814
|
const paramsKey = JSON.stringify(params);
|
|
2815
|
+
useResetOnClient(client, setTournaments, setError);
|
|
2537
2816
|
const fetch2 = useCallback(() => {
|
|
2538
2817
|
if (params === void 0) return;
|
|
2539
2818
|
setLoading(true);
|
|
@@ -2550,6 +2829,7 @@ function useTournament(tournamentId) {
|
|
|
2550
2829
|
const [tournament, setTournament] = useState(null);
|
|
2551
2830
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2552
2831
|
const [error, setError] = useState(null);
|
|
2832
|
+
useResetOnClient(client, setTournament, setError);
|
|
2553
2833
|
const fetch2 = useCallback(() => {
|
|
2554
2834
|
if (!tournamentId) return;
|
|
2555
2835
|
setLoading(true);
|
|
@@ -2566,6 +2846,7 @@ function useTournamentCount(phase) {
|
|
|
2566
2846
|
const [count, setCount] = useState(null);
|
|
2567
2847
|
const [loading, setLoading] = useState(true);
|
|
2568
2848
|
const [error, setError] = useState(null);
|
|
2849
|
+
useResetOnClient(client, setCount, setError);
|
|
2569
2850
|
const fetch2 = useCallback(() => {
|
|
2570
2851
|
setLoading(true);
|
|
2571
2852
|
setError(null);
|
|
@@ -2581,6 +2862,7 @@ function usePlayerTournamentCount(address, phase) {
|
|
|
2581
2862
|
const [count, setCount] = useState(null);
|
|
2582
2863
|
const [loading, setLoading] = useState(!!address);
|
|
2583
2864
|
const [error, setError] = useState(null);
|
|
2865
|
+
useResetOnClient(client, setCount, setError);
|
|
2584
2866
|
const fetch2 = useCallback(() => {
|
|
2585
2867
|
if (!address) return;
|
|
2586
2868
|
setLoading(true);
|
|
@@ -2597,6 +2879,7 @@ function useLeaderboard(tournamentId) {
|
|
|
2597
2879
|
const [leaderboard, setLeaderboard] = useState(null);
|
|
2598
2880
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2599
2881
|
const [error, setError] = useState(null);
|
|
2882
|
+
useResetOnClient(client, setLeaderboard, setError);
|
|
2600
2883
|
const fetch2 = useCallback(() => {
|
|
2601
2884
|
if (!tournamentId) return;
|
|
2602
2885
|
setLoading(true);
|
|
@@ -2613,6 +2896,7 @@ function useRegistrations(tournamentId, params) {
|
|
|
2613
2896
|
const [registrations, setRegistrations] = useState(null);
|
|
2614
2897
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2615
2898
|
const [error, setError] = useState(null);
|
|
2899
|
+
useResetOnClient(client, setRegistrations, setError);
|
|
2616
2900
|
const paramsKey = JSON.stringify(params);
|
|
2617
2901
|
const fetch2 = useCallback(() => {
|
|
2618
2902
|
if (!tournamentId) return;
|
|
@@ -2631,6 +2915,7 @@ function usePlayer(address) {
|
|
|
2631
2915
|
const [stats, setStats] = useState(null);
|
|
2632
2916
|
const [loading, setLoading] = useState(!!address);
|
|
2633
2917
|
const [error, setError] = useState(null);
|
|
2918
|
+
useResetOnClient(client, setTournaments, setStats, setError);
|
|
2634
2919
|
const fetch2 = useCallback(() => {
|
|
2635
2920
|
if (!address) return;
|
|
2636
2921
|
setLoading(true);
|
|
@@ -2653,6 +2938,7 @@ function usePlayerStats(address) {
|
|
|
2653
2938
|
const [stats, setStats] = useState(null);
|
|
2654
2939
|
const [loading, setLoading] = useState(!!address);
|
|
2655
2940
|
const [error, setError] = useState(null);
|
|
2941
|
+
useResetOnClient(client, setStats, setError);
|
|
2656
2942
|
const fetch2 = useCallback(() => {
|
|
2657
2943
|
if (!address) return;
|
|
2658
2944
|
setLoading(true);
|
|
@@ -2669,6 +2955,7 @@ function usePlayerTournaments(address, params) {
|
|
|
2669
2955
|
const [tournaments, setTournaments] = useState(null);
|
|
2670
2956
|
const [loading, setLoading] = useState(!!address);
|
|
2671
2957
|
const [error, setError] = useState(null);
|
|
2958
|
+
useResetOnClient(client, setTournaments, setError);
|
|
2672
2959
|
const paramsKey = JSON.stringify(params);
|
|
2673
2960
|
const fetch2 = useCallback(() => {
|
|
2674
2961
|
if (!address) return;
|
|
@@ -2686,6 +2973,7 @@ function useRewardClaims(tournamentId) {
|
|
|
2686
2973
|
const [rewardClaims, setRewardClaims] = useState(null);
|
|
2687
2974
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2688
2975
|
const [error, setError] = useState(null);
|
|
2976
|
+
useResetOnClient(client, setRewardClaims, setError);
|
|
2689
2977
|
const fetch2 = useCallback(() => {
|
|
2690
2978
|
if (!tournamentId) return;
|
|
2691
2979
|
setLoading(true);
|
|
@@ -2702,6 +2990,7 @@ function useRewardClaimsSummary(tournamentId) {
|
|
|
2702
2990
|
const [summary, setSummary] = useState(null);
|
|
2703
2991
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2704
2992
|
const [error, setError] = useState(null);
|
|
2993
|
+
useResetOnClient(client, setSummary, setError);
|
|
2705
2994
|
const fetch2 = useCallback(() => {
|
|
2706
2995
|
if (!tournamentId) return;
|
|
2707
2996
|
setLoading(true);
|
|
@@ -2718,6 +3007,7 @@ function usePrizes(tournamentId) {
|
|
|
2718
3007
|
const [prizes, setPrizes] = useState(null);
|
|
2719
3008
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2720
3009
|
const [error, setError] = useState(null);
|
|
3010
|
+
useResetOnClient(client, setPrizes, setError);
|
|
2721
3011
|
const fetch2 = useCallback(() => {
|
|
2722
3012
|
if (!tournamentId) return;
|
|
2723
3013
|
setLoading(true);
|
|
@@ -2734,6 +3024,7 @@ function usePrizeStats() {
|
|
|
2734
3024
|
const [prizeStats, setPrizeStats] = useState(null);
|
|
2735
3025
|
const [loading, setLoading] = useState(true);
|
|
2736
3026
|
const [error, setError] = useState(null);
|
|
3027
|
+
useResetOnClient(client, setPrizeStats, setError);
|
|
2737
3028
|
const fetch2 = useCallback(() => {
|
|
2738
3029
|
setLoading(true);
|
|
2739
3030
|
setError(null);
|
|
@@ -2749,6 +3040,7 @@ function usePrizeAggregation(tournamentId) {
|
|
|
2749
3040
|
const [prizeAggregation, setPrizeAggregation] = useState(null);
|
|
2750
3041
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2751
3042
|
const [error, setError] = useState(null);
|
|
3043
|
+
useResetOnClient(client, setPrizeAggregation, setError);
|
|
2752
3044
|
const fetch2 = useCallback(() => {
|
|
2753
3045
|
if (!tournamentId) return;
|
|
2754
3046
|
setLoading(true);
|
|
@@ -2765,6 +3057,7 @@ function useQualifications(tournamentId) {
|
|
|
2765
3057
|
const [qualifications, setQualifications] = useState(null);
|
|
2766
3058
|
const [loading, setLoading] = useState(!!tournamentId);
|
|
2767
3059
|
const [error, setError] = useState(null);
|
|
3060
|
+
useResetOnClient(client, setQualifications, setError);
|
|
2768
3061
|
const fetch2 = useCallback(() => {
|
|
2769
3062
|
if (!tournamentId) return;
|
|
2770
3063
|
setLoading(true);
|
|
@@ -2781,6 +3074,7 @@ function useActivityStats() {
|
|
|
2781
3074
|
const [stats, setStats] = useState(null);
|
|
2782
3075
|
const [loading, setLoading] = useState(true);
|
|
2783
3076
|
const [error, setError] = useState(null);
|
|
3077
|
+
useResetOnClient(client, setStats, setError);
|
|
2784
3078
|
const fetch2 = useCallback(() => {
|
|
2785
3079
|
setLoading(true);
|
|
2786
3080
|
setError(null);
|