@metamask-previews/transaction-pay-controller 22.4.0-preview-fe92f4bb3 → 22.5.0-preview-9b6bf0851
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +9 -2
- package/dist/strategy/across/across-quotes.cjs +126 -18
- package/dist/strategy/across/across-quotes.cjs.map +1 -1
- package/dist/strategy/across/across-quotes.d.cts.map +1 -1
- package/dist/strategy/across/across-quotes.d.mts.map +1 -1
- package/dist/strategy/across/across-quotes.mjs +126 -18
- package/dist/strategy/across/across-quotes.mjs.map +1 -1
- package/dist/utils/feature-flags.cjs +2 -2
- package/dist/utils/feature-flags.cjs.map +1 -1
- package/dist/utils/feature-flags.d.cts +0 -1
- package/dist/utils/feature-flags.d.cts.map +1 -1
- package/dist/utils/feature-flags.d.mts +0 -1
- package/dist/utils/feature-flags.d.mts.map +1 -1
- package/dist/utils/feature-flags.mjs +2 -2
- package/dist/utils/feature-flags.mjs.map +1 -1
- package/dist/utils/gas-station.cjs +1 -1
- package/dist/utils/gas-station.cjs.map +1 -1
- package/dist/utils/gas-station.mjs +1 -1
- package/dist/utils/gas-station.mjs.map +1 -1
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,12 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
### Fixed
|
|
11
|
+
|
|
12
|
+
- Handle gas-station and prefunded gas-estimate edge cases for Across Predict withdraw quotes ([#8762](https://github.com/MetaMask/core/pull/8762))
|
|
13
|
+
|
|
14
|
+
## [22.5.0]
|
|
15
|
+
|
|
10
16
|
### Added
|
|
11
17
|
|
|
12
18
|
- Add Across submit support for post-quote Predict withdraw flows ([#8761](https://github.com/MetaMask/core/pull/8761))
|
|
@@ -14,7 +20,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
14
20
|
|
|
15
21
|
### Changed
|
|
16
22
|
|
|
17
|
-
-
|
|
23
|
+
- Move the Relay gasless execution feature flag to `confirmations_pay_extended.payStrategies.relay.gaslessEnabled` ([#8810](https://github.com/MetaMask/core/pull/8810))
|
|
18
24
|
|
|
19
25
|
## [22.4.0]
|
|
20
26
|
|
|
@@ -894,7 +900,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
894
900
|
|
|
895
901
|
- Initial release ([#6820](https://github.com/MetaMask/core/pull/6820))
|
|
896
902
|
|
|
897
|
-
[Unreleased]: https://github.com/MetaMask/core/compare/@metamask/transaction-pay-controller@22.
|
|
903
|
+
[Unreleased]: https://github.com/MetaMask/core/compare/@metamask/transaction-pay-controller@22.5.0...HEAD
|
|
904
|
+
[22.5.0]: https://github.com/MetaMask/core/compare/@metamask/transaction-pay-controller@22.4.0...@metamask/transaction-pay-controller@22.5.0
|
|
898
905
|
[22.4.0]: https://github.com/MetaMask/core/compare/@metamask/transaction-pay-controller@22.3.1...@metamask/transaction-pay-controller@22.4.0
|
|
899
906
|
[22.3.1]: https://github.com/MetaMask/core/compare/@metamask/transaction-pay-controller@22.3.0...@metamask/transaction-pay-controller@22.3.1
|
|
900
907
|
[22.3.0]: https://github.com/MetaMask/core/compare/@metamask/transaction-pay-controller@22.2.0...@metamask/transaction-pay-controller@22.3.0
|
|
@@ -193,7 +193,7 @@ async function normalizeQuote(original, request, fullRequest) {
|
|
|
193
193
|
const { usdToFiatRate, sourceFiatRate, targetFiatRate } = getFiatRates(messenger, quote);
|
|
194
194
|
const dustUsd = calculateDustUsd(quote, request, targetFiatRate);
|
|
195
195
|
const dust = (0, amounts_1.getFiatValueFromUsd)(dustUsd, usdToFiatRate);
|
|
196
|
-
const { gasLimits, is7702, isGasFeeToken: isSourceGasFeeToken, requiresAuthorizationList, sourceNetwork, } = await calculateSourceNetworkCost(quote, messenger, request, fullRequest.transaction);
|
|
196
|
+
const { gasLimits, is7702, isGasFeeToken: isSourceGasFeeToken, requiresAuthorizationList, sourceNetwork, } = await calculateSourceNetworkCost(quote, messenger, request, fullRequest.transaction, fullRequest.accountSupports7702);
|
|
197
197
|
const targetNetwork = (0, amounts_1.getFiatValueFromUsd)(new bignumber_js_1.BigNumber(0), usdToFiatRate);
|
|
198
198
|
const inputAmountRaw = quote.inputAmount ?? '0';
|
|
199
199
|
const outputAmountRaw = new bignumber_js_1.BigNumber(quote.expectedOutputAmount ??
|
|
@@ -295,23 +295,28 @@ function getAmountFromTokenAmount({ amountRaw, decimals, fiatRate, }) {
|
|
|
295
295
|
usd,
|
|
296
296
|
};
|
|
297
297
|
}
|
|
298
|
-
async function calculateSourceNetworkCost(quote, messenger, request, transaction) {
|
|
298
|
+
async function calculateSourceNetworkCost(quote, messenger, request, transaction, accountSupports7702) {
|
|
299
299
|
const acrossFallbackGas = (0, feature_flags_1.getPayStrategiesConfig)(messenger).across.fallbackGas;
|
|
300
300
|
const { from, sourceChainId, sourceTokenAddress } = request;
|
|
301
301
|
const orderedTransactions = (0, transactions_1.getAcrossOrderedTransactions)({ quote });
|
|
302
302
|
const { swapTx } = quote;
|
|
303
303
|
const swapChainId = (0, controller_utils_1.toHex)(swapTx.chainId);
|
|
304
|
-
const
|
|
304
|
+
const isPredictWithdraw = request.isPostQuote === true && (0, transaction_1.isPredictWithdrawTransaction)(transaction);
|
|
305
|
+
const relaxPrefundedSourceEstimate = isPredictWithdraw &&
|
|
306
|
+
new bignumber_js_1.BigNumber(request.sourceTokenAmount).gt(request.sourceBalanceRaw);
|
|
307
|
+
const gasEstimateTransactions = orderedTransactions.map((orderedTransaction) => ({
|
|
308
|
+
chainId: (0, controller_utils_1.toHex)(orderedTransaction.chainId),
|
|
309
|
+
data: orderedTransaction.data,
|
|
310
|
+
from,
|
|
311
|
+
gas: orderedTransaction.gas,
|
|
312
|
+
to: orderedTransaction.to,
|
|
313
|
+
value: orderedTransaction.value ?? '0x0',
|
|
314
|
+
}));
|
|
315
|
+
const gasEstimates = await estimateAcrossQuoteGasLimits({
|
|
305
316
|
fallbackGas: acrossFallbackGas,
|
|
317
|
+
fallbackOnSimulationFailure: relaxPrefundedSourceEstimate,
|
|
306
318
|
messenger,
|
|
307
|
-
transactions:
|
|
308
|
-
chainId: (0, controller_utils_1.toHex)(orderedTransaction.chainId),
|
|
309
|
-
data: orderedTransaction.data,
|
|
310
|
-
from,
|
|
311
|
-
gas: orderedTransaction.gas,
|
|
312
|
-
to: orderedTransaction.to,
|
|
313
|
-
value: orderedTransaction.value ?? '0x0',
|
|
314
|
-
})),
|
|
319
|
+
transactions: gasEstimateTransactions,
|
|
315
320
|
});
|
|
316
321
|
const { batchGasLimit, is7702, requiresAuthorizationList, totalGasEstimate } = gasEstimates;
|
|
317
322
|
let sourceNetwork;
|
|
@@ -388,7 +393,10 @@ async function calculateSourceNetworkCost(quote, messenger, request, transaction
|
|
|
388
393
|
: result;
|
|
389
394
|
const nativeBalance = (0, token_1.getTokenBalance)(messenger, from, sourceChainId, (0, token_1.getNativeToken)(sourceChainId));
|
|
390
395
|
const hasNativeBalance = new bignumber_js_1.BigNumber(nativeBalance).isGreaterThanOrEqualTo(finalResult.sourceNetwork.max.raw);
|
|
391
|
-
if (
|
|
396
|
+
if (isPredictWithdraw && !accountSupports7702) {
|
|
397
|
+
return finalResult;
|
|
398
|
+
}
|
|
399
|
+
if (hasNativeBalance && !isPredictWithdraw) {
|
|
392
400
|
return finalResult;
|
|
393
401
|
}
|
|
394
402
|
const gasStationEligibility = (0, gas_station_1.getGasStationEligibility)(messenger, sourceChainId);
|
|
@@ -418,23 +426,123 @@ async function calculateSourceNetworkCost(quote, messenger, request, transaction
|
|
|
418
426
|
totalGasEstimate: finalResult.totalGasEstimate,
|
|
419
427
|
totalItemCount: Math.max(orderedTransactions.length + (request.isPostQuote ? 1 : 0), finalResult.gasLimits.length),
|
|
420
428
|
});
|
|
421
|
-
|
|
429
|
+
let gasFeeTokenNetwork;
|
|
430
|
+
if (gasFeeTokenCost) {
|
|
431
|
+
gasFeeTokenNetwork = {
|
|
432
|
+
estimate: gasFeeTokenCost,
|
|
433
|
+
max: gasFeeTokenCost,
|
|
434
|
+
};
|
|
435
|
+
}
|
|
436
|
+
else if (isPredictWithdraw) {
|
|
437
|
+
gasFeeTokenNetwork = calculateSourceGasFeeTokenNetworkFallback({
|
|
438
|
+
messenger,
|
|
439
|
+
nativeSourceNetwork: finalResult.sourceNetwork,
|
|
440
|
+
quote,
|
|
441
|
+
request,
|
|
442
|
+
});
|
|
443
|
+
}
|
|
444
|
+
if (!gasFeeTokenNetwork) {
|
|
422
445
|
return finalResult;
|
|
423
446
|
}
|
|
424
447
|
log('Using gas fee token for Across source network', {
|
|
425
|
-
gasFeeTokenCost,
|
|
448
|
+
gasFeeTokenCost: gasFeeTokenNetwork.max,
|
|
426
449
|
});
|
|
427
450
|
return {
|
|
428
451
|
isGasFeeToken: true,
|
|
429
|
-
sourceNetwork:
|
|
430
|
-
estimate: gasFeeTokenCost,
|
|
431
|
-
max: gasFeeTokenCost,
|
|
432
|
-
},
|
|
452
|
+
sourceNetwork: gasFeeTokenNetwork,
|
|
433
453
|
is7702: finalResult.is7702,
|
|
434
454
|
...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),
|
|
435
455
|
gasLimits: finalResult.gasLimits,
|
|
436
456
|
};
|
|
437
457
|
}
|
|
458
|
+
function calculateSourceGasFeeTokenNetworkFallback({ messenger, nativeSourceNetwork, quote, request, }) {
|
|
459
|
+
const sourceFiatRate = (0, token_1.getTokenFiatRate)(messenger, request.sourceTokenAddress, request.sourceChainId);
|
|
460
|
+
if (!sourceFiatRate) {
|
|
461
|
+
return undefined;
|
|
462
|
+
}
|
|
463
|
+
const estimate = calculateSourceGasFeeTokenAmountFallback({
|
|
464
|
+
decimals: quote.inputToken.decimals,
|
|
465
|
+
fiatRate: sourceFiatRate,
|
|
466
|
+
nativeGasCost: nativeSourceNetwork.estimate,
|
|
467
|
+
});
|
|
468
|
+
const max = calculateSourceGasFeeTokenAmountFallback({
|
|
469
|
+
decimals: quote.inputToken.decimals,
|
|
470
|
+
fiatRate: sourceFiatRate,
|
|
471
|
+
nativeGasCost: nativeSourceNetwork.max,
|
|
472
|
+
});
|
|
473
|
+
if (!estimate || !max) {
|
|
474
|
+
return undefined;
|
|
475
|
+
}
|
|
476
|
+
return { estimate, max };
|
|
477
|
+
}
|
|
478
|
+
function calculateSourceGasFeeTokenAmountFallback({ decimals, fiatRate, nativeGasCost, }) {
|
|
479
|
+
const usdRate = new bignumber_js_1.BigNumber(fiatRate.usdRate);
|
|
480
|
+
const nativeGasUsd = new bignumber_js_1.BigNumber(nativeGasCost.usd);
|
|
481
|
+
if (!usdRate.isFinite() ||
|
|
482
|
+
!usdRate.isGreaterThan(0) ||
|
|
483
|
+
!nativeGasUsd.isFinite() ||
|
|
484
|
+
!nativeGasUsd.isGreaterThan(0)) {
|
|
485
|
+
return undefined;
|
|
486
|
+
}
|
|
487
|
+
const amountRaw = nativeGasUsd
|
|
488
|
+
.dividedBy(usdRate)
|
|
489
|
+
.shiftedBy(decimals)
|
|
490
|
+
.integerValue(bignumber_js_1.BigNumber.ROUND_CEIL)
|
|
491
|
+
.toFixed(0);
|
|
492
|
+
return getAmountFromTokenAmount({
|
|
493
|
+
amountRaw,
|
|
494
|
+
decimals,
|
|
495
|
+
fiatRate,
|
|
496
|
+
});
|
|
497
|
+
}
|
|
498
|
+
async function estimateAcrossQuoteGasLimits({ fallbackGas, fallbackOnSimulationFailure, messenger, transactions, }) {
|
|
499
|
+
try {
|
|
500
|
+
const gasEstimates = await (0, quote_gas_1.estimateQuoteGasLimits)({
|
|
501
|
+
fallbackGas,
|
|
502
|
+
fallbackOnSimulationFailure,
|
|
503
|
+
messenger,
|
|
504
|
+
transactions,
|
|
505
|
+
});
|
|
506
|
+
if (fallbackOnSimulationFailure &&
|
|
507
|
+
fallbackGas !== undefined &&
|
|
508
|
+
gasEstimates.is7702 &&
|
|
509
|
+
gasEstimates.batchGasLimit !== undefined &&
|
|
510
|
+
gasEstimates.batchGasLimit.max > fallbackGas.max) {
|
|
511
|
+
// Prefunded Predict withdraws can produce inflated 7702 batch estimates
|
|
512
|
+
// because the source account does not yet hold the funds. Keep the gas
|
|
513
|
+
// reservation bounded by the configured Across fallback for this path.
|
|
514
|
+
return {
|
|
515
|
+
...gasEstimates,
|
|
516
|
+
batchGasLimit: fallbackGas,
|
|
517
|
+
gasLimits: [fallbackGas],
|
|
518
|
+
totalGasEstimate: fallbackGas.estimate,
|
|
519
|
+
totalGasLimit: fallbackGas.max,
|
|
520
|
+
};
|
|
521
|
+
}
|
|
522
|
+
return gasEstimates;
|
|
523
|
+
}
|
|
524
|
+
catch (error) {
|
|
525
|
+
if (!fallbackOnSimulationFailure || transactions.length <= 1) {
|
|
526
|
+
throw error;
|
|
527
|
+
}
|
|
528
|
+
const perTransactionGasEstimates = await Promise.all(transactions.map((transaction) => (0, quote_gas_1.estimateQuoteGasLimits)({
|
|
529
|
+
fallbackGas,
|
|
530
|
+
fallbackOnSimulationFailure: true,
|
|
531
|
+
messenger,
|
|
532
|
+
transactions: [transaction],
|
|
533
|
+
})));
|
|
534
|
+
const gasLimits = perTransactionGasEstimates.map((estimate) => estimate.gasLimits[0]);
|
|
535
|
+
const totalGasEstimate = gasLimits.reduce((total, gasLimit) => total + gasLimit.estimate, 0);
|
|
536
|
+
const totalGasLimit = gasLimits.reduce((total, gasLimit) => total + gasLimit.max, 0);
|
|
537
|
+
return {
|
|
538
|
+
gasLimits,
|
|
539
|
+
is7702: false,
|
|
540
|
+
totalGasEstimate,
|
|
541
|
+
totalGasLimit,
|
|
542
|
+
usedBatch: false,
|
|
543
|
+
};
|
|
544
|
+
}
|
|
545
|
+
}
|
|
438
546
|
function combinePostQuoteGas(gasResult, transaction, swapTx, messenger) {
|
|
439
547
|
const originalTxGas = (0, transactions_1.getOriginalTransactionGas)(transaction);
|
|
440
548
|
if (originalTxGas === undefined) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"across-quotes.cjs","sourceRoot":"","sources":["../../../src/strategy/across/across-quotes.ts"],"names":[],"mappings":"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","sourcesContent":["import { successfulFetch, toHex } from '@metamask/controller-utils';\nimport type { TransactionMeta } from '@metamask/transaction-controller';\nimport type { Hex } from '@metamask/utils';\nimport { createModuleLogger } from '@metamask/utils';\nimport { BigNumber } from 'bignumber.js';\n\nimport { TransactionPayStrategy } from '../../constants';\nimport { projectLogger } from '../../logger';\nimport type {\n Amount,\n FiatRates,\n PayStrategyGetQuotesRequest,\n QuoteRequest,\n TransactionPayControllerMessenger,\n TransactionPayQuote,\n} from '../../types';\nimport { getFiatValueFromUsd, sumAmounts } from '../../utils/amounts';\nimport { getPayStrategiesConfig, getSlippage } from '../../utils/feature-flags';\nimport { calculateGasCost } from '../../utils/gas';\nimport {\n getGasStationCostInSourceTokenRaw,\n getGasStationEligibility,\n} from '../../utils/gas-station';\nimport { estimateQuoteGasLimits } from '../../utils/quote-gas';\nimport {\n getNativeToken,\n getTokenBalance,\n getTokenFiatRate,\n} from '../../utils/token';\nimport { isPredictWithdrawTransaction } from '../../utils/transaction';\nimport type { AcrossDestination } from './across-actions';\nimport { getAcrossDestination } from './across-actions';\nimport { hasUnsupportedTransactionAuthorizationList } from './authorization-list';\nimport { normalizeAcrossRequest } from './perps';\nimport { isAcrossQuoteRequest } from './requests';\nimport {\n getAcrossOrderedTransactions,\n getOriginalTransactionGas,\n} from './transactions';\nimport type {\n AcrossAction,\n AcrossActionRequestBody,\n AcrossGasLimits,\n AcrossQuote,\n AcrossSwapApprovalResponse,\n} from './types';\n\nconst log = createModuleLogger(projectLogger, 'across-strategy');\n\nconst UNSUPPORTED_AUTHORIZATION_LIST_ERROR =\n 'Across does not support type-4/EIP-7702 authorization lists yet';\n\ntype AcrossQuoteWithoutMetaMask = Omit<AcrossQuote, 'metamask'>;\n\n/**\n * Fetch Across quotes.\n *\n * @param request - Request object.\n * @returns Array of quotes.\n */\nexport async function getAcrossQuotes(\n request: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>[]> {\n const { requests } = request;\n\n log('Fetching quotes', requests);\n\n try {\n const normalizedRequests = requests.filter(isAcrossQuoteRequest);\n\n if (normalizedRequests.length === 0) {\n return [];\n }\n\n if (\n hasUnsupportedTransactionAuthorizationList(\n request.transaction,\n normalizedRequests,\n )\n ) {\n throw new Error(UNSUPPORTED_AUTHORIZATION_LIST_ERROR);\n }\n\n return await Promise.all(\n normalizedRequests.map((singleRequest) =>\n getQuoteWithGasStationHandling(singleRequest, request),\n ),\n );\n } catch (error) {\n log('Error fetching quotes', { error });\n throw new Error(`Failed to fetch Across quotes: ${String(error)}`);\n }\n}\n\nasync function getSingleQuote(\n request: QuoteRequest,\n fullRequest: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>> {\n const { messenger, signal, transaction } = fullRequest;\n const normalizedRequest = normalizeAcrossRequest(request, transaction.type);\n const {\n from,\n isMaxAmount,\n sourceChainId,\n sourceTokenAddress,\n sourceTokenAmount,\n targetAmountMinimum,\n targetChainId,\n targetTokenAddress,\n } = normalizedRequest;\n\n const config = getPayStrategiesConfig(messenger);\n const slippageDecimal = getSlippage(\n messenger,\n sourceChainId,\n sourceTokenAddress,\n );\n\n const useExactInput = isMaxAmount\n ? true\n : normalizedRequest.isPostQuote === true;\n const amount = useExactInput ? sourceTokenAmount : targetAmountMinimum;\n const tradeType = useExactInput ? 'exactInput' : 'exactOutput';\n const destination = getAcrossDestinationForRequest(\n transaction,\n request,\n from,\n );\n\n const quote = await requestAcrossApproval({\n actions: destination.actions,\n amount,\n apiBase: config.across.apiBase,\n depositor: from,\n destinationChainId: targetChainId,\n inputToken: sourceTokenAddress,\n originChainId: sourceChainId,\n outputToken: targetTokenAddress,\n recipient: destination.recipient,\n signal,\n refundAddress: normalizedRequest.refundTo,\n slippage: slippageDecimal,\n tradeType,\n });\n\n const originalQuote: AcrossQuoteWithoutMetaMask = {\n quote,\n request: {\n actions: destination.actions,\n amount,\n tradeType,\n },\n };\n\n return await normalizeQuote(originalQuote, normalizedRequest, fullRequest);\n}\n\nfunction getAcrossDestinationForRequest(\n transaction: TransactionMeta,\n request: QuoteRequest,\n recipient: Hex,\n): AcrossDestination {\n if (request.isPostQuote) {\n return {\n actions: [],\n recipient,\n };\n }\n\n return getAcrossDestination(transaction, request);\n}\n\nasync function getQuoteWithGasStationHandling(\n request: QuoteRequest,\n fullRequest: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>> {\n // Phase 1 uses the requested source amount to discover whether Across will\n // pay source-chain gas with the source token, and what the max gas cost is.\n // Phase 2 repeats the quote with that max gas cost reserved from the source\n // amount, so execution can fund both the Across deposit and token-paid gas.\n const phase1Quote = await getSingleQuote(request, fullRequest);\n\n if (\n (!request.isMaxAmount && !request.isPostQuote) ||\n !phase1Quote.fees.isSourceGasFeeToken\n ) {\n return phase1Quote;\n }\n\n const requiresSourceGasReservation =\n request.isPostQuote === true &&\n isPredictWithdrawTransaction(fullRequest.transaction);\n\n const adjustedSourceAmount = new BigNumber(request.sourceTokenAmount)\n .minus(phase1Quote.fees.sourceNetwork.max.raw)\n .integerValue(BigNumber.ROUND_DOWN);\n\n if (!adjustedSourceAmount.isGreaterThan(0)) {\n log('Insufficient balance after gas subtraction for Across quote');\n if (requiresSourceGasReservation) {\n throw new Error(\n 'Across Predict withdraw source amount cannot cover source gas fee token',\n );\n }\n return phase1Quote;\n }\n\n log('Subtracting gas from source for Across quote', {\n adjustedSourceAmount: adjustedSourceAmount.toString(10),\n gasCostRaw: phase1Quote.fees.sourceNetwork.max.raw,\n originalSourceAmount: request.sourceTokenAmount,\n });\n\n try {\n const phase2Quote = await getSingleQuote(\n {\n ...request,\n sourceTokenAmount: adjustedSourceAmount.toFixed(\n 0,\n BigNumber.ROUND_DOWN,\n ),\n },\n fullRequest,\n );\n\n if (!phase2Quote.fees.isSourceGasFeeToken) {\n log('Across phase 2 lost gas fee token eligibility');\n if (requiresSourceGasReservation) {\n throw new Error(\n 'Across Predict withdraw quote lost source gas fee token eligibility',\n );\n }\n return phase1Quote;\n }\n\n const phase2GasCost = new BigNumber(phase2Quote.fees.sourceNetwork.max.raw);\n\n if (\n adjustedSourceAmount\n .plus(phase2GasCost)\n .isGreaterThan(request.sourceTokenAmount)\n ) {\n log('Across phase 2 quote exceeds original source amount', {\n adjustedSourceAmount: adjustedSourceAmount.toString(10),\n gasCostRaw: phase2GasCost.toString(10),\n originalSourceAmount: request.sourceTokenAmount,\n });\n if (requiresSourceGasReservation) {\n throw new Error(\n 'Across Predict withdraw source gas fee token quote exceeds source amount',\n );\n }\n return phase1Quote;\n }\n\n return phase2Quote;\n } catch (error) {\n log(\n requiresSourceGasReservation\n ? 'Across phase 2 quote failed after source gas reservation'\n : 'Across phase 2 quote failed, falling back to phase 1',\n { error },\n );\n if (requiresSourceGasReservation) {\n throw error;\n }\n return phase1Quote;\n }\n}\n\ntype AcrossApprovalRequest = {\n actions: AcrossAction[];\n amount: string;\n apiBase: string;\n depositor: Hex;\n destinationChainId: Hex;\n inputToken: Hex;\n originChainId: Hex;\n outputToken: Hex;\n recipient: Hex;\n refundAddress?: Hex;\n signal?: AbortSignal;\n slippage?: number;\n tradeType: 'exactInput' | 'exactOutput';\n};\n\nasync function requestAcrossApproval(\n request: AcrossApprovalRequest,\n): Promise<AcrossSwapApprovalResponse> {\n const {\n actions,\n amount,\n apiBase,\n depositor,\n destinationChainId,\n inputToken,\n originChainId,\n outputToken,\n recipient,\n refundAddress,\n signal,\n slippage,\n tradeType,\n } = request;\n\n const params = new URLSearchParams();\n params.set('tradeType', tradeType);\n params.set('amount', amount);\n params.set('inputToken', inputToken);\n params.set('outputToken', outputToken);\n params.set('originChainId', String(parseInt(originChainId, 16)));\n params.set('destinationChainId', String(parseInt(destinationChainId, 16)));\n params.set('depositor', depositor);\n params.set('recipient', recipient);\n\n if (refundAddress !== undefined) {\n params.set('refundAddress', refundAddress);\n }\n\n if (slippage !== undefined) {\n params.set('slippage', String(slippage));\n }\n\n const body: AcrossActionRequestBody = { actions };\n const url = `${apiBase}/swap/approval?${params.toString()}`;\n const options: RequestInit = {\n body: JSON.stringify(body),\n headers: {\n Accept: 'application/json',\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n signal,\n };\n\n const response = await successfulFetch(url, options);\n\n return (await response.json()) as AcrossSwapApprovalResponse;\n}\n\nasync function normalizeQuote(\n original: AcrossQuoteWithoutMetaMask,\n request: QuoteRequest,\n fullRequest: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>> {\n const { messenger } = fullRequest;\n const { quote } = original;\n\n const { usdToFiatRate, sourceFiatRate, targetFiatRate } = getFiatRates(\n messenger,\n quote,\n );\n\n const dustUsd = calculateDustUsd(quote, request, targetFiatRate);\n const dust = getFiatValueFromUsd(dustUsd, usdToFiatRate);\n\n const {\n gasLimits,\n is7702,\n isGasFeeToken: isSourceGasFeeToken,\n requiresAuthorizationList,\n sourceNetwork,\n } = await calculateSourceNetworkCost(\n quote,\n messenger,\n request,\n fullRequest.transaction,\n );\n\n const targetNetwork = getFiatValueFromUsd(new BigNumber(0), usdToFiatRate);\n\n const inputAmountRaw = quote.inputAmount ?? '0';\n const outputAmountRaw = new BigNumber(\n quote.expectedOutputAmount ??\n quote.minOutputAmount ??\n request.targetAmountMinimum ??\n '0',\n ).toString(10);\n\n const sourceAmount = getAmountFromTokenAmount({\n amountRaw: inputAmountRaw,\n decimals: quote.inputToken.decimals,\n fiatRate: sourceFiatRate,\n });\n\n const providerUsd = calculateProviderUsd(\n quote,\n inputAmountRaw,\n sourceFiatRate,\n targetFiatRate,\n quote.expectedOutputAmount,\n );\n const provider = getFiatValueFromUsd(providerUsd, usdToFiatRate);\n const metaMaskFee = getFiatValueFromUsd(\n new BigNumber(quote.fees?.app?.amountUsd ?? '0').abs(),\n usdToFiatRate,\n );\n\n const targetAmount = getAmountFromTokenAmount({\n amountRaw: outputAmountRaw,\n decimals: quote.outputToken.decimals,\n fiatRate: targetFiatRate,\n });\n\n const metamask = {\n gasLimits,\n is7702,\n ...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),\n };\n\n return {\n dust,\n estimatedDuration: quote.expectedFillTime ?? 0,\n fees: {\n isSourceGasFeeToken,\n metaMask: metaMaskFee,\n provider,\n sourceNetwork,\n targetNetwork,\n },\n original: {\n ...original,\n metamask,\n },\n request,\n sourceAmount,\n targetAmount,\n strategy: TransactionPayStrategy.Across,\n } as TransactionPayQuote<AcrossQuote>;\n}\n\nfunction getFiatRates(\n messenger: TransactionPayControllerMessenger,\n quote: AcrossSwapApprovalResponse,\n): {\n sourceFiatRate: FiatRates;\n targetFiatRate: FiatRates;\n usdToFiatRate: BigNumber;\n} {\n const sourceFiatRate = getTokenFiatRate(\n messenger,\n quote.inputToken.address,\n toHex(quote.inputToken.chainId),\n );\n\n if (!sourceFiatRate) {\n throw new Error('Source token fiat rate not found');\n }\n\n const targetFiatRate =\n getTokenFiatRate(\n messenger,\n quote.outputToken.address,\n toHex(quote.outputToken.chainId),\n ) ?? sourceFiatRate;\n\n const usdToFiatRate = new BigNumber(sourceFiatRate.fiatRate).dividedBy(\n sourceFiatRate.usdRate,\n );\n\n return { sourceFiatRate, targetFiatRate, usdToFiatRate };\n}\n\nfunction calculateDustUsd(\n quote: AcrossSwapApprovalResponse,\n request: QuoteRequest,\n targetFiatRate: FiatRates,\n): BigNumber {\n const expectedOutputRaw = quote.expectedOutputAmount;\n\n if (expectedOutputRaw === undefined) {\n return new BigNumber(0);\n }\n\n const expectedOutput = new BigNumber(expectedOutputRaw);\n const minimumOutput = new BigNumber(\n quote.minOutputAmount ?? request.targetAmountMinimum ?? '0',\n );\n\n const dustRaw = expectedOutput.minus(minimumOutput).isNegative()\n ? new BigNumber(0)\n : expectedOutput.minus(minimumOutput);\n const dustHuman = dustRaw.shiftedBy(-quote.outputToken.decimals);\n\n return dustHuman.multipliedBy(targetFiatRate.usdRate);\n}\n\nfunction calculateProviderUsd(\n quote: AcrossSwapApprovalResponse,\n inputAmountRaw: string,\n sourceFiatRate: FiatRates,\n targetFiatRate: FiatRates,\n expectedOutputRaw?: string,\n): BigNumber {\n const totalFeeUsd = quote.fees?.total?.amountUsd;\n\n if (totalFeeUsd !== undefined) {\n return new BigNumber(totalFeeUsd).abs();\n }\n\n if (expectedOutputRaw === undefined) {\n return new BigNumber(0);\n }\n\n const expectedOutput = new BigNumber(expectedOutputRaw);\n\n if (expectedOutput.lte(0)) {\n return new BigNumber(0);\n }\n\n const inputAmountUsd = new BigNumber(inputAmountRaw)\n .shiftedBy(-quote.inputToken.decimals)\n .multipliedBy(sourceFiatRate.usdRate);\n const expectedOutputUsd = expectedOutput\n .shiftedBy(-quote.outputToken.decimals)\n .multipliedBy(targetFiatRate.usdRate);\n const providerFeeUsd = inputAmountUsd.minus(expectedOutputUsd);\n\n return providerFeeUsd.isNegative() ? new BigNumber(0) : providerFeeUsd;\n}\n\nfunction getAmountFromTokenAmount({\n amountRaw,\n decimals,\n fiatRate,\n}: {\n amountRaw: string;\n decimals: number;\n fiatRate: FiatRates;\n}): Amount {\n const rawValue = new BigNumber(amountRaw);\n const raw = rawValue.toString(10);\n\n const humanValue = rawValue.shiftedBy(-decimals);\n const human = humanValue.toString(10);\n\n const usd = humanValue.multipliedBy(fiatRate.usdRate).toString(10);\n const fiat = humanValue.multipliedBy(fiatRate.fiatRate).toString(10);\n\n return {\n fiat,\n human,\n raw,\n usd,\n };\n}\n\nasync function calculateSourceNetworkCost(\n quote: AcrossSwapApprovalResponse,\n messenger: TransactionPayControllerMessenger,\n request: QuoteRequest,\n transaction: TransactionMeta,\n): Promise<{\n sourceNetwork: TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'];\n gasLimits: AcrossGasLimits;\n isGasFeeToken?: boolean;\n is7702: boolean;\n requiresAuthorizationList?: true;\n}> {\n const acrossFallbackGas =\n getPayStrategiesConfig(messenger).across.fallbackGas;\n const { from, sourceChainId, sourceTokenAddress } = request;\n const orderedTransactions = getAcrossOrderedTransactions({ quote });\n const { swapTx } = quote;\n const swapChainId = toHex(swapTx.chainId);\n const gasEstimates = await estimateQuoteGasLimits({\n fallbackGas: acrossFallbackGas,\n messenger,\n transactions: orderedTransactions.map((orderedTransaction) => ({\n chainId: toHex(orderedTransaction.chainId),\n data: orderedTransaction.data,\n from,\n gas: orderedTransaction.gas,\n to: orderedTransaction.to,\n value: orderedTransaction.value ?? '0x0',\n })),\n });\n\n const { batchGasLimit, is7702, requiresAuthorizationList, totalGasEstimate } =\n gasEstimates;\n\n let sourceNetwork: TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'];\n let gasLimits: AcrossGasLimits;\n\n if (is7702) {\n if (!batchGasLimit) {\n throw new Error('Across combined batch gas estimate missing');\n }\n\n const estimate = calculateGasCost({\n chainId: swapChainId,\n gas: batchGasLimit.estimate,\n maxFeePerGas: swapTx.maxFeePerGas,\n maxPriorityFeePerGas: swapTx.maxPriorityFeePerGas,\n messenger,\n });\n const max = calculateGasCost({\n chainId: swapChainId,\n gas: batchGasLimit.max,\n isMax: true,\n maxFeePerGas: swapTx.maxFeePerGas,\n maxPriorityFeePerGas: swapTx.maxPriorityFeePerGas,\n messenger,\n });\n\n sourceNetwork = {\n estimate,\n max,\n };\n gasLimits = [\n {\n estimate: batchGasLimit.estimate,\n max: batchGasLimit.max,\n },\n ];\n } else {\n const transactionGasLimits = orderedTransactions.map(\n (orderedTransaction, index) => ({\n gasEstimate: gasEstimates.gasLimits[index],\n orderedTransaction,\n }),\n );\n\n const estimate = sumAmounts(\n transactionGasLimits.map(({ gasEstimate, orderedTransaction }) =>\n calculateGasCost({\n chainId: toHex(orderedTransaction.chainId),\n gas: gasEstimate.estimate,\n maxFeePerGas: orderedTransaction.maxFeePerGas,\n maxPriorityFeePerGas: orderedTransaction.maxPriorityFeePerGas,\n messenger,\n }),\n ),\n );\n\n const max = sumAmounts(\n transactionGasLimits.map(({ gasEstimate, orderedTransaction }) =>\n calculateGasCost({\n chainId: toHex(orderedTransaction.chainId),\n gas: gasEstimate.max,\n isMax: true,\n maxFeePerGas: orderedTransaction.maxFeePerGas,\n maxPriorityFeePerGas: orderedTransaction.maxPriorityFeePerGas,\n messenger,\n }),\n ),\n );\n\n sourceNetwork = {\n estimate,\n max,\n };\n gasLimits = transactionGasLimits.map(({ gasEstimate }) => ({\n estimate: gasEstimate.estimate,\n max: gasEstimate.max,\n }));\n }\n\n const result = {\n sourceNetwork,\n is7702,\n ...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),\n gasLimits,\n totalGasEstimate,\n totalGasLimit: gasEstimates.totalGasLimit,\n };\n\n const finalResult = request.isPostQuote\n ? combinePostQuoteGas(result, transaction, swapTx, messenger)\n : result;\n\n const nativeBalance = getTokenBalance(\n messenger,\n from,\n sourceChainId,\n getNativeToken(sourceChainId),\n );\n const hasNativeBalance = new BigNumber(nativeBalance).isGreaterThanOrEqualTo(\n finalResult.sourceNetwork.max.raw,\n );\n\n if (hasNativeBalance) {\n return finalResult;\n }\n\n const gasStationEligibility = getGasStationEligibility(\n messenger,\n sourceChainId,\n );\n\n if (gasStationEligibility.isDisabledChain) {\n log('Skipping Across gas station as disabled chain', { sourceChainId });\n return finalResult;\n }\n\n if (!gasStationEligibility.chainSupportsGasStation) {\n log('Skipping Across gas station as chain does not support EIP-7702', {\n sourceChainId,\n });\n return finalResult;\n }\n\n const firstTransaction = orderedTransactions[0];\n\n const gasFeeTokenCost = await getGasStationCostInSourceTokenRaw({\n firstStepData: {\n data: firstTransaction.data,\n to: firstTransaction.to,\n value: firstTransaction.value,\n },\n messenger,\n request: {\n from,\n sourceChainId,\n sourceTokenAddress,\n },\n totalGasEstimate: finalResult.totalGasEstimate,\n totalItemCount: Math.max(\n orderedTransactions.length + (request.isPostQuote ? 1 : 0),\n finalResult.gasLimits.length,\n ),\n });\n\n if (!gasFeeTokenCost) {\n return finalResult;\n }\n\n log('Using gas fee token for Across source network', {\n gasFeeTokenCost,\n });\n\n return {\n isGasFeeToken: true,\n sourceNetwork: {\n estimate: gasFeeTokenCost,\n max: gasFeeTokenCost,\n },\n is7702: finalResult.is7702,\n ...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),\n gasLimits: finalResult.gasLimits,\n };\n}\n\nfunction combinePostQuoteGas(\n gasResult: {\n sourceNetwork: TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'];\n gasLimits: AcrossGasLimits;\n is7702: boolean;\n requiresAuthorizationList?: true;\n totalGasEstimate: number;\n totalGasLimit: number;\n },\n transaction: TransactionMeta,\n swapTx: AcrossSwapApprovalResponse['swapTx'],\n messenger: TransactionPayControllerMessenger,\n): typeof gasResult {\n const originalTxGas = getOriginalTransactionGas(transaction);\n\n if (originalTxGas === undefined) {\n return gasResult;\n }\n\n const gasLimits = gasResult.is7702\n ? [\n {\n estimate: gasResult.gasLimits[0].estimate + originalTxGas,\n max: gasResult.gasLimits[0].max + originalTxGas,\n },\n ]\n : [\n {\n estimate: originalTxGas,\n max: originalTxGas,\n },\n ...gasResult.gasLimits,\n ];\n\n const totalGasEstimate = gasResult.totalGasEstimate + originalTxGas;\n const totalGasLimit = gasResult.totalGasLimit + originalTxGas;\n const originalSourceNetwork = calculateOriginalSourceNetworkCost({\n gas: originalTxGas,\n messenger,\n swapTx,\n transaction,\n });\n\n return {\n ...gasResult,\n sourceNetwork: {\n estimate: sumAmounts([\n gasResult.sourceNetwork.estimate,\n originalSourceNetwork.estimate,\n ]),\n max: sumAmounts([gasResult.sourceNetwork.max, originalSourceNetwork.max]),\n },\n gasLimits,\n totalGasEstimate,\n totalGasLimit,\n };\n}\n\nfunction calculateOriginalSourceNetworkCost({\n gas,\n messenger,\n swapTx,\n transaction,\n}: {\n gas: number;\n messenger: TransactionPayControllerMessenger;\n swapTx: AcrossSwapApprovalResponse['swapTx'];\n transaction: TransactionMeta;\n}): TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'] {\n const originalTransactionWithGas = transaction.nestedTransactions?.find(\n (tx) => tx.gas,\n );\n const maxFeePerGas =\n originalTransactionWithGas?.maxFeePerGas ??\n transaction.txParams.maxFeePerGas;\n const maxPriorityFeePerGas =\n originalTransactionWithGas?.maxPriorityFeePerGas ??\n transaction.txParams.maxPriorityFeePerGas;\n\n return {\n estimate: calculateGasCost({\n chainId: transaction.chainId ?? toHex(swapTx.chainId),\n gas,\n maxFeePerGas,\n maxPriorityFeePerGas,\n messenger,\n }),\n max: calculateGasCost({\n chainId: transaction.chainId ?? toHex(swapTx.chainId),\n gas,\n isMax: true,\n maxFeePerGas,\n maxPriorityFeePerGas,\n messenger,\n }),\n };\n}\n"]}
|
|
1
|
+
{"version":3,"file":"across-quotes.cjs","sourceRoot":"","sources":["../../../src/strategy/across/across-quotes.ts"],"names":[],"mappings":"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","sourcesContent":["import { successfulFetch, toHex } from '@metamask/controller-utils';\nimport type { TransactionMeta } from '@metamask/transaction-controller';\nimport type { Hex } from '@metamask/utils';\nimport { createModuleLogger } from '@metamask/utils';\nimport { BigNumber } from 'bignumber.js';\n\nimport { TransactionPayStrategy } from '../../constants';\nimport { projectLogger } from '../../logger';\nimport type {\n Amount,\n FiatRates,\n PayStrategyGetQuotesRequest,\n QuoteRequest,\n TransactionPayControllerMessenger,\n TransactionPayQuote,\n} from '../../types';\nimport { getFiatValueFromUsd, sumAmounts } from '../../utils/amounts';\nimport { getPayStrategiesConfig, getSlippage } from '../../utils/feature-flags';\nimport { calculateGasCost } from '../../utils/gas';\nimport {\n getGasStationCostInSourceTokenRaw,\n getGasStationEligibility,\n} from '../../utils/gas-station';\nimport { estimateQuoteGasLimits } from '../../utils/quote-gas';\nimport type { QuoteGasTransaction } from '../../utils/quote-gas';\nimport {\n getNativeToken,\n getTokenBalance,\n getTokenFiatRate,\n} from '../../utils/token';\nimport { isPredictWithdrawTransaction } from '../../utils/transaction';\nimport type { AcrossDestination } from './across-actions';\nimport { getAcrossDestination } from './across-actions';\nimport { hasUnsupportedTransactionAuthorizationList } from './authorization-list';\nimport { normalizeAcrossRequest } from './perps';\nimport { isAcrossQuoteRequest } from './requests';\nimport {\n getAcrossOrderedTransactions,\n getOriginalTransactionGas,\n} from './transactions';\nimport type {\n AcrossAction,\n AcrossActionRequestBody,\n AcrossGasLimits,\n AcrossQuote,\n AcrossSwapApprovalResponse,\n} from './types';\n\nconst log = createModuleLogger(projectLogger, 'across-strategy');\n\nconst UNSUPPORTED_AUTHORIZATION_LIST_ERROR =\n 'Across does not support type-4/EIP-7702 authorization lists yet';\n\ntype AcrossQuoteWithoutMetaMask = Omit<AcrossQuote, 'metamask'>;\n\n/**\n * Fetch Across quotes.\n *\n * @param request - Request object.\n * @returns Array of quotes.\n */\nexport async function getAcrossQuotes(\n request: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>[]> {\n const { requests } = request;\n\n log('Fetching quotes', requests);\n\n try {\n const normalizedRequests = requests.filter(isAcrossQuoteRequest);\n\n if (normalizedRequests.length === 0) {\n return [];\n }\n\n if (\n hasUnsupportedTransactionAuthorizationList(\n request.transaction,\n normalizedRequests,\n )\n ) {\n throw new Error(UNSUPPORTED_AUTHORIZATION_LIST_ERROR);\n }\n\n return await Promise.all(\n normalizedRequests.map((singleRequest) =>\n getQuoteWithGasStationHandling(singleRequest, request),\n ),\n );\n } catch (error) {\n log('Error fetching quotes', { error });\n throw new Error(`Failed to fetch Across quotes: ${String(error)}`);\n }\n}\n\nasync function getSingleQuote(\n request: QuoteRequest,\n fullRequest: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>> {\n const { messenger, signal, transaction } = fullRequest;\n const normalizedRequest = normalizeAcrossRequest(request, transaction.type);\n const {\n from,\n isMaxAmount,\n sourceChainId,\n sourceTokenAddress,\n sourceTokenAmount,\n targetAmountMinimum,\n targetChainId,\n targetTokenAddress,\n } = normalizedRequest;\n\n const config = getPayStrategiesConfig(messenger);\n const slippageDecimal = getSlippage(\n messenger,\n sourceChainId,\n sourceTokenAddress,\n );\n\n const useExactInput = isMaxAmount\n ? true\n : normalizedRequest.isPostQuote === true;\n const amount = useExactInput ? sourceTokenAmount : targetAmountMinimum;\n const tradeType = useExactInput ? 'exactInput' : 'exactOutput';\n const destination = getAcrossDestinationForRequest(\n transaction,\n request,\n from,\n );\n\n const quote = await requestAcrossApproval({\n actions: destination.actions,\n amount,\n apiBase: config.across.apiBase,\n depositor: from,\n destinationChainId: targetChainId,\n inputToken: sourceTokenAddress,\n originChainId: sourceChainId,\n outputToken: targetTokenAddress,\n recipient: destination.recipient,\n signal,\n refundAddress: normalizedRequest.refundTo,\n slippage: slippageDecimal,\n tradeType,\n });\n\n const originalQuote: AcrossQuoteWithoutMetaMask = {\n quote,\n request: {\n actions: destination.actions,\n amount,\n tradeType,\n },\n };\n\n return await normalizeQuote(originalQuote, normalizedRequest, fullRequest);\n}\n\nfunction getAcrossDestinationForRequest(\n transaction: TransactionMeta,\n request: QuoteRequest,\n recipient: Hex,\n): AcrossDestination {\n if (request.isPostQuote) {\n return {\n actions: [],\n recipient,\n };\n }\n\n return getAcrossDestination(transaction, request);\n}\n\nasync function getQuoteWithGasStationHandling(\n request: QuoteRequest,\n fullRequest: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>> {\n // Phase 1 uses the requested source amount to discover whether Across will\n // pay source-chain gas with the source token, and what the max gas cost is.\n // Phase 2 repeats the quote with that max gas cost reserved from the source\n // amount, so execution can fund both the Across deposit and token-paid gas.\n const phase1Quote = await getSingleQuote(request, fullRequest);\n\n if (\n (!request.isMaxAmount && !request.isPostQuote) ||\n !phase1Quote.fees.isSourceGasFeeToken\n ) {\n return phase1Quote;\n }\n\n const requiresSourceGasReservation =\n request.isPostQuote === true &&\n isPredictWithdrawTransaction(fullRequest.transaction);\n\n const adjustedSourceAmount = new BigNumber(request.sourceTokenAmount)\n .minus(phase1Quote.fees.sourceNetwork.max.raw)\n .integerValue(BigNumber.ROUND_DOWN);\n\n if (!adjustedSourceAmount.isGreaterThan(0)) {\n log('Insufficient balance after gas subtraction for Across quote');\n if (requiresSourceGasReservation) {\n throw new Error(\n 'Across Predict withdraw source amount cannot cover source gas fee token',\n );\n }\n return phase1Quote;\n }\n\n log('Subtracting gas from source for Across quote', {\n adjustedSourceAmount: adjustedSourceAmount.toString(10),\n gasCostRaw: phase1Quote.fees.sourceNetwork.max.raw,\n originalSourceAmount: request.sourceTokenAmount,\n });\n\n try {\n const phase2Quote = await getSingleQuote(\n {\n ...request,\n sourceTokenAmount: adjustedSourceAmount.toFixed(\n 0,\n BigNumber.ROUND_DOWN,\n ),\n },\n fullRequest,\n );\n\n if (!phase2Quote.fees.isSourceGasFeeToken) {\n log('Across phase 2 lost gas fee token eligibility');\n if (requiresSourceGasReservation) {\n throw new Error(\n 'Across Predict withdraw quote lost source gas fee token eligibility',\n );\n }\n return phase1Quote;\n }\n\n const phase2GasCost = new BigNumber(phase2Quote.fees.sourceNetwork.max.raw);\n\n if (\n adjustedSourceAmount\n .plus(phase2GasCost)\n .isGreaterThan(request.sourceTokenAmount)\n ) {\n log('Across phase 2 quote exceeds original source amount', {\n adjustedSourceAmount: adjustedSourceAmount.toString(10),\n gasCostRaw: phase2GasCost.toString(10),\n originalSourceAmount: request.sourceTokenAmount,\n });\n if (requiresSourceGasReservation) {\n throw new Error(\n 'Across Predict withdraw source gas fee token quote exceeds source amount',\n );\n }\n return phase1Quote;\n }\n\n return phase2Quote;\n } catch (error) {\n log(\n requiresSourceGasReservation\n ? 'Across phase 2 quote failed after source gas reservation'\n : 'Across phase 2 quote failed, falling back to phase 1',\n { error },\n );\n if (requiresSourceGasReservation) {\n throw error;\n }\n return phase1Quote;\n }\n}\n\ntype AcrossApprovalRequest = {\n actions: AcrossAction[];\n amount: string;\n apiBase: string;\n depositor: Hex;\n destinationChainId: Hex;\n inputToken: Hex;\n originChainId: Hex;\n outputToken: Hex;\n recipient: Hex;\n refundAddress?: Hex;\n signal?: AbortSignal;\n slippage?: number;\n tradeType: 'exactInput' | 'exactOutput';\n};\n\nasync function requestAcrossApproval(\n request: AcrossApprovalRequest,\n): Promise<AcrossSwapApprovalResponse> {\n const {\n actions,\n amount,\n apiBase,\n depositor,\n destinationChainId,\n inputToken,\n originChainId,\n outputToken,\n recipient,\n refundAddress,\n signal,\n slippage,\n tradeType,\n } = request;\n\n const params = new URLSearchParams();\n params.set('tradeType', tradeType);\n params.set('amount', amount);\n params.set('inputToken', inputToken);\n params.set('outputToken', outputToken);\n params.set('originChainId', String(parseInt(originChainId, 16)));\n params.set('destinationChainId', String(parseInt(destinationChainId, 16)));\n params.set('depositor', depositor);\n params.set('recipient', recipient);\n\n if (refundAddress !== undefined) {\n params.set('refundAddress', refundAddress);\n }\n\n if (slippage !== undefined) {\n params.set('slippage', String(slippage));\n }\n\n const body: AcrossActionRequestBody = { actions };\n const url = `${apiBase}/swap/approval?${params.toString()}`;\n const options: RequestInit = {\n body: JSON.stringify(body),\n headers: {\n Accept: 'application/json',\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n signal,\n };\n\n const response = await successfulFetch(url, options);\n\n return (await response.json()) as AcrossSwapApprovalResponse;\n}\n\nasync function normalizeQuote(\n original: AcrossQuoteWithoutMetaMask,\n request: QuoteRequest,\n fullRequest: PayStrategyGetQuotesRequest,\n): Promise<TransactionPayQuote<AcrossQuote>> {\n const { messenger } = fullRequest;\n const { quote } = original;\n\n const { usdToFiatRate, sourceFiatRate, targetFiatRate } = getFiatRates(\n messenger,\n quote,\n );\n\n const dustUsd = calculateDustUsd(quote, request, targetFiatRate);\n const dust = getFiatValueFromUsd(dustUsd, usdToFiatRate);\n\n const {\n gasLimits,\n is7702,\n isGasFeeToken: isSourceGasFeeToken,\n requiresAuthorizationList,\n sourceNetwork,\n } = await calculateSourceNetworkCost(\n quote,\n messenger,\n request,\n fullRequest.transaction,\n fullRequest.accountSupports7702,\n );\n\n const targetNetwork = getFiatValueFromUsd(new BigNumber(0), usdToFiatRate);\n\n const inputAmountRaw = quote.inputAmount ?? '0';\n const outputAmountRaw = new BigNumber(\n quote.expectedOutputAmount ??\n quote.minOutputAmount ??\n request.targetAmountMinimum ??\n '0',\n ).toString(10);\n\n const sourceAmount = getAmountFromTokenAmount({\n amountRaw: inputAmountRaw,\n decimals: quote.inputToken.decimals,\n fiatRate: sourceFiatRate,\n });\n\n const providerUsd = calculateProviderUsd(\n quote,\n inputAmountRaw,\n sourceFiatRate,\n targetFiatRate,\n quote.expectedOutputAmount,\n );\n const provider = getFiatValueFromUsd(providerUsd, usdToFiatRate);\n const metaMaskFee = getFiatValueFromUsd(\n new BigNumber(quote.fees?.app?.amountUsd ?? '0').abs(),\n usdToFiatRate,\n );\n\n const targetAmount = getAmountFromTokenAmount({\n amountRaw: outputAmountRaw,\n decimals: quote.outputToken.decimals,\n fiatRate: targetFiatRate,\n });\n\n const metamask = {\n gasLimits,\n is7702,\n ...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),\n };\n\n return {\n dust,\n estimatedDuration: quote.expectedFillTime ?? 0,\n fees: {\n isSourceGasFeeToken,\n metaMask: metaMaskFee,\n provider,\n sourceNetwork,\n targetNetwork,\n },\n original: {\n ...original,\n metamask,\n },\n request,\n sourceAmount,\n targetAmount,\n strategy: TransactionPayStrategy.Across,\n } as TransactionPayQuote<AcrossQuote>;\n}\n\nfunction getFiatRates(\n messenger: TransactionPayControllerMessenger,\n quote: AcrossSwapApprovalResponse,\n): {\n sourceFiatRate: FiatRates;\n targetFiatRate: FiatRates;\n usdToFiatRate: BigNumber;\n} {\n const sourceFiatRate = getTokenFiatRate(\n messenger,\n quote.inputToken.address,\n toHex(quote.inputToken.chainId),\n );\n\n if (!sourceFiatRate) {\n throw new Error('Source token fiat rate not found');\n }\n\n const targetFiatRate =\n getTokenFiatRate(\n messenger,\n quote.outputToken.address,\n toHex(quote.outputToken.chainId),\n ) ?? sourceFiatRate;\n\n const usdToFiatRate = new BigNumber(sourceFiatRate.fiatRate).dividedBy(\n sourceFiatRate.usdRate,\n );\n\n return { sourceFiatRate, targetFiatRate, usdToFiatRate };\n}\n\nfunction calculateDustUsd(\n quote: AcrossSwapApprovalResponse,\n request: QuoteRequest,\n targetFiatRate: FiatRates,\n): BigNumber {\n const expectedOutputRaw = quote.expectedOutputAmount;\n\n if (expectedOutputRaw === undefined) {\n return new BigNumber(0);\n }\n\n const expectedOutput = new BigNumber(expectedOutputRaw);\n const minimumOutput = new BigNumber(\n quote.minOutputAmount ?? request.targetAmountMinimum ?? '0',\n );\n\n const dustRaw = expectedOutput.minus(minimumOutput).isNegative()\n ? new BigNumber(0)\n : expectedOutput.minus(minimumOutput);\n const dustHuman = dustRaw.shiftedBy(-quote.outputToken.decimals);\n\n return dustHuman.multipliedBy(targetFiatRate.usdRate);\n}\n\nfunction calculateProviderUsd(\n quote: AcrossSwapApprovalResponse,\n inputAmountRaw: string,\n sourceFiatRate: FiatRates,\n targetFiatRate: FiatRates,\n expectedOutputRaw?: string,\n): BigNumber {\n const totalFeeUsd = quote.fees?.total?.amountUsd;\n\n if (totalFeeUsd !== undefined) {\n return new BigNumber(totalFeeUsd).abs();\n }\n\n if (expectedOutputRaw === undefined) {\n return new BigNumber(0);\n }\n\n const expectedOutput = new BigNumber(expectedOutputRaw);\n\n if (expectedOutput.lte(0)) {\n return new BigNumber(0);\n }\n\n const inputAmountUsd = new BigNumber(inputAmountRaw)\n .shiftedBy(-quote.inputToken.decimals)\n .multipliedBy(sourceFiatRate.usdRate);\n const expectedOutputUsd = expectedOutput\n .shiftedBy(-quote.outputToken.decimals)\n .multipliedBy(targetFiatRate.usdRate);\n const providerFeeUsd = inputAmountUsd.minus(expectedOutputUsd);\n\n return providerFeeUsd.isNegative() ? new BigNumber(0) : providerFeeUsd;\n}\n\nfunction getAmountFromTokenAmount({\n amountRaw,\n decimals,\n fiatRate,\n}: {\n amountRaw: string;\n decimals: number;\n fiatRate: FiatRates;\n}): Amount {\n const rawValue = new BigNumber(amountRaw);\n const raw = rawValue.toString(10);\n\n const humanValue = rawValue.shiftedBy(-decimals);\n const human = humanValue.toString(10);\n\n const usd = humanValue.multipliedBy(fiatRate.usdRate).toString(10);\n const fiat = humanValue.multipliedBy(fiatRate.fiatRate).toString(10);\n\n return {\n fiat,\n human,\n raw,\n usd,\n };\n}\n\nasync function calculateSourceNetworkCost(\n quote: AcrossSwapApprovalResponse,\n messenger: TransactionPayControllerMessenger,\n request: QuoteRequest,\n transaction: TransactionMeta,\n accountSupports7702: boolean,\n): Promise<{\n sourceNetwork: TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'];\n gasLimits: AcrossGasLimits;\n isGasFeeToken?: boolean;\n is7702: boolean;\n requiresAuthorizationList?: true;\n}> {\n const acrossFallbackGas =\n getPayStrategiesConfig(messenger).across.fallbackGas;\n const { from, sourceChainId, sourceTokenAddress } = request;\n const orderedTransactions = getAcrossOrderedTransactions({ quote });\n const { swapTx } = quote;\n const swapChainId = toHex(swapTx.chainId);\n const isPredictWithdraw =\n request.isPostQuote === true && isPredictWithdrawTransaction(transaction);\n const relaxPrefundedSourceEstimate =\n isPredictWithdraw &&\n new BigNumber(request.sourceTokenAmount).gt(request.sourceBalanceRaw);\n const gasEstimateTransactions = orderedTransactions.map(\n (orderedTransaction) => ({\n chainId: toHex(orderedTransaction.chainId),\n data: orderedTransaction.data,\n from,\n gas: orderedTransaction.gas,\n to: orderedTransaction.to,\n value: orderedTransaction.value ?? '0x0',\n }),\n );\n\n const gasEstimates = await estimateAcrossQuoteGasLimits({\n fallbackGas: acrossFallbackGas,\n fallbackOnSimulationFailure: relaxPrefundedSourceEstimate,\n messenger,\n transactions: gasEstimateTransactions,\n });\n\n const { batchGasLimit, is7702, requiresAuthorizationList, totalGasEstimate } =\n gasEstimates;\n\n let sourceNetwork: TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'];\n let gasLimits: AcrossGasLimits;\n\n if (is7702) {\n if (!batchGasLimit) {\n throw new Error('Across combined batch gas estimate missing');\n }\n\n const estimate = calculateGasCost({\n chainId: swapChainId,\n gas: batchGasLimit.estimate,\n maxFeePerGas: swapTx.maxFeePerGas,\n maxPriorityFeePerGas: swapTx.maxPriorityFeePerGas,\n messenger,\n });\n const max = calculateGasCost({\n chainId: swapChainId,\n gas: batchGasLimit.max,\n isMax: true,\n maxFeePerGas: swapTx.maxFeePerGas,\n maxPriorityFeePerGas: swapTx.maxPriorityFeePerGas,\n messenger,\n });\n\n sourceNetwork = {\n estimate,\n max,\n };\n gasLimits = [\n {\n estimate: batchGasLimit.estimate,\n max: batchGasLimit.max,\n },\n ];\n } else {\n const transactionGasLimits = orderedTransactions.map(\n (orderedTransaction, index) => ({\n gasEstimate: gasEstimates.gasLimits[index],\n orderedTransaction,\n }),\n );\n\n const estimate = sumAmounts(\n transactionGasLimits.map(({ gasEstimate, orderedTransaction }) =>\n calculateGasCost({\n chainId: toHex(orderedTransaction.chainId),\n gas: gasEstimate.estimate,\n maxFeePerGas: orderedTransaction.maxFeePerGas,\n maxPriorityFeePerGas: orderedTransaction.maxPriorityFeePerGas,\n messenger,\n }),\n ),\n );\n\n const max = sumAmounts(\n transactionGasLimits.map(({ gasEstimate, orderedTransaction }) =>\n calculateGasCost({\n chainId: toHex(orderedTransaction.chainId),\n gas: gasEstimate.max,\n isMax: true,\n maxFeePerGas: orderedTransaction.maxFeePerGas,\n maxPriorityFeePerGas: orderedTransaction.maxPriorityFeePerGas,\n messenger,\n }),\n ),\n );\n\n sourceNetwork = {\n estimate,\n max,\n };\n gasLimits = transactionGasLimits.map(({ gasEstimate }) => ({\n estimate: gasEstimate.estimate,\n max: gasEstimate.max,\n }));\n }\n\n const result = {\n sourceNetwork,\n is7702,\n ...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),\n gasLimits,\n totalGasEstimate,\n totalGasLimit: gasEstimates.totalGasLimit,\n };\n\n const finalResult = request.isPostQuote\n ? combinePostQuoteGas(result, transaction, swapTx, messenger)\n : result;\n\n const nativeBalance = getTokenBalance(\n messenger,\n from,\n sourceChainId,\n getNativeToken(sourceChainId),\n );\n const hasNativeBalance = new BigNumber(nativeBalance).isGreaterThanOrEqualTo(\n finalResult.sourceNetwork.max.raw,\n );\n\n if (isPredictWithdraw && !accountSupports7702) {\n return finalResult;\n }\n\n if (hasNativeBalance && !isPredictWithdraw) {\n return finalResult;\n }\n\n const gasStationEligibility = getGasStationEligibility(\n messenger,\n sourceChainId,\n );\n\n if (gasStationEligibility.isDisabledChain) {\n log('Skipping Across gas station as disabled chain', { sourceChainId });\n return finalResult;\n }\n\n if (!gasStationEligibility.chainSupportsGasStation) {\n log('Skipping Across gas station as chain does not support EIP-7702', {\n sourceChainId,\n });\n return finalResult;\n }\n\n const firstTransaction = orderedTransactions[0];\n\n const gasFeeTokenCost = await getGasStationCostInSourceTokenRaw({\n firstStepData: {\n data: firstTransaction.data,\n to: firstTransaction.to,\n value: firstTransaction.value,\n },\n messenger,\n request: {\n from,\n sourceChainId,\n sourceTokenAddress,\n },\n totalGasEstimate: finalResult.totalGasEstimate,\n totalItemCount: Math.max(\n orderedTransactions.length + (request.isPostQuote ? 1 : 0),\n finalResult.gasLimits.length,\n ),\n });\n\n let gasFeeTokenNetwork:\n | TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork']\n | undefined;\n\n if (gasFeeTokenCost) {\n gasFeeTokenNetwork = {\n estimate: gasFeeTokenCost,\n max: gasFeeTokenCost,\n };\n } else if (isPredictWithdraw) {\n gasFeeTokenNetwork = calculateSourceGasFeeTokenNetworkFallback({\n messenger,\n nativeSourceNetwork: finalResult.sourceNetwork,\n quote,\n request,\n });\n }\n\n if (!gasFeeTokenNetwork) {\n return finalResult;\n }\n\n log('Using gas fee token for Across source network', {\n gasFeeTokenCost: gasFeeTokenNetwork.max,\n });\n\n return {\n isGasFeeToken: true,\n sourceNetwork: gasFeeTokenNetwork,\n is7702: finalResult.is7702,\n ...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),\n gasLimits: finalResult.gasLimits,\n };\n}\n\nfunction calculateSourceGasFeeTokenNetworkFallback({\n messenger,\n nativeSourceNetwork,\n quote,\n request,\n}: {\n messenger: TransactionPayControllerMessenger;\n nativeSourceNetwork: TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'];\n quote: AcrossSwapApprovalResponse;\n request: QuoteRequest;\n}): TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'] | undefined {\n const sourceFiatRate = getTokenFiatRate(\n messenger,\n request.sourceTokenAddress,\n request.sourceChainId,\n );\n\n if (!sourceFiatRate) {\n return undefined;\n }\n\n const estimate = calculateSourceGasFeeTokenAmountFallback({\n decimals: quote.inputToken.decimals,\n fiatRate: sourceFiatRate,\n nativeGasCost: nativeSourceNetwork.estimate,\n });\n const max = calculateSourceGasFeeTokenAmountFallback({\n decimals: quote.inputToken.decimals,\n fiatRate: sourceFiatRate,\n nativeGasCost: nativeSourceNetwork.max,\n });\n\n if (!estimate || !max) {\n return undefined;\n }\n\n return { estimate, max };\n}\n\nfunction calculateSourceGasFeeTokenAmountFallback({\n decimals,\n fiatRate,\n nativeGasCost,\n}: {\n decimals: number;\n fiatRate: FiatRates;\n nativeGasCost: Amount;\n}): Amount | undefined {\n const usdRate = new BigNumber(fiatRate.usdRate);\n const nativeGasUsd = new BigNumber(nativeGasCost.usd);\n\n if (\n !usdRate.isFinite() ||\n !usdRate.isGreaterThan(0) ||\n !nativeGasUsd.isFinite() ||\n !nativeGasUsd.isGreaterThan(0)\n ) {\n return undefined;\n }\n\n const amountRaw = nativeGasUsd\n .dividedBy(usdRate)\n .shiftedBy(decimals)\n .integerValue(BigNumber.ROUND_CEIL)\n .toFixed(0);\n\n return getAmountFromTokenAmount({\n amountRaw,\n decimals,\n fiatRate,\n });\n}\n\nasync function estimateAcrossQuoteGasLimits({\n fallbackGas,\n fallbackOnSimulationFailure,\n messenger,\n transactions,\n}: {\n fallbackGas?: {\n estimate: number;\n max: number;\n };\n fallbackOnSimulationFailure: boolean;\n messenger: TransactionPayControllerMessenger;\n transactions: QuoteGasTransaction[];\n}): Promise<Awaited<ReturnType<typeof estimateQuoteGasLimits>>> {\n try {\n const gasEstimates = await estimateQuoteGasLimits({\n fallbackGas,\n fallbackOnSimulationFailure,\n messenger,\n transactions,\n });\n\n if (\n fallbackOnSimulationFailure &&\n fallbackGas !== undefined &&\n gasEstimates.is7702 &&\n gasEstimates.batchGasLimit !== undefined &&\n gasEstimates.batchGasLimit.max > fallbackGas.max\n ) {\n // Prefunded Predict withdraws can produce inflated 7702 batch estimates\n // because the source account does not yet hold the funds. Keep the gas\n // reservation bounded by the configured Across fallback for this path.\n return {\n ...gasEstimates,\n batchGasLimit: fallbackGas,\n gasLimits: [fallbackGas],\n totalGasEstimate: fallbackGas.estimate,\n totalGasLimit: fallbackGas.max,\n };\n }\n\n return gasEstimates;\n } catch (error) {\n if (!fallbackOnSimulationFailure || transactions.length <= 1) {\n throw error;\n }\n\n const perTransactionGasEstimates = await Promise.all(\n transactions.map((transaction) =>\n estimateQuoteGasLimits({\n fallbackGas,\n fallbackOnSimulationFailure: true,\n messenger,\n transactions: [transaction],\n }),\n ),\n );\n const gasLimits = perTransactionGasEstimates.map(\n (estimate) => estimate.gasLimits[0],\n );\n const totalGasEstimate = gasLimits.reduce(\n (total, gasLimit) => total + gasLimit.estimate,\n 0,\n );\n const totalGasLimit = gasLimits.reduce(\n (total, gasLimit) => total + gasLimit.max,\n 0,\n );\n\n return {\n gasLimits,\n is7702: false,\n totalGasEstimate,\n totalGasLimit,\n usedBatch: false,\n };\n }\n}\n\nfunction combinePostQuoteGas(\n gasResult: {\n sourceNetwork: TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'];\n gasLimits: AcrossGasLimits;\n is7702: boolean;\n requiresAuthorizationList?: true;\n totalGasEstimate: number;\n totalGasLimit: number;\n },\n transaction: TransactionMeta,\n swapTx: AcrossSwapApprovalResponse['swapTx'],\n messenger: TransactionPayControllerMessenger,\n): typeof gasResult {\n const originalTxGas = getOriginalTransactionGas(transaction);\n\n if (originalTxGas === undefined) {\n return gasResult;\n }\n\n const gasLimits = gasResult.is7702\n ? [\n {\n estimate: gasResult.gasLimits[0].estimate + originalTxGas,\n max: gasResult.gasLimits[0].max + originalTxGas,\n },\n ]\n : [\n {\n estimate: originalTxGas,\n max: originalTxGas,\n },\n ...gasResult.gasLimits,\n ];\n\n const totalGasEstimate = gasResult.totalGasEstimate + originalTxGas;\n const totalGasLimit = gasResult.totalGasLimit + originalTxGas;\n const originalSourceNetwork = calculateOriginalSourceNetworkCost({\n gas: originalTxGas,\n messenger,\n swapTx,\n transaction,\n });\n\n return {\n ...gasResult,\n sourceNetwork: {\n estimate: sumAmounts([\n gasResult.sourceNetwork.estimate,\n originalSourceNetwork.estimate,\n ]),\n max: sumAmounts([gasResult.sourceNetwork.max, originalSourceNetwork.max]),\n },\n gasLimits,\n totalGasEstimate,\n totalGasLimit,\n };\n}\n\nfunction calculateOriginalSourceNetworkCost({\n gas,\n messenger,\n swapTx,\n transaction,\n}: {\n gas: number;\n messenger: TransactionPayControllerMessenger;\n swapTx: AcrossSwapApprovalResponse['swapTx'];\n transaction: TransactionMeta;\n}): TransactionPayQuote<AcrossQuote>['fees']['sourceNetwork'] {\n const originalTransactionWithGas = transaction.nestedTransactions?.find(\n (tx) => tx.gas,\n );\n const maxFeePerGas =\n originalTransactionWithGas?.maxFeePerGas ??\n transaction.txParams.maxFeePerGas;\n const maxPriorityFeePerGas =\n originalTransactionWithGas?.maxPriorityFeePerGas ??\n transaction.txParams.maxPriorityFeePerGas;\n\n return {\n estimate: calculateGasCost({\n chainId: transaction.chainId ?? toHex(swapTx.chainId),\n gas,\n maxFeePerGas,\n maxPriorityFeePerGas,\n messenger,\n }),\n max: calculateGasCost({\n chainId: transaction.chainId ?? toHex(swapTx.chainId),\n gas,\n isMax: true,\n maxFeePerGas,\n maxPriorityFeePerGas,\n messenger,\n }),\n };\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"across-quotes.d.cts","sourceRoot":"","sources":["../../../src/strategy/across/across-quotes.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAGV,2BAA2B,EAG3B,mBAAmB,EACpB,wBAAoB;
|
|
1
|
+
{"version":3,"file":"across-quotes.d.cts","sourceRoot":"","sources":["../../../src/strategy/across/across-quotes.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAGV,2BAA2B,EAG3B,mBAAmB,EACpB,wBAAoB;AAyBrB,OAAO,KAAK,EAIV,WAAW,EAEZ,oBAAgB;AASjB;;;;;GAKG;AACH,wBAAsB,eAAe,CACnC,OAAO,EAAE,2BAA2B,GACnC,OAAO,CAAC,mBAAmB,CAAC,WAAW,CAAC,EAAE,CAAC,CA8B7C"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"across-quotes.d.mts","sourceRoot":"","sources":["../../../src/strategy/across/across-quotes.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAGV,2BAA2B,EAG3B,mBAAmB,EACpB,wBAAoB;
|
|
1
|
+
{"version":3,"file":"across-quotes.d.mts","sourceRoot":"","sources":["../../../src/strategy/across/across-quotes.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAGV,2BAA2B,EAG3B,mBAAmB,EACpB,wBAAoB;AAyBrB,OAAO,KAAK,EAIV,WAAW,EAEZ,oBAAgB;AASjB;;;;;GAKG;AACH,wBAAsB,eAAe,CACnC,OAAO,EAAE,2BAA2B,GACnC,OAAO,CAAC,mBAAmB,CAAC,WAAW,CAAC,EAAE,CAAC,CA8B7C"}
|
|
@@ -189,7 +189,7 @@ async function normalizeQuote(original, request, fullRequest) {
|
|
|
189
189
|
const { usdToFiatRate, sourceFiatRate, targetFiatRate } = getFiatRates(messenger, quote);
|
|
190
190
|
const dustUsd = calculateDustUsd(quote, request, targetFiatRate);
|
|
191
191
|
const dust = getFiatValueFromUsd(dustUsd, usdToFiatRate);
|
|
192
|
-
const { gasLimits, is7702, isGasFeeToken: isSourceGasFeeToken, requiresAuthorizationList, sourceNetwork, } = await calculateSourceNetworkCost(quote, messenger, request, fullRequest.transaction);
|
|
192
|
+
const { gasLimits, is7702, isGasFeeToken: isSourceGasFeeToken, requiresAuthorizationList, sourceNetwork, } = await calculateSourceNetworkCost(quote, messenger, request, fullRequest.transaction, fullRequest.accountSupports7702);
|
|
193
193
|
const targetNetwork = getFiatValueFromUsd(new BigNumber(0), usdToFiatRate);
|
|
194
194
|
const inputAmountRaw = quote.inputAmount ?? '0';
|
|
195
195
|
const outputAmountRaw = new BigNumber(quote.expectedOutputAmount ??
|
|
@@ -291,23 +291,28 @@ function getAmountFromTokenAmount({ amountRaw, decimals, fiatRate, }) {
|
|
|
291
291
|
usd,
|
|
292
292
|
};
|
|
293
293
|
}
|
|
294
|
-
async function calculateSourceNetworkCost(quote, messenger, request, transaction) {
|
|
294
|
+
async function calculateSourceNetworkCost(quote, messenger, request, transaction, accountSupports7702) {
|
|
295
295
|
const acrossFallbackGas = getPayStrategiesConfig(messenger).across.fallbackGas;
|
|
296
296
|
const { from, sourceChainId, sourceTokenAddress } = request;
|
|
297
297
|
const orderedTransactions = getAcrossOrderedTransactions({ quote });
|
|
298
298
|
const { swapTx } = quote;
|
|
299
299
|
const swapChainId = toHex(swapTx.chainId);
|
|
300
|
-
const
|
|
300
|
+
const isPredictWithdraw = request.isPostQuote === true && isPredictWithdrawTransaction(transaction);
|
|
301
|
+
const relaxPrefundedSourceEstimate = isPredictWithdraw &&
|
|
302
|
+
new BigNumber(request.sourceTokenAmount).gt(request.sourceBalanceRaw);
|
|
303
|
+
const gasEstimateTransactions = orderedTransactions.map((orderedTransaction) => ({
|
|
304
|
+
chainId: toHex(orderedTransaction.chainId),
|
|
305
|
+
data: orderedTransaction.data,
|
|
306
|
+
from,
|
|
307
|
+
gas: orderedTransaction.gas,
|
|
308
|
+
to: orderedTransaction.to,
|
|
309
|
+
value: orderedTransaction.value ?? '0x0',
|
|
310
|
+
}));
|
|
311
|
+
const gasEstimates = await estimateAcrossQuoteGasLimits({
|
|
301
312
|
fallbackGas: acrossFallbackGas,
|
|
313
|
+
fallbackOnSimulationFailure: relaxPrefundedSourceEstimate,
|
|
302
314
|
messenger,
|
|
303
|
-
transactions:
|
|
304
|
-
chainId: toHex(orderedTransaction.chainId),
|
|
305
|
-
data: orderedTransaction.data,
|
|
306
|
-
from,
|
|
307
|
-
gas: orderedTransaction.gas,
|
|
308
|
-
to: orderedTransaction.to,
|
|
309
|
-
value: orderedTransaction.value ?? '0x0',
|
|
310
|
-
})),
|
|
315
|
+
transactions: gasEstimateTransactions,
|
|
311
316
|
});
|
|
312
317
|
const { batchGasLimit, is7702, requiresAuthorizationList, totalGasEstimate } = gasEstimates;
|
|
313
318
|
let sourceNetwork;
|
|
@@ -384,7 +389,10 @@ async function calculateSourceNetworkCost(quote, messenger, request, transaction
|
|
|
384
389
|
: result;
|
|
385
390
|
const nativeBalance = getTokenBalance(messenger, from, sourceChainId, getNativeToken(sourceChainId));
|
|
386
391
|
const hasNativeBalance = new BigNumber(nativeBalance).isGreaterThanOrEqualTo(finalResult.sourceNetwork.max.raw);
|
|
387
|
-
if (
|
|
392
|
+
if (isPredictWithdraw && !accountSupports7702) {
|
|
393
|
+
return finalResult;
|
|
394
|
+
}
|
|
395
|
+
if (hasNativeBalance && !isPredictWithdraw) {
|
|
388
396
|
return finalResult;
|
|
389
397
|
}
|
|
390
398
|
const gasStationEligibility = getGasStationEligibility(messenger, sourceChainId);
|
|
@@ -414,23 +422,123 @@ async function calculateSourceNetworkCost(quote, messenger, request, transaction
|
|
|
414
422
|
totalGasEstimate: finalResult.totalGasEstimate,
|
|
415
423
|
totalItemCount: Math.max(orderedTransactions.length + (request.isPostQuote ? 1 : 0), finalResult.gasLimits.length),
|
|
416
424
|
});
|
|
417
|
-
|
|
425
|
+
let gasFeeTokenNetwork;
|
|
426
|
+
if (gasFeeTokenCost) {
|
|
427
|
+
gasFeeTokenNetwork = {
|
|
428
|
+
estimate: gasFeeTokenCost,
|
|
429
|
+
max: gasFeeTokenCost,
|
|
430
|
+
};
|
|
431
|
+
}
|
|
432
|
+
else if (isPredictWithdraw) {
|
|
433
|
+
gasFeeTokenNetwork = calculateSourceGasFeeTokenNetworkFallback({
|
|
434
|
+
messenger,
|
|
435
|
+
nativeSourceNetwork: finalResult.sourceNetwork,
|
|
436
|
+
quote,
|
|
437
|
+
request,
|
|
438
|
+
});
|
|
439
|
+
}
|
|
440
|
+
if (!gasFeeTokenNetwork) {
|
|
418
441
|
return finalResult;
|
|
419
442
|
}
|
|
420
443
|
log('Using gas fee token for Across source network', {
|
|
421
|
-
gasFeeTokenCost,
|
|
444
|
+
gasFeeTokenCost: gasFeeTokenNetwork.max,
|
|
422
445
|
});
|
|
423
446
|
return {
|
|
424
447
|
isGasFeeToken: true,
|
|
425
|
-
sourceNetwork:
|
|
426
|
-
estimate: gasFeeTokenCost,
|
|
427
|
-
max: gasFeeTokenCost,
|
|
428
|
-
},
|
|
448
|
+
sourceNetwork: gasFeeTokenNetwork,
|
|
429
449
|
is7702: finalResult.is7702,
|
|
430
450
|
...(requiresAuthorizationList ? { requiresAuthorizationList } : {}),
|
|
431
451
|
gasLimits: finalResult.gasLimits,
|
|
432
452
|
};
|
|
433
453
|
}
|
|
454
|
+
function calculateSourceGasFeeTokenNetworkFallback({ messenger, nativeSourceNetwork, quote, request, }) {
|
|
455
|
+
const sourceFiatRate = getTokenFiatRate(messenger, request.sourceTokenAddress, request.sourceChainId);
|
|
456
|
+
if (!sourceFiatRate) {
|
|
457
|
+
return undefined;
|
|
458
|
+
}
|
|
459
|
+
const estimate = calculateSourceGasFeeTokenAmountFallback({
|
|
460
|
+
decimals: quote.inputToken.decimals,
|
|
461
|
+
fiatRate: sourceFiatRate,
|
|
462
|
+
nativeGasCost: nativeSourceNetwork.estimate,
|
|
463
|
+
});
|
|
464
|
+
const max = calculateSourceGasFeeTokenAmountFallback({
|
|
465
|
+
decimals: quote.inputToken.decimals,
|
|
466
|
+
fiatRate: sourceFiatRate,
|
|
467
|
+
nativeGasCost: nativeSourceNetwork.max,
|
|
468
|
+
});
|
|
469
|
+
if (!estimate || !max) {
|
|
470
|
+
return undefined;
|
|
471
|
+
}
|
|
472
|
+
return { estimate, max };
|
|
473
|
+
}
|
|
474
|
+
function calculateSourceGasFeeTokenAmountFallback({ decimals, fiatRate, nativeGasCost, }) {
|
|
475
|
+
const usdRate = new BigNumber(fiatRate.usdRate);
|
|
476
|
+
const nativeGasUsd = new BigNumber(nativeGasCost.usd);
|
|
477
|
+
if (!usdRate.isFinite() ||
|
|
478
|
+
!usdRate.isGreaterThan(0) ||
|
|
479
|
+
!nativeGasUsd.isFinite() ||
|
|
480
|
+
!nativeGasUsd.isGreaterThan(0)) {
|
|
481
|
+
return undefined;
|
|
482
|
+
}
|
|
483
|
+
const amountRaw = nativeGasUsd
|
|
484
|
+
.dividedBy(usdRate)
|
|
485
|
+
.shiftedBy(decimals)
|
|
486
|
+
.integerValue(BigNumber.ROUND_CEIL)
|
|
487
|
+
.toFixed(0);
|
|
488
|
+
return getAmountFromTokenAmount({
|
|
489
|
+
amountRaw,
|
|
490
|
+
decimals,
|
|
491
|
+
fiatRate,
|
|
492
|
+
});
|
|
493
|
+
}
|
|
494
|
+
async function estimateAcrossQuoteGasLimits({ fallbackGas, fallbackOnSimulationFailure, messenger, transactions, }) {
|
|
495
|
+
try {
|
|
496
|
+
const gasEstimates = await estimateQuoteGasLimits({
|
|
497
|
+
fallbackGas,
|
|
498
|
+
fallbackOnSimulationFailure,
|
|
499
|
+
messenger,
|
|
500
|
+
transactions,
|
|
501
|
+
});
|
|
502
|
+
if (fallbackOnSimulationFailure &&
|
|
503
|
+
fallbackGas !== undefined &&
|
|
504
|
+
gasEstimates.is7702 &&
|
|
505
|
+
gasEstimates.batchGasLimit !== undefined &&
|
|
506
|
+
gasEstimates.batchGasLimit.max > fallbackGas.max) {
|
|
507
|
+
// Prefunded Predict withdraws can produce inflated 7702 batch estimates
|
|
508
|
+
// because the source account does not yet hold the funds. Keep the gas
|
|
509
|
+
// reservation bounded by the configured Across fallback for this path.
|
|
510
|
+
return {
|
|
511
|
+
...gasEstimates,
|
|
512
|
+
batchGasLimit: fallbackGas,
|
|
513
|
+
gasLimits: [fallbackGas],
|
|
514
|
+
totalGasEstimate: fallbackGas.estimate,
|
|
515
|
+
totalGasLimit: fallbackGas.max,
|
|
516
|
+
};
|
|
517
|
+
}
|
|
518
|
+
return gasEstimates;
|
|
519
|
+
}
|
|
520
|
+
catch (error) {
|
|
521
|
+
if (!fallbackOnSimulationFailure || transactions.length <= 1) {
|
|
522
|
+
throw error;
|
|
523
|
+
}
|
|
524
|
+
const perTransactionGasEstimates = await Promise.all(transactions.map((transaction) => estimateQuoteGasLimits({
|
|
525
|
+
fallbackGas,
|
|
526
|
+
fallbackOnSimulationFailure: true,
|
|
527
|
+
messenger,
|
|
528
|
+
transactions: [transaction],
|
|
529
|
+
})));
|
|
530
|
+
const gasLimits = perTransactionGasEstimates.map((estimate) => estimate.gasLimits[0]);
|
|
531
|
+
const totalGasEstimate = gasLimits.reduce((total, gasLimit) => total + gasLimit.estimate, 0);
|
|
532
|
+
const totalGasLimit = gasLimits.reduce((total, gasLimit) => total + gasLimit.max, 0);
|
|
533
|
+
return {
|
|
534
|
+
gasLimits,
|
|
535
|
+
is7702: false,
|
|
536
|
+
totalGasEstimate,
|
|
537
|
+
totalGasLimit,
|
|
538
|
+
usedBatch: false,
|
|
539
|
+
};
|
|
540
|
+
}
|
|
541
|
+
}
|
|
434
542
|
function combinePostQuoteGas(gasResult, transaction, swapTx, messenger) {
|
|
435
543
|
const originalTxGas = getOriginalTransactionGas(transaction);
|
|
436
544
|
if (originalTxGas === undefined) {
|