@wtflabs/x402 0.0.1-beta.0

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.
Files changed (96) hide show
  1. package/README.md +60 -0
  2. package/dist/cjs/client/index.d.ts +64 -0
  3. package/dist/cjs/client/index.js +832 -0
  4. package/dist/cjs/client/index.js.map +1 -0
  5. package/dist/cjs/config-CFBSAuxW.d.ts +10 -0
  6. package/dist/cjs/config-Dfuvno71.d.ts +19 -0
  7. package/dist/cjs/facilitator/index.d.ts +42 -0
  8. package/dist/cjs/facilitator/index.js +2574 -0
  9. package/dist/cjs/facilitator/index.js.map +1 -0
  10. package/dist/cjs/index.d.ts +16 -0
  11. package/dist/cjs/index.js +2974 -0
  12. package/dist/cjs/index.js.map +1 -0
  13. package/dist/cjs/middleware-6_1ApcJn.d.ts +93 -0
  14. package/dist/cjs/middleware-B_ewwsQp.d.ts +93 -0
  15. package/dist/cjs/middleware-Brgsx32F.d.ts +93 -0
  16. package/dist/cjs/middleware-BwfW7mAs.d.ts +93 -0
  17. package/dist/cjs/middleware-CQb61c1k.d.ts +93 -0
  18. package/dist/cjs/middleware-DB9lqy9f.d.ts +93 -0
  19. package/dist/cjs/middleware-DcHctwQV.d.ts +93 -0
  20. package/dist/cjs/middleware-De0jD3Bp.d.ts +93 -0
  21. package/dist/cjs/middleware-HoFOmpgv.d.ts +93 -0
  22. package/dist/cjs/middleware-Y8AiAfYw.d.ts +93 -0
  23. package/dist/cjs/middleware-pnres9YM.d.ts +93 -0
  24. package/dist/cjs/network-FrFmmiyj.d.ts +11 -0
  25. package/dist/cjs/network-RtNddYQk.d.ts +11 -0
  26. package/dist/cjs/paywall/index.d.ts +30 -0
  27. package/dist/cjs/paywall/index.js +131 -0
  28. package/dist/cjs/paywall/index.js.map +1 -0
  29. package/dist/cjs/rpc-BMvnNNHd.d.ts +35 -0
  30. package/dist/cjs/rpc-Ca8eHCWz.d.ts +35 -0
  31. package/dist/cjs/schemes/index.d.ts +533 -0
  32. package/dist/cjs/schemes/index.js +3144 -0
  33. package/dist/cjs/schemes/index.js.map +1 -0
  34. package/dist/cjs/shared/evm/index.d.ts +71 -0
  35. package/dist/cjs/shared/evm/index.js +947 -0
  36. package/dist/cjs/shared/evm/index.js.map +1 -0
  37. package/dist/cjs/shared/index.d.ts +182 -0
  38. package/dist/cjs/shared/index.js +674 -0
  39. package/dist/cjs/shared/index.js.map +1 -0
  40. package/dist/cjs/types/index.d.ts +1515 -0
  41. package/dist/cjs/types/index.js +1645 -0
  42. package/dist/cjs/types/index.js.map +1 -0
  43. package/dist/cjs/verify/index.d.ts +7 -0
  44. package/dist/cjs/verify/index.js +438 -0
  45. package/dist/cjs/verify/index.js.map +1 -0
  46. package/dist/cjs/wallet-BRWfOM5D.d.ts +153 -0
  47. package/dist/cjs/wallet-BTqCm9Zp.d.ts +27 -0
  48. package/dist/cjs/wallet-BYRAGtOB.d.ts +153 -0
  49. package/dist/cjs/wallet-BmEtlgEf.d.ts +48 -0
  50. package/dist/cjs/wallet-CNOAmyZ6.d.ts +48 -0
  51. package/dist/cjs/wallet-CQ0Fe_M5.d.ts +88 -0
  52. package/dist/cjs/wallet-D1SoxFTw.d.ts +48 -0
  53. package/dist/cjs/wallet-SJ-hbjm9.d.ts +153 -0
  54. package/dist/cjs/wallet-SJKJpUgQ.d.ts +167 -0
  55. package/dist/cjs/wallet-ecnda4Aj.d.ts +48 -0
  56. package/dist/cjs/wallet-gP8Qoi-c.d.ts +74 -0
  57. package/dist/cjs/x402Specs-B7InXo2L.d.ts +1065 -0
  58. package/dist/cjs/x402Specs-BLH3j34O.d.ts +1696 -0
  59. package/dist/cjs/x402Specs-C7LipAZg.d.ts +1715 -0
  60. package/dist/cjs/x402Specs-CYq5tSY1.d.ts +1745 -0
  61. package/dist/cjs/x402Specs-CeajqonG.d.ts +1696 -0
  62. package/dist/cjs/x402Specs-qMujgEV5.d.ts +1715 -0
  63. package/dist/cjs/x402Specs-qUBCpcuz.d.ts +1715 -0
  64. package/dist/esm/chunk-34YNR4LY.mjs +106 -0
  65. package/dist/esm/chunk-34YNR4LY.mjs.map +1 -0
  66. package/dist/esm/chunk-57UEJN5U.mjs +1416 -0
  67. package/dist/esm/chunk-57UEJN5U.mjs.map +1 -0
  68. package/dist/esm/chunk-5LTKIVOA.mjs +858 -0
  69. package/dist/esm/chunk-5LTKIVOA.mjs.map +1 -0
  70. package/dist/esm/chunk-AQQR4PXH.mjs +80 -0
  71. package/dist/esm/chunk-AQQR4PXH.mjs.map +1 -0
  72. package/dist/esm/chunk-LGXWNXCO.mjs +76 -0
  73. package/dist/esm/chunk-LGXWNXCO.mjs.map +1 -0
  74. package/dist/esm/chunk-RX2JKK4O.mjs +349 -0
  75. package/dist/esm/chunk-RX2JKK4O.mjs.map +1 -0
  76. package/dist/esm/chunk-UCBE7FDY.mjs +1041 -0
  77. package/dist/esm/chunk-UCBE7FDY.mjs.map +1 -0
  78. package/dist/esm/client/index.mjs +17 -0
  79. package/dist/esm/client/index.mjs.map +1 -0
  80. package/dist/esm/facilitator/index.mjs +14 -0
  81. package/dist/esm/facilitator/index.mjs.map +1 -0
  82. package/dist/esm/index.mjs +28 -0
  83. package/dist/esm/index.mjs.map +1 -0
  84. package/dist/esm/paywall/index.mjs +46 -0
  85. package/dist/esm/paywall/index.mjs.map +1 -0
  86. package/dist/esm/schemes/index.mjs +16 -0
  87. package/dist/esm/schemes/index.mjs.map +1 -0
  88. package/dist/esm/shared/evm/index.mjs +20 -0
  89. package/dist/esm/shared/evm/index.mjs.map +1 -0
  90. package/dist/esm/shared/index.mjs +31 -0
  91. package/dist/esm/shared/index.mjs.map +1 -0
  92. package/dist/esm/types/index.mjs +87 -0
  93. package/dist/esm/types/index.mjs.map +1 -0
  94. package/dist/esm/verify/index.mjs +105 -0
  95. package/dist/esm/verify/index.mjs.map +1 -0
  96. package/package.json +148 -0
