@imtbl/sdk 0.27.15 → 0.28.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.
@@ -7,7 +7,7 @@ import { TradeType, Percent } from '@uniswap/sdk-core';
7
7
  import assert from 'assert';
8
8
  import { FeeAmount, Route, SwapQuoter, Pool, Trade, toHex as toHex$1, encodeRouteToPath } from '@uniswap/v3-sdk';
9
9
  import { keccak256 as keccak256$1 } from '@ethersproject/solidity';
10
- import { SwapRouter } from '@uniswap/router-sdk';
10
+ import { SwapRouter, PaymentsExtended } from '@uniswap/router-sdk';
11
11
  import FormData from 'form-data';
12
12
  import { Seaport as Seaport$1 } from '@opensea/seaport-js';
13
13
 
@@ -14739,6 +14739,7 @@ const newAmount = (amount, token) => ({
14739
14739
  });
14740
14740
  const isERC20Amount = (amount) => amount.token.type === 'erc20';
14741
14741
  const isNativeAmount = (amount) => amount.token.type === 'native';
14742
+ const isNative = (token) => token.type === 'native';
14742
14743
  const addERC20Amount = (a, b) => {
14743
14744
  // Make sure the ERC20s have the same address
14744
14745
  if (a.token.address !== b.token.address)
@@ -15392,92 +15393,193 @@ const IMMUTABLE_TESTNET_COMMON_ROUTING_TOKENS = [
15392
15393
 
15393
15394
  const zeroNativeCurrencyValue = '0x00';
15394
15395
  const multicallWithDeadlineFunctionSignature = 'multicall(uint256,bytes[])';
15395
- function buildSwapParametersForSinglePoolSwap(fromAddress, trade, route, amountIn, amountOut, secondaryFees, secondaryFeeContract) {
15396
+ function buildSinglePoolSwap(tokenIn, tokenOut, recipient, trade, route, amountIn, amountOut, routerContract, paymentsContract) {
15397
+ const calldatas = [];
15398
+ if (trade.tradeType === Uniswap.TradeType.EXACT_INPUT) {
15399
+ calldatas.push(routerContract.encodeFunctionData('exactInputSingle', [
15400
+ {
15401
+ tokenIn: route.tokenPath[0].address,
15402
+ tokenOut: route.tokenPath[1].address,
15403
+ fee: route.pools[0].fee,
15404
+ recipient,
15405
+ amountIn,
15406
+ amountOutMinimum: amountOut,
15407
+ sqrtPriceLimitX96: 0,
15408
+ },
15409
+ ]));
15410
+ }
15411
+ if (trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT) {
15412
+ calldatas.push(routerContract.encodeFunctionData('exactOutputSingle', [
15413
+ {
15414
+ tokenIn: route.tokenPath[0].address,
15415
+ tokenOut: route.tokenPath[1].address,
15416
+ fee: route.pools[0].fee,
15417
+ recipient,
15418
+ amountInMaximum: amountIn,
15419
+ amountOut,
15420
+ sqrtPriceLimitX96: 0,
15421
+ },
15422
+ ]));
15423
+ }
15424
+ const shouldRefundNativeTokens = trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT && isNative(tokenIn);
15425
+ if (shouldRefundNativeTokens) {
15426
+ // Refund ETH if the input token is native and the swap is exact output
15427
+ calldatas.push(paymentsContract.encodeFunctionData('refundETH'));
15428
+ }
15429
+ const shouldUnwrapTokens = isNative(tokenOut);
15430
+ if (shouldUnwrapTokens) {
15431
+ // Unwrap the output token if the user specified a native token as the output
15432
+ calldatas.push(paymentsContract.encodeFunctionData('unwrapWETH9(uint256)', [amountOut]));
15433
+ }
15434
+ return calldatas;
15435
+ }
15436
+ function buildSinglePoolSwapWithFees(recipient, trade, route, amountIn, amountOut, secondaryFees, secondaryFeeContract) {
15396
15437
  const secondaryFeeValues = secondaryFees.map((fee) => ({
15397
15438
  feeBasisPoints: fee.basisPoints,
15398
15439
  recipient: fee.recipient,
15399
15440
  }));
15400
- if (trade.tradeType === TradeType.EXACT_INPUT) {
15401
- return secondaryFeeContract.encodeFunctionData('exactInputSingleWithSecondaryFee', [
15441
+ const calldatas = [];
15442
+ if (trade.tradeType === Uniswap.TradeType.EXACT_INPUT) {
15443
+ calldatas.push(secondaryFeeContract.encodeFunctionData('exactInputSingleWithSecondaryFee', [
15402
15444
  secondaryFeeValues,
15403
15445
  {
15404
15446
  tokenIn: route.tokenPath[0].address,
15405
15447
  tokenOut: route.tokenPath[1].address,
15406
15448
  fee: route.pools[0].fee,
15407
- recipient: fromAddress,
15449
+ recipient,
15408
15450
  amountIn,
15409
15451
  amountOutMinimum: amountOut,
15410
15452
  sqrtPriceLimitX96: 0,
15411
15453
  },
15412
- ]);
15454
+ ]));
15413
15455
  }
15414
- return secondaryFeeContract.encodeFunctionData('exactOutputSingleWithSecondaryFee', [
15415
- secondaryFeeValues,
15416
- {
15417
- tokenIn: route.tokenPath[0].address,
15418
- tokenOut: route.tokenPath[1].address,
15419
- fee: route.pools[0].fee,
15420
- recipient: fromAddress,
15421
- amountInMaximum: amountIn,
15422
- amountOut,
15423
- sqrtPriceLimitX96: 0,
15424
- },
15425
- ]);
15456
+ if (trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT) {
15457
+ calldatas.push(secondaryFeeContract.encodeFunctionData('exactOutputSingleWithSecondaryFee', [
15458
+ secondaryFeeValues,
15459
+ {
15460
+ tokenIn: route.tokenPath[0].address,
15461
+ tokenOut: route.tokenPath[1].address,
15462
+ fee: route.pools[0].fee,
15463
+ recipient,
15464
+ amountInMaximum: amountIn,
15465
+ amountOut,
15466
+ sqrtPriceLimitX96: 0,
15467
+ },
15468
+ ]));
15469
+ }
15470
+ // TODO: Add refundETH method when support is added in SecondaryFee contract
15471
+ return calldatas;
15472
+ }
15473
+ function buildMultiPoolSwap(tokenIn, tokenOut, recipient, trade, route, amountIn, amountOut, routerContract, paymentsContract) {
15474
+ const path = encodeRouteToPath(route, trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT);
15475
+ const calldatas = [];
15476
+ if (trade.tradeType === Uniswap.TradeType.EXACT_INPUT) {
15477
+ calldatas.push(routerContract.encodeFunctionData('exactInput', [
15478
+ {
15479
+ path,
15480
+ recipient,
15481
+ amountIn,
15482
+ amountOutMinimum: amountOut,
15483
+ },
15484
+ ]));
15485
+ }
15486
+ if (trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT) {
15487
+ calldatas.push(routerContract.encodeFunctionData('exactOutput', [
15488
+ {
15489
+ path,
15490
+ recipient,
15491
+ amountInMaximum: amountIn,
15492
+ amountOut,
15493
+ },
15494
+ ]));
15495
+ }
15496
+ const shouldRefundNativeTokens = trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT && isNative(tokenIn);
15497
+ if (shouldRefundNativeTokens) {
15498
+ // Refund ETH if the input token is native and the swap is exact output
15499
+ calldatas.push(paymentsContract.encodeFunctionData('refundETH'));
15500
+ }
15501
+ const shouldUnwrapTokens = isNative(tokenOut);
15502
+ if (shouldUnwrapTokens) {
15503
+ // Unwrap the output token if the user specified a native token as the output
15504
+ calldatas.push(paymentsContract.encodeFunctionData('unwrapWETH9(uint256)', [amountOut]));
15505
+ }
15506
+ return calldatas;
15426
15507
  }
15427
- function buildSwapParametersForMultiPoolSwap(fromAddress, trade, route, amountIn, amountOut, secondaryFees, secondaryFeeContract) {
15428
- const path = encodeRouteToPath(route, trade.tradeType === TradeType.EXACT_OUTPUT);
15508
+ function buildMultiPoolSwapWithFees(recipient, trade, route, amountIn, amountOut, secondaryFees, secondaryFeeContract) {
15509
+ const path = encodeRouteToPath(route, trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT);
15429
15510
  const secondaryFeeValues = secondaryFees.map((fee) => ({
15430
15511
  feeBasisPoints: fee.basisPoints,
15431
15512
  recipient: fee.recipient,
15432
15513
  }));
15433
- if (trade.tradeType === TradeType.EXACT_INPUT) {
15434
- return secondaryFeeContract.encodeFunctionData('exactInputWithSecondaryFee', [
15514
+ const calldatas = [];
15515
+ if (trade.tradeType === Uniswap.TradeType.EXACT_INPUT) {
15516
+ calldatas.push(secondaryFeeContract.encodeFunctionData('exactInputWithSecondaryFee', [
15435
15517
  secondaryFeeValues,
15436
15518
  {
15437
15519
  path,
15438
- recipient: fromAddress,
15520
+ recipient,
15439
15521
  amountIn,
15440
15522
  amountOutMinimum: amountOut,
15441
15523
  },
15442
- ]);
15524
+ ]));
15443
15525
  }
15444
- return secondaryFeeContract.encodeFunctionData('exactOutputWithSecondaryFee', [
15445
- secondaryFeeValues,
15446
- {
15447
- path,
15448
- recipient: fromAddress,
15449
- amountInMaximum: amountIn,
15450
- amountOut,
15451
- },
15452
- ]);
15526
+ if (trade.tradeType === Uniswap.TradeType.EXACT_OUTPUT) {
15527
+ calldatas.push(secondaryFeeContract.encodeFunctionData('exactOutputWithSecondaryFee', [
15528
+ secondaryFeeValues,
15529
+ {
15530
+ path,
15531
+ recipient,
15532
+ amountInMaximum: amountIn,
15533
+ amountOut,
15534
+ },
15535
+ ]));
15536
+ }
15537
+ // TODO: Add refundETH method when support is added in SecondaryFee contract
15538
+ return calldatas;
15453
15539
  }
15454
15540
  /**
15455
- * Builds swap parameters
15456
- * @param fromAddress the msg.sender of the transaction
15457
- * @param secondaryFeeAddress the secondary fee contract address
15458
- * @param trade details of the swap, including the route, input/output tokens and amounts
15459
- * @param options additional swap options
15460
- * @returns calldata for the swap
15541
+ * Builds and array of calldatas for the swap to be executed in the multicall method
15542
+ * @param tokenIn The token to be swapped
15543
+ * @param tokenOut The token to be received
15544
+ * @param fromAddress The address of the user
15545
+ * @param trade The trade to be executed
15546
+ * @param secondaryFees Secondary fees to be applied to the swap
15547
+ * @param secondaryFeeContract The SecondaryFee contract interface
15548
+ * @param routerContract The SwapRouter02 contract interface
15549
+ * @param paymentsContract The PaymentsExtended contract interface
15550
+ * @param maximumAmountIn The maximum amount of tokenIn to be swapped
15551
+ * @param minimumAmountOut The minimum amount of tokenOut to be received
15552
+ * @returns calldatas that make up the swap transaction
15461
15553
  */
15462
- function buildSwapParameters(fromAddress, trade, options, secondaryFees, secondaryFeeContract, maximumAmountIn, minimumAmountOut) {
15554
+ function buildSwapParameters(tokenIn, tokenOut, recipient, trade, secondaryFees, secondaryFeeContract, routerContract, paymentsContract, maximumAmountIn, minimumAmountOut) {
15463
15555
  // @dev we don't support multiple swaps in a single transaction
15464
15556
  // there will always be only one swap in the trade regardless of the trade type
15465
15557
  const { route } = trade.swaps[0];
15466
15558
  const isSinglePoolSwap = route.pools.length === 1;
15559
+ const hasSecondaryFees = secondaryFees.length > 0;
15467
15560
  if (isSinglePoolSwap) {
15468
- return buildSwapParametersForSinglePoolSwap(fromAddress, trade, route, maximumAmountIn, minimumAmountOut, secondaryFees, secondaryFeeContract);
15561
+ if (hasSecondaryFees) {
15562
+ return buildSinglePoolSwapWithFees(recipient, trade, route, maximumAmountIn, minimumAmountOut, secondaryFees, secondaryFeeContract);
15563
+ }
15564
+ return buildSinglePoolSwap(tokenIn, tokenOut, recipient, trade, route, maximumAmountIn, minimumAmountOut, routerContract, paymentsContract);
15565
+ }
15566
+ if (hasSecondaryFees) {
15567
+ return buildMultiPoolSwapWithFees(recipient, trade, route, maximumAmountIn, minimumAmountOut, secondaryFees, secondaryFeeContract);
15469
15568
  }
15470
- return buildSwapParametersForMultiPoolSwap(fromAddress, trade, route, maximumAmountIn, minimumAmountOut, secondaryFees, secondaryFeeContract);
15569
+ return buildMultiPoolSwap(tokenIn, tokenOut, recipient, trade, route, maximumAmountIn, minimumAmountOut, routerContract, paymentsContract);
15471
15570
  }
15472
- function createSwapCallParametersWithFees(trade, fromAddress, swapOptions, secondaryFees, maximumAmountIn, minimumAmountOut) {
15571
+ function createSwapCallParameters(tokenIn, tokenOut, trade, recipient, swapOptions, secondaryFees, maximumAmountIn, minimumAmountOut) {
15473
15572
  const secondaryFeeContract = SecondaryFee__factory.createInterface();
15474
- const swapWithFeesCalldata = buildSwapParameters(fromAddress, trade, swapOptions, secondaryFees, secondaryFeeContract, maximumAmountIn, minimumAmountOut);
15573
+ const routerContract = SwapRouter.INTERFACE;
15574
+ const paymentsContract = PaymentsExtended.INTERFACE;
15575
+ const calldatas = buildSwapParameters(tokenIn, tokenOut, recipient, trade, secondaryFees, secondaryFeeContract, routerContract, paymentsContract, maximumAmountIn, minimumAmountOut);
15576
+ // Create the multicall transaction using the calldatas generated above
15475
15577
  return secondaryFeeContract.encodeFunctionData(multicallWithDeadlineFunctionSignature, [
15476
15578
  swapOptions.deadlineOrPreviousBlockhash,
15477
- [swapWithFeesCalldata],
15579
+ calldatas,
15478
15580
  ]);
15479
15581
  }
15480
- function createSwapParameters(adjustedQuote, fromAddress, slippage, deadline, secondaryFees) {
15582
+ function createSwapParameters(tokenIn, tokenOut, adjustedQuote, fromAddress, slippage, deadline, secondaryFees) {
15481
15583
  // Create an unchecked trade to be used in generating swap parameters.
15482
15584
  const uncheckedTrade = Trade.createUncheckedTrade({
15483
15585
  route: adjustedQuote.route,
@@ -15492,29 +15594,26 @@ function createSwapParameters(adjustedQuote, fromAddress, slippage, deadline, se
15492
15594
  deadlineOrPreviousBlockhash: deadline,
15493
15595
  };
15494
15596
  // If the trade type is EXACT_INPUT, then the maximum amount-in is the user-specified amount (no slippage applied)
15597
+ // For EXACT_OUTPUT, the maximum amount-in is the amount-in with slippage applied
15495
15598
  // https://github.com/Uniswap/v3-sdk/blob/81d66099f07d1ec350767f497ef73222575fe032/src/entities/trade.ts#L456
15496
15599
  const maximumAmountIn = toHex$1(uncheckedTrade.maximumAmountIn(options.slippageTolerance).quotient);
15497
15600
  const minimumAmountOut = toHex$1(uncheckedTrade.minimumAmountOut(options.slippageTolerance).quotient);
15498
- if (secondaryFees.length === 0) {
15499
- // Generate swap parameters without secondary fee contract details
15500
- return { calldata: SwapRouter.swapCallParameters([uncheckedTrade], options).calldata, maximumAmountIn };
15501
- }
15502
15601
  return {
15503
- calldata: createSwapCallParametersWithFees(uncheckedTrade, fromAddress, options, secondaryFees, maximumAmountIn, minimumAmountOut),
15602
+ calldata: createSwapCallParameters(tokenIn, tokenOut, uncheckedTrade, fromAddress, options, secondaryFees, maximumAmountIn, minimumAmountOut),
15504
15603
  maximumAmountIn,
15505
15604
  };
15506
15605
  }
15507
15606
  const getTransactionValue = (tokenIn, maximumAmountIn) => tokenIn.type === 'native' ? maximumAmountIn : zeroNativeCurrencyValue;
15508
- function getSwap(tokenIn, adjustedQuote, fromAddress, slippage, deadline, peripheryRouterAddress, secondaryFeesAddress, gasPrice, secondaryFees) {
15509
- // TODO: TP-1651: Include `refundETH` transaction as final step for native Exact Output swaps
15510
- const { calldata, maximumAmountIn } = createSwapParameters(adjustedQuote, fromAddress, slippage, deadline, secondaryFees);
15607
+ function getSwap(tokenIn, tokenOut, adjustedQuote, fromAddress, slippage, deadline, routerContractAddress, secondaryFeesContractAddress, gasPrice, secondaryFees) {
15608
+ const swapRecipient = isNative(tokenOut) ? routerContractAddress : fromAddress;
15609
+ const { calldata, maximumAmountIn } = createSwapParameters(tokenIn, tokenOut, adjustedQuote, swapRecipient, slippage, deadline, secondaryFees);
15511
15610
  // TODO: Add additional gas fee estimates for secondary fees
15512
15611
  const gasFeeEstimate = gasPrice ? calculateGasFee(gasPrice, adjustedQuote.gasEstimate) : null;
15513
15612
  const transactionValue = getTransactionValue(tokenIn, maximumAmountIn);
15514
15613
  return {
15515
15614
  transaction: {
15516
15615
  data: calldata,
15517
- to: secondaryFees.length > 0 ? secondaryFeesAddress : peripheryRouterAddress,
15616
+ to: secondaryFees.length > 0 ? secondaryFeesContractAddress : routerContractAddress,
15518
15617
  value: transactionValue,
15519
15618
  from: fromAddress,
15520
15619
  },
@@ -15522,7 +15621,7 @@ function getSwap(tokenIn, adjustedQuote, fromAddress, slippage, deadline, periph
15522
15621
  };
15523
15622
  }
15524
15623
  const adjustAmountIn = (ourQuote, amountSpecified, fees, nativeTokenService) => {
15525
- if (ourQuote.tradeType === TradeType.EXACT_OUTPUT) {
15624
+ if (ourQuote.tradeType === Uniswap.TradeType.EXACT_OUTPUT) {
15526
15625
  // when doing exact output, calculate the fees based on the amountIn
15527
15626
  const amountToAdd = canUnwrapToken(fees.token)
15528
15627
  ? nativeTokenService.unwrapAmount(ourQuote.amountIn)
@@ -15728,7 +15827,7 @@ class Exchange {
15728
15827
  fetchGasPrice(this.provider, this.nativeToken),
15729
15828
  ]);
15730
15829
  const adjustedQuote = adjustQuoteWithFees(ourQuote, amountSpecified, fees, this.nativeTokenService);
15731
- const swap = getSwap(tokenIn, adjustedQuote, fromAddress, slippagePercent, deadline, this.routerContractAddress, this.secondaryFeeContractAddress, gasPrice, secondaryFees);
15830
+ const swap = getSwap(tokenIn, tokenOut, adjustedQuote, fromAddress, slippagePercent, deadline, this.routerContractAddress, this.secondaryFeeContractAddress, gasPrice, secondaryFees);
15732
15831
  const { quotedAmount, quotedAmountWithMaxSlippage } = prepareUserQuote(this.nativeTokenService, adjustedQuote, slippagePercent, otherToken);
15733
15832
  const preparedApproval = prepareApproval(tradeType, amountSpecified, quotedAmountWithMaxSlippage, {
15734
15833
  routerAddress: this.routerContractAddress,
@@ -16372,7 +16471,7 @@ var CancelledOrderStatus;
16372
16471
  var FailedOrderCancellation;
16373
16472
  (function (FailedOrderCancellation) {
16374
16473
  (function (reason_code) {
16375
- reason_code["ALREADY_FILLED"] = "ALREADY_FILLED";
16474
+ reason_code["FILLED"] = "FILLED";
16376
16475
  })(FailedOrderCancellation.reason_code || (FailedOrderCancellation.reason_code = {}));
16377
16476
  })(FailedOrderCancellation || (FailedOrderCancellation = {}));
16378
16477
 
@@ -16426,10 +16525,12 @@ var TransactionPurpose;
16426
16525
  (function (TransactionPurpose) {
16427
16526
  TransactionPurpose["APPROVAL"] = "APPROVAL";
16428
16527
  TransactionPurpose["FULFILL_ORDER"] = "FULFILL_ORDER";
16528
+ TransactionPurpose["CANCEL"] = "CANCEL";
16429
16529
  })(TransactionPurpose || (TransactionPurpose = {}));
16430
16530
  var SignablePurpose;
16431
16531
  (function (SignablePurpose) {
16432
16532
  SignablePurpose["CREATE_LISTING"] = "CREATE_LISTING";
16533
+ SignablePurpose["OFF_CHAIN_CANCELLATION"] = "OFF_CHAIN_CANCELLATION";
16433
16534
  })(SignablePurpose || (SignablePurpose = {}));
16434
16535
  var ActionType;
16435
16536
  (function (ActionType) {
@@ -16826,11 +16927,15 @@ class Seaport {
16826
16927
  .reduce((p, c) => (new Date(p) < new Date(c) ? p : c)),
16827
16928
  };
16828
16929
  }
16829
- async cancelOrder(order, account) {
16830
- const { orderComponents } = this.mapImmutableOrderToSeaportOrderComponents(order);
16831
- const seaportLib = this.getSeaportLib(order);
16832
- const cancellationTransaction = await seaportLib.cancelOrders([orderComponents], account);
16833
- return prepareTransaction(cancellationTransaction)();
16930
+ async cancelOrders(orders, account) {
16931
+ const orderComponents = orders.map((order) => this.mapImmutableOrderToSeaportOrderComponents(order).orderComponents);
16932
+ const seaportLib = this.getSeaportLib(orders[0]);
16933
+ const cancellationTransaction = await seaportLib.cancelOrders(orderComponents, account);
16934
+ return {
16935
+ type: ActionType.TRANSACTION,
16936
+ buildTransaction: prepareTransaction(cancellationTransaction),
16937
+ purpose: TransactionPurpose.CANCEL,
16938
+ };
16834
16939
  }
16835
16940
  mapImmutableOrderToSeaportOrderComponents(order) {
16836
16941
  const orderCounter = order.protocol_data.counter;
@@ -16932,6 +17037,16 @@ class ImmutableApiClient {
16932
17037
  ...listTradesParams,
16933
17038
  });
16934
17039
  }
17040
+ async cancelOrders(orderIds, accountAddress, signature) {
17041
+ return this.orderbookService.cancelOrders({
17042
+ chainName: this.chainName,
17043
+ requestBody: {
17044
+ account_address: accountAddress,
17045
+ orders: orderIds,
17046
+ signature,
17047
+ },
17048
+ });
17049
+ }
16935
17050
  async createListing({ orderHash, orderComponents, orderSignature, makerFees, }) {
16936
17051
  if (orderComponents.offer.length !== 1) {
16937
17052
  throw new Error('Only one item can be listed at a time');
@@ -17233,24 +17348,89 @@ class Orderbook {
17233
17348
  }
17234
17349
  }
17235
17350
  /**
17236
- * Get an unsigned cancel order transaction. Orders can only be cancelled by
17237
- * the account that created them.
17238
- * @param {string} listingId - The listingId to cancel.
17351
+ * Cancelling orders is a gasless alternative to on-chain cancellation exposed with
17352
+ * `cancelOrdersOnChain`. For the orderbook to authenticate the cancellation, the creator
17353
+ * of the orders must sign an EIP712 message containing the orderIds
17354
+ * @param {string} orderIds - The orderIds to attempt to cancel.
17355
+ * @return {PrepareCancelOrdersResponse} The signable action to cancel the orders.
17356
+ */
17357
+ async prepareOrderCancellations(orderIds) {
17358
+ const network = await this.orderbookConfig.provider.getNetwork();
17359
+ const domain = {
17360
+ name: 'imtbl-order-book',
17361
+ chainId: network.chainId,
17362
+ verifyingContract: this.orderbookConfig.seaportContractAddress,
17363
+ };
17364
+ const types = {
17365
+ // eslint-disable-next-line @typescript-eslint/naming-convention
17366
+ CancelPayload: [
17367
+ { name: 'orders', type: 'Order[]' },
17368
+ ],
17369
+ // eslint-disable-next-line @typescript-eslint/naming-convention
17370
+ Order: [
17371
+ { name: 'id', type: 'string' },
17372
+ ],
17373
+ };
17374
+ const cancelMessage = {
17375
+ orders: orderIds.map((id) => ({ id })),
17376
+ };
17377
+ return {
17378
+ signableAction: {
17379
+ purpose: SignablePurpose.OFF_CHAIN_CANCELLATION,
17380
+ type: ActionType.SIGNABLE,
17381
+ message: {
17382
+ domain,
17383
+ types,
17384
+ value: cancelMessage,
17385
+ },
17386
+ },
17387
+ };
17388
+ }
17389
+ /**
17390
+ * Cancelling orders is a gasless alternative to on-chain cancellation exposed with
17391
+ * `cancelOrdersOnChain`. Orders cancelled this way cannot be fulfilled and will be removed
17392
+ * from the orderbook. If there is pending fulfillment data outstanding for the order, its
17393
+ * cancellation will be pending until the fulfillment window has passed.
17394
+ * `prepareOffchainOrderCancellations` can be used to get the signable action that is signed
17395
+ * to get the signature required for this call.
17396
+ * @param {string[]} orderIds - The orderIds to attempt to cancel.
17397
+ * @param {string} accountAddress - The address of the account cancelling the orders.
17398
+ * @param {string} accountAddress - The address of the account cancelling the orders.
17399
+ * @return {CancelOrdersResult} The result of the off-chain cancellation request
17400
+ */
17401
+ async cancelOrders(orderIds, accountAddress, signature) {
17402
+ return this.apiClient.cancelOrders(orderIds, accountAddress, signature);
17403
+ }
17404
+ /**
17405
+ * Get an unsigned order cancellation transaction. Orders can only be cancelled by
17406
+ * the account that created them. All of the orders must be from the same seaport contract.
17407
+ * If trying to cancel orders from multiple seaport contracts, group the orderIds by seaport
17408
+ * contract and call this method for each group.
17409
+ * @param {string[]} orderIds - The orderIds to cancel.
17239
17410
  * @param {string} accountAddress - The address of the account cancelling the order.
17240
- * @return {CancelOrderResponse} The unsigned cancel order transaction
17411
+ * @return {CancelOrdersOnChainResponse} The unsigned cancel order action
17241
17412
  */
17242
- async cancelOrder(listingId, accountAddress) {
17243
- const orderResult = await this.apiClient.getListing(listingId);
17244
- if (orderResult.result.status.name !== OrderStatusName$1.ACTIVE
17245
- && orderResult.result.status.name !== OrderStatusName$1.INACTIVE
17246
- && orderResult.result.status.name !== OrderStatusName$1.PENDING) {
17247
- throw new Error(`Cannot cancel order with status ${orderResult.result.status}`);
17413
+ async cancelOrdersOnChain(orderIds, accountAddress) {
17414
+ const orderResults = await Promise.all(orderIds.map((id) => this.apiClient.getListing(id)));
17415
+ // eslint-disable-next-line no-restricted-syntax
17416
+ for (const orderResult of orderResults) {
17417
+ if (orderResult.result.status.name !== OrderStatusName$1.ACTIVE
17418
+ && orderResult.result.status.name !== OrderStatusName$1.INACTIVE
17419
+ && orderResult.result.status.name !== OrderStatusName$1.PENDING) {
17420
+ throw new Error(`Cannot cancel order with status ${orderResult.result.status}`);
17421
+ }
17422
+ if (orderResult.result.account_address !== accountAddress.toLowerCase()) {
17423
+ throw new Error(`Only account ${orderResult.result.account_address} can cancel order ${orderResult.result.id}`);
17424
+ }
17248
17425
  }
17249
- if (orderResult.result.account_address !== accountAddress.toLowerCase()) {
17250
- throw new Error(`Only account ${orderResult.result.account_address} can cancel order ${listingId}`);
17426
+ const orders = orderResults.map((orderResult) => orderResult.result);
17427
+ const seaportAddresses = orders.map((o) => o.protocol_data.seaport_address);
17428
+ const distinctSeaportAddresses = new Set(...[seaportAddresses]);
17429
+ if (distinctSeaportAddresses.size !== 1) {
17430
+ throw new Error('Cannot cancel multiple orders from different seaport contracts. Please group your orderIds accordingly');
17251
17431
  }
17252
- const cancelOrderTransaction = await this.seaport.cancelOrder(orderResult.result, accountAddress);
17253
- return { unsignedCancelOrderTransaction: cancelOrderTransaction };
17432
+ const cancellationAction = await this.seaport.cancelOrders(orders, accountAddress);
17433
+ return { cancellationAction };
17254
17434
  }
17255
17435
  }
17256
17436
 
@@ -20607,7 +20787,7 @@ class APIError extends Error {
20607
20787
 
20608
20788
  /* eslint-disable implicit-arrow-linebreak */
20609
20789
  const defaultHeaders = {
20610
- sdkVersion: 'ts-immutable-sdk-multi-rollup-api-client-0.27.15',
20790
+ sdkVersion: 'ts-immutable-sdk-multi-rollup-api-client-0.28.0',
20611
20791
  };
20612
20792
  /**
20613
20793
  * createAPIConfiguration to create a custom Configuration
@@ -24717,8 +24897,10 @@ const $9c3db1bb9c8b69d3$export$70b61ad426ddbe54 = async (config, provider, order
24717
24897
  try {
24718
24898
  const offererAddress = await (0, $458d407830d66110$export$5280dbcb91c8b391)(config, "Time to get the address from the provider", provider.getSigner().getAddress());
24719
24899
  const orderbook = $67fc622a2b913d5f$export$c60ce6c6a92bc2ff(config);
24720
- const cancelOrderResponse = await (0, $458d407830d66110$export$5280dbcb91c8b391)(config, "Time to get the cancel order from the orderbook", orderbook.cancelOrder(orderId, offererAddress));
24721
- unsignedCancelOrderTransaction = cancelOrderResponse.unsignedCancelOrderTransaction;
24900
+ const cancelOrderResponse = await (0, $458d407830d66110$export$5280dbcb91c8b391)(config, "Time to get the cancel order from the orderbook", orderbook.cancelOrdersOnChain([
24901
+ orderId
24902
+ ], offererAddress));
24903
+ unsignedCancelOrderTransaction = await cancelOrderResponse.cancellationAction.buildTransaction();
24722
24904
  } catch (err) {
24723
24905
  throw new ($a8bc256d81a5e2c1$export$b722478a3cbfa3bc)("An error occurred while cancelling the order listing", ($a8bc256d81a5e2c1$export$e3dc0620abde7f5a).CANCEL_ORDER_LISTING_ERROR, {
24724
24906
  orderId: orderId,
@@ -25,7 +25,7 @@ var $045213b18e9f1f94$export$75be0f6af9650f2c;
25
25
  })($045213b18e9f1f94$export$75be0f6af9650f2c || ($045213b18e9f1f94$export$75be0f6af9650f2c = {}));
26
26
 
27
27
 
28
- const $d663162fd5a0853f$export$38a083d9fb5551ca = "0.27.15";
28
+ const $d663162fd5a0853f$export$38a083d9fb5551ca = "0.28.0";
29
29
  const $d663162fd5a0853f$export$83bf90b30cdfd29f = ()=>false;
30
30
  const $d663162fd5a0853f$export$1169f5475725171b = ()=>$d663162fd5a0853f$export$38a083d9fb5551ca;
31
31
 
@@ -16,7 +16,7 @@ const createImmutableXConfiguration = ({ basePath, chainID, coreContractAddress,
16
16
  chainID,
17
17
  coreContractAddress,
18
18
  registrationContractAddress,
19
- sdkVersion: 'ts-immutable-sdk-0.27.15',
19
+ sdkVersion: 'ts-immutable-sdk-0.28.0',
20
20
  });
21
21
  /**
22
22
  * Sets `sdkVersion` at the time of build