@playmos/sdk 0.3.15 → 0.3.16

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/CHANGELOG.md CHANGED
@@ -4,6 +4,11 @@ All notable changes to `@playmos/sdk`. This project adheres to [Semantic Version
4
4
 
5
5
  ## Unreleased
6
6
 
7
+ ## [0.3.16] — 2026-09-11
8
+
9
+ ### Added/Fixed
10
+ - EOA / Chrome Coinbase extension: `sendCalls` falls back to sequential `eth_sendTransaction` when `wallet_sendCalls` is missing or fails (not a user cancel). Skip USDC approve when allowance already covers. (#746 / #745)
11
+
7
12
  ## [0.3.15] — 2026-09-11
8
13
 
9
14
  ### Added
package/README.md CHANGED
@@ -97,7 +97,7 @@ const entry = await playmos.enterRound({
97
97
 
98
98
  ### Your own contest pool — `epochs.preparePool` (you sign)
99
99
 
100
- `@playmos/sdk` **0.3.15** ships `epochs.preparePool` and `epochs.prepareSeries` with `unsignedTx` on the typed response. It calls the live API. Playmos sets `broadcast: false` and does **not** send the transaction.
100
+ `@playmos/sdk` **0.3.16** ships `epochs.preparePool` and `epochs.prepareSeries` with `unsignedTx` on the typed response. It calls the live API. Playmos sets `broadcast: false` and does **not** send the transaction.
101
101
 
102
102
  1. Fund your studio wallet on Base Sepolia (ETH + test USDC). Playmos has no faucet — use [Coinbase's faucet docs](https://docs.cdp.coinbase.com/faucets/introduction/welcome).
103
103
  2. Call `epochs.preparePool({ studioWallet })` or `POST /v1/epochs/pools/prepare`. Use `feeSink` from that response (`0xD84c190085aa59c48a9B478Ea333D50B8DF4aD42`).
@@ -1,4 +1,4 @@
1
- import { keccak256, toHex, numberToHex, encodeFunctionData, toBytes, getAddress } from 'viem';
1
+ import { keccak256, toHex, numberToHex, encodeFunctionData, toBytes, getAddress, decodeFunctionData } from 'viem';
2
2
 
3
3
  // src/errors.ts
4
4
  var PlaymosError = class extends Error {
@@ -140,6 +140,35 @@ var prizePoolAbi = [
140
140
  outputs: [{ name: "amount", type: "uint256" }]
141
141
  }
142
142
  ];
143
+ var erc20AllowanceAbi = [
144
+ {
145
+ type: "function",
146
+ name: "allowance",
147
+ stateMutability: "view",
148
+ inputs: [
149
+ { name: "owner", type: "address" },
150
+ { name: "spender", type: "address" }
151
+ ],
152
+ outputs: [{ type: "uint256" }]
153
+ }
154
+ ];
155
+ var SEQUENTIAL_TX_ID_PREFIX = "eth:";
156
+ var USER_CANCEL_RE = /reject|denied|cancel|closed/i;
157
+ function sequentialTxId(txHash) {
158
+ return `${SEQUENTIAL_TX_ID_PREFIX}${txHash}`;
159
+ }
160
+ function sequentialTxHashFromId(id) {
161
+ if (!id.startsWith(SEQUENTIAL_TX_ID_PREFIX)) return void 0;
162
+ const hash = id.slice(SEQUENTIAL_TX_ID_PREFIX.length);
163
+ if (/^0x[0-9a-fA-F]{64}$/.test(hash)) return hash;
164
+ return void 0;
165
+ }
166
+ function errorMessage(e) {
167
+ return e?.message ?? String(e);
168
+ }
169
+ function isUserCancel(msg) {
170
+ return USER_CANCEL_RE.test(msg);
171
+ }
143
172
  async function sendCalls(provider, from, chainId, calls, paymasterUrl) {
144
173
  const params = {
145
174
  version: "2.0.0",
@@ -151,23 +180,85 @@ async function sendCalls(provider, from, chainId, calls, paymasterUrl) {
151
180
  if (paymasterUrl) {
152
181
  params.capabilities = { paymasterService: { url: paymasterUrl } };
153
182
  }
154
- let result;
155
183
  try {
156
- result = await provider.request({ method: "wallet_sendCalls", params: [params] });
184
+ const result = await provider.request({ method: "wallet_sendCalls", params: [params] });
185
+ const id = typeof result === "string" ? result : result?.id ?? "";
186
+ if (!id) throw new PaymentFailedError("Wallet returned no calls id.");
187
+ return { id };
157
188
  } catch (e) {
189
+ if (e instanceof PaymentFailedError) throw e;
158
190
  if (e instanceof WalletTimeoutError) throw e;
159
- const msg = e?.message ?? String(e);
160
- if (/reject|denied|cancel|closed/i.test(msg)) {
191
+ const msg = errorMessage(e);
192
+ if (isUserCancel(msg)) {
161
193
  throw new WalletConnectionError("The player cancelled or closed the payment sheet.", { cause: msg });
162
194
  }
163
- throw new PaymentFailedError("wallet_sendCalls failed.", { cause: msg });
195
+ return sendCallsSequentially(provider, from, calls);
164
196
  }
165
- const id = typeof result === "string" ? result : result?.id ?? "";
166
- if (!id) throw new PaymentFailedError("Wallet returned no calls id.");
167
- return { id };
197
+ }
198
+ async function skipCoveredApprove(provider, from, calls) {
199
+ const first = calls[0];
200
+ if (!first) return calls;
201
+ let spender;
202
+ let amount;
203
+ try {
204
+ const decoded = decodeFunctionData({ abi: erc20Abi, data: first.data });
205
+ if (decoded.functionName !== "approve") return calls;
206
+ spender = decoded.args[0];
207
+ amount = decoded.args[1];
208
+ } catch {
209
+ return calls;
210
+ }
211
+ try {
212
+ const data = encodeFunctionData({
213
+ abi: erc20AllowanceAbi,
214
+ functionName: "allowance",
215
+ args: [from, spender]
216
+ });
217
+ const raw = await provider.request({
218
+ method: "eth_call",
219
+ params: [{ to: first.to, data }, "latest"]
220
+ });
221
+ const allowance = BigInt(typeof raw === "string" && raw !== "0x" ? raw : "0");
222
+ if (allowance >= amount) return calls.slice(1);
223
+ } catch {
224
+ }
225
+ return calls;
226
+ }
227
+ async function sendCallsSequentially(provider, from, calls) {
228
+ const toSend = await skipCoveredApprove(provider, from, calls);
229
+ if (toSend.length === 0) {
230
+ throw new PaymentFailedError("No wallet calls to send.");
231
+ }
232
+ let lastHash;
233
+ for (const call of toSend) {
234
+ let hash;
235
+ try {
236
+ hash = await provider.request({
237
+ method: "eth_sendTransaction",
238
+ params: [{ from, to: call.to, data: call.data }]
239
+ });
240
+ } catch (e) {
241
+ if (e instanceof WalletTimeoutError) throw e;
242
+ const msg = errorMessage(e);
243
+ if (isUserCancel(msg)) {
244
+ throw new WalletConnectionError("The player cancelled or closed the payment sheet.", { cause: msg });
245
+ }
246
+ throw new PaymentFailedError("eth_sendTransaction failed.", { cause: msg });
247
+ }
248
+ if (typeof hash !== "string" || !/^0x[0-9a-fA-F]{64}$/.test(hash)) {
249
+ throw new PaymentFailedError("Wallet returned no transaction hash.");
250
+ }
251
+ lastHash = hash;
252
+ }
253
+ if (!lastHash) throw new PaymentFailedError("Wallet returned no transaction hash.");
254
+ return { id: sequentialTxId(lastHash) };
168
255
  }
169
256
  async function waitForCalls(provider, id, timeoutMs = 6e4) {
170
257
  if (!id) return { status: "FAILED" };
258
+ const sequentialHash = sequentialTxHashFromId(id);
259
+ if (sequentialHash) {
260
+ return waitForTransactionReceipt(provider, sequentialHash, timeoutMs);
261
+ }
171
262
  const deadline = Date.now() + timeoutMs;
172
263
  while (Date.now() < deadline) {
173
264
  try {
@@ -190,6 +281,30 @@ async function waitForCalls(provider, id, timeoutMs = 6e4) {
190
281
  }
191
282
  return { status: "PENDING" };
192
283
  }
284
+ async function waitForTransactionReceipt(provider, txHash, timeoutMs) {
285
+ const deadline = Date.now() + timeoutMs;
286
+ while (Date.now() < deadline) {
287
+ try {
288
+ const res = await provider.request({
289
+ method: "eth_getTransactionReceipt",
290
+ params: [txHash]
291
+ });
292
+ if (res && res.status !== void 0 && res.status !== null) {
293
+ const code = typeof res.status === "number" ? res.status : Number(res.status);
294
+ if (code === 1) return { status: "CONFIRMED", txHash };
295
+ if (code === 0) return { status: "FAILED", txHash };
296
+ }
297
+ } catch (e) {
298
+ if (e instanceof WalletTimeoutError) {
299
+ await new Promise((r) => setTimeout(r, 900));
300
+ continue;
301
+ }
302
+ throw e;
303
+ }
304
+ await new Promise((r) => setTimeout(r, 900));
305
+ }
306
+ return { status: "PENDING", txHash };
307
+ }
193
308
  function encodeApprove(spender, amountUnits) {
194
309
  return encodeFunctionData({ abi: erc20Abi, functionName: "approve", args: [spender, amountUnits] });
195
310
  }
@@ -735,9 +735,12 @@ interface SettleRoundResult {
735
735
 
736
736
  /**
737
737
  * EIP-5792 batch primitives — ported from the proven game-hub `payEntryOnchain`
738
- * path (`OnchainEntry.ts`). One `wallet_sendCalls` sends `approve` + the settling
739
- * call as ONE atomic confirmation; the paymaster sponsors gas when configured.
740
- * The player sees a single Apple-Pay-style sheet.
738
+ * path (`OnchainEntry.ts`). `wallet_sendCalls` still sends `approve` + the
739
+ * settling call as one atomic confirmation when the wallet can batch (paymaster
740
+ * sponsors gas when configured). If `wallet_sendCalls` is missing or fails on an
741
+ * EOA — not a user cancel — the same Call[] is sent as sequential
742
+ * `eth_sendTransaction`s. That fallback is not atomic and never attaches a
743
+ * paymaster. Covered USDC allowance skips the approve tx (one confirm).
741
744
  */
742
745
 
743
746
  interface Call {
@@ -735,9 +735,12 @@ interface SettleRoundResult {
735
735
 
736
736
  /**
737
737
  * EIP-5792 batch primitives — ported from the proven game-hub `payEntryOnchain`
738
- * path (`OnchainEntry.ts`). One `wallet_sendCalls` sends `approve` + the settling
739
- * call as ONE atomic confirmation; the paymaster sponsors gas when configured.
740
- * The player sees a single Apple-Pay-style sheet.
738
+ * path (`OnchainEntry.ts`). `wallet_sendCalls` still sends `approve` + the
739
+ * settling call as one atomic confirmation when the wallet can batch (paymaster
740
+ * sponsors gas when configured). If `wallet_sendCalls` is missing or fails on an
741
+ * EOA — not a user cancel — the same Call[] is sent as sequential
742
+ * `eth_sendTransaction`s. That fallback is not atomic and never attaches a
743
+ * paymaster. Covered USDC allowance skips the approve tx (one confirm).
741
744
  */
742
745
 
743
746
  interface Call {
package/dist/index.cjs CHANGED
@@ -718,6 +718,37 @@ var prizePoolAbi = [
718
718
  outputs: [{ name: "amount", type: "uint256" }]
719
719
  }
720
720
  ];
721
+
722
+ // src/chain/batch.ts
723
+ var erc20AllowanceAbi = [
724
+ {
725
+ type: "function",
726
+ name: "allowance",
727
+ stateMutability: "view",
728
+ inputs: [
729
+ { name: "owner", type: "address" },
730
+ { name: "spender", type: "address" }
731
+ ],
732
+ outputs: [{ type: "uint256" }]
733
+ }
734
+ ];
735
+ var SEQUENTIAL_TX_ID_PREFIX = "eth:";
736
+ var USER_CANCEL_RE = /reject|denied|cancel|closed/i;
737
+ function sequentialTxId(txHash) {
738
+ return `${SEQUENTIAL_TX_ID_PREFIX}${txHash}`;
739
+ }
740
+ function sequentialTxHashFromId(id) {
741
+ if (!id.startsWith(SEQUENTIAL_TX_ID_PREFIX)) return void 0;
742
+ const hash = id.slice(SEQUENTIAL_TX_ID_PREFIX.length);
743
+ if (/^0x[0-9a-fA-F]{64}$/.test(hash)) return hash;
744
+ return void 0;
745
+ }
746
+ function errorMessage(e) {
747
+ return e?.message ?? String(e);
748
+ }
749
+ function isUserCancel(msg) {
750
+ return USER_CANCEL_RE.test(msg);
751
+ }
721
752
  async function sendCalls(provider, from, chainId, calls, paymasterUrl) {
722
753
  const params = {
723
754
  version: "2.0.0",
@@ -729,23 +760,85 @@ async function sendCalls(provider, from, chainId, calls, paymasterUrl) {
729
760
  if (paymasterUrl) {
730
761
  params.capabilities = { paymasterService: { url: paymasterUrl } };
731
762
  }
732
- let result;
733
763
  try {
734
- result = await provider.request({ method: "wallet_sendCalls", params: [params] });
764
+ const result = await provider.request({ method: "wallet_sendCalls", params: [params] });
765
+ const id = typeof result === "string" ? result : result?.id ?? "";
766
+ if (!id) throw new PaymentFailedError("Wallet returned no calls id.");
767
+ return { id };
735
768
  } catch (e) {
769
+ if (e instanceof PaymentFailedError) throw e;
736
770
  if (e instanceof WalletTimeoutError) throw e;
737
- const msg = e?.message ?? String(e);
738
- if (/reject|denied|cancel|closed/i.test(msg)) {
771
+ const msg = errorMessage(e);
772
+ if (isUserCancel(msg)) {
739
773
  throw new WalletConnectionError("The player cancelled or closed the payment sheet.", { cause: msg });
740
774
  }
741
- throw new PaymentFailedError("wallet_sendCalls failed.", { cause: msg });
775
+ return sendCallsSequentially(provider, from, calls);
776
+ }
777
+ }
778
+ async function skipCoveredApprove(provider, from, calls) {
779
+ const first = calls[0];
780
+ if (!first) return calls;
781
+ let spender;
782
+ let amount;
783
+ try {
784
+ const decoded = viem.decodeFunctionData({ abi: erc20Abi, data: first.data });
785
+ if (decoded.functionName !== "approve") return calls;
786
+ spender = decoded.args[0];
787
+ amount = decoded.args[1];
788
+ } catch {
789
+ return calls;
790
+ }
791
+ try {
792
+ const data = viem.encodeFunctionData({
793
+ abi: erc20AllowanceAbi,
794
+ functionName: "allowance",
795
+ args: [from, spender]
796
+ });
797
+ const raw = await provider.request({
798
+ method: "eth_call",
799
+ params: [{ to: first.to, data }, "latest"]
800
+ });
801
+ const allowance = BigInt(typeof raw === "string" && raw !== "0x" ? raw : "0");
802
+ if (allowance >= amount) return calls.slice(1);
803
+ } catch {
742
804
  }
743
- const id = typeof result === "string" ? result : result?.id ?? "";
744
- if (!id) throw new PaymentFailedError("Wallet returned no calls id.");
745
- return { id };
805
+ return calls;
806
+ }
807
+ async function sendCallsSequentially(provider, from, calls) {
808
+ const toSend = await skipCoveredApprove(provider, from, calls);
809
+ if (toSend.length === 0) {
810
+ throw new PaymentFailedError("No wallet calls to send.");
811
+ }
812
+ let lastHash;
813
+ for (const call of toSend) {
814
+ let hash;
815
+ try {
816
+ hash = await provider.request({
817
+ method: "eth_sendTransaction",
818
+ params: [{ from, to: call.to, data: call.data }]
819
+ });
820
+ } catch (e) {
821
+ if (e instanceof WalletTimeoutError) throw e;
822
+ const msg = errorMessage(e);
823
+ if (isUserCancel(msg)) {
824
+ throw new WalletConnectionError("The player cancelled or closed the payment sheet.", { cause: msg });
825
+ }
826
+ throw new PaymentFailedError("eth_sendTransaction failed.", { cause: msg });
827
+ }
828
+ if (typeof hash !== "string" || !/^0x[0-9a-fA-F]{64}$/.test(hash)) {
829
+ throw new PaymentFailedError("Wallet returned no transaction hash.");
830
+ }
831
+ lastHash = hash;
832
+ }
833
+ if (!lastHash) throw new PaymentFailedError("Wallet returned no transaction hash.");
834
+ return { id: sequentialTxId(lastHash) };
746
835
  }
747
836
  async function waitForCalls(provider, id, timeoutMs = 6e4) {
748
837
  if (!id) return { status: "FAILED" };
838
+ const sequentialHash = sequentialTxHashFromId(id);
839
+ if (sequentialHash) {
840
+ return waitForTransactionReceipt(provider, sequentialHash, timeoutMs);
841
+ }
749
842
  const deadline = Date.now() + timeoutMs;
750
843
  while (Date.now() < deadline) {
751
844
  try {
@@ -768,6 +861,30 @@ async function waitForCalls(provider, id, timeoutMs = 6e4) {
768
861
  }
769
862
  return { status: "PENDING" };
770
863
  }
864
+ async function waitForTransactionReceipt(provider, txHash, timeoutMs) {
865
+ const deadline = Date.now() + timeoutMs;
866
+ while (Date.now() < deadline) {
867
+ try {
868
+ const res = await provider.request({
869
+ method: "eth_getTransactionReceipt",
870
+ params: [txHash]
871
+ });
872
+ if (res && res.status !== void 0 && res.status !== null) {
873
+ const code = typeof res.status === "number" ? res.status : Number(res.status);
874
+ if (code === 1) return { status: "CONFIRMED", txHash };
875
+ if (code === 0) return { status: "FAILED", txHash };
876
+ }
877
+ } catch (e) {
878
+ if (e instanceof WalletTimeoutError) {
879
+ await new Promise((r) => setTimeout(r, 900));
880
+ continue;
881
+ }
882
+ throw e;
883
+ }
884
+ await new Promise((r) => setTimeout(r, 900));
885
+ }
886
+ return { status: "PENDING", txHash };
887
+ }
771
888
  function encodeApprove(spender, amountUnits) {
772
889
  return viem.encodeFunctionData({ abi: erc20Abi, functionName: "approve", args: [spender, amountUnits] });
773
890
  }
package/dist/index.d.cts CHANGED
@@ -1,5 +1,5 @@
1
- import { C as Call, P as PlaymosConfig, O as OnchainStatus, N as Network, W as WebhookEvent, R as RoundOpenInput, a as RoundState, b as RoundSettleInput, S as SettleRoundResult, c as RoundCancelInput, d as CancelRoundResult, e as RoundGetResult, A as ActiveSeriesRound, f as PayoutNoticesResult, g as PrizeBalance, h as WithdrawResult, i as AgentWallet, j as AgentFundResult, T as TransferResult, E as EscrowHoldInput, k as EscrowHoldResult, l as EscrowResolveResult, M as MarketplaceListInput, L as Listing, m as MarketplaceSaleResult, n as MarketplaceGetResult, o as PayInput, p as Payment, q as EnterRoundInput, r as TransferReconcile, s as WaitOptions, t as TransferInput, u as TransferConfirmOptions, V as VerifyResult, v as PayoutRule } from './errors-WcDNfb4q.cjs';
2
- export { w as ActiveForSeriesResult, x as AgentEconomyConfig, y as AlreadyEnteredError, z as ApiError, B as AuthError, D as ConfigError, F as ContractConfig, G as Eip1193Provider, H as GasConfig, I as GasMode, J as InsufficientGasError, K as InvalidAmountError, Q as ListingStatus, U as MarketplaceItem, X as MarketplaceSale, Y as MissingFieldError, Z as NothingToWithdrawError, _ as PaymentFailedError, $ as PaymentStatus, a0 as PayoutNotice, a1 as PayoutNoticeStatus, a2 as PlaymosError, a3 as PlaymosErrorCode, a4 as RetryOptions, a5 as RoundGetVia, a6 as RoundStatus, a7 as WalletConfig, a8 as WalletConnectionError, a9 as WalletConnector, aa as WalletTimeoutError, ab as WebhookEventType, ac as buildEpochExecuteSettlementCall } from './errors-WcDNfb4q.cjs';
1
+ import { C as Call, P as PlaymosConfig, O as OnchainStatus, N as Network, W as WebhookEvent, R as RoundOpenInput, a as RoundState, b as RoundSettleInput, S as SettleRoundResult, c as RoundCancelInput, d as CancelRoundResult, e as RoundGetResult, A as ActiveSeriesRound, f as PayoutNoticesResult, g as PrizeBalance, h as WithdrawResult, i as AgentWallet, j as AgentFundResult, T as TransferResult, E as EscrowHoldInput, k as EscrowHoldResult, l as EscrowResolveResult, M as MarketplaceListInput, L as Listing, m as MarketplaceSaleResult, n as MarketplaceGetResult, o as PayInput, p as Payment, q as EnterRoundInput, r as TransferReconcile, s as WaitOptions, t as TransferInput, u as TransferConfirmOptions, V as VerifyResult, v as PayoutRule } from './errors-CdzI_iYO.cjs';
2
+ export { w as ActiveForSeriesResult, x as AgentEconomyConfig, y as AlreadyEnteredError, z as ApiError, B as AuthError, D as ConfigError, F as ContractConfig, G as Eip1193Provider, H as GasConfig, I as GasMode, J as InsufficientGasError, K as InvalidAmountError, Q as ListingStatus, U as MarketplaceItem, X as MarketplaceSale, Y as MissingFieldError, Z as NothingToWithdrawError, _ as PaymentFailedError, $ as PaymentStatus, a0 as PayoutNotice, a1 as PayoutNoticeStatus, a2 as PlaymosError, a3 as PlaymosErrorCode, a4 as RetryOptions, a5 as RoundGetVia, a6 as RoundStatus, a7 as WalletConfig, a8 as WalletConnectionError, a9 as WalletConnector, aa as WalletTimeoutError, ab as WebhookEventType, ac as buildEpochExecuteSettlementCall } from './errors-CdzI_iYO.cjs';
3
3
 
4
4
  /**
5
5
  * Thin REST client for the Playmos service. Every SDK method that touches the
package/dist/index.d.ts CHANGED
@@ -1,5 +1,5 @@
1
- import { C as Call, P as PlaymosConfig, O as OnchainStatus, N as Network, W as WebhookEvent, R as RoundOpenInput, a as RoundState, b as RoundSettleInput, S as SettleRoundResult, c as RoundCancelInput, d as CancelRoundResult, e as RoundGetResult, A as ActiveSeriesRound, f as PayoutNoticesResult, g as PrizeBalance, h as WithdrawResult, i as AgentWallet, j as AgentFundResult, T as TransferResult, E as EscrowHoldInput, k as EscrowHoldResult, l as EscrowResolveResult, M as MarketplaceListInput, L as Listing, m as MarketplaceSaleResult, n as MarketplaceGetResult, o as PayInput, p as Payment, q as EnterRoundInput, r as TransferReconcile, s as WaitOptions, t as TransferInput, u as TransferConfirmOptions, V as VerifyResult, v as PayoutRule } from './errors-WcDNfb4q.js';
2
- export { w as ActiveForSeriesResult, x as AgentEconomyConfig, y as AlreadyEnteredError, z as ApiError, B as AuthError, D as ConfigError, F as ContractConfig, G as Eip1193Provider, H as GasConfig, I as GasMode, J as InsufficientGasError, K as InvalidAmountError, Q as ListingStatus, U as MarketplaceItem, X as MarketplaceSale, Y as MissingFieldError, Z as NothingToWithdrawError, _ as PaymentFailedError, $ as PaymentStatus, a0 as PayoutNotice, a1 as PayoutNoticeStatus, a2 as PlaymosError, a3 as PlaymosErrorCode, a4 as RetryOptions, a5 as RoundGetVia, a6 as RoundStatus, a7 as WalletConfig, a8 as WalletConnectionError, a9 as WalletConnector, aa as WalletTimeoutError, ab as WebhookEventType, ac as buildEpochExecuteSettlementCall } from './errors-WcDNfb4q.js';
1
+ import { C as Call, P as PlaymosConfig, O as OnchainStatus, N as Network, W as WebhookEvent, R as RoundOpenInput, a as RoundState, b as RoundSettleInput, S as SettleRoundResult, c as RoundCancelInput, d as CancelRoundResult, e as RoundGetResult, A as ActiveSeriesRound, f as PayoutNoticesResult, g as PrizeBalance, h as WithdrawResult, i as AgentWallet, j as AgentFundResult, T as TransferResult, E as EscrowHoldInput, k as EscrowHoldResult, l as EscrowResolveResult, M as MarketplaceListInput, L as Listing, m as MarketplaceSaleResult, n as MarketplaceGetResult, o as PayInput, p as Payment, q as EnterRoundInput, r as TransferReconcile, s as WaitOptions, t as TransferInput, u as TransferConfirmOptions, V as VerifyResult, v as PayoutRule } from './errors-CdzI_iYO.js';
2
+ export { w as ActiveForSeriesResult, x as AgentEconomyConfig, y as AlreadyEnteredError, z as ApiError, B as AuthError, D as ConfigError, F as ContractConfig, G as Eip1193Provider, H as GasConfig, I as GasMode, J as InsufficientGasError, K as InvalidAmountError, Q as ListingStatus, U as MarketplaceItem, X as MarketplaceSale, Y as MissingFieldError, Z as NothingToWithdrawError, _ as PaymentFailedError, $ as PaymentStatus, a0 as PayoutNotice, a1 as PayoutNoticeStatus, a2 as PlaymosError, a3 as PlaymosErrorCode, a4 as RetryOptions, a5 as RoundGetVia, a6 as RoundStatus, a7 as WalletConfig, a8 as WalletConnectionError, a9 as WalletConnector, aa as WalletTimeoutError, ab as WebhookEventType, ac as buildEpochExecuteSettlementCall } from './errors-CdzI_iYO.js';
3
3
 
4
4
  /**
5
5
  * Thin REST client for the Playmos service. Every SDK method that touches the
package/dist/index.js CHANGED
@@ -1,5 +1,5 @@
1
- import { AuthError, InvalidAmountError, epochPrizePoolEnterAbi, seriesToBytes32, identityToBytes32, encodeApprove, epochPrizePoolRefundAbi, ConfigError, epochPrizePoolCreateSeriesAbi, MissingFieldError, buildEpochExecuteSettlementCall, PaymentFailedError, epochPrizePoolViewAbi, ApiError, assertEnoughGas, sendCalls, waitForCalls, NothingToWithdrawError, buildWithdrawCall, WalletTimeoutError, buildIapCalls, buildEntryCalls, prizePoolAbi, WalletConnectionError, AlreadyEnteredError } from './chunk-ROWX6HVU.js';
2
- export { AlreadyEnteredError, ApiError, AuthError, ConfigError, InsufficientGasError, InvalidAmountError, MissingFieldError, NothingToWithdrawError, PaymentFailedError, PlaymosError, WalletConnectionError, WalletTimeoutError, buildEpochExecuteSettlementCall, identityToBytes32, seriesToBytes32 } from './chunk-ROWX6HVU.js';
1
+ import { AuthError, InvalidAmountError, epochPrizePoolEnterAbi, seriesToBytes32, identityToBytes32, encodeApprove, epochPrizePoolRefundAbi, ConfigError, epochPrizePoolCreateSeriesAbi, MissingFieldError, buildEpochExecuteSettlementCall, PaymentFailedError, epochPrizePoolViewAbi, ApiError, assertEnoughGas, sendCalls, waitForCalls, NothingToWithdrawError, buildWithdrawCall, WalletTimeoutError, buildIapCalls, buildEntryCalls, prizePoolAbi, WalletConnectionError, AlreadyEnteredError } from './chunk-U6BPSEKC.js';
2
+ export { AlreadyEnteredError, ApiError, AuthError, ConfigError, InsufficientGasError, InvalidAmountError, MissingFieldError, NothingToWithdrawError, PaymentFailedError, PlaymosError, WalletConnectionError, WalletTimeoutError, buildEpochExecuteSettlementCall, identityToBytes32, seriesToBytes32 } from './chunk-U6BPSEKC.js';
3
3
  import { encodeFunctionData, encodeAbiParameters, decodeFunctionResult } from 'viem';
4
4
 
5
5
  // src/config.ts
package/dist/server.d.cts CHANGED
@@ -1,5 +1,5 @@
1
- import { a2 as PlaymosError, W as WebhookEvent } from './errors-WcDNfb4q.cjs';
2
- export { ad as enterPathToBytes32 } from './errors-WcDNfb4q.cjs';
1
+ import { a2 as PlaymosError, W as WebhookEvent } from './errors-CdzI_iYO.cjs';
2
+ export { ad as enterPathToBytes32 } from './errors-CdzI_iYO.cjs';
3
3
 
4
4
  /**
5
5
  * Webhook signature verification (spec §6.2) — server-side only.
package/dist/server.d.ts CHANGED
@@ -1,5 +1,5 @@
1
- import { a2 as PlaymosError, W as WebhookEvent } from './errors-WcDNfb4q.js';
2
- export { ad as enterPathToBytes32 } from './errors-WcDNfb4q.js';
1
+ import { a2 as PlaymosError, W as WebhookEvent } from './errors-CdzI_iYO.js';
2
+ export { ad as enterPathToBytes32 } from './errors-CdzI_iYO.js';
3
3
 
4
4
  /**
5
5
  * Webhook signature verification (spec §6.2) — server-side only.
package/dist/server.js CHANGED
@@ -1,5 +1,5 @@
1
- import { PlaymosError, ApiError, toBytes32 } from './chunk-ROWX6HVU.js';
2
- export { toBytes32 as enterPathToBytes32 } from './chunk-ROWX6HVU.js';
1
+ import { PlaymosError, ApiError, toBytes32 } from './chunk-U6BPSEKC.js';
2
+ export { toBytes32 as enterPathToBytes32 } from './chunk-U6BPSEKC.js';
3
3
  import { timingSafeEqual, createHmac } from 'crypto';
4
4
  import { encodeFunctionData, decodeFunctionResult } from 'viem';
5
5
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@playmos/sdk",
3
- "version": "0.3.15",
3
+ "version": "0.3.16",
4
4
  "description": "Playmos SDK — stablecoin payments for games on Base. IAP and skill contests are flat 1%. USD in, USDC on-chain, no crypto UX for players.",
5
5
  "license": "MIT",
6
6
  "private": false,