@payai/x402-evm 2.3.6 → 2.4.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.
- package/dist/cjs/exact/client/index.d.ts +3 -2
- package/dist/cjs/exact/client/index.js +173 -194
- package/dist/cjs/exact/client/index.js.map +1 -1
- package/dist/cjs/exact/facilitator/index.js +199 -185
- package/dist/cjs/exact/facilitator/index.js.map +1 -1
- package/dist/cjs/exact/server/index.d.ts +18 -17
- package/dist/cjs/exact/server/index.js +100 -55
- package/dist/cjs/exact/server/index.js.map +1 -1
- package/dist/cjs/exact/v1/client/index.js +3 -1
- package/dist/cjs/exact/v1/client/index.js.map +1 -1
- package/dist/cjs/exact/v1/facilitator/index.js +3 -1
- package/dist/cjs/exact/v1/facilitator/index.js.map +1 -1
- package/dist/cjs/index.d.ts +38 -2
- package/dist/cjs/index.js +441 -191
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/{permit2-U9Zolx3O.d.ts → permit2-CyZxwngN.d.ts} +278 -87
- package/dist/cjs/scheme-CXDF0D2A.d.ts +47 -0
- package/dist/cjs/upto/client/index.d.ts +32 -0
- package/dist/cjs/upto/client/index.js +507 -0
- package/dist/cjs/upto/client/index.js.map +1 -0
- package/dist/cjs/upto/facilitator/index.d.ts +52 -0
- package/dist/cjs/upto/facilitator/index.js +1233 -0
- package/dist/cjs/upto/facilitator/index.js.map +1 -0
- package/dist/cjs/upto/server/index.d.ts +77 -0
- package/dist/cjs/upto/server/index.js +246 -0
- package/dist/cjs/upto/server/index.js.map +1 -0
- package/dist/cjs/v1/index.d.ts +2 -0
- package/dist/cjs/v1/index.js +3 -1
- package/dist/cjs/v1/index.js.map +1 -1
- package/dist/esm/chunk-C4ZQMS77.mjs +629 -0
- package/dist/esm/chunk-C4ZQMS77.mjs.map +1 -0
- package/dist/esm/chunk-CRT6YNY5.mjs +529 -0
- package/dist/esm/chunk-CRT6YNY5.mjs.map +1 -0
- package/dist/esm/chunk-D6RXZXOS.mjs +158 -0
- package/dist/esm/chunk-D6RXZXOS.mjs.map +1 -0
- package/dist/esm/chunk-GJ57SZGI.mjs +121 -0
- package/dist/esm/chunk-GJ57SZGI.mjs.map +1 -0
- package/dist/esm/chunk-JII456TS.mjs +34 -0
- package/dist/esm/chunk-JII456TS.mjs.map +1 -0
- package/dist/esm/chunk-NSFLAANF.mjs +80 -0
- package/dist/esm/chunk-NSFLAANF.mjs.map +1 -0
- package/dist/esm/{chunk-PCJKIY5G.mjs → chunk-RYT6M3PA.mjs} +29 -501
- package/dist/esm/chunk-RYT6M3PA.mjs.map +1 -0
- package/dist/esm/chunk-WKBC5YMI.mjs +291 -0
- package/dist/esm/chunk-WKBC5YMI.mjs.map +1 -0
- package/dist/esm/exact/client/index.d.mts +3 -2
- package/dist/esm/exact/client/index.mjs +8 -5
- package/dist/esm/exact/facilitator/index.mjs +84 -430
- package/dist/esm/exact/facilitator/index.mjs.map +1 -1
- package/dist/esm/exact/server/index.d.mts +18 -17
- package/dist/esm/exact/server/index.mjs +28 -55
- package/dist/esm/exact/server/index.mjs.map +1 -1
- package/dist/esm/exact/v1/client/index.mjs +2 -1
- package/dist/esm/exact/v1/facilitator/index.mjs +2 -1
- package/dist/esm/index.d.mts +38 -2
- package/dist/esm/index.mjs +21 -8
- package/dist/esm/index.mjs.map +1 -1
- package/dist/esm/{permit2-Bbh3a8_h.d.mts → permit2-CyZxwngN.d.mts} +278 -87
- package/dist/esm/scheme-DCR7hsa3.d.mts +47 -0
- package/dist/esm/upto/client/index.d.mts +32 -0
- package/dist/esm/upto/client/index.mjs +18 -0
- package/dist/esm/upto/client/index.mjs.map +1 -0
- package/dist/esm/upto/facilitator/index.d.mts +52 -0
- package/dist/esm/upto/facilitator/index.mjs +473 -0
- package/dist/esm/upto/facilitator/index.mjs.map +1 -0
- package/dist/esm/upto/server/index.d.mts +77 -0
- package/dist/esm/upto/server/index.mjs +145 -0
- package/dist/esm/upto/server/index.mjs.map +1 -0
- package/dist/esm/v1/index.d.mts +2 -0
- package/dist/esm/v1/index.mjs +2 -1
- package/package.json +31 -1
- package/dist/esm/chunk-GD4MKCN7.mjs +0 -57
- package/dist/esm/chunk-GD4MKCN7.mjs.map +0 -1
- package/dist/esm/chunk-LWO35IGS.mjs +0 -518
- package/dist/esm/chunk-LWO35IGS.mjs.map +0 -1
- package/dist/esm/chunk-PCJKIY5G.mjs.map +0 -1
- package/dist/esm/chunk-TKN5V2BV.mjs +0 -13
- package/dist/esm/chunk-TKN5V2BV.mjs.map +0 -1
|
@@ -0,0 +1,507 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
6
|
+
var __export = (target, all) => {
|
|
7
|
+
for (var name in all)
|
|
8
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
9
|
+
};
|
|
10
|
+
var __copyProps = (to, from, except, desc) => {
|
|
11
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
12
|
+
for (let key of __getOwnPropNames(from))
|
|
13
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
14
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
15
|
+
}
|
|
16
|
+
return to;
|
|
17
|
+
};
|
|
18
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
|
+
|
|
20
|
+
// src/upto/client/index.ts
|
|
21
|
+
var client_exports = {};
|
|
22
|
+
__export(client_exports, {
|
|
23
|
+
UptoEvmScheme: () => UptoEvmScheme,
|
|
24
|
+
createPermit2ApprovalTx: () => createPermit2ApprovalTx,
|
|
25
|
+
erc20AllowanceAbi: () => erc20AllowanceAbi,
|
|
26
|
+
getPermit2AllowanceReadParams: () => getPermit2AllowanceReadParams
|
|
27
|
+
});
|
|
28
|
+
module.exports = __toCommonJS(client_exports);
|
|
29
|
+
|
|
30
|
+
// src/constants.ts
|
|
31
|
+
var uptoPermit2WitnessTypes = {
|
|
32
|
+
PermitWitnessTransferFrom: [
|
|
33
|
+
{ name: "permitted", type: "TokenPermissions" },
|
|
34
|
+
{ name: "spender", type: "address" },
|
|
35
|
+
{ name: "nonce", type: "uint256" },
|
|
36
|
+
{ name: "deadline", type: "uint256" },
|
|
37
|
+
{ name: "witness", type: "Witness" }
|
|
38
|
+
],
|
|
39
|
+
TokenPermissions: [
|
|
40
|
+
{ name: "token", type: "address" },
|
|
41
|
+
{ name: "amount", type: "uint256" }
|
|
42
|
+
],
|
|
43
|
+
Witness: [
|
|
44
|
+
{ name: "to", type: "address" },
|
|
45
|
+
{ name: "facilitator", type: "address" },
|
|
46
|
+
{ name: "validAfter", type: "uint256" }
|
|
47
|
+
]
|
|
48
|
+
};
|
|
49
|
+
var eip2612PermitTypes = {
|
|
50
|
+
Permit: [
|
|
51
|
+
{ name: "owner", type: "address" },
|
|
52
|
+
{ name: "spender", type: "address" },
|
|
53
|
+
{ name: "value", type: "uint256" },
|
|
54
|
+
{ name: "nonce", type: "uint256" },
|
|
55
|
+
{ name: "deadline", type: "uint256" }
|
|
56
|
+
]
|
|
57
|
+
};
|
|
58
|
+
var eip2612NoncesAbi = [
|
|
59
|
+
{
|
|
60
|
+
type: "function",
|
|
61
|
+
name: "nonces",
|
|
62
|
+
inputs: [{ name: "owner", type: "address" }],
|
|
63
|
+
outputs: [{ type: "uint256" }],
|
|
64
|
+
stateMutability: "view"
|
|
65
|
+
}
|
|
66
|
+
];
|
|
67
|
+
var erc20ApproveAbi = [
|
|
68
|
+
{
|
|
69
|
+
type: "function",
|
|
70
|
+
name: "approve",
|
|
71
|
+
inputs: [
|
|
72
|
+
{ name: "spender", type: "address" },
|
|
73
|
+
{ name: "amount", type: "uint256" }
|
|
74
|
+
],
|
|
75
|
+
outputs: [{ type: "bool" }],
|
|
76
|
+
stateMutability: "nonpayable"
|
|
77
|
+
}
|
|
78
|
+
];
|
|
79
|
+
var erc20AllowanceAbi = [
|
|
80
|
+
{
|
|
81
|
+
type: "function",
|
|
82
|
+
name: "allowance",
|
|
83
|
+
inputs: [
|
|
84
|
+
{ name: "owner", type: "address" },
|
|
85
|
+
{ name: "spender", type: "address" }
|
|
86
|
+
],
|
|
87
|
+
outputs: [{ type: "uint256" }],
|
|
88
|
+
stateMutability: "view"
|
|
89
|
+
}
|
|
90
|
+
];
|
|
91
|
+
var ERC20_APPROVE_GAS_LIMIT = 70000n;
|
|
92
|
+
var DEFAULT_MAX_FEE_PER_GAS = 1000000000n;
|
|
93
|
+
var DEFAULT_MAX_PRIORITY_FEE_PER_GAS = 100000000n;
|
|
94
|
+
var PERMIT2_ADDRESS = "0x000000000022D473030F116dDEE9F6B43aC78BA3";
|
|
95
|
+
var x402UptoPermit2ProxyAddress = "0x4020A4f3b7b90ccA423B9fabCc0CE57C6C240002";
|
|
96
|
+
|
|
97
|
+
// src/utils.ts
|
|
98
|
+
var import_viem = require("viem");
|
|
99
|
+
function getEvmChainId(network) {
|
|
100
|
+
if (network.startsWith("eip155:")) {
|
|
101
|
+
const idStr = network.split(":")[1];
|
|
102
|
+
const chainId = parseInt(idStr, 10);
|
|
103
|
+
if (isNaN(chainId)) {
|
|
104
|
+
throw new Error(`Invalid CAIP-2 chain ID: ${network}`);
|
|
105
|
+
}
|
|
106
|
+
return chainId;
|
|
107
|
+
}
|
|
108
|
+
throw new Error(`Unsupported network format: ${network} (expected eip155:CHAIN_ID)`);
|
|
109
|
+
}
|
|
110
|
+
function getCrypto() {
|
|
111
|
+
const cryptoObj = globalThis.crypto;
|
|
112
|
+
if (!cryptoObj) {
|
|
113
|
+
throw new Error("Crypto API not available");
|
|
114
|
+
}
|
|
115
|
+
return cryptoObj;
|
|
116
|
+
}
|
|
117
|
+
function createPermit2Nonce() {
|
|
118
|
+
const randomBytes = getCrypto().getRandomValues(new Uint8Array(32));
|
|
119
|
+
return BigInt((0, import_viem.toHex)(randomBytes)).toString();
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
// src/upto/client/permit2.ts
|
|
123
|
+
var import_viem6 = require("viem");
|
|
124
|
+
|
|
125
|
+
// src/exact/client/permit2.ts
|
|
126
|
+
var import_viem5 = require("viem");
|
|
127
|
+
|
|
128
|
+
// src/exact/extensions.ts
|
|
129
|
+
var EIP2612_GAS_SPONSORING_KEY = "eip2612GasSponsoring";
|
|
130
|
+
var ERC20_APPROVAL_GAS_SPONSORING_KEY = "erc20ApprovalGasSponsoring";
|
|
131
|
+
var ERC20_APPROVAL_GAS_SPONSORING_VERSION = "1";
|
|
132
|
+
|
|
133
|
+
// src/shared/permit2.ts
|
|
134
|
+
var import_viem4 = require("viem");
|
|
135
|
+
|
|
136
|
+
// src/multicall.ts
|
|
137
|
+
var import_viem2 = require("viem");
|
|
138
|
+
|
|
139
|
+
// src/shared/erc20approval.ts
|
|
140
|
+
var import_viem3 = require("viem");
|
|
141
|
+
|
|
142
|
+
// src/exact/client/permit2.ts
|
|
143
|
+
var MAX_UINT256 = BigInt("0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff");
|
|
144
|
+
function createPermit2ApprovalTx(tokenAddress) {
|
|
145
|
+
const data = (0, import_viem5.encodeFunctionData)({
|
|
146
|
+
abi: erc20ApproveAbi,
|
|
147
|
+
functionName: "approve",
|
|
148
|
+
args: [PERMIT2_ADDRESS, MAX_UINT256]
|
|
149
|
+
});
|
|
150
|
+
return {
|
|
151
|
+
to: (0, import_viem5.getAddress)(tokenAddress),
|
|
152
|
+
data
|
|
153
|
+
};
|
|
154
|
+
}
|
|
155
|
+
function getPermit2AllowanceReadParams(params) {
|
|
156
|
+
return {
|
|
157
|
+
address: (0, import_viem5.getAddress)(params.tokenAddress),
|
|
158
|
+
abi: erc20AllowanceAbi,
|
|
159
|
+
functionName: "allowance",
|
|
160
|
+
args: [(0, import_viem5.getAddress)(params.ownerAddress), PERMIT2_ADDRESS]
|
|
161
|
+
};
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
// src/upto/client/permit2.ts
|
|
165
|
+
async function createUptoPermit2Payload(signer, x402Version, paymentRequirements) {
|
|
166
|
+
const facilitatorAddress = paymentRequirements.extra?.facilitatorAddress;
|
|
167
|
+
if (!facilitatorAddress) {
|
|
168
|
+
throw new Error(
|
|
169
|
+
"upto scheme requires facilitatorAddress in paymentRequirements.extra. Ensure the server is configured with an upto facilitator that provides getExtra()."
|
|
170
|
+
);
|
|
171
|
+
}
|
|
172
|
+
const now = Math.floor(Date.now() / 1e3);
|
|
173
|
+
const nonce = createPermit2Nonce();
|
|
174
|
+
const validAfter = (now - 600).toString();
|
|
175
|
+
const deadline = (now + paymentRequirements.maxTimeoutSeconds).toString();
|
|
176
|
+
if (BigInt(deadline) <= BigInt(validAfter)) {
|
|
177
|
+
throw new Error(
|
|
178
|
+
`Invalid time window: deadline (${deadline}) must be after validAfter (${validAfter}). Check that maxTimeoutSeconds (${paymentRequirements.maxTimeoutSeconds}) is positive.`
|
|
179
|
+
);
|
|
180
|
+
}
|
|
181
|
+
const permit2Authorization = {
|
|
182
|
+
from: signer.address,
|
|
183
|
+
permitted: {
|
|
184
|
+
token: (0, import_viem6.getAddress)(paymentRequirements.asset),
|
|
185
|
+
amount: paymentRequirements.amount
|
|
186
|
+
},
|
|
187
|
+
spender: x402UptoPermit2ProxyAddress,
|
|
188
|
+
nonce,
|
|
189
|
+
deadline,
|
|
190
|
+
witness: {
|
|
191
|
+
to: (0, import_viem6.getAddress)(paymentRequirements.payTo),
|
|
192
|
+
facilitator: (0, import_viem6.getAddress)(facilitatorAddress),
|
|
193
|
+
validAfter
|
|
194
|
+
}
|
|
195
|
+
};
|
|
196
|
+
const chainId = getEvmChainId(paymentRequirements.network);
|
|
197
|
+
const signature = await signer.signTypedData({
|
|
198
|
+
domain: { name: "Permit2", chainId, verifyingContract: PERMIT2_ADDRESS },
|
|
199
|
+
types: uptoPermit2WitnessTypes,
|
|
200
|
+
primaryType: "PermitWitnessTransferFrom",
|
|
201
|
+
message: {
|
|
202
|
+
permitted: {
|
|
203
|
+
token: (0, import_viem6.getAddress)(permit2Authorization.permitted.token),
|
|
204
|
+
amount: BigInt(permit2Authorization.permitted.amount)
|
|
205
|
+
},
|
|
206
|
+
spender: (0, import_viem6.getAddress)(permit2Authorization.spender),
|
|
207
|
+
nonce: BigInt(permit2Authorization.nonce),
|
|
208
|
+
deadline: BigInt(permit2Authorization.deadline),
|
|
209
|
+
witness: {
|
|
210
|
+
to: (0, import_viem6.getAddress)(permit2Authorization.witness.to),
|
|
211
|
+
facilitator: (0, import_viem6.getAddress)(permit2Authorization.witness.facilitator),
|
|
212
|
+
validAfter: BigInt(permit2Authorization.witness.validAfter)
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
});
|
|
216
|
+
return {
|
|
217
|
+
x402Version,
|
|
218
|
+
payload: { signature, permit2Authorization }
|
|
219
|
+
};
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
// src/shared/extensions.ts
|
|
223
|
+
var import_viem10 = require("viem");
|
|
224
|
+
|
|
225
|
+
// src/exact/client/eip2612.ts
|
|
226
|
+
var import_viem7 = require("viem");
|
|
227
|
+
async function signEip2612Permit(signer, tokenAddress, tokenName, tokenVersion, chainId, deadline, permittedAmount) {
|
|
228
|
+
const owner = signer.address;
|
|
229
|
+
const spender = (0, import_viem7.getAddress)(PERMIT2_ADDRESS);
|
|
230
|
+
const nonce = await signer.readContract({
|
|
231
|
+
address: tokenAddress,
|
|
232
|
+
abi: eip2612NoncesAbi,
|
|
233
|
+
functionName: "nonces",
|
|
234
|
+
args: [owner]
|
|
235
|
+
});
|
|
236
|
+
const domain = {
|
|
237
|
+
name: tokenName,
|
|
238
|
+
version: tokenVersion,
|
|
239
|
+
chainId,
|
|
240
|
+
verifyingContract: tokenAddress
|
|
241
|
+
};
|
|
242
|
+
const approvalAmount = BigInt(permittedAmount);
|
|
243
|
+
const message = {
|
|
244
|
+
owner,
|
|
245
|
+
spender,
|
|
246
|
+
value: approvalAmount,
|
|
247
|
+
nonce,
|
|
248
|
+
deadline: BigInt(deadline)
|
|
249
|
+
};
|
|
250
|
+
const signature = await signer.signTypedData({
|
|
251
|
+
domain,
|
|
252
|
+
types: eip2612PermitTypes,
|
|
253
|
+
primaryType: "Permit",
|
|
254
|
+
message
|
|
255
|
+
});
|
|
256
|
+
return {
|
|
257
|
+
from: owner,
|
|
258
|
+
asset: tokenAddress,
|
|
259
|
+
spender,
|
|
260
|
+
amount: approvalAmount.toString(),
|
|
261
|
+
nonce: nonce.toString(),
|
|
262
|
+
deadline,
|
|
263
|
+
signature,
|
|
264
|
+
version: "1"
|
|
265
|
+
};
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
// src/exact/client/erc20approval.ts
|
|
269
|
+
var import_viem8 = require("viem");
|
|
270
|
+
async function signErc20ApprovalTransaction(signer, tokenAddress, chainId) {
|
|
271
|
+
const from = signer.address;
|
|
272
|
+
const spender = (0, import_viem8.getAddress)(PERMIT2_ADDRESS);
|
|
273
|
+
const data = (0, import_viem8.encodeFunctionData)({
|
|
274
|
+
abi: erc20ApproveAbi,
|
|
275
|
+
functionName: "approve",
|
|
276
|
+
args: [spender, import_viem8.maxUint256]
|
|
277
|
+
});
|
|
278
|
+
const nonce = await signer.getTransactionCount({ address: from });
|
|
279
|
+
let maxFeePerGas;
|
|
280
|
+
let maxPriorityFeePerGas;
|
|
281
|
+
try {
|
|
282
|
+
const fees = await signer.estimateFeesPerGas?.();
|
|
283
|
+
if (!fees) {
|
|
284
|
+
throw new Error("no fee estimates available");
|
|
285
|
+
}
|
|
286
|
+
maxFeePerGas = fees.maxFeePerGas;
|
|
287
|
+
maxPriorityFeePerGas = fees.maxPriorityFeePerGas;
|
|
288
|
+
} catch {
|
|
289
|
+
maxFeePerGas = DEFAULT_MAX_FEE_PER_GAS;
|
|
290
|
+
maxPriorityFeePerGas = DEFAULT_MAX_PRIORITY_FEE_PER_GAS;
|
|
291
|
+
}
|
|
292
|
+
const signedTransaction = await signer.signTransaction({
|
|
293
|
+
to: tokenAddress,
|
|
294
|
+
data,
|
|
295
|
+
nonce,
|
|
296
|
+
gas: ERC20_APPROVE_GAS_LIMIT,
|
|
297
|
+
maxFeePerGas,
|
|
298
|
+
maxPriorityFeePerGas,
|
|
299
|
+
chainId
|
|
300
|
+
});
|
|
301
|
+
return {
|
|
302
|
+
from,
|
|
303
|
+
asset: tokenAddress,
|
|
304
|
+
spender,
|
|
305
|
+
amount: import_viem8.maxUint256.toString(),
|
|
306
|
+
signedTransaction,
|
|
307
|
+
version: ERC20_APPROVAL_GAS_SPONSORING_VERSION
|
|
308
|
+
};
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
// src/shared/rpc.ts
|
|
312
|
+
var import_viem9 = require("viem");
|
|
313
|
+
var rpcClientCache = /* @__PURE__ */ new Map();
|
|
314
|
+
function isConfigByChainId(options) {
|
|
315
|
+
const keys = Object.keys(options);
|
|
316
|
+
return keys.length > 0 && keys.every((key) => /^\d+$/.test(key));
|
|
317
|
+
}
|
|
318
|
+
function getRpcClient(rpcUrl) {
|
|
319
|
+
const existing = rpcClientCache.get(rpcUrl);
|
|
320
|
+
if (existing) {
|
|
321
|
+
return existing;
|
|
322
|
+
}
|
|
323
|
+
const client = (0, import_viem9.createPublicClient)({
|
|
324
|
+
transport: (0, import_viem9.http)(rpcUrl)
|
|
325
|
+
});
|
|
326
|
+
rpcClientCache.set(rpcUrl, client);
|
|
327
|
+
return client;
|
|
328
|
+
}
|
|
329
|
+
function resolveRpcUrl(network, options) {
|
|
330
|
+
if (!options) {
|
|
331
|
+
return void 0;
|
|
332
|
+
}
|
|
333
|
+
if (isConfigByChainId(options)) {
|
|
334
|
+
const chainId = getEvmChainId(network);
|
|
335
|
+
const optionsByChainId = options;
|
|
336
|
+
return optionsByChainId[chainId]?.rpcUrl;
|
|
337
|
+
}
|
|
338
|
+
return options.rpcUrl;
|
|
339
|
+
}
|
|
340
|
+
function resolveExtensionRpcCapabilities(network, signer, options) {
|
|
341
|
+
const capabilities = {
|
|
342
|
+
signTransaction: signer.signTransaction,
|
|
343
|
+
readContract: signer.readContract,
|
|
344
|
+
getTransactionCount: signer.getTransactionCount,
|
|
345
|
+
estimateFeesPerGas: signer.estimateFeesPerGas
|
|
346
|
+
};
|
|
347
|
+
const needsRpcBackfill = !capabilities.readContract || !capabilities.getTransactionCount || !capabilities.estimateFeesPerGas;
|
|
348
|
+
if (!needsRpcBackfill) {
|
|
349
|
+
return capabilities;
|
|
350
|
+
}
|
|
351
|
+
const rpcUrl = resolveRpcUrl(network, options);
|
|
352
|
+
if (!rpcUrl) {
|
|
353
|
+
return capabilities;
|
|
354
|
+
}
|
|
355
|
+
const rpcClient = getRpcClient(rpcUrl);
|
|
356
|
+
if (!capabilities.readContract) {
|
|
357
|
+
capabilities.readContract = (args) => rpcClient.readContract(args);
|
|
358
|
+
}
|
|
359
|
+
if (!capabilities.getTransactionCount) {
|
|
360
|
+
capabilities.getTransactionCount = async (args) => rpcClient.getTransactionCount({ address: args.address });
|
|
361
|
+
}
|
|
362
|
+
if (!capabilities.estimateFeesPerGas) {
|
|
363
|
+
capabilities.estimateFeesPerGas = async () => rpcClient.estimateFeesPerGas();
|
|
364
|
+
}
|
|
365
|
+
return capabilities;
|
|
366
|
+
}
|
|
367
|
+
|
|
368
|
+
// src/shared/extensions.ts
|
|
369
|
+
async function trySignEip2612PermitExtension(signer, options, requirements, result, context) {
|
|
370
|
+
const capabilities = resolveExtensionRpcCapabilities(requirements.network, signer, options);
|
|
371
|
+
if (!capabilities.readContract) {
|
|
372
|
+
return void 0;
|
|
373
|
+
}
|
|
374
|
+
if (!context?.extensions?.[EIP2612_GAS_SPONSORING_KEY]) {
|
|
375
|
+
return void 0;
|
|
376
|
+
}
|
|
377
|
+
const tokenName = requirements.extra?.name;
|
|
378
|
+
const tokenVersion = requirements.extra?.version;
|
|
379
|
+
if (!tokenName || !tokenVersion) {
|
|
380
|
+
return void 0;
|
|
381
|
+
}
|
|
382
|
+
const chainId = getEvmChainId(requirements.network);
|
|
383
|
+
const tokenAddress = (0, import_viem10.getAddress)(requirements.asset);
|
|
384
|
+
try {
|
|
385
|
+
const allowance = await capabilities.readContract({
|
|
386
|
+
address: tokenAddress,
|
|
387
|
+
abi: erc20AllowanceAbi,
|
|
388
|
+
functionName: "allowance",
|
|
389
|
+
args: [signer.address, PERMIT2_ADDRESS]
|
|
390
|
+
});
|
|
391
|
+
if (allowance >= BigInt(requirements.amount)) {
|
|
392
|
+
return void 0;
|
|
393
|
+
}
|
|
394
|
+
} catch {
|
|
395
|
+
}
|
|
396
|
+
const permit2Auth = result.payload?.permit2Authorization;
|
|
397
|
+
const deadline = permit2Auth?.deadline ?? Math.floor(Date.now() / 1e3 + requirements.maxTimeoutSeconds).toString();
|
|
398
|
+
const info = await signEip2612Permit(
|
|
399
|
+
{
|
|
400
|
+
address: signer.address,
|
|
401
|
+
signTypedData: (msg) => signer.signTypedData(msg),
|
|
402
|
+
readContract: capabilities.readContract
|
|
403
|
+
},
|
|
404
|
+
tokenAddress,
|
|
405
|
+
tokenName,
|
|
406
|
+
tokenVersion,
|
|
407
|
+
chainId,
|
|
408
|
+
deadline,
|
|
409
|
+
requirements.amount
|
|
410
|
+
);
|
|
411
|
+
return {
|
|
412
|
+
[EIP2612_GAS_SPONSORING_KEY]: { info }
|
|
413
|
+
};
|
|
414
|
+
}
|
|
415
|
+
async function trySignErc20ApprovalExtension(signer, options, requirements, context) {
|
|
416
|
+
const capabilities = resolveExtensionRpcCapabilities(requirements.network, signer, options);
|
|
417
|
+
if (!capabilities.readContract) {
|
|
418
|
+
return void 0;
|
|
419
|
+
}
|
|
420
|
+
if (!context?.extensions?.[ERC20_APPROVAL_GAS_SPONSORING_KEY]) {
|
|
421
|
+
return void 0;
|
|
422
|
+
}
|
|
423
|
+
if (!capabilities.signTransaction || !capabilities.getTransactionCount) {
|
|
424
|
+
return void 0;
|
|
425
|
+
}
|
|
426
|
+
const chainId = getEvmChainId(requirements.network);
|
|
427
|
+
const tokenAddress = (0, import_viem10.getAddress)(requirements.asset);
|
|
428
|
+
try {
|
|
429
|
+
const allowance = await capabilities.readContract({
|
|
430
|
+
address: tokenAddress,
|
|
431
|
+
abi: erc20AllowanceAbi,
|
|
432
|
+
functionName: "allowance",
|
|
433
|
+
args: [signer.address, PERMIT2_ADDRESS]
|
|
434
|
+
});
|
|
435
|
+
if (allowance >= BigInt(requirements.amount)) {
|
|
436
|
+
return void 0;
|
|
437
|
+
}
|
|
438
|
+
} catch {
|
|
439
|
+
}
|
|
440
|
+
const info = await signErc20ApprovalTransaction(
|
|
441
|
+
{
|
|
442
|
+
address: signer.address,
|
|
443
|
+
signTransaction: capabilities.signTransaction,
|
|
444
|
+
getTransactionCount: capabilities.getTransactionCount,
|
|
445
|
+
estimateFeesPerGas: capabilities.estimateFeesPerGas
|
|
446
|
+
},
|
|
447
|
+
tokenAddress,
|
|
448
|
+
chainId
|
|
449
|
+
);
|
|
450
|
+
return {
|
|
451
|
+
[ERC20_APPROVAL_GAS_SPONSORING_KEY]: { info }
|
|
452
|
+
};
|
|
453
|
+
}
|
|
454
|
+
|
|
455
|
+
// src/upto/client/scheme.ts
|
|
456
|
+
var UptoEvmScheme = class {
|
|
457
|
+
/**
|
|
458
|
+
* Creates a new UptoEvmScheme instance.
|
|
459
|
+
*
|
|
460
|
+
* @param signer - The EVM signer for client operations
|
|
461
|
+
* @param options - Optional RPC configuration
|
|
462
|
+
*/
|
|
463
|
+
constructor(signer, options) {
|
|
464
|
+
this.signer = signer;
|
|
465
|
+
this.options = options;
|
|
466
|
+
this.scheme = "upto";
|
|
467
|
+
}
|
|
468
|
+
/**
|
|
469
|
+
* Creates a payment payload for the Upto scheme using Permit2.
|
|
470
|
+
*
|
|
471
|
+
* @param x402Version - The x402 protocol version
|
|
472
|
+
* @param paymentRequirements - The payment requirements
|
|
473
|
+
* @param context - Optional context with server-declared extensions
|
|
474
|
+
* @returns Promise resolving to a payment payload result
|
|
475
|
+
*/
|
|
476
|
+
async createPaymentPayload(x402Version, paymentRequirements, context) {
|
|
477
|
+
const result = await createUptoPermit2Payload(this.signer, x402Version, paymentRequirements);
|
|
478
|
+
const eip2612Extensions = await trySignEip2612PermitExtension(
|
|
479
|
+
this.signer,
|
|
480
|
+
this.options,
|
|
481
|
+
paymentRequirements,
|
|
482
|
+
result,
|
|
483
|
+
context
|
|
484
|
+
);
|
|
485
|
+
if (eip2612Extensions) {
|
|
486
|
+
return { ...result, extensions: eip2612Extensions };
|
|
487
|
+
}
|
|
488
|
+
const erc20Extensions = await trySignErc20ApprovalExtension(
|
|
489
|
+
this.signer,
|
|
490
|
+
this.options,
|
|
491
|
+
paymentRequirements,
|
|
492
|
+
context
|
|
493
|
+
);
|
|
494
|
+
if (erc20Extensions) {
|
|
495
|
+
return { ...result, extensions: erc20Extensions };
|
|
496
|
+
}
|
|
497
|
+
return result;
|
|
498
|
+
}
|
|
499
|
+
};
|
|
500
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
501
|
+
0 && (module.exports = {
|
|
502
|
+
UptoEvmScheme,
|
|
503
|
+
createPermit2ApprovalTx,
|
|
504
|
+
erc20AllowanceAbi,
|
|
505
|
+
getPermit2AllowanceReadParams
|
|
506
|
+
});
|
|
507
|
+
//# sourceMappingURL=index.js.map
|