@dexterai/x402 1.7.2 → 1.8.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.
@@ -1,34 +1,4 @@
1
- var __defProp = Object.defineProperty;
2
- var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
3
- var __getOwnPropNames = Object.getOwnPropertyNames;
4
- var __hasOwnProp = Object.prototype.hasOwnProperty;
5
- var __esm = (fn, res) => function __init() {
6
- return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
7
- };
8
- var __export = (target, all) => {
9
- for (var name in all)
10
- __defProp(target, name, { get: all[name], enumerable: true });
11
- };
12
- var __copyProps = (to, from, except, desc) => {
13
- if (from && typeof from === "object" || typeof from === "function") {
14
- for (let key of __getOwnPropNames(from))
15
- if (!__hasOwnProp.call(to, key) && key !== except)
16
- __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
- }
18
- return to;
19
- };
20
- var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
21
-
22
1
  // src/adapters/solana.ts
23
- var solana_exports = {};
24
- __export(solana_exports, {
25
- SOLANA_DEVNET: () => SOLANA_DEVNET,
26
- SOLANA_MAINNET: () => SOLANA_MAINNET,
27
- SOLANA_TESTNET: () => SOLANA_TESTNET,
28
- SolanaAdapter: () => SolanaAdapter,
29
- createSolanaAdapter: () => createSolanaAdapter,
30
- isSolanaWallet: () => isSolanaWallet
31
- });
32
2
  import {
33
3
  PublicKey,
34
4
  Connection,
@@ -44,415 +14,409 @@ import {
44
14
  TOKEN_PROGRAM_ID,
45
15
  TOKEN_2022_PROGRAM_ID
46
16
  } from "@solana/spl-token";
17
+ var SOLANA_MAINNET = "solana:5eykt4UsFv8P8NJdTREpY1vzqKqZKvdp";
18
+ var SOLANA_DEVNET = "solana:EtWTRABZaYq6iMfeYKouRu166VU2xqa1";
19
+ var SOLANA_TESTNET = "solana:4uhcVJyU9pJkvQyS88uRDiswHXSCkY3z";
20
+ var DEFAULT_RPC_URLS = {
21
+ [SOLANA_MAINNET]: "https://api.dexter.cash/api/solana/rpc",
22
+ [SOLANA_DEVNET]: "https://api.devnet.solana.com",
23
+ [SOLANA_TESTNET]: "https://api.testnet.solana.com"
24
+ };
25
+ var DEFAULT_COMPUTE_UNIT_LIMIT = 12e3;
26
+ var DEFAULT_COMPUTE_UNIT_PRICE_MICROLAMPORTS = 1;
47
27
  function isSolanaWallet(wallet) {
48
28
  if (!wallet || typeof wallet !== "object") return false;
49
29
  const w = wallet;
50
30
  return "publicKey" in w && "signTransaction" in w && typeof w.signTransaction === "function";
51
31
  }
52
- function createSolanaAdapter(config) {
53
- return new SolanaAdapter(config);
54
- }
55
- var SOLANA_MAINNET, SOLANA_DEVNET, SOLANA_TESTNET, DEFAULT_RPC_URLS, DEFAULT_COMPUTE_UNIT_LIMIT, DEFAULT_COMPUTE_UNIT_PRICE_MICROLAMPORTS, SolanaAdapter;
56
- var init_solana = __esm({
57
- "src/adapters/solana.ts"() {
58
- "use strict";
59
- SOLANA_MAINNET = "solana:5eykt4UsFv8P8NJdTREpY1vzqKqZKvdp";
60
- SOLANA_DEVNET = "solana:EtWTRABZaYq6iMfeYKouRu166VU2xqa1";
61
- SOLANA_TESTNET = "solana:4uhcVJyU9pJkvQyS88uRDiswHXSCkY3z";
62
- DEFAULT_RPC_URLS = {
63
- [SOLANA_MAINNET]: "https://api.dexter.cash/api/solana/rpc",
64
- [SOLANA_DEVNET]: "https://api.devnet.solana.com",
65
- [SOLANA_TESTNET]: "https://api.testnet.solana.com"
32
+ var SolanaAdapter = class {
33
+ name = "Solana";
34
+ networks = [SOLANA_MAINNET, SOLANA_DEVNET, SOLANA_TESTNET];
35
+ config;
36
+ log;
37
+ constructor(config = {}) {
38
+ this.config = config;
39
+ this.log = config.verbose ? console.log.bind(console, "[x402:solana]") : () => {
66
40
  };
67
- DEFAULT_COMPUTE_UNIT_LIMIT = 12e3;
68
- DEFAULT_COMPUTE_UNIT_PRICE_MICROLAMPORTS = 1;
69
- SolanaAdapter = class {
70
- name = "Solana";
71
- networks = [SOLANA_MAINNET, SOLANA_DEVNET, SOLANA_TESTNET];
72
- config;
73
- log;
74
- constructor(config = {}) {
75
- this.config = config;
76
- this.log = config.verbose ? console.log.bind(console, "[x402:solana]") : () => {
77
- };
78
- }
79
- canHandle(network) {
80
- if (this.networks.includes(network)) return true;
81
- if (network === "solana") return true;
82
- if (network === "solana-devnet") return true;
83
- if (network === "solana-testnet") return true;
84
- if (network.startsWith("solana:")) return true;
85
- return false;
86
- }
87
- getDefaultRpcUrl(network) {
88
- if (this.config.rpcUrls?.[network]) {
89
- return this.config.rpcUrls[network];
90
- }
91
- if (DEFAULT_RPC_URLS[network]) {
92
- return DEFAULT_RPC_URLS[network];
93
- }
94
- if (network === "solana") return DEFAULT_RPC_URLS[SOLANA_MAINNET];
95
- if (network === "solana-devnet") return DEFAULT_RPC_URLS[SOLANA_DEVNET];
96
- if (network === "solana-testnet") return DEFAULT_RPC_URLS[SOLANA_TESTNET];
97
- return DEFAULT_RPC_URLS[SOLANA_MAINNET];
98
- }
99
- getAddress(wallet) {
100
- if (!isSolanaWallet(wallet)) return null;
101
- return wallet.publicKey?.toBase58() ?? null;
102
- }
103
- isConnected(wallet) {
104
- if (!isSolanaWallet(wallet)) return false;
105
- return wallet.publicKey !== null;
106
- }
107
- async getBalance(accept, wallet, rpcUrl) {
108
- if (!isSolanaWallet(wallet) || !wallet.publicKey) {
109
- return 0;
110
- }
111
- const url = rpcUrl || this.getDefaultRpcUrl(accept.network);
112
- const connection = new Connection(url, "confirmed");
113
- const userPubkey = new PublicKey(wallet.publicKey.toBase58());
114
- const mintPubkey = new PublicKey(accept.asset);
115
- try {
116
- const mintInfo = await connection.getAccountInfo(mintPubkey, "confirmed");
117
- const programId = mintInfo?.owner.toBase58() === TOKEN_2022_PROGRAM_ID.toBase58() ? TOKEN_2022_PROGRAM_ID : TOKEN_PROGRAM_ID;
118
- const ata = await getAssociatedTokenAddress(
119
- mintPubkey,
120
- userPubkey,
121
- false,
122
- programId
123
- );
124
- const account = await getAccount(connection, ata, void 0, programId);
125
- const decimals = accept.extra?.decimals ?? 6;
126
- return Number(account.amount) / Math.pow(10, decimals);
127
- } catch {
128
- return 0;
129
- }
130
- }
131
- async buildTransaction(accept, wallet, rpcUrl) {
132
- if (!isSolanaWallet(wallet)) {
133
- throw new Error("Invalid Solana wallet");
134
- }
135
- if (!wallet.publicKey) {
136
- throw new Error("Wallet not connected");
137
- }
138
- const url = rpcUrl || this.getDefaultRpcUrl(accept.network);
139
- const connection = new Connection(url, "confirmed");
140
- const userPubkey = new PublicKey(wallet.publicKey.toBase58());
141
- const { payTo, asset, extra } = accept;
142
- const amount = accept.amount || accept.maxAmountRequired;
143
- if (!amount) {
144
- throw new Error("Missing amount in payment requirements");
145
- }
146
- if (!extra?.feePayer) {
147
- throw new Error("Missing feePayer in payment requirements");
148
- }
149
- const feePayerPubkey = new PublicKey(extra.feePayer);
150
- const mintPubkey = new PublicKey(asset);
151
- const destinationPubkey = new PublicKey(payTo);
152
- this.log("Building transaction:", {
153
- from: userPubkey.toBase58(),
154
- to: payTo,
155
- amount,
156
- asset,
157
- feePayer: extra.feePayer
158
- });
159
- const instructions = [];
160
- instructions.push(
161
- ComputeBudgetProgram.setComputeUnitLimit({
162
- units: DEFAULT_COMPUTE_UNIT_LIMIT
163
- })
164
- );
165
- instructions.push(
166
- ComputeBudgetProgram.setComputeUnitPrice({
167
- microLamports: DEFAULT_COMPUTE_UNIT_PRICE_MICROLAMPORTS
168
- })
169
- );
170
- const mintInfo = await connection.getAccountInfo(mintPubkey, "confirmed");
171
- if (!mintInfo) {
172
- throw new Error(`Token mint ${asset} not found`);
173
- }
174
- const programId = mintInfo.owner.toBase58() === TOKEN_2022_PROGRAM_ID.toBase58() ? TOKEN_2022_PROGRAM_ID : TOKEN_PROGRAM_ID;
175
- const mint = await getMint(connection, mintPubkey, void 0, programId);
176
- if (typeof extra?.decimals === "number" && mint.decimals !== extra.decimals) {
177
- this.log(
178
- `Decimals mismatch: requirements say ${extra.decimals}, mint says ${mint.decimals}`
179
- );
180
- }
181
- const sourceAta = await getAssociatedTokenAddress(
182
- mintPubkey,
183
- userPubkey,
184
- false,
185
- programId
186
- );
187
- const destinationAta = await getAssociatedTokenAddress(
188
- mintPubkey,
189
- destinationPubkey,
190
- false,
191
- programId
192
- );
193
- const sourceAtaInfo = await connection.getAccountInfo(sourceAta, "confirmed");
194
- if (!sourceAtaInfo) {
195
- throw new Error(
196
- `No token account found for ${asset}. Please ensure you have USDC in your wallet.`
197
- );
198
- }
199
- const destAtaInfo = await connection.getAccountInfo(destinationAta, "confirmed");
200
- if (!destAtaInfo) {
201
- throw new Error(
202
- `Seller token account not found. The seller (${payTo}) must have a USDC account.`
203
- );
204
- }
205
- const amountBigInt = BigInt(amount);
206
- instructions.push(
207
- createTransferCheckedInstruction(
208
- sourceAta,
209
- mintPubkey,
210
- destinationAta,
211
- userPubkey,
212
- amountBigInt,
213
- mint.decimals,
214
- [],
215
- programId
216
- )
217
- );
218
- const { blockhash } = await connection.getLatestBlockhash("confirmed");
219
- const message = new TransactionMessage({
220
- payerKey: feePayerPubkey,
221
- recentBlockhash: blockhash,
222
- instructions
223
- }).compileToV0Message();
224
- const transaction = new VersionedTransaction(message);
225
- const signedTx = await wallet.signTransaction(transaction);
226
- this.log("Transaction signed successfully");
227
- return {
228
- serialized: Buffer.from(signedTx.serialize()).toString("base64")
229
- };
230
- }
41
+ }
42
+ canHandle(network) {
43
+ if (this.networks.includes(network)) return true;
44
+ if (network === "solana") return true;
45
+ if (network === "solana-devnet") return true;
46
+ if (network === "solana-testnet") return true;
47
+ if (network.startsWith("solana:")) return true;
48
+ return false;
49
+ }
50
+ getDefaultRpcUrl(network) {
51
+ if (this.config.rpcUrls?.[network]) {
52
+ return this.config.rpcUrls[network];
53
+ }
54
+ if (DEFAULT_RPC_URLS[network]) {
55
+ return DEFAULT_RPC_URLS[network];
56
+ }
57
+ if (network === "solana") return DEFAULT_RPC_URLS[SOLANA_MAINNET];
58
+ if (network === "solana-devnet") return DEFAULT_RPC_URLS[SOLANA_DEVNET];
59
+ if (network === "solana-testnet") return DEFAULT_RPC_URLS[SOLANA_TESTNET];
60
+ return DEFAULT_RPC_URLS[SOLANA_MAINNET];
61
+ }
62
+ getAddress(wallet) {
63
+ if (!isSolanaWallet(wallet)) return null;
64
+ return wallet.publicKey?.toBase58() ?? null;
65
+ }
66
+ isConnected(wallet) {
67
+ if (!isSolanaWallet(wallet)) return false;
68
+ return wallet.publicKey !== null;
69
+ }
70
+ async getBalance(accept, wallet, rpcUrl) {
71
+ if (!isSolanaWallet(wallet) || !wallet.publicKey) {
72
+ return 0;
73
+ }
74
+ const url = rpcUrl || this.getDefaultRpcUrl(accept.network);
75
+ const connection = new Connection(url, "confirmed");
76
+ const userPubkey = new PublicKey(wallet.publicKey.toBase58());
77
+ const mintPubkey = new PublicKey(accept.asset);
78
+ try {
79
+ const mintInfo = await connection.getAccountInfo(mintPubkey, "confirmed");
80
+ const programId = mintInfo?.owner.toBase58() === TOKEN_2022_PROGRAM_ID.toBase58() ? TOKEN_2022_PROGRAM_ID : TOKEN_PROGRAM_ID;
81
+ const ata = await getAssociatedTokenAddress(
82
+ mintPubkey,
83
+ userPubkey,
84
+ false,
85
+ programId
86
+ );
87
+ const account = await getAccount(connection, ata, void 0, programId);
88
+ const decimals = accept.extra?.decimals ?? 6;
89
+ return Number(account.amount) / Math.pow(10, decimals);
90
+ } catch {
91
+ return 0;
92
+ }
93
+ }
94
+ async buildTransaction(accept, wallet, rpcUrl) {
95
+ if (!isSolanaWallet(wallet)) {
96
+ throw new Error("Invalid Solana wallet");
97
+ }
98
+ if (!wallet.publicKey) {
99
+ throw new Error("Wallet not connected");
100
+ }
101
+ const url = rpcUrl || this.getDefaultRpcUrl(accept.network);
102
+ const connection = new Connection(url, "confirmed");
103
+ const userPubkey = new PublicKey(wallet.publicKey.toBase58());
104
+ const { payTo, asset, extra } = accept;
105
+ const amount = accept.amount || accept.maxAmountRequired;
106
+ if (!amount) {
107
+ throw new Error("Missing amount in payment requirements");
108
+ }
109
+ if (!extra?.feePayer) {
110
+ throw new Error("Missing feePayer in payment requirements");
111
+ }
112
+ const feePayerPubkey = new PublicKey(extra.feePayer);
113
+ const mintPubkey = new PublicKey(asset);
114
+ const destinationPubkey = new PublicKey(payTo);
115
+ this.log("Building transaction:", {
116
+ from: userPubkey.toBase58(),
117
+ to: payTo,
118
+ amount,
119
+ asset,
120
+ feePayer: extra.feePayer
121
+ });
122
+ const instructions = [];
123
+ instructions.push(
124
+ ComputeBudgetProgram.setComputeUnitLimit({
125
+ units: DEFAULT_COMPUTE_UNIT_LIMIT
126
+ })
127
+ );
128
+ instructions.push(
129
+ ComputeBudgetProgram.setComputeUnitPrice({
130
+ microLamports: DEFAULT_COMPUTE_UNIT_PRICE_MICROLAMPORTS
131
+ })
132
+ );
133
+ const mintInfo = await connection.getAccountInfo(mintPubkey, "confirmed");
134
+ if (!mintInfo) {
135
+ throw new Error(`Token mint ${asset} not found`);
136
+ }
137
+ const programId = mintInfo.owner.toBase58() === TOKEN_2022_PROGRAM_ID.toBase58() ? TOKEN_2022_PROGRAM_ID : TOKEN_PROGRAM_ID;
138
+ const mint = await getMint(connection, mintPubkey, void 0, programId);
139
+ if (typeof extra?.decimals === "number" && mint.decimals !== extra.decimals) {
140
+ this.log(
141
+ `Decimals mismatch: requirements say ${extra.decimals}, mint says ${mint.decimals}`
142
+ );
143
+ }
144
+ const sourceAta = await getAssociatedTokenAddress(
145
+ mintPubkey,
146
+ userPubkey,
147
+ false,
148
+ programId
149
+ );
150
+ const destinationAta = await getAssociatedTokenAddress(
151
+ mintPubkey,
152
+ destinationPubkey,
153
+ false,
154
+ programId
155
+ );
156
+ const sourceAtaInfo = await connection.getAccountInfo(sourceAta, "confirmed");
157
+ if (!sourceAtaInfo) {
158
+ throw new Error(
159
+ `No token account found for ${asset}. Please ensure you have USDC in your wallet.`
160
+ );
161
+ }
162
+ const destAtaInfo = await connection.getAccountInfo(destinationAta, "confirmed");
163
+ if (!destAtaInfo) {
164
+ throw new Error(
165
+ `Seller token account not found. The seller (${payTo}) must have a USDC account.`
166
+ );
167
+ }
168
+ const amountBigInt = BigInt(amount);
169
+ instructions.push(
170
+ createTransferCheckedInstruction(
171
+ sourceAta,
172
+ mintPubkey,
173
+ destinationAta,
174
+ userPubkey,
175
+ amountBigInt,
176
+ mint.decimals,
177
+ [],
178
+ programId
179
+ )
180
+ );
181
+ const { blockhash } = await connection.getLatestBlockhash("confirmed");
182
+ const message = new TransactionMessage({
183
+ payerKey: feePayerPubkey,
184
+ recentBlockhash: blockhash,
185
+ instructions
186
+ }).compileToV0Message();
187
+ const transaction = new VersionedTransaction(message);
188
+ const signedTx = await wallet.signTransaction(transaction);
189
+ this.log("Transaction signed successfully");
190
+ return {
191
+ serialized: Buffer.from(signedTx.serialize()).toString("base64")
231
192
  };
232
193
  }
233
- });
194
+ };
195
+ function createSolanaAdapter(config) {
196
+ return new SolanaAdapter(config);
197
+ }
234
198
 
235
199
  // src/adapters/evm.ts
236
- var evm_exports = {};
237
- __export(evm_exports, {
238
- ARBITRUM_ONE: () => ARBITRUM_ONE,
239
- BASE_MAINNET: () => BASE_MAINNET,
240
- BASE_SEPOLIA: () => BASE_SEPOLIA,
241
- ETHEREUM_MAINNET: () => ETHEREUM_MAINNET,
242
- EvmAdapter: () => EvmAdapter,
243
- USDC_ADDRESSES: () => USDC_ADDRESSES,
244
- createEvmAdapter: () => createEvmAdapter,
245
- isEvmWallet: () => isEvmWallet
246
- });
200
+ var BASE_MAINNET = "eip155:8453";
201
+ var BASE_SEPOLIA = "eip155:84532";
202
+ var ARBITRUM_ONE = "eip155:42161";
203
+ var POLYGON = "eip155:137";
204
+ var OPTIMISM = "eip155:10";
205
+ var AVALANCHE = "eip155:43114";
206
+ var SKALE_BASE = "eip155:1187947933";
207
+ var SKALE_BASE_SEPOLIA = "eip155:324705682";
208
+ var ETHEREUM_MAINNET = "eip155:1";
209
+ var CHAIN_IDS = {
210
+ [BASE_MAINNET]: 8453,
211
+ [BASE_SEPOLIA]: 84532,
212
+ [ARBITRUM_ONE]: 42161,
213
+ [POLYGON]: 137,
214
+ [OPTIMISM]: 10,
215
+ [AVALANCHE]: 43114,
216
+ [SKALE_BASE]: 1187947933,
217
+ [SKALE_BASE_SEPOLIA]: 324705682,
218
+ [ETHEREUM_MAINNET]: 1
219
+ };
220
+ var DEFAULT_RPC_URLS2 = {
221
+ [BASE_MAINNET]: "https://api.dexter.cash/api/base/rpc",
222
+ [BASE_SEPOLIA]: "https://sepolia.base.org",
223
+ [ARBITRUM_ONE]: "https://arb1.arbitrum.io/rpc",
224
+ [POLYGON]: "https://polygon-rpc.com",
225
+ [OPTIMISM]: "https://mainnet.optimism.io",
226
+ [AVALANCHE]: "https://api.avax.network/ext/bc/C/rpc",
227
+ [SKALE_BASE]: "https://skale-base.skalenodes.com/v1/base",
228
+ [SKALE_BASE_SEPOLIA]: "https://base-sepolia-testnet.skalenodes.com/v1/jubilant-horrible-ancha",
229
+ [ETHEREUM_MAINNET]: "https://eth.llamarpc.com"
230
+ };
231
+ var USDC_ADDRESSES = {
232
+ [BASE_MAINNET]: "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913",
233
+ [BASE_SEPOLIA]: "0x036CbD53842c5426634e7929541eC2318f3dCF7e",
234
+ [ARBITRUM_ONE]: "0xaf88d065e77c8cC2239327C5EDb3A432268e5831",
235
+ [POLYGON]: "0x3c499c542cEF5E3811e1192ce70d8cC03d5c3359",
236
+ [OPTIMISM]: "0x0b2C639c533813f4Aa9D7837CAf62653d097Ff85",
237
+ [AVALANCHE]: "0xB97EF9Ef8734C71904D8002F8b6Bc66Dd9c48a6E",
238
+ [SKALE_BASE]: "0x85889c8c714505E0c94b30fcfcF64fE3Ac8FCb20",
239
+ [SKALE_BASE_SEPOLIA]: "0x2e08028E3C4c2356572E096d8EF835cD5C6030bD",
240
+ [ETHEREUM_MAINNET]: "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48"
241
+ };
247
242
  function isEvmWallet(wallet) {
248
243
  if (!wallet || typeof wallet !== "object") return false;
249
244
  const w = wallet;
250
245
  return "address" in w && typeof w.address === "string" && w.address.startsWith("0x");
251
246
  }
252
- function createEvmAdapter(config) {
253
- return new EvmAdapter(config);
254
- }
255
- var BASE_MAINNET, BASE_SEPOLIA, ETHEREUM_MAINNET, ARBITRUM_ONE, CHAIN_IDS, DEFAULT_RPC_URLS2, USDC_ADDRESSES, EvmAdapter;
256
- var init_evm = __esm({
257
- "src/adapters/evm.ts"() {
258
- "use strict";
259
- BASE_MAINNET = "eip155:8453";
260
- BASE_SEPOLIA = "eip155:84532";
261
- ETHEREUM_MAINNET = "eip155:1";
262
- ARBITRUM_ONE = "eip155:42161";
263
- CHAIN_IDS = {
264
- [BASE_MAINNET]: 8453,
265
- [BASE_SEPOLIA]: 84532,
266
- [ETHEREUM_MAINNET]: 1,
267
- [ARBITRUM_ONE]: 42161
268
- };
269
- DEFAULT_RPC_URLS2 = {
270
- [BASE_MAINNET]: "https://api.dexter.cash/api/base/rpc",
271
- [BASE_SEPOLIA]: "https://sepolia.base.org",
272
- [ETHEREUM_MAINNET]: "https://eth.llamarpc.com",
273
- [ARBITRUM_ONE]: "https://arb1.arbitrum.io/rpc"
274
- };
275
- USDC_ADDRESSES = {
276
- [BASE_MAINNET]: "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913",
277
- [ETHEREUM_MAINNET]: "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48",
278
- [ARBITRUM_ONE]: "0xaf88d065e77c8cC2239327C5EDb3A432268e5831"
247
+ var EvmAdapter = class {
248
+ name = "EVM";
249
+ networks = [BASE_MAINNET, BASE_SEPOLIA, ETHEREUM_MAINNET, ARBITRUM_ONE];
250
+ config;
251
+ log;
252
+ constructor(config = {}) {
253
+ this.config = config;
254
+ this.log = config.verbose ? console.log.bind(console, "[x402:evm]") : () => {
279
255
  };
280
- EvmAdapter = class {
281
- name = "EVM";
282
- networks = [BASE_MAINNET, BASE_SEPOLIA, ETHEREUM_MAINNET, ARBITRUM_ONE];
283
- config;
284
- log;
285
- constructor(config = {}) {
286
- this.config = config;
287
- this.log = config.verbose ? console.log.bind(console, "[x402:evm]") : () => {
288
- };
289
- }
290
- canHandle(network) {
291
- if (this.networks.includes(network)) return true;
292
- if (network === "base") return true;
293
- if (network === "ethereum") return true;
294
- if (network === "arbitrum") return true;
295
- if (network.startsWith("eip155:")) return true;
296
- return false;
297
- }
298
- getDefaultRpcUrl(network) {
299
- if (this.config.rpcUrls?.[network]) {
300
- return this.config.rpcUrls[network];
301
- }
302
- if (DEFAULT_RPC_URLS2[network]) {
303
- return DEFAULT_RPC_URLS2[network];
304
- }
305
- if (network === "base") return DEFAULT_RPC_URLS2[BASE_MAINNET];
306
- if (network === "ethereum") return DEFAULT_RPC_URLS2[ETHEREUM_MAINNET];
307
- if (network === "arbitrum") return DEFAULT_RPC_URLS2[ARBITRUM_ONE];
308
- return DEFAULT_RPC_URLS2[BASE_MAINNET];
309
- }
310
- getAddress(wallet) {
311
- if (!isEvmWallet(wallet)) return null;
312
- return wallet.address;
313
- }
314
- isConnected(wallet) {
315
- if (!isEvmWallet(wallet)) return false;
316
- return !!wallet.address;
317
- }
318
- getChainId(network) {
319
- if (CHAIN_IDS[network]) return CHAIN_IDS[network];
320
- if (network.startsWith("eip155:")) {
321
- const chainIdStr = network.split(":")[1];
322
- return parseInt(chainIdStr, 10);
323
- }
324
- if (network === "base") return 8453;
325
- if (network === "ethereum") return 1;
326
- if (network === "arbitrum") return 42161;
327
- return 8453;
328
- }
329
- async getBalance(accept, wallet, rpcUrl) {
330
- if (!isEvmWallet(wallet) || !wallet.address) {
331
- return 0;
332
- }
333
- const url = rpcUrl || this.getDefaultRpcUrl(accept.network);
334
- try {
335
- const data = this.encodeBalanceOf(wallet.address);
336
- const response = await fetch(url, {
337
- method: "POST",
338
- headers: { "Content-Type": "application/json" },
339
- body: JSON.stringify({
340
- jsonrpc: "2.0",
341
- id: 1,
342
- method: "eth_call",
343
- params: [
344
- {
345
- to: accept.asset,
346
- data
347
- },
348
- "latest"
349
- ]
350
- })
351
- });
352
- const result = await response.json();
353
- if (result.error || !result.result) {
354
- return 0;
355
- }
356
- const balance = BigInt(result.result);
357
- const decimals = accept.extra?.decimals ?? 6;
358
- return Number(balance) / Math.pow(10, decimals);
359
- } catch {
360
- return 0;
361
- }
362
- }
363
- encodeBalanceOf(address) {
364
- const selector = "0x70a08231";
365
- const paddedAddress = address.slice(2).toLowerCase().padStart(64, "0");
366
- return selector + paddedAddress;
367
- }
368
- async buildTransaction(accept, wallet, _rpcUrl) {
369
- if (!isEvmWallet(wallet)) {
370
- throw new Error("Invalid EVM wallet");
371
- }
372
- if (!wallet.address) {
373
- throw new Error("Wallet not connected");
374
- }
375
- const { payTo, asset, extra } = accept;
376
- const amount = accept.amount || accept.maxAmountRequired;
377
- if (!amount) {
378
- throw new Error("Missing amount in payment requirements");
379
- }
380
- this.log("Building EVM transaction:", {
381
- from: wallet.address,
382
- to: payTo,
383
- amount,
384
- asset,
385
- network: accept.network
386
- });
387
- const chainId = this.getChainId(accept.network);
388
- const domain = {
389
- name: extra?.name ?? "USD Coin",
390
- version: extra?.version ?? "2",
391
- chainId: BigInt(chainId),
392
- verifyingContract: asset
393
- };
394
- const types = {
395
- TransferWithAuthorization: [
396
- { name: "from", type: "address" },
397
- { name: "to", type: "address" },
398
- { name: "value", type: "uint256" },
399
- { name: "validAfter", type: "uint256" },
400
- { name: "validBefore", type: "uint256" },
401
- { name: "nonce", type: "bytes32" }
256
+ }
257
+ canHandle(network) {
258
+ if (this.networks.includes(network)) return true;
259
+ if (network === "base") return true;
260
+ if (network === "ethereum") return true;
261
+ if (network === "arbitrum") return true;
262
+ if (network.startsWith("eip155:")) return true;
263
+ return false;
264
+ }
265
+ getDefaultRpcUrl(network) {
266
+ if (this.config.rpcUrls?.[network]) {
267
+ return this.config.rpcUrls[network];
268
+ }
269
+ if (DEFAULT_RPC_URLS2[network]) {
270
+ return DEFAULT_RPC_URLS2[network];
271
+ }
272
+ if (network === "base") return DEFAULT_RPC_URLS2[BASE_MAINNET];
273
+ if (network === "ethereum") return DEFAULT_RPC_URLS2[ETHEREUM_MAINNET];
274
+ if (network === "arbitrum") return DEFAULT_RPC_URLS2[ARBITRUM_ONE];
275
+ return DEFAULT_RPC_URLS2[BASE_MAINNET];
276
+ }
277
+ getAddress(wallet) {
278
+ if (!isEvmWallet(wallet)) return null;
279
+ return wallet.address;
280
+ }
281
+ isConnected(wallet) {
282
+ if (!isEvmWallet(wallet)) return false;
283
+ return !!wallet.address;
284
+ }
285
+ getChainId(network) {
286
+ if (CHAIN_IDS[network]) return CHAIN_IDS[network];
287
+ if (network.startsWith("eip155:")) {
288
+ const chainIdStr = network.split(":")[1];
289
+ return parseInt(chainIdStr, 10);
290
+ }
291
+ if (network === "base") return 8453;
292
+ if (network === "ethereum") return 1;
293
+ if (network === "arbitrum") return 42161;
294
+ return 8453;
295
+ }
296
+ async getBalance(accept, wallet, rpcUrl) {
297
+ if (!isEvmWallet(wallet) || !wallet.address) {
298
+ return 0;
299
+ }
300
+ const url = rpcUrl || this.getDefaultRpcUrl(accept.network);
301
+ try {
302
+ const data = this.encodeBalanceOf(wallet.address);
303
+ const response = await fetch(url, {
304
+ method: "POST",
305
+ headers: { "Content-Type": "application/json" },
306
+ body: JSON.stringify({
307
+ jsonrpc: "2.0",
308
+ id: 1,
309
+ method: "eth_call",
310
+ params: [
311
+ {
312
+ to: accept.asset,
313
+ data
314
+ },
315
+ "latest"
402
316
  ]
403
- };
404
- const nonce = "0x" + [...Array(32)].map(() => Math.floor(Math.random() * 256).toString(16).padStart(2, "0")).join("");
405
- const now = Math.floor(Date.now() / 1e3);
406
- const authorization = {
407
- from: wallet.address,
408
- to: payTo,
409
- value: amount,
410
- // string
411
- validAfter: String(now - 600),
412
- // 10 minutes before (matching upstream)
413
- validBefore: String(now + (accept.maxTimeoutSeconds || 60)),
414
- nonce
415
- };
416
- const message = {
417
- from: wallet.address,
418
- to: payTo,
419
- value: BigInt(amount),
420
- validAfter: BigInt(now - 600),
421
- validBefore: BigInt(now + (accept.maxTimeoutSeconds || 60)),
422
- nonce
423
- };
424
- if (!wallet.signTypedData) {
425
- throw new Error("Wallet does not support signTypedData (EIP-712)");
426
- }
427
- const signature = await wallet.signTypedData({
428
- domain,
429
- types,
430
- primaryType: "TransferWithAuthorization",
431
- message
432
- });
433
- this.log("EIP-712 signature obtained");
434
- const payload = {
435
- authorization,
436
- signature
437
- };
438
- return {
439
- serialized: JSON.stringify(payload),
440
- signature
441
- };
317
+ })
318
+ });
319
+ const result = await response.json();
320
+ if (result.error || !result.result) {
321
+ return 0;
442
322
  }
323
+ const balance = BigInt(result.result);
324
+ const decimals = accept.extra?.decimals ?? 6;
325
+ return Number(balance) / Math.pow(10, decimals);
326
+ } catch {
327
+ return 0;
328
+ }
329
+ }
330
+ encodeBalanceOf(address) {
331
+ const selector = "0x70a08231";
332
+ const paddedAddress = address.slice(2).toLowerCase().padStart(64, "0");
333
+ return selector + paddedAddress;
334
+ }
335
+ async buildTransaction(accept, wallet, _rpcUrl) {
336
+ if (!isEvmWallet(wallet)) {
337
+ throw new Error("Invalid EVM wallet");
338
+ }
339
+ if (!wallet.address) {
340
+ throw new Error("Wallet not connected");
341
+ }
342
+ const { payTo, asset, extra } = accept;
343
+ const amount = accept.amount || accept.maxAmountRequired;
344
+ if (!amount) {
345
+ throw new Error("Missing amount in payment requirements");
346
+ }
347
+ this.log("Building EVM transaction:", {
348
+ from: wallet.address,
349
+ to: payTo,
350
+ amount,
351
+ asset,
352
+ network: accept.network
353
+ });
354
+ const chainId = this.getChainId(accept.network);
355
+ const domain = {
356
+ name: extra?.name ?? "USD Coin",
357
+ version: extra?.version ?? "2",
358
+ chainId: BigInt(chainId),
359
+ verifyingContract: asset
360
+ };
361
+ const types = {
362
+ TransferWithAuthorization: [
363
+ { name: "from", type: "address" },
364
+ { name: "to", type: "address" },
365
+ { name: "value", type: "uint256" },
366
+ { name: "validAfter", type: "uint256" },
367
+ { name: "validBefore", type: "uint256" },
368
+ { name: "nonce", type: "bytes32" }
369
+ ]
370
+ };
371
+ const nonce = "0x" + [...Array(32)].map(() => Math.floor(Math.random() * 256).toString(16).padStart(2, "0")).join("");
372
+ const now = Math.floor(Date.now() / 1e3);
373
+ const authorization = {
374
+ from: wallet.address,
375
+ to: payTo,
376
+ value: amount,
377
+ // string
378
+ validAfter: String(now - 600),
379
+ // 10 minutes before (matching upstream)
380
+ validBefore: String(now + (accept.maxTimeoutSeconds || 60)),
381
+ nonce
382
+ };
383
+ const message = {
384
+ from: wallet.address,
385
+ to: payTo,
386
+ value: BigInt(amount),
387
+ validAfter: BigInt(now - 600),
388
+ validBefore: BigInt(now + (accept.maxTimeoutSeconds || 60)),
389
+ nonce
390
+ };
391
+ if (!wallet.signTypedData) {
392
+ throw new Error("Wallet does not support signTypedData (EIP-712)");
393
+ }
394
+ const signature = await wallet.signTypedData({
395
+ domain,
396
+ types,
397
+ primaryType: "TransferWithAuthorization",
398
+ message
399
+ });
400
+ this.log("EIP-712 signature obtained");
401
+ const payload = {
402
+ authorization,
403
+ signature
404
+ };
405
+ return {
406
+ serialized: JSON.stringify(payload),
407
+ signature
443
408
  };
444
409
  }
445
- });
410
+ };
411
+ function createEvmAdapter(config) {
412
+ return new EvmAdapter(config);
413
+ }
446
414
 
447
415
  // src/adapters/index.ts
448
- init_solana();
449
- init_evm();
450
416
  function createDefaultAdapters(verbose = false) {
451
- const { createSolanaAdapter: createSolanaAdapter2 } = (init_solana(), __toCommonJS(solana_exports));
452
- const { createEvmAdapter: createEvmAdapter2 } = (init_evm(), __toCommonJS(evm_exports));
453
417
  return [
454
- createSolanaAdapter2({ verbose }),
455
- createEvmAdapter2({ verbose })
418
+ createSolanaAdapter({ verbose }),
419
+ createEvmAdapter({ verbose })
456
420
  ];
457
421
  }
458
422
  function findAdapter(adapters, network) {
@@ -460,14 +424,20 @@ function findAdapter(adapters, network) {
460
424
  }
461
425
  export {
462
426
  ARBITRUM_ONE,
427
+ AVALANCHE,
463
428
  BASE_MAINNET,
464
429
  BASE_SEPOLIA,
465
430
  ETHEREUM_MAINNET,
466
431
  EvmAdapter,
432
+ OPTIMISM,
433
+ POLYGON,
434
+ SKALE_BASE,
435
+ SKALE_BASE_SEPOLIA,
467
436
  SOLANA_DEVNET,
468
437
  SOLANA_MAINNET,
469
438
  SOLANA_TESTNET,
470
439
  SolanaAdapter,
440
+ USDC_ADDRESSES,
471
441
  createDefaultAdapters,
472
442
  createEvmAdapter,
473
443
  createSolanaAdapter,