@kayibal/fynd-client 0.1.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/autogen.d.ts +17 -0
- package/dist/autogen.d.ts.map +1 -0
- package/dist/autogen.js +17 -0
- package/dist/autogen.js.map +1 -0
- package/dist/client-fee.d.ts +16 -0
- package/dist/client-fee.d.ts.map +1 -0
- package/dist/client-fee.js +50 -0
- package/dist/client-fee.js.map +1 -0
- package/dist/client.d.ts +224 -0
- package/dist/client.d.ts.map +1 -0
- package/dist/client.js +498 -0
- package/dist/client.js.map +1 -0
- package/dist/error.d.ts +38 -0
- package/dist/error.d.ts.map +1 -0
- package/dist/error.js +75 -0
- package/dist/error.js.map +1 -0
- package/dist/index.d.ts +12 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +7 -0
- package/dist/index.js.map +1 -0
- package/dist/mapping.d.ts +12 -0
- package/dist/mapping.d.ts.map +1 -0
- package/dist/mapping.js +143 -0
- package/dist/mapping.js.map +1 -0
- package/dist/permit2.d.ts +26 -0
- package/dist/permit2.d.ts.map +1 -0
- package/dist/permit2.js +77 -0
- package/dist/permit2.js.map +1 -0
- package/dist/signing.d.ts +89 -0
- package/dist/signing.d.ts.map +1 -0
- package/dist/signing.js +39 -0
- package/dist/signing.js.map +1 -0
- package/dist/types.d.ts +177 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +2 -0
- package/dist/types.js.map +1 -0
- package/dist/viem.d.ts +72 -0
- package/dist/viem.d.ts.map +1 -0
- package/dist/viem.js +93 -0
- package/dist/viem.js.map +1 -0
- package/package.json +28 -0
package/dist/client.js
ADDED
|
@@ -0,0 +1,498 @@
|
|
|
1
|
+
import { decodeAbiParameters, encodeFunctionData, keccak256, serializeTransaction, toHex } from 'viem';
|
|
2
|
+
import { createFyndClient } from "./autogen.js";
|
|
3
|
+
import { FyndError } from "./error.js";
|
|
4
|
+
import * as mapping from "./mapping.js";
|
|
5
|
+
import { DEFAULT_SETTLE_TIMEOUT_MS, } from "./signing.js";
|
|
6
|
+
const ERC20_APPROVE_ABI = [{
|
|
7
|
+
name: 'approve', type: 'function',
|
|
8
|
+
inputs: [{ name: 'spender', type: 'address' }, { name: 'amount', type: 'uint256' }],
|
|
9
|
+
outputs: [{ type: 'bool' }],
|
|
10
|
+
stateMutability: 'nonpayable',
|
|
11
|
+
}];
|
|
12
|
+
// ERC-20 Transfer(address,address,uint256)
|
|
13
|
+
const ERC20_TRANSFER_TOPIC = keccak256(toHex('Transfer(address,address,uint256)'));
|
|
14
|
+
// ERC-6909 Transfer(address,address,address,uint256,uint256)
|
|
15
|
+
const ERC6909_TRANSFER_TOPIC = keccak256(toHex('Transfer(address,address,address,uint256,uint256)'));
|
|
16
|
+
/**
|
|
17
|
+
* Client for the Fynd swap routing API.
|
|
18
|
+
*
|
|
19
|
+
* Provides methods to request quotes, build signable payloads, and execute
|
|
20
|
+
* signed swap transactions on-chain.
|
|
21
|
+
*
|
|
22
|
+
* Requires `provider` for building signable payloads and executing transactions.
|
|
23
|
+
* Optionally accepts a separate `submitProvider` for broadcasting (falls back to `provider`).
|
|
24
|
+
*/
|
|
25
|
+
export class FyndClient {
|
|
26
|
+
constructor(options) {
|
|
27
|
+
this.infoPromise = undefined;
|
|
28
|
+
this.http = createFyndClient(options.baseUrl);
|
|
29
|
+
this.options = options;
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Requests a swap quote from the solver.
|
|
33
|
+
*
|
|
34
|
+
* Retries automatically on transient server errors (`TIMEOUT`, `QUEUE_FULL`,
|
|
35
|
+
* `SERVICE_OVERLOADED`, `STALE_DATA`, `NOT_READY`) using exponential backoff
|
|
36
|
+
* with jitter. Configure retry behavior via {@link FyndClientOptions.retry}
|
|
37
|
+
* (defaults: 3 attempts, 100ms initial backoff, 2s max backoff).
|
|
38
|
+
*
|
|
39
|
+
* Each request is subject to an HTTP timeout controlled by
|
|
40
|
+
* {@link FyndClientOptions.timeoutMs} (default: 30s).
|
|
41
|
+
*
|
|
42
|
+
* @throws {FyndError} With a server error code (`NO_ROUTE_FOUND`, `INSUFFICIENT_LIQUIDITY`, etc.) on non-retryable failures.
|
|
43
|
+
* @throws {FyndError} With code `HTTP` on network-level failures.
|
|
44
|
+
*/
|
|
45
|
+
async quote(params) {
|
|
46
|
+
const tokenOut = params.order.tokenOut;
|
|
47
|
+
const receiver = params.order.receiver ?? params.order.sender;
|
|
48
|
+
const retry = this.options.retry ?? {};
|
|
49
|
+
const maxAttempts = retry.maxAttempts ?? 3;
|
|
50
|
+
const initialBackoffMs = retry.initialBackoffMs ?? 100;
|
|
51
|
+
const maxBackoffMs = retry.maxBackoffMs ?? 2000;
|
|
52
|
+
const body = mapping.toWireRequest({ ...params, order: { ...params.order, receiver } });
|
|
53
|
+
let delay = initialBackoffMs;
|
|
54
|
+
for (let attempt = 1; attempt <= maxAttempts; attempt++) {
|
|
55
|
+
try {
|
|
56
|
+
return await this.doQuote(body, tokenOut, receiver);
|
|
57
|
+
}
|
|
58
|
+
catch (e) {
|
|
59
|
+
if (e instanceof FyndError && e.isRetryable() && attempt < maxAttempts) {
|
|
60
|
+
const jittered = delay * (0.75 + Math.random() * 0.5);
|
|
61
|
+
await sleep(jittered);
|
|
62
|
+
delay = Math.min(delay * 2, maxBackoffMs);
|
|
63
|
+
}
|
|
64
|
+
else {
|
|
65
|
+
throw e;
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
// Unreachable but satisfies TypeScript exhaustiveness
|
|
70
|
+
throw FyndError.config("retry loop exhausted without result");
|
|
71
|
+
}
|
|
72
|
+
async doQuote(body, tokenOut, receiver) {
|
|
73
|
+
const timeoutMs = this.options.timeoutMs ?? 30000;
|
|
74
|
+
const { data, error } = await this.http.POST("/v1/quote", {
|
|
75
|
+
body,
|
|
76
|
+
signal: AbortSignal.timeout(timeoutMs),
|
|
77
|
+
});
|
|
78
|
+
if (error !== undefined) {
|
|
79
|
+
// openapi-fetch does not yet union error shapes per status code; cast is required here
|
|
80
|
+
throw FyndError.fromWireError(error);
|
|
81
|
+
}
|
|
82
|
+
if (data === undefined) {
|
|
83
|
+
throw FyndError.config("server returned no data for successful response");
|
|
84
|
+
}
|
|
85
|
+
return mapping.fromWireQuote(data, tokenOut, receiver);
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Returns the solver's health status.
|
|
89
|
+
*
|
|
90
|
+
* Unlike {@link quote}, this method does not retry on transient errors.
|
|
91
|
+
*
|
|
92
|
+
* @throws {FyndError} With a server error code if the solver reports unhealthy.
|
|
93
|
+
* @throws {FyndError} With code `HTTP` on network-level failures.
|
|
94
|
+
*/
|
|
95
|
+
async health() {
|
|
96
|
+
const { data, error } = await this.http.GET("/v1/health");
|
|
97
|
+
if (error !== undefined) {
|
|
98
|
+
// GET /v1/health has no error schema, so openapi-fetch types error as the success shape;
|
|
99
|
+
// route through unknown to satisfy the type checker.
|
|
100
|
+
throw FyndError.fromWireError(error);
|
|
101
|
+
}
|
|
102
|
+
if (data === undefined) {
|
|
103
|
+
throw FyndError.config("server returned no data for health response");
|
|
104
|
+
}
|
|
105
|
+
return mapping.fromWireHealth(data);
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* Fetches and caches static instance metadata from `GET /v1/info`.
|
|
109
|
+
*
|
|
110
|
+
* The result is cached for the lifetime of the client. On failure, the cache
|
|
111
|
+
* is cleared so the next call retries.
|
|
112
|
+
*
|
|
113
|
+
* @throws {FyndError} With a server error code on non-OK responses.
|
|
114
|
+
* @throws {FyndError} With code `HTTP` on network-level failures.
|
|
115
|
+
*/
|
|
116
|
+
async info() {
|
|
117
|
+
this.infoPromise ?? (this.infoPromise = this.fetchInfo().catch((err) => {
|
|
118
|
+
this.infoPromise = undefined;
|
|
119
|
+
throw err;
|
|
120
|
+
}));
|
|
121
|
+
return this.infoPromise;
|
|
122
|
+
}
|
|
123
|
+
async fetchInfo() {
|
|
124
|
+
const timeoutMs = this.options.timeoutMs ?? 30000;
|
|
125
|
+
const { data, error } = await this.http.GET("/v1/info", {
|
|
126
|
+
signal: AbortSignal.timeout(timeoutMs),
|
|
127
|
+
});
|
|
128
|
+
if (error !== undefined) {
|
|
129
|
+
throw FyndError.fromWireError(error);
|
|
130
|
+
}
|
|
131
|
+
if (data === undefined) {
|
|
132
|
+
throw FyndError.config("server returned no data for /v1/info");
|
|
133
|
+
}
|
|
134
|
+
return mapping.fromWireInstanceInfo(data);
|
|
135
|
+
}
|
|
136
|
+
/**
|
|
137
|
+
* Builds an unsigned EIP-1559 transaction payload from a quote, ready for wallet signing.
|
|
138
|
+
*
|
|
139
|
+
* Fetches the sender's nonce, current gas fees, and gas estimate from the provider
|
|
140
|
+
* unless overridden via {@link SigningHints}.
|
|
141
|
+
*
|
|
142
|
+
* The quote must include a `transaction` field (returned when `encodingOptions`
|
|
143
|
+
* is set in the quote request). The `to`, `value`, and `data` fields are read
|
|
144
|
+
* from `quote.transaction`.
|
|
145
|
+
*
|
|
146
|
+
* When `hints.simulate` is `true`, the transaction is executed via `eth_call`
|
|
147
|
+
* before returning. This catches reverts early but adds one RPC round-trip.
|
|
148
|
+
*
|
|
149
|
+
* @param quote - A quote obtained from {@link quote}. Must have `transaction` populated.
|
|
150
|
+
* @param hints - Optional overrides for nonce, gas fees, gas limit (defaults to `eth_estimateGas`), sender, and simulation.
|
|
151
|
+
* @throws {FyndError} With code `CONFIG` if `provider` or `sender` is not configured.
|
|
152
|
+
* @throws {FyndError} With code `CONFIG` if `quote.transaction` is absent (forgot `encodingOptions`).
|
|
153
|
+
* @throws {FyndError} With code `SIMULATE_FAILED` if `hints.simulate` is `true` and the `eth_call` reverts.
|
|
154
|
+
*/
|
|
155
|
+
async swapPayload(quote, hints) {
|
|
156
|
+
if (quote.backend !== 'fynd') {
|
|
157
|
+
throw new Error('not implemented: Turbine backend signing');
|
|
158
|
+
}
|
|
159
|
+
return this.fyndSwapPayload(quote, hints ?? {});
|
|
160
|
+
}
|
|
161
|
+
async fyndSwapPayload(quote, hints) {
|
|
162
|
+
const senderOpt = hints.sender ?? this.options.sender;
|
|
163
|
+
if (senderOpt === undefined) {
|
|
164
|
+
throw FyndError.config("sender is required: set FyndClientOptions.sender or SigningHints.sender");
|
|
165
|
+
}
|
|
166
|
+
const sender = senderOpt;
|
|
167
|
+
const provider = this.options.provider;
|
|
168
|
+
if (provider === undefined) {
|
|
169
|
+
throw FyndError.config("provider is required for swapPayload");
|
|
170
|
+
}
|
|
171
|
+
const nonce = hints.nonce !== undefined
|
|
172
|
+
? hints.nonce
|
|
173
|
+
: await provider.getTransactionCount({ address: sender });
|
|
174
|
+
const { maxFeePerGas, maxPriorityFeePerGas } = hints.maxFeePerGas !== undefined && hints.maxPriorityFeePerGas !== undefined
|
|
175
|
+
? { maxFeePerGas: hints.maxFeePerGas, maxPriorityFeePerGas: hints.maxPriorityFeePerGas }
|
|
176
|
+
: await provider.estimateFeesPerGas();
|
|
177
|
+
const txData = quote.transaction;
|
|
178
|
+
if (txData === undefined) {
|
|
179
|
+
throw FyndError.config("quote has no calldata; set encodingOptions in QuoteOptions");
|
|
180
|
+
}
|
|
181
|
+
const txBase = {
|
|
182
|
+
chainId: this.options.chainId,
|
|
183
|
+
nonce,
|
|
184
|
+
maxFeePerGas,
|
|
185
|
+
maxPriorityFeePerGas,
|
|
186
|
+
to: txData.to,
|
|
187
|
+
value: txData.value,
|
|
188
|
+
data: txData.data,
|
|
189
|
+
};
|
|
190
|
+
const gas = hints.gasLimit !== undefined
|
|
191
|
+
? hints.gasLimit
|
|
192
|
+
: await provider.estimateGas({ ...txBase, gas: 0n });
|
|
193
|
+
const tx = { ...txBase, gas };
|
|
194
|
+
if (hints.simulate === true) {
|
|
195
|
+
await provider.call(tx).catch((err) => {
|
|
196
|
+
throw FyndError.simulateFailed(`transaction simulation failed: ${String(err)}`);
|
|
197
|
+
});
|
|
198
|
+
}
|
|
199
|
+
const payload = { quote, tx };
|
|
200
|
+
return { kind: 'fynd', payload };
|
|
201
|
+
}
|
|
202
|
+
/**
|
|
203
|
+
* Broadcasts a signed order on-chain and returns a handle to await settlement.
|
|
204
|
+
*
|
|
205
|
+
* Uses `submitProvider` if configured, otherwise falls back to `provider`.
|
|
206
|
+
* The signed transaction is serialized as an EIP-1559 envelope and sent via
|
|
207
|
+
* `eth_sendRawTransaction`.
|
|
208
|
+
*
|
|
209
|
+
* Call {@link ExecutionReceipt.settle} on the returned handle to poll for
|
|
210
|
+
* the transaction receipt. Settlement polling has a default timeout of
|
|
211
|
+
* {@link DEFAULT_SETTLE_TIMEOUT_MS} (120s), configurable via {@link SettleOptions.timeoutMs}.
|
|
212
|
+
* The settled result includes `gasCost` (gasUsed * effectiveGasPrice) and
|
|
213
|
+
* `settledAmount` (parsed from ERC-20/ERC-6909 Transfer logs to the receiver).
|
|
214
|
+
*
|
|
215
|
+
* When `dryRun` is `true`, the transaction is simulated via `eth_call` and
|
|
216
|
+
* `eth_estimateGas` without broadcasting. The returned `settle()` resolves
|
|
217
|
+
* immediately with estimated gas cost and decoded return data.
|
|
218
|
+
*
|
|
219
|
+
* @param order - A signed swap from {@link assembleSignedSwap}.
|
|
220
|
+
* @param options - Set `dryRun: true` to simulate without broadcasting.
|
|
221
|
+
* @throws {FyndError} With code `CONFIG` if no provider is configured.
|
|
222
|
+
* @throws {FyndError} With code `CONFIG` if the signature has an invalid v byte.
|
|
223
|
+
* @throws {FyndError} With code `SIMULATE_FAILED` when `dryRun` is `true` and the simulation reverts.
|
|
224
|
+
* @throws {FyndError} With code `EXECUTION_REVERTED` when the mined transaction reverts.
|
|
225
|
+
*/
|
|
226
|
+
async executeSwap(order, options) {
|
|
227
|
+
const { payload, signature } = order;
|
|
228
|
+
const tx = payload.payload.tx;
|
|
229
|
+
const quote = payload.payload.quote;
|
|
230
|
+
if (options?.dryRun === true) {
|
|
231
|
+
return this.dryRunExecute(tx, quote);
|
|
232
|
+
}
|
|
233
|
+
const provider = this.options.submitProvider ?? this.options.provider;
|
|
234
|
+
if (provider === undefined) {
|
|
235
|
+
throw FyndError.config("provider is required for executeSwap");
|
|
236
|
+
}
|
|
237
|
+
const txHash = await this.serializeAndBroadcast(tx, signature);
|
|
238
|
+
const tokenOut = quote.tokenOut;
|
|
239
|
+
const receiver = quote.receiver;
|
|
240
|
+
return {
|
|
241
|
+
settle: async (options) => {
|
|
242
|
+
const timeoutMs = options?.timeoutMs ?? DEFAULT_SETTLE_TIMEOUT_MS;
|
|
243
|
+
const receipt = await this.pollForReceipt(provider, txHash, timeoutMs);
|
|
244
|
+
if (receipt.status === 0) {
|
|
245
|
+
const reason = this.options.fetchRevertReason !== false
|
|
246
|
+
? await this.getRevertReason(provider, tx, txHash)
|
|
247
|
+
: 'revert reason fetching disabled';
|
|
248
|
+
throw FyndError.executionReverted(`swap reverted: ${reason}`);
|
|
249
|
+
}
|
|
250
|
+
const settledAmount = computeSettledAmount(receipt, tokenOut, receiver);
|
|
251
|
+
const gasCost = receipt.gasUsed * receipt.effectiveGasPrice;
|
|
252
|
+
// exactOptionalPropertyTypes: spread optional fields only when defined
|
|
253
|
+
return {
|
|
254
|
+
txHash,
|
|
255
|
+
gasCost,
|
|
256
|
+
...(settledAmount !== undefined ? { settledAmount } : {}),
|
|
257
|
+
};
|
|
258
|
+
},
|
|
259
|
+
};
|
|
260
|
+
}
|
|
261
|
+
async serializeAndBroadcast(tx, signature) {
|
|
262
|
+
const provider = this.options.submitProvider ?? this.options.provider;
|
|
263
|
+
if (provider === undefined) {
|
|
264
|
+
throw FyndError.config("provider is required for broadcast");
|
|
265
|
+
}
|
|
266
|
+
// Parse r, s, yParity from the 65-byte hex signature: r[32] + s[32] + v[1]
|
|
267
|
+
// signature is '0x' + 130 hex chars (65 bytes)
|
|
268
|
+
const r = `0x${signature.slice(2, 66)}`;
|
|
269
|
+
const s = `0x${signature.slice(66, 130)}`;
|
|
270
|
+
const vByte = parseInt(signature.slice(130, 132), 16);
|
|
271
|
+
// Normalize: legacy v=27/28 → yParity 0/1; EIP-1559 v=0/1 pass through
|
|
272
|
+
const vNormalized = vByte === 27 ? 0 : vByte === 28 ? 1 : vByte;
|
|
273
|
+
if (vNormalized !== 0 && vNormalized !== 1) {
|
|
274
|
+
throw FyndError.config(`invalid signature v byte: ${vByte}`);
|
|
275
|
+
}
|
|
276
|
+
const yParity = vNormalized;
|
|
277
|
+
const rawTx = serializeTransaction({
|
|
278
|
+
type: 'eip1559',
|
|
279
|
+
chainId: tx.chainId,
|
|
280
|
+
nonce: tx.nonce,
|
|
281
|
+
maxFeePerGas: tx.maxFeePerGas,
|
|
282
|
+
maxPriorityFeePerGas: tx.maxPriorityFeePerGas,
|
|
283
|
+
gas: tx.gas,
|
|
284
|
+
to: tx.to,
|
|
285
|
+
value: tx.value,
|
|
286
|
+
data: tx.data,
|
|
287
|
+
}, { r, s, yParity });
|
|
288
|
+
return provider.sendRawTransaction(rawTx);
|
|
289
|
+
}
|
|
290
|
+
async getRevertReason(provider, tx, txHash) {
|
|
291
|
+
if (provider.debugTraceTransaction !== undefined) {
|
|
292
|
+
try {
|
|
293
|
+
const trace = await provider.debugTraceTransaction(txHash);
|
|
294
|
+
return decodeRevertData(trace.output);
|
|
295
|
+
}
|
|
296
|
+
catch { /* fall through to eth_call */ }
|
|
297
|
+
}
|
|
298
|
+
console.warn('[fynd] debug_traceTransaction unavailable; replaying via eth_call — ' +
|
|
299
|
+
'revert reason may differ if block state has changed since execution');
|
|
300
|
+
return provider.call(tx).then(() => 'transaction reverted with no revert data', (err) => String(err));
|
|
301
|
+
}
|
|
302
|
+
async pollForReceipt(provider, txHash, timeoutMs) {
|
|
303
|
+
const deadline = Date.now() + timeoutMs;
|
|
304
|
+
for (;;) {
|
|
305
|
+
const receipt = await provider.getTransactionReceipt({ hash: txHash });
|
|
306
|
+
if (receipt !== null) {
|
|
307
|
+
return receipt;
|
|
308
|
+
}
|
|
309
|
+
if (Date.now() >= deadline) {
|
|
310
|
+
throw FyndError.timeout(`transaction ${txHash} did not settle within ${timeoutMs}ms`);
|
|
311
|
+
}
|
|
312
|
+
await sleep(2000);
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
/**
|
|
316
|
+
* Builds an unsigned EIP-1559 `approve(spender, amount)` transaction for the given token,
|
|
317
|
+
* or `null` if the approval is not needed.
|
|
318
|
+
*
|
|
319
|
+
* Returns `null` immediately when `params.transferType` is `'none'`.
|
|
320
|
+
* When `params.checkAllowance` is `true`, reads the on-chain allowance first and returns
|
|
321
|
+
* `null` if it is already sufficient (skipping nonce and fee resolution).
|
|
322
|
+
*
|
|
323
|
+
* Fetches the spender address from `GET /v1/info` (cached after first call):
|
|
324
|
+
* `'transfer_from'` → router, `'transfer_from_permit2'` → Permit2.
|
|
325
|
+
* Reads nonce and gas fees from `provider` unless overridden via `hints`.
|
|
326
|
+
* Gas defaults to `hints.gasLimit ?? 65_000n`.
|
|
327
|
+
*
|
|
328
|
+
* @param params - Token, amount, transfer type, and optional allowance-check flag.
|
|
329
|
+
* @param hints - Optional overrides for sender, nonce, gas fees, and gas limit.
|
|
330
|
+
* @throws {FyndError} With code `CONFIG` if `provider` or `sender` is not configured.
|
|
331
|
+
* @throws {FyndError} With code `CONFIG` if `params.checkAllowance` is `true` and `provider.readAllowance` is absent.
|
|
332
|
+
*/
|
|
333
|
+
async approval(params, hints) {
|
|
334
|
+
if (params.transferType === 'none')
|
|
335
|
+
return null;
|
|
336
|
+
const info = await this.info();
|
|
337
|
+
const spender = params.transferType === 'transfer_from_permit2'
|
|
338
|
+
? info.permit2Address
|
|
339
|
+
: info.routerAddress;
|
|
340
|
+
const provider = this.options.provider;
|
|
341
|
+
if (provider === undefined)
|
|
342
|
+
throw FyndError.config("provider is required for approval");
|
|
343
|
+
const senderOpt = hints?.sender ?? this.options.sender;
|
|
344
|
+
if (senderOpt === undefined)
|
|
345
|
+
throw FyndError.config("sender is required for approval");
|
|
346
|
+
const sender = senderOpt;
|
|
347
|
+
const { token, amount } = params;
|
|
348
|
+
if (params.checkAllowance === true) {
|
|
349
|
+
if (provider.readAllowance === undefined) {
|
|
350
|
+
throw FyndError.config("provider.readAllowance is required when checkAllowance is true");
|
|
351
|
+
}
|
|
352
|
+
const current = await provider.readAllowance(token, sender, spender);
|
|
353
|
+
if (current >= amount)
|
|
354
|
+
return null;
|
|
355
|
+
}
|
|
356
|
+
const nonce = hints?.nonce !== undefined
|
|
357
|
+
? hints.nonce
|
|
358
|
+
: await provider.getTransactionCount({ address: sender });
|
|
359
|
+
const { maxFeePerGas, maxPriorityFeePerGas } = hints?.maxFeePerGas !== undefined && hints?.maxPriorityFeePerGas !== undefined
|
|
360
|
+
? { maxFeePerGas: hints.maxFeePerGas, maxPriorityFeePerGas: hints.maxPriorityFeePerGas }
|
|
361
|
+
: await provider.estimateFeesPerGas();
|
|
362
|
+
const gas = hints?.gasLimit ?? 65000n;
|
|
363
|
+
const data = encodeFunctionData({
|
|
364
|
+
abi: ERC20_APPROVE_ABI,
|
|
365
|
+
functionName: 'approve',
|
|
366
|
+
args: [spender, amount],
|
|
367
|
+
});
|
|
368
|
+
const tx = {
|
|
369
|
+
chainId: this.options.chainId,
|
|
370
|
+
nonce,
|
|
371
|
+
maxFeePerGas,
|
|
372
|
+
maxPriorityFeePerGas,
|
|
373
|
+
gas,
|
|
374
|
+
to: token,
|
|
375
|
+
value: 0n,
|
|
376
|
+
data,
|
|
377
|
+
};
|
|
378
|
+
return { tx, token, spender, amount };
|
|
379
|
+
}
|
|
380
|
+
/**
|
|
381
|
+
* Broadcasts a signed ERC-20 approval and polls for inclusion.
|
|
382
|
+
*
|
|
383
|
+
* @param signedApproval - Signed approval from {@link approval} + wallet signature.
|
|
384
|
+
* @param options - Optional poll timeout (defaults to {@link DEFAULT_SETTLE_TIMEOUT_MS}).
|
|
385
|
+
* @throws {FyndError} With code `CONFIG` if no provider is configured.
|
|
386
|
+
* @throws {FyndError} With code `SETTLE_TIMEOUT` if the transaction does not confirm in time.
|
|
387
|
+
* @throws {FyndError} With code `EXECUTION_REVERTED` when the mined transaction reverts.
|
|
388
|
+
*/
|
|
389
|
+
async executeApproval(signedApproval, options) {
|
|
390
|
+
const provider = this.options.submitProvider ?? this.options.provider;
|
|
391
|
+
if (provider === undefined)
|
|
392
|
+
throw FyndError.config("provider is required for executeApproval");
|
|
393
|
+
const txHash = await this.serializeAndBroadcast(signedApproval.tx, signedApproval.signature);
|
|
394
|
+
const receipt = await this.pollForReceipt(provider, txHash, options?.timeoutMs ?? DEFAULT_SETTLE_TIMEOUT_MS);
|
|
395
|
+
if (receipt.status === 0) {
|
|
396
|
+
const reason = this.options.fetchRevertReason !== false
|
|
397
|
+
? await this.getRevertReason(provider, signedApproval.tx, txHash)
|
|
398
|
+
: 'revert reason fetching disabled';
|
|
399
|
+
throw FyndError.executionReverted(`approval reverted: ${reason}`);
|
|
400
|
+
}
|
|
401
|
+
return { txHash, gasCost: receipt.gasUsed * receipt.effectiveGasPrice };
|
|
402
|
+
}
|
|
403
|
+
async dryRunExecute(tx, quote) {
|
|
404
|
+
const provider = this.options.provider;
|
|
405
|
+
if (provider === undefined) {
|
|
406
|
+
throw FyndError.config("provider is required for dry-run execute");
|
|
407
|
+
}
|
|
408
|
+
const callResult = await provider.call(tx).catch((err) => {
|
|
409
|
+
throw FyndError.simulateFailed(`dry run simulation failed: ${String(err)}`);
|
|
410
|
+
});
|
|
411
|
+
const gasUsed = await provider.estimateGas(tx).catch((err) => {
|
|
412
|
+
throw FyndError.simulateFailed(`dry run gas estimation failed: ${String(err)}`);
|
|
413
|
+
});
|
|
414
|
+
// Parse first 32 bytes of return data as uint256 settled amount.
|
|
415
|
+
// Hex string: '0x' + 64 hex chars = 66 chars total for 32 bytes.
|
|
416
|
+
const returnData = callResult.data;
|
|
417
|
+
const settledAmount = returnData !== undefined && returnData.length >= 66
|
|
418
|
+
? BigInt(`0x${returnData.slice(2, 66)}`)
|
|
419
|
+
: undefined;
|
|
420
|
+
const gasCost = gasUsed * tx.maxFeePerGas;
|
|
421
|
+
// No txHash for dry-run
|
|
422
|
+
void quote;
|
|
423
|
+
return {
|
|
424
|
+
settle: async () => ({
|
|
425
|
+
gasCost,
|
|
426
|
+
// exactOptionalPropertyTypes: spread optional fields only when defined
|
|
427
|
+
...(settledAmount !== undefined ? { settledAmount } : {}),
|
|
428
|
+
}),
|
|
429
|
+
};
|
|
430
|
+
}
|
|
431
|
+
}
|
|
432
|
+
function sleep(ms) {
|
|
433
|
+
return new Promise(resolve => setTimeout(resolve, ms));
|
|
434
|
+
}
|
|
435
|
+
function computeSettledAmount(receipt, tokenOut, receiver) {
|
|
436
|
+
let total = 0n;
|
|
437
|
+
let found = false;
|
|
438
|
+
for (const log of receipt.logs) {
|
|
439
|
+
if (log.address.toLowerCase() !== tokenOut.toLowerCase())
|
|
440
|
+
continue;
|
|
441
|
+
if (log.topics.length === 0)
|
|
442
|
+
continue;
|
|
443
|
+
const topic0 = log.topics[0];
|
|
444
|
+
if (topic0 === undefined)
|
|
445
|
+
continue;
|
|
446
|
+
if (topic0 === ERC20_TRANSFER_TOPIC && log.topics.length >= 3) {
|
|
447
|
+
// topics[2] = to address (padded to 32 bytes, address in last 20 bytes)
|
|
448
|
+
const toTopic = log.topics[2];
|
|
449
|
+
if (toTopic === undefined)
|
|
450
|
+
continue;
|
|
451
|
+
const toAddr = `0x${toTopic.slice(-40)}`;
|
|
452
|
+
if (toAddr.toLowerCase() === receiver.toLowerCase()) {
|
|
453
|
+
// data = uint256 amount (32 bytes = 64 hex chars after '0x')
|
|
454
|
+
const amount = BigInt(`0x${log.data.slice(2, 66)}`);
|
|
455
|
+
total += amount;
|
|
456
|
+
found = true;
|
|
457
|
+
}
|
|
458
|
+
}
|
|
459
|
+
else if (topic0 === ERC6909_TRANSFER_TOPIC && log.topics.length >= 3) {
|
|
460
|
+
// topics[2] = to address
|
|
461
|
+
const toTopic = log.topics[2];
|
|
462
|
+
if (toTopic === undefined)
|
|
463
|
+
continue;
|
|
464
|
+
const toAddr = `0x${toTopic.slice(-40)}`;
|
|
465
|
+
if (toAddr.toLowerCase() === receiver.toLowerCase()) {
|
|
466
|
+
// data layout: caller[32 bytes] + amount[32 bytes]
|
|
467
|
+
// amount starts at byte offset 32 → hex positions 2+64=66 to 66+64=130
|
|
468
|
+
const amount = BigInt(`0x${log.data.slice(66, 130)}`);
|
|
469
|
+
total += amount;
|
|
470
|
+
found = true;
|
|
471
|
+
}
|
|
472
|
+
}
|
|
473
|
+
}
|
|
474
|
+
return found ? total : undefined;
|
|
475
|
+
}
|
|
476
|
+
const ERROR_SELECTOR = '0x08c379a0';
|
|
477
|
+
const PANIC_SELECTOR = '0x4e487b71';
|
|
478
|
+
/** Decode a Solidity revert payload into a human-readable string. */
|
|
479
|
+
function decodeRevertData(output) {
|
|
480
|
+
if (output === '0x')
|
|
481
|
+
return 'empty revert data';
|
|
482
|
+
if (output.startsWith(ERROR_SELECTOR) && output.length > 10) {
|
|
483
|
+
try {
|
|
484
|
+
const [msg] = decodeAbiParameters([{ type: 'string' }], `0x${output.slice(10)}`);
|
|
485
|
+
return msg;
|
|
486
|
+
}
|
|
487
|
+
catch { /* fall through */ }
|
|
488
|
+
}
|
|
489
|
+
if (output.startsWith(PANIC_SELECTOR) && output.length > 10) {
|
|
490
|
+
try {
|
|
491
|
+
const [code] = decodeAbiParameters([{ type: 'uint256' }], `0x${output.slice(10)}`);
|
|
492
|
+
return `Panic(${code})`;
|
|
493
|
+
}
|
|
494
|
+
catch { /* fall through */ }
|
|
495
|
+
}
|
|
496
|
+
return `revert data: ${output}`;
|
|
497
|
+
}
|
|
498
|
+
//# sourceMappingURL=client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.js","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
|
package/dist/error.d.ts
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import type { components } from "./autogen.js";
|
|
2
|
+
type WireErrorResponse = components["schemas"]["ErrorResponse"];
|
|
3
|
+
/** Error code returned by the Fynd server. Kept in sync with the server schema. */
|
|
4
|
+
export type ServerErrorCode = 'BAD_REQUEST' | 'NO_ROUTE_FOUND' | 'INSUFFICIENT_LIQUIDITY' | 'TIMEOUT' | 'QUEUE_FULL' | 'SERVICE_OVERLOADED' | 'STALE_DATA' | 'INVALID_ORDER' | 'INTERNAL_ERROR' | 'NOT_READY' | 'ALGORITHM_ERROR' | {
|
|
5
|
+
kind: 'UNKNOWN';
|
|
6
|
+
raw: string;
|
|
7
|
+
};
|
|
8
|
+
/** Error code originating from the client SDK itself. */
|
|
9
|
+
export type ClientErrorCode = 'HTTP' | 'DESERIALIZE' | 'CONFIG' | 'SIMULATE_FAILED' | 'SETTLE_TIMEOUT' | 'EXECUTION_REVERTED';
|
|
10
|
+
/** Union of all error codes, covering both server and client errors. */
|
|
11
|
+
export type ErrorCode = ServerErrorCode | ClientErrorCode;
|
|
12
|
+
/**
|
|
13
|
+
* Typed error thrown by all Fynd client operations.
|
|
14
|
+
*
|
|
15
|
+
* Use {@link FyndError.code} to programmatically handle specific failure modes,
|
|
16
|
+
* and {@link FyndError.isRetryable} to decide whether to retry.
|
|
17
|
+
*/
|
|
18
|
+
export declare class FyndError extends Error {
|
|
19
|
+
/** Machine-readable error code identifying the failure category. */
|
|
20
|
+
readonly code: ErrorCode;
|
|
21
|
+
/** Optional structured details from the server error response. */
|
|
22
|
+
readonly details?: unknown;
|
|
23
|
+
constructor(message: string, code: ErrorCode, details?: unknown);
|
|
24
|
+
/** Returns `true` if the error is transient and the operation can be retried. */
|
|
25
|
+
isRetryable(): boolean;
|
|
26
|
+
/** Creates a `FyndError` from a server error response or unstructured error. */
|
|
27
|
+
static fromWireError(wire: WireErrorResponse | unknown): FyndError;
|
|
28
|
+
/** Creates a `CONFIG` error for invalid or missing client configuration. */
|
|
29
|
+
static config(message: string): FyndError;
|
|
30
|
+
/** Creates a `SIMULATE_FAILED` error when an on-chain simulation reverts. */
|
|
31
|
+
static simulateFailed(reason: string): FyndError;
|
|
32
|
+
/** Creates a `SETTLE_TIMEOUT` error when transaction confirmation takes too long. */
|
|
33
|
+
static timeout(message: string): FyndError;
|
|
34
|
+
/** Creates an `EXECUTION_REVERTED` error when a mined transaction reverts. */
|
|
35
|
+
static executionReverted(reason: string): FyndError;
|
|
36
|
+
}
|
|
37
|
+
export {};
|
|
38
|
+
//# sourceMappingURL=error.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"error.d.ts","sourceRoot":"","sources":["../src/error.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,KAAK,iBAAiB,GAAG,UAAU,CAAC,SAAS,CAAC,CAAC,eAAe,CAAC,CAAC;AAEhE,mFAAmF;AACnF,MAAM,MAAM,eAAe,GACvB,aAAa,GACb,gBAAgB,GAChB,wBAAwB,GACxB,SAAS,GACT,YAAY,GACZ,oBAAoB,GACpB,YAAY,GACZ,eAAe,GACf,gBAAgB,GAChB,WAAW,GACX,iBAAiB,GACjB;IAAE,IAAI,EAAE,SAAS,CAAC;IAAC,GAAG,EAAE,MAAM,CAAA;CAAE,CAAC;AAErC,yDAAyD;AACzD,MAAM,MAAM,eAAe,GAAG,MAAM,GAAG,aAAa,GAAG,QAAQ,GAAG,iBAAiB,GAAG,gBAAgB,GAAG,oBAAoB,CAAC;AAE9H,wEAAwE;AACxE,MAAM,MAAM,SAAS,GAAG,eAAe,GAAG,eAAe,CAAC;AAyB1D;;;;;GAKG;AACH,qBAAa,SAAU,SAAQ,KAAK;IAClC,oEAAoE;IACpE,QAAQ,CAAC,IAAI,EAAE,SAAS,CAAC;IACzB,kEAAkE;IAClE,QAAQ,CAAC,OAAO,CAAC,EAAE,OAAO,CAAC;gBAEf,OAAO,EAAE,MAAM,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,CAAC,EAAE,OAAO;IAS/D,iFAAiF;IACjF,WAAW,IAAI,OAAO;IAOtB,gFAAgF;IAChF,MAAM,CAAC,aAAa,CAAC,IAAI,EAAE,iBAAiB,GAAG,OAAO,GAAG,SAAS;IAclE,4EAA4E;IAC5E,MAAM,CAAC,MAAM,CAAC,OAAO,EAAE,MAAM,GAAG,SAAS;IAIzC,6EAA6E;IAC7E,MAAM,CAAC,cAAc,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS;IAIhD,qFAAqF;IACrF,MAAM,CAAC,OAAO,CAAC,OAAO,EAAE,MAAM,GAAG,SAAS;IAI1C,8EAA8E;IAC9E,MAAM,CAAC,iBAAiB,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS;CAGpD"}
|
package/dist/error.js
ADDED
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
const KNOWN_SERVER_CODES = new Set([
|
|
2
|
+
'BAD_REQUEST',
|
|
3
|
+
'NO_ROUTE_FOUND',
|
|
4
|
+
'INSUFFICIENT_LIQUIDITY',
|
|
5
|
+
'TIMEOUT',
|
|
6
|
+
'QUEUE_FULL',
|
|
7
|
+
'SERVICE_OVERLOADED',
|
|
8
|
+
'STALE_DATA',
|
|
9
|
+
'INVALID_ORDER',
|
|
10
|
+
'INTERNAL_ERROR',
|
|
11
|
+
'NOT_READY',
|
|
12
|
+
'ALGORITHM_ERROR',
|
|
13
|
+
]);
|
|
14
|
+
const RETRYABLE_CODES = new Set([
|
|
15
|
+
'TIMEOUT',
|
|
16
|
+
'QUEUE_FULL',
|
|
17
|
+
'SERVICE_OVERLOADED',
|
|
18
|
+
'STALE_DATA',
|
|
19
|
+
'NOT_READY',
|
|
20
|
+
'HTTP',
|
|
21
|
+
]);
|
|
22
|
+
/**
|
|
23
|
+
* Typed error thrown by all Fynd client operations.
|
|
24
|
+
*
|
|
25
|
+
* Use {@link FyndError.code} to programmatically handle specific failure modes,
|
|
26
|
+
* and {@link FyndError.isRetryable} to decide whether to retry.
|
|
27
|
+
*/
|
|
28
|
+
export class FyndError extends Error {
|
|
29
|
+
constructor(message, code, details) {
|
|
30
|
+
super(message);
|
|
31
|
+
this.name = 'FyndError';
|
|
32
|
+
this.code = code;
|
|
33
|
+
if (details !== undefined) {
|
|
34
|
+
this.details = details;
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
/** Returns `true` if the error is transient and the operation can be retried. */
|
|
38
|
+
isRetryable() {
|
|
39
|
+
if (typeof this.code === 'string') {
|
|
40
|
+
return RETRYABLE_CODES.has(this.code);
|
|
41
|
+
}
|
|
42
|
+
return false;
|
|
43
|
+
}
|
|
44
|
+
/** Creates a `FyndError` from a server error response or unstructured error. */
|
|
45
|
+
static fromWireError(wire) {
|
|
46
|
+
const obj = wire;
|
|
47
|
+
const rawCode = obj['code'];
|
|
48
|
+
const rawError = obj['error'];
|
|
49
|
+
if (typeof rawCode !== 'string' || typeof rawError !== 'string') {
|
|
50
|
+
const message = typeof wire === 'string' ? wire : JSON.stringify(wire);
|
|
51
|
+
return new FyndError(message, 'HTTP');
|
|
52
|
+
}
|
|
53
|
+
const code = KNOWN_SERVER_CODES.has(rawCode)
|
|
54
|
+
? rawCode
|
|
55
|
+
: { kind: 'UNKNOWN', raw: rawCode };
|
|
56
|
+
return new FyndError(rawError, code, obj['details']);
|
|
57
|
+
}
|
|
58
|
+
/** Creates a `CONFIG` error for invalid or missing client configuration. */
|
|
59
|
+
static config(message) {
|
|
60
|
+
return new FyndError(message, 'CONFIG');
|
|
61
|
+
}
|
|
62
|
+
/** Creates a `SIMULATE_FAILED` error when an on-chain simulation reverts. */
|
|
63
|
+
static simulateFailed(reason) {
|
|
64
|
+
return new FyndError(reason, 'SIMULATE_FAILED');
|
|
65
|
+
}
|
|
66
|
+
/** Creates a `SETTLE_TIMEOUT` error when transaction confirmation takes too long. */
|
|
67
|
+
static timeout(message) {
|
|
68
|
+
return new FyndError(message, 'SETTLE_TIMEOUT');
|
|
69
|
+
}
|
|
70
|
+
/** Creates an `EXECUTION_REVERTED` error when a mined transaction reverts. */
|
|
71
|
+
static executionReverted(reason) {
|
|
72
|
+
return new FyndError(reason, 'EXECUTION_REVERTED');
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
//# sourceMappingURL=error.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"error.js","sourceRoot":"","sources":["../src/error.ts"],"names":[],"mappings":"AAyBA,MAAM,kBAAkB,GAAG,IAAI,GAAG,CAAC;IACjC,aAAa;IACb,gBAAgB;IAChB,wBAAwB;IACxB,SAAS;IACT,YAAY;IACZ,oBAAoB;IACpB,YAAY;IACZ,eAAe;IACf,gBAAgB;IAChB,WAAW;IACX,iBAAiB;CAClB,CAAC,CAAC;AAEH,MAAM,eAAe,GAAG,IAAI,GAAG,CAAS;IACtC,SAAS;IACT,YAAY;IACZ,oBAAoB;IACpB,YAAY;IACZ,WAAW;IACX,MAAM;CACP,CAAC,CAAC;AAEH;;;;;GAKG;AACH,MAAM,OAAO,SAAU,SAAQ,KAAK;IAMlC,YAAY,OAAe,EAAE,IAAe,EAAE,OAAiB;QAC7D,KAAK,CAAC,OAAO,CAAC,CAAC;QACf,IAAI,CAAC,IAAI,GAAG,WAAW,CAAC;QACxB,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC;QACjB,IAAI,OAAO,KAAK,SAAS,EAAE,CAAC;YAC1B,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACzB,CAAC;IACH,CAAC;IAED,iFAAiF;IACjF,WAAW;QACT,IAAI,OAAO,IAAI,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;YAClC,OAAO,eAAe,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACxC,CAAC;QACD,OAAO,KAAK,CAAC;IACf,CAAC;IAED,gFAAgF;IAChF,MAAM,CAAC,aAAa,CAAC,IAAiC;QACpD,MAAM,GAAG,GAAG,IAA+B,CAAC;QAC5C,MAAM,OAAO,GAAG,GAAG,CAAC,MAAM,CAAC,CAAC;QAC5B,MAAM,QAAQ,GAAG,GAAG,CAAC,OAAO,CAAC,CAAC;QAC9B,IAAI,OAAO,OAAO,KAAK,QAAQ,IAAI,OAAO,QAAQ,KAAK,QAAQ,EAAE,CAAC;YAChE,MAAM,OAAO,GAAG,OAAO,IAAI,KAAK,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;YACvE,OAAO,IAAI,SAAS,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;QACxC,CAAC;QACD,MAAM,IAAI,GAAc,kBAAkB,CAAC,GAAG,CAAC,OAAO,CAAC;YACrD,CAAC,CAAE,OAA2B;YAC9B,CAAC,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,GAAG,EAAE,OAAO,EAAE,CAAC;QACtC,OAAO,IAAI,SAAS,CAAC,QAAQ,EAAE,IAAI,EAAE,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC;IACvD,CAAC;IAED,4EAA4E;IAC5E,MAAM,CAAC,MAAM,CAAC,OAAe;QAC3B,OAAO,IAAI,SAAS,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;IAC1C,CAAC;IAED,6EAA6E;IAC7E,MAAM,CAAC,cAAc,CAAC,MAAc;QAClC,OAAO,IAAI,SAAS,CAAC,MAAM,EAAE,iBAAiB,CAAC,CAAC;IAClD,CAAC;IAED,qFAAqF;IACrF,MAAM,CAAC,OAAO,CAAC,OAAe;QAC5B,OAAO,IAAI,SAAS,CAAC,OAAO,EAAE,gBAAgB,CAAC,CAAC;IAClD,CAAC;IAED,8EAA8E;IAC9E,MAAM,CAAC,iBAAiB,CAAC,MAAc;QACrC,OAAO,IAAI,SAAS,CAAC,MAAM,EAAE,oBAAoB,CAAC,CAAC;IACrD,CAAC;CACF"}
|