@@ -0,0 +1,1416 @@
1
+ import {
2
+ createAndSignPayment,
3
+ createNonce,
4
+ createPayment,
5
+ createPaymentHeader,
6
+ createPaymentHeader2,
7
+ decodePayment,
8
+ encodePayment,
9
+ preparePaymentHeader,
10
+ signAuthorization,
11
+ signPaymentHeader
12
+ } from "./chunk-RX2JKK4O.mjs";
13
+ import {
14
+ ErrorReasons,
15
+ PERMIT2_ADDRESS,
16
+ SupportedSVMNetworks,
17
+ authorizationTypes,
18
+ decodeTransactionFromPayload,
19
+ erc20PermitABI,
20
+ getNetworkId,
21
+ getRpcClient,
22
+ getRpcSubscriptions,
23
+ getTokenPayerFromTransaction,
24
+ isSignerWallet,
25
+ permit2ABI,
26
+ permit2Types,
27
+ permitTypes,
28
+ signAndSimulateTransaction
29
+ } from "./chunk-UCBE7FDY.mjs";
30
+ import {
31
+ getERC20Allowance,
32
+ getERC20Balance,
33
+ getVersion,
34
+ usdcABI
35
+ } from "./chunk-5LTKIVOA.mjs";
36
+ import {
37
+ __export,
38
+ config
39
+ } from "./chunk-AQQR4PXH.mjs";
40
+
41
+ // src/schemes/exact/index.ts
42
+ var exact_exports = {};
43
+ __export(exact_exports, {
44
+ SCHEME: () => SCHEME,
45
+ evm: () => evm_exports,
46
+ svm: () => svm_exports
47
+ });
48
+
49
+ // src/schemes/exact/evm/index.ts
50
+ var evm_exports = {};
51
+ __export(evm_exports, {
52
+ decodePayment: () => decodePayment,
53
+ eip3009: () => eip3009_exports,
54
+ encodePayment: () => encodePayment,
55
+ permit: () => permit_exports,
56
+ permit2: () => permit2_exports,
57
+ settle: () => settle4,
58
+ verify: () => verify4
59
+ });
60
+
61
+ // src/schemes/exact/evm/eip3009/facilitator.ts
62
+ import { getAddress, parseErc6492Signature } from "viem";
63
+ async function verify(client, payload, paymentRequirements) {
64
+ const exactEvmPayload = payload.payload;
65
+ if (exactEvmPayload.authorizationType !== "eip3009") {
66
+ return {
67
+ isValid: false,
68
+ invalidReason: "unsupported_authorization_type",
69
+ payer: ""
70
+ };
71
+ }
72
+ if (payload.scheme !== SCHEME || paymentRequirements.scheme !== SCHEME) {
73
+ return {
74
+ isValid: false,
75
+ invalidReason: `unsupported_scheme`,
76
+ payer: exactEvmPayload.authorization.from
77
+ };
78
+ }
79
+ let name;
80
+ let chainId;
81
+ let erc20Address;
82
+ let version;
83
+ try {
84
+ chainId = getNetworkId(payload.network);
85
+ name = paymentRequirements.extra?.name ?? config[chainId.toString()].usdcName;
86
+ erc20Address = paymentRequirements.asset;
87
+ version = paymentRequirements.extra?.version ?? await getVersion(client, erc20Address);
88
+ } catch {
89
+ return {
90
+ isValid: false,
91
+ invalidReason: `invalid_network`,
92
+ payer: exactEvmPayload.authorization.from
93
+ };
94
+ }
95
+ const permitTypedData = {
96
+ types: authorizationTypes,
97
+ primaryType: "TransferWithAuthorization",
98
+ domain: {
99
+ name,
100
+ version,
101
+ chainId,
102
+ verifyingContract: erc20Address
103
+ },
104
+ message: {
105
+ from: exactEvmPayload.authorization.from,
106
+ to: exactEvmPayload.authorization.to,
107
+ value: exactEvmPayload.authorization.value,
108
+ validAfter: exactEvmPayload.authorization.validAfter,
109
+ validBefore: exactEvmPayload.authorization.validBefore,
110
+ nonce: exactEvmPayload.authorization.nonce
111
+ }
112
+ };
113
+ const recoveredAddress = await client.verifyTypedData({
114
+ address: exactEvmPayload.authorization.from,
115
+ ...permitTypedData,
116
+ signature: exactEvmPayload.signature
117
+ });
118
+ if (!recoveredAddress) {
119
+ return {
120
+ isValid: false,
121
+ invalidReason: "invalid_exact_evm_payload_signature",
122
+ //"Invalid permit signature",
123
+ payer: exactEvmPayload.authorization.from
124
+ };
125
+ }
126
+ if (getAddress(exactEvmPayload.authorization.to) !== getAddress(paymentRequirements.payTo)) {
127
+ return {
128
+ isValid: false,
129
+ invalidReason: "invalid_exact_evm_payload_recipient_mismatch",
130
+ payer: exactEvmPayload.authorization.from
131
+ };
132
+ }
133
+ if (BigInt(exactEvmPayload.authorization.validBefore) < BigInt(Math.floor(Date.now() / 1e3) + 6)) {
134
+ return {
135
+ isValid: false,
136
+ invalidReason: "invalid_exact_evm_payload_authorization_valid_before",
137
+ //"Deadline on permit isn't far enough in the future",
138
+ payer: exactEvmPayload.authorization.from
139
+ };
140
+ }
141
+ if (BigInt(exactEvmPayload.authorization.validAfter) > BigInt(Math.floor(Date.now() / 1e3))) {
142
+ return {
143
+ isValid: false,
144
+ invalidReason: "invalid_exact_evm_payload_authorization_valid_after",
145
+ //"Deadline on permit is in the future",
146
+ payer: exactEvmPayload.authorization.from
147
+ };
148
+ }
149
+ const balance = await getERC20Balance(
150
+ client,
151
+ erc20Address,
152
+ exactEvmPayload.authorization.from
153
+ );
154
+ if (balance < BigInt(paymentRequirements.maxAmountRequired)) {
155
+ return {
156
+ isValid: false,
157
+ invalidReason: "insufficient_funds",
158
+ //"Client does not have enough funds",
159
+ payer: exactEvmPayload.authorization.from
160
+ };
161
+ }
162
+ if (BigInt(exactEvmPayload.authorization.value) < BigInt(paymentRequirements.maxAmountRequired)) {
163
+ return {
164
+ isValid: false,
165
+ invalidReason: "invalid_exact_evm_payload_authorization_value",
166
+ //"Value in payload is not enough to cover paymentRequirements.maxAmountRequired",
167
+ payer: exactEvmPayload.authorization.from
168
+ };
169
+ }
170
+ return {
171
+ isValid: true,
172
+ invalidReason: void 0,
173
+ payer: exactEvmPayload.authorization.from
174
+ };
175
+ }
176
+ async function settle(wallet, paymentPayload, paymentRequirements) {
177
+ const payload = paymentPayload.payload;
178
+ if (payload.authorizationType !== "eip3009") {
179
+ return {
180
+ success: false,
181
+ errorReason: "unsupported_authorization_type",
182
+ transaction: "",
183
+ network: paymentPayload.network,
184
+ payer: ""
185
+ };
186
+ }
187
+ const valid = await verify(wallet, paymentPayload, paymentRequirements);
188
+ if (!valid.isValid) {
189
+ return {
190
+ success: false,
191
+ network: paymentPayload.network,
192
+ transaction: "",
193
+ errorReason: valid.invalidReason ?? "invalid_scheme",
194
+ //`Payment is no longer valid: ${valid.invalidReason}`,
195
+ payer: payload.authorization.from
196
+ };
197
+ }
198
+ const { signature } = parseErc6492Signature(payload.signature);
199
+ const tx = await wallet.writeContract({
200
+ address: paymentRequirements.asset,
201
+ abi: usdcABI,
202
+ functionName: "transferWithAuthorization",
203
+ args: [
204
+ payload.authorization.from,
205
+ payload.authorization.to,
206
+ BigInt(payload.authorization.value),
207
+ BigInt(payload.authorization.validAfter),
208
+ BigInt(payload.authorization.validBefore),
209
+ payload.authorization.nonce,
210
+ signature
211
+ ],
212
+ chain: wallet.chain
213
+ });
214
+ const receipt = await wallet.waitForTransactionReceipt({ hash: tx });
215
+ if (receipt.status !== "success") {
216
+ return {
217
+ success: false,
218
+ errorReason: "invalid_transaction_state",
219
+ //`Transaction failed`,
220
+ transaction: tx,
221
+ network: paymentPayload.network,
222
+ payer: payload.authorization.from
223
+ };
224
+ }
225
+ return {
226
+ success: true,
227
+ transaction: tx,
228
+ network: paymentPayload.network,
229
+ payer: payload.authorization.from
230
+ };
231
+ }
232
+
233
+ // src/schemes/exact/evm/permit/facilitator.ts
234
+ import { getAddress as getAddress3 } from "viem";
235
+
236
+ // src/schemes/exact/evm/permit/sign.ts
237
+ import { getAddress as getAddress2 } from "viem";
238
+ async function signPermit(walletClient, { owner, spender, value, deadline }, { asset, network }) {
239
+ const chainId = getNetworkId(network);
240
+ const tokenAddress = getAddress2(asset);
241
+ let nonce;
242
+ let name;
243
+ let version;
244
+ if (isSignerWallet(walletClient)) {
245
+ [nonce, name, version] = await Promise.all([
246
+ walletClient.readContract({
247
+ address: tokenAddress,
248
+ abi: erc20PermitABI,
249
+ functionName: "nonces",
250
+ args: [getAddress2(owner)]
251
+ }),
252
+ walletClient.readContract({
253
+ address: tokenAddress,
254
+ abi: erc20PermitABI,
255
+ functionName: "name"
256
+ }),
257
+ walletClient.readContract({
258
+ address: tokenAddress,
259
+ abi: erc20PermitABI,
260
+ functionName: "version"
261
+ })
262
+ ]);
263
+ } else {
264
+ throw new Error("Local account signing for permit requires a connected client");
265
+ }
266
+ const data = {
267
+ types: permitTypes,
268
+ domain: {
269
+ name,
270
+ version,
271
+ chainId,
272
+ verifyingContract: tokenAddress
273
+ },
274
+ primaryType: "Permit",
275
+ message: {
276
+ owner: getAddress2(owner),
277
+ spender: getAddress2(spender),
278
+ value,
279
+ nonce,
280
+ deadline
281
+ }
282
+ };
283
+ if (isSignerWallet(walletClient)) {
284
+ const signature = await walletClient.signTypedData(data);
285
+ return {
286
+ signature,
287
+ nonce: nonce.toString()
288
+ };
289
+ }
290
+ const account = walletClient;
291
+ if (account.signTypedData) {
292
+ const signature = await account.signTypedData(data);
293
+ return {
294
+ signature,
295
+ nonce: nonce.toString()
296
+ };
297
+ }
298
+ throw new Error("Invalid wallet client provided does not support signTypedData");
299
+ }
300
+ function splitSignature(signature) {
301
+ const sig = signature.slice(2);
302
+ const r = `0x${sig.slice(0, 64)}`;
303
+ const s = `0x${sig.slice(64, 128)}`;
304
+ let v = parseInt(sig.slice(128, 130), 16);
305
+ if (v < 27) {
306
+ v += 27;
307
+ }
308
+ return { v, r, s };
309
+ }
310
+
311
+ // src/types/shared/evm/permitProxyABI.ts
312
+ var permitProxyContractABI = [
313
+ {
314
+ inputs: [
315
+ {
316
+ internalType: "address",
317
+ name: "token",
318
+ type: "address"
319
+ },
320
+ {
321
+ internalType: "address",
322
+ name: "owner",
323
+ type: "address"
324
+ },
325
+ {
326
+ internalType: "address",
327
+ name: "spender",
328
+ type: "address"
329
+ },
330
+ {
331
+ internalType: "uint256",
332
+ name: "value",
333
+ type: "uint256"
334
+ },
335
+ {
336
+ internalType: "uint256",
337
+ name: "deadline",
338
+ type: "uint256"
339
+ },
340
+ {
341
+ internalType: "uint8",
342
+ name: "v",
343
+ type: "uint8"
344
+ },
345
+ {
346
+ internalType: "bytes32",
347
+ name: "r",
348
+ type: "bytes32"
349
+ },
350
+ {
351
+ internalType: "bytes32",
352
+ name: "s",
353
+ type: "bytes32"
354
+ },
355
+ {
356
+ internalType: "address",
357
+ name: "to",
358
+ type: "address"
359
+ }
360
+ ],
361
+ name: "permitAndTransfer",
362
+ outputs: [],
363
+ stateMutability: "nonpayable",
364
+ type: "function"
365
+ }
366
+ ];
367
+
368
+ // src/schemes/exact/evm/permit/facilitator.ts
369
+ async function verify2(client, payload, paymentRequirements) {
370
+ if (payload.payload.authorizationType !== "permit" || payload.scheme !== SCHEME || paymentRequirements.scheme !== SCHEME) {
371
+ return {
372
+ isValid: false,
373
+ invalidReason: "unsupported_scheme"
374
+ };
375
+ }
376
+ const permitPayload = payload.payload;
377
+ const { owner, spender, value, deadline, nonce } = permitPayload.authorization;
378
+ let name;
379
+ let version;
380
+ let erc20Address;
381
+ let chainId;
382
+ try {
383
+ chainId = getNetworkId(payload.network);
384
+ erc20Address = paymentRequirements.asset;
385
+ name = paymentRequirements.extra?.name ?? await client.readContract({
386
+ address: erc20Address,
387
+ abi: erc20PermitABI,
388
+ functionName: "name"
389
+ });
390
+ version = paymentRequirements.extra?.version ?? await getVersion(client, erc20Address);
391
+ } catch {
392
+ return {
393
+ isValid: false,
394
+ invalidReason: "invalid_network",
395
+ payer: owner
396
+ };
397
+ }
398
+ const permitTypedData = {
399
+ types: permitTypes,
400
+ domain: {
401
+ name,
402
+ version,
403
+ chainId,
404
+ verifyingContract: erc20Address
405
+ },
406
+ primaryType: "Permit",
407
+ message: {
408
+ owner: getAddress3(owner),
409
+ spender: getAddress3(spender),
410
+ value,
411
+ nonce,
412
+ deadline
413
+ }
414
+ };
415
+ const recoveredAddress = await client.verifyTypedData({
416
+ address: owner,
417
+ ...permitTypedData,
418
+ signature: permitPayload.signature
419
+ });
420
+ if (!recoveredAddress) {
421
+ return {
422
+ isValid: false,
423
+ invalidReason: "invalid_permit_signature",
424
+ payer: owner
425
+ };
426
+ }
427
+ const now = Math.floor(Date.now() / 1e3);
428
+ if (BigInt(deadline) < now) {
429
+ return {
430
+ isValid: false,
431
+ invalidReason: "permit_expired",
432
+ payer: owner
433
+ };
434
+ }
435
+ if (paymentRequirements.extra?.proxyAddress) {
436
+ if (getAddress3(spender) !== getAddress3(paymentRequirements.extra?.proxyAddress)) {
437
+ return {
438
+ isValid: false,
439
+ invalidReason: "invalid_spender_address",
440
+ payer: owner
441
+ };
442
+ }
443
+ } else {
444
+ if (client.account && getAddress3(spender) !== getAddress3(client.account.address)) {
445
+ return {
446
+ isValid: false,
447
+ invalidReason: "invalid_spender_address",
448
+ payer: owner
449
+ };
450
+ }
451
+ }
452
+ const balance = await getERC20Balance(client, erc20Address, owner);
453
+ if (balance < BigInt(paymentRequirements.maxAmountRequired)) {
454
+ return {
455
+ isValid: false,
456
+ invalidReason: "insufficient_funds",
457
+ payer: owner
458
+ };
459
+ }
460
+ if (BigInt(value) < BigInt(paymentRequirements.maxAmountRequired)) {
461
+ return {
462
+ isValid: false,
463
+ invalidReason: "invalid_exact_evm_payload_authorization_value",
464
+ payer: owner
465
+ };
466
+ }
467
+ return {
468
+ isValid: true,
469
+ payer: owner
470
+ };
471
+ }
472
+ async function settle2(wallet, paymentPayload, paymentRequirements) {
473
+ const permitPayload = paymentPayload.payload;
474
+ if (permitPayload.authorizationType !== "permit") {
475
+ return {
476
+ success: false,
477
+ errorReason: "invalid_authorization_type",
478
+ transaction: "",
479
+ network: paymentPayload.network,
480
+ payer: ""
481
+ };
482
+ }
483
+ const valid = await verify2(wallet, paymentPayload, paymentRequirements);
484
+ if (!valid.isValid) {
485
+ return {
486
+ success: false,
487
+ network: paymentPayload.network,
488
+ transaction: "",
489
+ errorReason: valid.invalidReason ?? "invalid_payment",
490
+ payer: permitPayload.authorization.owner
491
+ };
492
+ }
493
+ const { owner, spender, value, deadline } = permitPayload.authorization;
494
+ const { v, r, s } = splitSignature(permitPayload.signature);
495
+ const tokenAddress = paymentRequirements.asset;
496
+ const txNonce = await wallet.getTransactionCount({
497
+ address: wallet.account.address
498
+ });
499
+ let transactionHash;
500
+ if (paymentRequirements.extra?.proxyAddress) {
501
+ transactionHash = await wallet.writeContract({
502
+ address: paymentRequirements.extra.proxyAddress,
503
+ abi: permitProxyContractABI,
504
+ functionName: "permitAndTransfer",
505
+ args: [
506
+ tokenAddress,
507
+ owner,
508
+ spender,
509
+ BigInt(value),
510
+ BigInt(deadline),
511
+ v,
512
+ r,
513
+ s,
514
+ paymentRequirements.payTo
515
+ ],
516
+ chain: wallet.chain,
517
+ nonce: txNonce
518
+ });
519
+ const receipt = await wallet.waitForTransactionReceipt({ hash: transactionHash });
520
+ if (receipt.status !== "success") {
521
+ return {
522
+ success: false,
523
+ errorReason: "transaction_failed",
524
+ transaction: transactionHash,
525
+ network: paymentPayload.network,
526
+ payer: owner
527
+ };
528
+ }
529
+ } else {
530
+ const [permitTx, transferTx] = await Promise.all([
531
+ // Call permit to approve the spender
532
+ wallet.writeContract({
533
+ address: tokenAddress,
534
+ abi: erc20PermitABI,
535
+ functionName: "permit",
536
+ args: [owner, spender, BigInt(value), BigInt(deadline), v, r, s],
537
+ chain: wallet.chain,
538
+ nonce: txNonce
539
+ }),
540
+ // Call transferFrom to transfer tokens to payTo address
541
+ wallet.writeContract({
542
+ address: tokenAddress,
543
+ abi: erc20PermitABI,
544
+ functionName: "transferFrom",
545
+ args: [owner, paymentRequirements.payTo, BigInt(value)],
546
+ chain: wallet.chain,
547
+ nonce: txNonce + 1
548
+ })
549
+ ]);
550
+ const [, receipt] = await Promise.all([
551
+ wallet.waitForTransactionReceipt({ hash: permitTx }),
552
+ wallet.waitForTransactionReceipt({ hash: transferTx })
553
+ ]);
554
+ if (receipt.status !== "success") {
555
+ return {
556
+ success: false,
557
+ errorReason: "transaction_failed",
558
+ transaction: transferTx,
559
+ network: paymentPayload.network,
560
+ payer: owner
561
+ };
562
+ }
563
+ transactionHash = transferTx;
564
+ }
565
+ return {
566
+ success: true,
567
+ transaction: transactionHash,
568
+ network: paymentPayload.network,
569
+ payer: owner
570
+ };
571
+ }
572
+
573
+ // src/schemes/exact/evm/permit2/facilitator.ts
574
+ import { getAddress as getAddress4 } from "viem";
575
+ async function verify3(client, payload, paymentRequirements) {
576
+ if (payload.payload.authorizationType !== "permit2" || payload.scheme !== SCHEME || paymentRequirements.scheme !== SCHEME) {
577
+ return {
578
+ isValid: false,
579
+ invalidReason: "unsupported_scheme"
580
+ };
581
+ }
582
+ const permit2Payload = payload.payload;
583
+ const { owner, spender, token, amount, deadline, nonce } = permit2Payload.authorization;
584
+ const chainId = getNetworkId(payload.network);
585
+ const tokenAddress = getAddress4(token);
586
+ const ownerAddress = getAddress4(owner);
587
+ const permit2TypedData = {
588
+ types: permit2Types,
589
+ domain: {
590
+ name: "Permit2",
591
+ chainId,
592
+ verifyingContract: PERMIT2_ADDRESS
593
+ },
594
+ primaryType: "PermitTransferFrom",
595
+ message: {
596
+ permitted: {
597
+ token: tokenAddress,
598
+ amount
599
+ },
600
+ spender: getAddress4(spender),
601
+ nonce,
602
+ deadline
603
+ }
604
+ };
605
+ const recoveredAddress = await client.verifyTypedData({
606
+ address: ownerAddress,
607
+ ...permit2TypedData,
608
+ signature: permit2Payload.signature
609
+ });
610
+ if (!recoveredAddress) {
611
+ return {
612
+ isValid: false,
613
+ invalidReason: "invalid_permit2_signature",
614
+ payer: owner
615
+ };
616
+ }
617
+ const now = Math.floor(Date.now() / 1e3);
618
+ if (BigInt(deadline) < now) {
619
+ return {
620
+ isValid: false,
621
+ invalidReason: "permit2_expired",
622
+ payer: owner
623
+ };
624
+ }
625
+ if (client.account && getAddress4(spender) !== getAddress4(client.account.address)) {
626
+ return {
627
+ isValid: false,
628
+ invalidReason: "invalid_spender_address",
629
+ payer: owner
630
+ };
631
+ }
632
+ if (tokenAddress.toLowerCase() !== paymentRequirements.asset.toLowerCase()) {
633
+ return {
634
+ isValid: false,
635
+ invalidReason: "token_mismatch",
636
+ payer: owner
637
+ };
638
+ }
639
+ const allowance = await getERC20Allowance(client, tokenAddress, ownerAddress, PERMIT2_ADDRESS);
640
+ if (allowance < BigInt(paymentRequirements.maxAmountRequired)) {
641
+ return {
642
+ isValid: false,
643
+ invalidReason: "permit2_not_approved",
644
+ payer: owner
645
+ };
646
+ }
647
+ const balance = await getERC20Balance(client, tokenAddress, ownerAddress);
648
+ if (balance < BigInt(paymentRequirements.maxAmountRequired)) {
649
+ return {
650
+ isValid: false,
651
+ invalidReason: "insufficient_funds",
652
+ payer: owner
653
+ };
654
+ }
655
+ if (BigInt(amount) < BigInt(paymentRequirements.maxAmountRequired)) {
656
+ return {
657
+ isValid: false,
658
+ invalidReason: "invalid_exact_evm_payload_authorization_value",
659
+ payer: owner
660
+ };
661
+ }
662
+ return {
663
+ isValid: true,
664
+ payer: owner
665
+ };
666
+ }
667
+ async function settle3(wallet, paymentPayload, paymentRequirements) {
668
+ const permit2Payload = paymentPayload.payload;
669
+ if (permit2Payload.authorizationType !== "permit2") {
670
+ return {
671
+ success: false,
672
+ errorReason: "invalid_authorization_type",
673
+ transaction: "",
674
+ network: paymentPayload.network,
675
+ payer: ""
676
+ };
677
+ }
678
+ const valid = await verify3(wallet, paymentPayload, paymentRequirements);
679
+ if (!valid.isValid) {
680
+ return {
681
+ success: false,
682
+ network: paymentPayload.network,
683
+ transaction: "",
684
+ errorReason: valid.invalidReason ?? "invalid_payment",
685
+ payer: permit2Payload.authorization.owner
686
+ };
687
+ }
688
+ const { owner, token, amount, deadline, nonce } = permit2Payload.authorization;
689
+ const tokenAddress = getAddress4(token);
690
+ const ownerAddress = getAddress4(owner);
691
+ const tx = await wallet.writeContract({
692
+ address: PERMIT2_ADDRESS,
693
+ abi: permit2ABI,
694
+ functionName: "permitTransferFrom",
695
+ args: [
696
+ {
697
+ permitted: {
698
+ token: tokenAddress,
699
+ amount: BigInt(amount)
700
+ },
701
+ nonce: BigInt(nonce),
702
+ deadline: BigInt(deadline)
703
+ },
704
+ {
705
+ to: paymentRequirements.payTo,
706
+ requestedAmount: BigInt(amount)
707
+ },
708
+ ownerAddress,
709
+ permit2Payload.signature
710
+ ],
711
+ chain: wallet.chain
712
+ });
713
+ const receipt = await wallet.waitForTransactionReceipt({ hash: tx });
714
+ if (receipt.status !== "success") {
715
+ return {
716
+ success: false,
717
+ errorReason: "transaction_failed",
718
+ transaction: tx,
719
+ network: paymentPayload.network,
720
+ payer: owner
721
+ };
722
+ }
723
+ return {
724
+ success: true,
725
+ transaction: tx,
726
+ network: paymentPayload.network,
727
+ payer: owner
728
+ };
729
+ }
730
+
731
+ // src/schemes/exact/evm/eip3009/index.ts
732
+ var eip3009_exports = {};
733
+ __export(eip3009_exports, {
734
+ createNonce: () => createNonce,
735
+ createPayment: () => createPayment,
736
+ createPaymentHeader: () => createPaymentHeader,
737
+ preparePaymentHeader: () => preparePaymentHeader,
738
+ settle: () => settle,
739
+ signAuthorization: () => signAuthorization,
740
+ signPaymentHeader: () => signPaymentHeader,
741
+ verify: () => verify
742
+ });
743
+
744
+ // src/schemes/exact/evm/permit/index.ts
745
+ var permit_exports = {};
746
+ __export(permit_exports, {
747
+ createPayment: () => createPayment2,
748
+ createPaymentHeader: () => createPaymentHeader3,
749
+ preparePaymentHeader: () => preparePaymentHeader2,
750
+ settle: () => settle2,
751
+ signPaymentHeader: () => signPaymentHeader2,
752
+ signPermit: () => signPermit,
753
+ splitSignature: () => splitSignature,
754
+ verify: () => verify2
755
+ });
756
+
757
+ // src/schemes/exact/evm/permit/client.ts
758
+ function preparePaymentHeader2(from, x402Version, paymentRequirements) {
759
+ const deadline = BigInt(
760
+ Math.floor(Date.now() / 1e3 + paymentRequirements.maxTimeoutSeconds)
761
+ ).toString();
762
+ return {
763
+ x402Version,
764
+ scheme: paymentRequirements.scheme,
765
+ network: paymentRequirements.network,
766
+ payload: {
767
+ authorizationType: "permit",
768
+ signature: void 0,
769
+ authorization: {
770
+ owner: from,
771
+ spender: paymentRequirements.payTo,
772
+ value: paymentRequirements.maxAmountRequired,
773
+ deadline
774
+ }
775
+ }
776
+ };
777
+ }
778
+ async function signPaymentHeader2(client, paymentRequirements, unsignedPaymentHeader) {
779
+ const { owner, spender, value, deadline } = unsignedPaymentHeader.payload.authorization;
780
+ const { signature, nonce } = await signPermit(
781
+ client,
782
+ { owner, spender, value, deadline },
783
+ paymentRequirements
784
+ );
785
+ return {
786
+ ...unsignedPaymentHeader,
787
+ payload: {
788
+ authorizationType: "permit",
789
+ signature,
790
+ authorization: {
791
+ owner,
792
+ spender,
793
+ value,
794
+ deadline,
795
+ nonce: nonce.toString()
796
+ }
797
+ }
798
+ };
799
+ }
800
+ async function createPayment2(client, x402Version, paymentRequirements) {
801
+ const from = isSignerWallet(client) ? client.account.address : client.address;
802
+ const unsignedPaymentHeader = preparePaymentHeader2(from, x402Version, paymentRequirements);
803
+ return signPaymentHeader2(client, paymentRequirements, unsignedPaymentHeader);
804
+ }
805
+ async function createPaymentHeader3(client, x402Version, paymentRequirements) {
806
+ const payment = await createPayment2(client, x402Version, paymentRequirements);
807
+ return encodePayment(payment);
808
+ }
809
+
810
+ // src/schemes/exact/evm/permit2/index.ts
811
+ var permit2_exports = {};
812
+ __export(permit2_exports, {
813
+ createPayment: () => createPayment3,
814
+ createPaymentHeader: () => createPaymentHeader4,
815
+ createPermit2Nonce: () => createPermit2Nonce,
816
+ preparePaymentHeader: () => preparePaymentHeader3,
817
+ settle: () => settle3,
818
+ signPaymentHeader: () => signPaymentHeader3,
819
+ signPermit2: () => signPermit2,
820
+ verify: () => verify3
821
+ });
822
+
823
+ // src/schemes/exact/evm/permit2/sign.ts
824
+ import { getAddress as getAddress5 } from "viem";
825
+ async function signPermit2(walletClient, { owner, spender, token, amount, deadline }, { network }) {
826
+ const chainId = getNetworkId(network);
827
+ const tokenAddress = getAddress5(token);
828
+ const ownerAddress = getAddress5(owner);
829
+ const spenderAddress = getAddress5(spender);
830
+ const nonce = await createPermit2Nonce(walletClient, ownerAddress);
831
+ const data = {
832
+ types: permit2Types,
833
+ domain: {
834
+ name: "Permit2",
835
+ chainId,
836
+ verifyingContract: PERMIT2_ADDRESS
837
+ },
838
+ primaryType: "PermitTransferFrom",
839
+ message: {
840
+ permitted: {
841
+ token: tokenAddress,
842
+ amount: BigInt(amount)
843
+ },
844
+ spender: spenderAddress,
845
+ nonce,
846
+ deadline: BigInt(deadline)
847
+ }
848
+ };
849
+ if (isSignerWallet(walletClient)) {
850
+ const signature = await walletClient.signTypedData(data);
851
+ return {
852
+ signature,
853
+ nonce: nonce.toString()
854
+ };
855
+ }
856
+ const account = walletClient;
857
+ if (account.signTypedData) {
858
+ const signature = await account.signTypedData(data);
859
+ return {
860
+ signature,
861
+ nonce: nonce.toString()
862
+ };
863
+ }
864
+ throw new Error("Invalid wallet client provided does not support signTypedData");
865
+ }
866
+ async function createPermit2Nonce(walletClient, ownerAddress) {
867
+ if (!isSignerWallet(walletClient)) {
868
+ throw new Error("Local account signing for permit2 requires a connected client");
869
+ }
870
+ const timestamp = BigInt(Math.floor(Date.now() / 1e3));
871
+ const randomOffset = BigInt(Math.floor(Math.random() * 1e3));
872
+ let nonce = timestamp * 1000n + randomOffset;
873
+ try {
874
+ const wordPos = nonce / 256n;
875
+ const bitIndex = nonce % 256n;
876
+ const bitmap = await walletClient.readContract({
877
+ address: PERMIT2_ADDRESS,
878
+ abi: permit2ABI,
879
+ functionName: "nonceBitmap",
880
+ args: [ownerAddress, wordPos]
881
+ });
882
+ const used = bitmap >> bitIndex & 1n;
883
+ if (used === 1n) {
884
+ nonce += 1n;
885
+ }
886
+ } catch (error) {
887
+ console.warn("Could not check nonce bitmap, using timestamp-based nonce:", error);
888
+ }
889
+ return nonce;
890
+ }
891
+
892
+ // src/schemes/exact/evm/permit2/client.ts
893
+ function preparePaymentHeader3(from, x402Version, paymentRequirements) {
894
+ const deadline = BigInt(
895
+ Math.floor(Date.now() / 1e3 + paymentRequirements.maxTimeoutSeconds)
896
+ ).toString();
897
+ return {
898
+ x402Version,
899
+ scheme: paymentRequirements.scheme,
900
+ network: paymentRequirements.network,
901
+ payload: {
902
+ authorizationType: "permit2",
903
+ signature: void 0,
904
+ authorization: {
905
+ owner: from,
906
+ spender: paymentRequirements.payTo,
907
+ token: paymentRequirements.asset,
908
+ amount: paymentRequirements.maxAmountRequired,
909
+ deadline
910
+ }
911
+ }
912
+ };
913
+ }
914
+ async function signPaymentHeader3(client, paymentRequirements, unsignedPaymentHeader) {
915
+ const { owner, spender, token, amount, deadline } = unsignedPaymentHeader.payload.authorization;
916
+ const { signature, nonce } = await signPermit2(
917
+ client,
918
+ { owner, spender, token, amount, deadline },
919
+ paymentRequirements
920
+ );
921
+ return {
922
+ ...unsignedPaymentHeader,
923
+ payload: {
924
+ authorizationType: "permit2",
925
+ signature,
926
+ authorization: {
927
+ owner,
928
+ spender,
929
+ token,
930
+ amount,
931
+ deadline,
932
+ nonce
933
+ }
934
+ }
935
+ };
936
+ }
937
+ async function createPayment3(client, x402Version, paymentRequirements) {
938
+ const from = isSignerWallet(client) ? client.account.address : client.address;
939
+ const unsignedPaymentHeader = preparePaymentHeader3(from, x402Version, paymentRequirements);
940
+ return signPaymentHeader3(client, paymentRequirements, unsignedPaymentHeader);
941
+ }
942
+ async function createPaymentHeader4(client, x402Version, paymentRequirements) {
943
+ const payment = await createPayment3(client, x402Version, paymentRequirements);
944
+ return encodePayment(payment);
945
+ }
946
+
947
+ // src/schemes/exact/evm/index.ts
948
+ async function verify4(client, payload, paymentRequirements) {
949
+ const exactEvmPayload = payload.payload;
950
+ switch (exactEvmPayload.authorizationType) {
951
+ case "eip3009":
952
+ return verify(
953
+ client,
954
+ payload,
955
+ paymentRequirements
956
+ );
957
+ case "permit":
958
+ return verify2(client, payload, paymentRequirements);
959
+ case "permit2":
960
+ return verify3(
961
+ client,
962
+ payload,
963
+ paymentRequirements
964
+ );
965
+ default:
966
+ return {
967
+ isValid: false,
968
+ invalidReason: "unsupported_authorization_type",
969
+ payer: ""
970
+ };
971
+ }
972
+ }
973
+ async function settle4(wallet, paymentPayload, paymentRequirements) {
974
+ const payload = paymentPayload.payload;
975
+ switch (payload.authorizationType) {
976
+ case "eip3009":
977
+ return settle(
978
+ wallet,
979
+ paymentPayload,
980
+ paymentRequirements
981
+ );
982
+ case "permit":
983
+ return settle2(
984
+ wallet,
985
+ paymentPayload,
986
+ paymentRequirements
987
+ );
988
+ case "permit2":
989
+ return settle3(
990
+ wallet,
991
+ paymentPayload,
992
+ paymentRequirements
993
+ );
994
+ default:
995
+ return {
996
+ success: false,
997
+ errorReason: "unsupported_authorization_type",
998
+ transaction: "",
999
+ network: paymentPayload.network,
1000
+ payer: ""
1001
+ };
1002
+ }
1003
+ }
1004
+
1005
+ // src/schemes/exact/svm/index.ts
1006
+ var svm_exports = {};
1007
+ __export(svm_exports, {
1008
+ confirmSignedTransaction: () => confirmSignedTransaction,
1009
+ createAndSignPayment: () => createAndSignPayment,
1010
+ createPaymentHeader: () => createPaymentHeader2,
1011
+ getValidatedTransferCheckedInstruction: () => getValidatedTransferCheckedInstruction,
1012
+ sendAndConfirmSignedTransaction: () => sendAndConfirmSignedTransaction,
1013
+ sendSignedTransaction: () => sendSignedTransaction,
1014
+ settle: () => settle5,
1015
+ transactionIntrospection: () => transactionIntrospection,
1016
+ verify: () => verify5,
1017
+ verifyComputeLimitInstruction: () => verifyComputeLimitInstruction,
1018
+ verifyComputePriceInstruction: () => verifyComputePriceInstruction,
1019
+ verifyCreateATAInstruction: () => verifyCreateATAInstruction,
1020
+ verifySchemesAndNetworks: () => verifySchemesAndNetworks,
1021
+ verifyTransactionInstructions: () => verifyTransactionInstructions,
1022
+ verifyTransferCheckedInstruction: () => verifyTransferCheckedInstruction,
1023
+ verifyTransferInstruction: () => verifyTransferInstruction
1024
+ });
1025
+
1026
+ // src/schemes/exact/svm/facilitator/settle.ts
1027
+ import {
1028
+ assertIsTransactionMessageWithBlockhashLifetime,
1029
+ decompileTransactionMessageFetchingLookupTables,
1030
+ getBase64EncodedWireTransaction,
1031
+ getCompiledTransactionMessageDecoder as getCompiledTransactionMessageDecoder2,
1032
+ getSignatureFromTransaction,
1033
+ isSolanaError,
1034
+ signTransaction,
1035
+ SOLANA_ERROR__BLOCK_HEIGHT_EXCEEDED
1036
+ } from "@solana/kit";
1037
+ import {
1038
+ createBlockHeightExceedencePromiseFactory,
1039
+ waitForRecentTransactionConfirmation,
1040
+ createRecentSignatureConfirmationPromiseFactory
1041
+ } from "@solana/transaction-confirmation";
1042
+
1043
+ // src/schemes/exact/svm/facilitator/verify.ts
1044
+ import {
1045
+ assertIsInstructionWithAccounts,
1046
+ assertIsInstructionWithData,
1047
+ decompileTransactionMessage,
1048
+ fetchEncodedAccounts,
1049
+ getCompiledTransactionMessageDecoder
1050
+ } from "@solana/kit";
1051
+ import {
1052
+ parseSetComputeUnitLimitInstruction,
1053
+ parseSetComputeUnitPriceInstruction,
1054
+ COMPUTE_BUDGET_PROGRAM_ADDRESS
1055
+ } from "@solana-program/compute-budget";
1056
+ import {
1057
+ findAssociatedTokenPda,
1058
+ identifyToken2022Instruction,
1059
+ parseCreateAssociatedTokenInstruction,
1060
+ parseTransferCheckedInstruction as parseTransferCheckedInstruction2022,
1061
+ Token2022Instruction,
1062
+ TOKEN_2022_PROGRAM_ADDRESS
1063
+ } from "@solana-program/token-2022";
1064
+ import {
1065
+ identifyTokenInstruction,
1066
+ parseTransferCheckedInstruction as parseTransferCheckedInstructionToken,
1067
+ TOKEN_PROGRAM_ADDRESS,
1068
+ TokenInstruction
1069
+ } from "@solana-program/token";
1070
+ async function verify5(signer, payload, paymentRequirements, config2) {
1071
+ try {
1072
+ verifySchemesAndNetworks(payload, paymentRequirements);
1073
+ const svmPayload = payload.payload;
1074
+ const decodedTransaction = decodeTransactionFromPayload(svmPayload);
1075
+ const rpc = getRpcClient(paymentRequirements.network, config2?.svmConfig?.rpcUrl);
1076
+ await transactionIntrospection(svmPayload, paymentRequirements, config2);
1077
+ const simulateResult = await signAndSimulateTransaction(signer, decodedTransaction, rpc);
1078
+ if (simulateResult.value?.err) {
1079
+ throw new Error(`invalid_exact_svm_payload_transaction_simulation_failed`);
1080
+ }
1081
+ return {
1082
+ isValid: true,
1083
+ invalidReason: void 0,
1084
+ payer: getTokenPayerFromTransaction(decodedTransaction)
1085
+ };
1086
+ } catch (error) {
1087
+ if (error instanceof Error) {
1088
+ if (ErrorReasons.includes(error.message)) {
1089
+ return {
1090
+ isValid: false,
1091
+ invalidReason: error.message,
1092
+ payer: (() => {
1093
+ try {
1094
+ const tx = decodeTransactionFromPayload(payload.payload);
1095
+ return getTokenPayerFromTransaction(tx);
1096
+ } catch {
1097
+ return void 0;
1098
+ }
1099
+ })()
1100
+ };
1101
+ }
1102
+ }
1103
+ console.error(error);
1104
+ return {
1105
+ isValid: false,
1106
+ invalidReason: "unexpected_verify_error",
1107
+ payer: (() => {
1108
+ try {
1109
+ const tx = decodeTransactionFromPayload(payload.payload);
1110
+ return getTokenPayerFromTransaction(tx);
1111
+ } catch {
1112
+ return void 0;
1113
+ }
1114
+ })()
1115
+ };
1116
+ }
1117
+ }
1118
+ function verifySchemesAndNetworks(payload, paymentRequirements) {
1119
+ if (payload.scheme !== SCHEME || paymentRequirements.scheme !== SCHEME) {
1120
+ throw new Error("unsupported_scheme");
1121
+ }
1122
+ if (payload.network !== paymentRequirements.network || !SupportedSVMNetworks.includes(paymentRequirements.network)) {
1123
+ throw new Error("invalid_network");
1124
+ }
1125
+ }
1126
+ async function transactionIntrospection(svmPayload, paymentRequirements, config2) {
1127
+ const rpc = getRpcClient(paymentRequirements.network, config2?.svmConfig?.rpcUrl);
1128
+ const decodedTransaction = decodeTransactionFromPayload(svmPayload);
1129
+ const compiledTransactionMessage = getCompiledTransactionMessageDecoder().decode(
1130
+ decodedTransaction.messageBytes
1131
+ );
1132
+ const transactionMessage = decompileTransactionMessage(
1133
+ compiledTransactionMessage
1134
+ );
1135
+ await verifyTransactionInstructions(transactionMessage, paymentRequirements, rpc);
1136
+ }
1137
+ async function verifyTransactionInstructions(transactionMessage, paymentRequirements, rpc) {
1138
+ if (transactionMessage.instructions.length !== 3 && transactionMessage.instructions.length !== 4) {
1139
+ throw new Error(`invalid_exact_svm_payload_transaction_instructions_length`);
1140
+ }
1141
+ verifyComputeLimitInstruction(transactionMessage.instructions[0]);
1142
+ verifyComputePriceInstruction(transactionMessage.instructions[1]);
1143
+ if (transactionMessage.instructions.length === 3) {
1144
+ await verifyTransferInstruction(
1145
+ transactionMessage.instructions[2],
1146
+ paymentRequirements,
1147
+ {
1148
+ txHasCreateDestATAInstruction: false
1149
+ },
1150
+ rpc
1151
+ );
1152
+ } else {
1153
+ verifyCreateATAInstruction(transactionMessage.instructions[2], paymentRequirements);
1154
+ await verifyTransferInstruction(
1155
+ transactionMessage.instructions[3],
1156
+ paymentRequirements,
1157
+ {
1158
+ txHasCreateDestATAInstruction: true
1159
+ },
1160
+ rpc
1161
+ );
1162
+ }
1163
+ }
1164
+ function verifyComputeLimitInstruction(instruction) {
1165
+ try {
1166
+ if (instruction.programAddress.toString() !== COMPUTE_BUDGET_PROGRAM_ADDRESS.toString() || instruction.data?.[0] !== 2) {
1167
+ throw new Error(
1168
+ `invalid_exact_svm_payload_transaction_instructions_compute_limit_instruction`
1169
+ );
1170
+ }
1171
+ parseSetComputeUnitLimitInstruction(
1172
+ instruction
1173
+ );
1174
+ } catch (error) {
1175
+ console.error(error);
1176
+ throw new Error(`invalid_exact_svm_payload_transaction_instructions_compute_limit_instruction`);
1177
+ }
1178
+ }
1179
+ function verifyComputePriceInstruction(instruction) {
1180
+ if (instruction.programAddress.toString() !== COMPUTE_BUDGET_PROGRAM_ADDRESS.toString() || instruction.data?.[0] !== 3) {
1181
+ throw new Error(`invalid_exact_svm_payload_transaction_instructions_compute_price_instruction`);
1182
+ }
1183
+ const parsedInstruction = parseSetComputeUnitPriceInstruction(
1184
+ instruction
1185
+ );
1186
+ if (parsedInstruction.data.microLamports > 5 * 1e6) {
1187
+ throw new Error(
1188
+ `invalid_exact_svm_payload_transaction_instructions_compute_price_instruction_too_high`
1189
+ );
1190
+ }
1191
+ }
1192
+ function verifyCreateATAInstruction(instruction, paymentRequirements) {
1193
+ let createATAInstruction;
1194
+ try {
1195
+ assertIsInstructionWithAccounts(instruction);
1196
+ assertIsInstructionWithData(instruction);
1197
+ createATAInstruction = parseCreateAssociatedTokenInstruction({
1198
+ ...instruction,
1199
+ data: new Uint8Array(instruction.data)
1200
+ });
1201
+ } catch (error) {
1202
+ console.error(error);
1203
+ throw new Error(`invalid_exact_svm_payload_transaction_create_ata_instruction`);
1204
+ }
1205
+ if (createATAInstruction.accounts.owner.address !== paymentRequirements.payTo) {
1206
+ throw new Error(`invalid_exact_svm_payload_transaction_create_ata_instruction_incorrect_payee`);
1207
+ }
1208
+ if (createATAInstruction.accounts.mint.address !== paymentRequirements.asset) {
1209
+ throw new Error(`invalid_exact_svm_payload_transaction_create_ata_instruction_incorrect_asset`);
1210
+ }
1211
+ }
1212
+ async function verifyTransferInstruction(instruction, paymentRequirements, { txHasCreateDestATAInstruction }, rpc) {
1213
+ const tokenInstruction = getValidatedTransferCheckedInstruction(instruction);
1214
+ await verifyTransferCheckedInstruction(
1215
+ tokenInstruction,
1216
+ paymentRequirements,
1217
+ {
1218
+ txHasCreateDestATAInstruction
1219
+ },
1220
+ rpc
1221
+ );
1222
+ }
1223
+ async function verifyTransferCheckedInstruction(parsedInstruction, paymentRequirements, { txHasCreateDestATAInstruction }, rpc) {
1224
+ const tokenProgramAddress = parsedInstruction.programAddress.toString() === TOKEN_PROGRAM_ADDRESS.toString() ? TOKEN_PROGRAM_ADDRESS : TOKEN_2022_PROGRAM_ADDRESS;
1225
+ const payToATA = await findAssociatedTokenPda({
1226
+ mint: paymentRequirements.asset,
1227
+ owner: paymentRequirements.payTo,
1228
+ tokenProgram: tokenProgramAddress
1229
+ });
1230
+ if (parsedInstruction.accounts.destination.address !== payToATA[0]) {
1231
+ throw new Error(`invalid_exact_svm_payload_transaction_transfer_to_incorrect_ata`);
1232
+ }
1233
+ const addresses = [parsedInstruction.accounts.source.address, payToATA[0]];
1234
+ const maybeAccounts = await fetchEncodedAccounts(rpc, addresses);
1235
+ const missingAccounts = maybeAccounts.filter((a) => !a.exists);
1236
+ for (const missingAccount of missingAccounts) {
1237
+ if (missingAccount.address === parsedInstruction.accounts.source.address) {
1238
+ throw new Error(`invalid_exact_svm_payload_transaction_sender_ata_not_found`);
1239
+ }
1240
+ if (missingAccount.address === payToATA[0] && !txHasCreateDestATAInstruction) {
1241
+ throw new Error(`invalid_exact_svm_payload_transaction_receiver_ata_not_found`);
1242
+ }
1243
+ }
1244
+ const instructionAmount = parsedInstruction.data.amount;
1245
+ const paymentRequirementsAmount = BigInt(paymentRequirements.maxAmountRequired);
1246
+ if (instructionAmount !== paymentRequirementsAmount) {
1247
+ throw new Error(`invalid_exact_svm_payload_transaction_amount_mismatch`);
1248
+ }
1249
+ }
1250
+ function getValidatedTransferCheckedInstruction(instruction) {
1251
+ try {
1252
+ assertIsInstructionWithData(instruction);
1253
+ assertIsInstructionWithAccounts(instruction);
1254
+ } catch (error) {
1255
+ console.error(error);
1256
+ throw new Error(`invalid_exact_svm_payload_transaction_instructions`);
1257
+ }
1258
+ let tokenInstruction;
1259
+ if (instruction.programAddress.toString() === TOKEN_PROGRAM_ADDRESS.toString()) {
1260
+ const identifiedInstruction = identifyTokenInstruction(instruction);
1261
+ if (identifiedInstruction !== TokenInstruction.TransferChecked) {
1262
+ throw new Error(
1263
+ `invalid_exact_svm_payload_transaction_instruction_not_spl_token_transfer_checked`
1264
+ );
1265
+ }
1266
+ tokenInstruction = parseTransferCheckedInstructionToken({
1267
+ ...instruction,
1268
+ data: new Uint8Array(instruction.data)
1269
+ });
1270
+ } else if (instruction.programAddress.toString() === TOKEN_2022_PROGRAM_ADDRESS.toString()) {
1271
+ const identifiedInstruction = identifyToken2022Instruction(instruction);
1272
+ if (identifiedInstruction !== Token2022Instruction.TransferChecked) {
1273
+ throw new Error(
1274
+ `invalid_exact_svm_payload_transaction_instruction_not_token_2022_transfer_checked`
1275
+ );
1276
+ }
1277
+ tokenInstruction = parseTransferCheckedInstruction2022({
1278
+ ...instruction,
1279
+ data: new Uint8Array(instruction.data)
1280
+ });
1281
+ } else {
1282
+ throw new Error(`invalid_exact_svm_payload_transaction_not_a_transfer_instruction`);
1283
+ }
1284
+ return tokenInstruction;
1285
+ }
1286
+
1287
+ // src/schemes/exact/svm/facilitator/settle.ts
1288
+ async function settle5(signer, payload, paymentRequirements, config2) {
1289
+ const verifyResponse = await verify5(signer, payload, paymentRequirements, config2);
1290
+ if (!verifyResponse.isValid) {
1291
+ return {
1292
+ success: false,
1293
+ errorReason: verifyResponse.invalidReason,
1294
+ network: payload.network,
1295
+ transaction: ""
1296
+ };
1297
+ }
1298
+ const svmPayload = payload.payload;
1299
+ const decodedTransaction = decodeTransactionFromPayload(svmPayload);
1300
+ const signedTransaction = await signTransaction([signer.keyPair], decodedTransaction);
1301
+ const payer = getTokenPayerFromTransaction(decodedTransaction);
1302
+ const rpc = getRpcClient(paymentRequirements.network, config2?.svmConfig?.rpcUrl);
1303
+ const rpcSubscriptions = getRpcSubscriptions(
1304
+ paymentRequirements.network,
1305
+ config2?.svmConfig?.rpcUrl
1306
+ );
1307
+ try {
1308
+ const { success, errorReason, signature } = await sendAndConfirmSignedTransaction(
1309
+ signedTransaction,
1310
+ rpc,
1311
+ rpcSubscriptions
1312
+ );
1313
+ return {
1314
+ success,
1315
+ errorReason,
1316
+ payer,
1317
+ transaction: signature,
1318
+ network: payload.network
1319
+ };
1320
+ } catch (error) {
1321
+ console.error("Unexpected error during transaction settlement:", error);
1322
+ return {
1323
+ success: false,
1324
+ errorReason: "unexpected_settle_error",
1325
+ network: payload.network,
1326
+ transaction: getSignatureFromTransaction(signedTransaction),
1327
+ payer
1328
+ };
1329
+ }
1330
+ }
1331
+ async function sendSignedTransaction(signedTransaction, rpc, sendTxConfig = {
1332
+ skipPreflight: true,
1333
+ encoding: "base64"
1334
+ }) {
1335
+ const base64EncodedTransaction = getBase64EncodedWireTransaction(signedTransaction);
1336
+ return await rpc.sendTransaction(base64EncodedTransaction, sendTxConfig).send();
1337
+ }
1338
+ async function confirmSignedTransaction(signedTransaction, rpc, rpcSubscriptions) {
1339
+ const signature = getSignatureFromTransaction(signedTransaction);
1340
+ const abortController = new AbortController();
1341
+ const timeout = setTimeout(() => {
1342
+ abortController.abort("Transaction confirmation timed out after 60 seconds");
1343
+ }, 6e4);
1344
+ try {
1345
+ const compiledTransactionMessage = getCompiledTransactionMessageDecoder2().decode(
1346
+ signedTransaction.messageBytes
1347
+ );
1348
+ const decompiledTransactionMessage = await decompileTransactionMessageFetchingLookupTables(
1349
+ compiledTransactionMessage,
1350
+ rpc
1351
+ );
1352
+ assertIsTransactionMessageWithBlockhashLifetime(decompiledTransactionMessage);
1353
+ const signedTransactionWithBlockhashLifetime = {
1354
+ ...signedTransaction,
1355
+ lifetimeConstraint: decompiledTransactionMessage.lifetimeConstraint
1356
+ };
1357
+ const commitment = "confirmed";
1358
+ const getRecentSignatureConfirmationPromise = createRecentSignatureConfirmationPromiseFactory({
1359
+ rpc,
1360
+ rpcSubscriptions
1361
+ });
1362
+ const getBlockHeightExceedencePromise = createBlockHeightExceedencePromiseFactory({
1363
+ rpc,
1364
+ rpcSubscriptions
1365
+ });
1366
+ const config2 = {
1367
+ abortSignal: abortController.signal,
1368
+ commitment,
1369
+ getBlockHeightExceedencePromise,
1370
+ getRecentSignatureConfirmationPromise
1371
+ };
1372
+ await waitForRecentTransactionConfirmation({
1373
+ ...config2,
1374
+ transaction: signedTransactionWithBlockhashLifetime
1375
+ });
1376
+ return {
1377
+ success: true,
1378
+ signature
1379
+ };
1380
+ } catch (error) {
1381
+ console.error(error);
1382
+ if (isSolanaError(error, SOLANA_ERROR__BLOCK_HEIGHT_EXCEEDED)) {
1383
+ return {
1384
+ success: false,
1385
+ errorReason: "settle_exact_svm_block_height_exceeded",
1386
+ signature
1387
+ };
1388
+ } else if (error instanceof DOMException && error.name === "AbortError") {
1389
+ return {
1390
+ success: false,
1391
+ errorReason: "settle_exact_svm_transaction_confirmation_timed_out",
1392
+ signature
1393
+ };
1394
+ } else {
1395
+ throw error;
1396
+ }
1397
+ } finally {
1398
+ clearTimeout(timeout);
1399
+ }
1400
+ }
1401
+ async function sendAndConfirmSignedTransaction(signedTransaction, rpc, rpcSubscriptions) {
1402
+ await sendSignedTransaction(signedTransaction, rpc);
1403
+ return await confirmSignedTransaction(signedTransaction, rpc, rpcSubscriptions);
1404
+ }
1405
+
1406
+ // src/schemes/exact/index.ts
1407
+ var SCHEME = "exact";
1408
+
1409
+ export {
1410
+ verify5 as verify,
1411
+ settle5 as settle,
1412
+ exact_exports,
1413
+ verify4 as verify2,
1414
+ settle4 as settle2
1415
+ };
1416
+ //# sourceMappingURL=chunk-57UEJN5U.mjs.map