PHP WebShell

Текущая директория: /usr/lib/node_modules/bitgo/node_modules/@iota/iota-sdk/dist/esm/transactions/intents

Просмотр файла: CoinWithBalance.js

import { bigint, object, parse, string } from "valibot";
import { bcs } from "../../bcs/index.js";
import { normalizeStructTag } from "../../utils/iota-types.js";
import { Commands } from "../Commands.js";
import { Inputs } from "../Inputs.js";
import { getClient } from "../json-rpc-resolver.js";
const COIN_WITH_BALANCE = "CoinWithBalance";
const IOTA_TYPE = normalizeStructTag("0x2::iota::IOTA");
function coinWithBalance({
  type = IOTA_TYPE,
  balance,
  useGasCoin = true
}) {
  return (tx) => {
    tx.addIntentResolver(COIN_WITH_BALANCE, resolveCoinBalance);
    const coinType = type === "gas" ? type : normalizeStructTag(type);
    return tx.add(
      Commands.Intent({
        name: COIN_WITH_BALANCE,
        inputs: {},
        data: {
          type: coinType === IOTA_TYPE && useGasCoin ? "gas" : coinType,
          balance: BigInt(balance)
        }
      })
    );
  };
}
const CoinWithBalanceData = object({
  type: string(),
  balance: bigint()
});
async function resolveCoinBalance(transactionData, buildOptions, next) {
  const coinTypes = /* @__PURE__ */ new Set();
  const totalByType = /* @__PURE__ */ new Map();
  if (!transactionData.sender) {
    throw new Error("Sender must be set to resolve CoinWithBalance");
  }
  for (const command of transactionData.commands) {
    if (command.$kind === "$Intent" && command.$Intent.name === COIN_WITH_BALANCE) {
      const { type, balance } = parse(CoinWithBalanceData, command.$Intent.data);
      if (type !== "gas" && balance > 0n) {
        coinTypes.add(type);
      }
      totalByType.set(type, (totalByType.get(type) ?? 0n) + balance);
    }
  }
  const usedIds = /* @__PURE__ */ new Set();
  for (const input of transactionData.inputs) {
    if (input.Object?.ImmOrOwnedObject) {
      usedIds.add(input.Object.ImmOrOwnedObject.objectId);
    }
    if (input.UnresolvedObject?.objectId) {
      usedIds.add(input.UnresolvedObject.objectId);
    }
  }
  const coinsByType = /* @__PURE__ */ new Map();
  const client = getClient(buildOptions);
  await Promise.all(
    [...coinTypes].map(async (coinType) => {
      coinsByType.set(
        coinType,
        await getCoinsOfType({
          coinType,
          balance: totalByType.get(coinType),
          client,
          owner: transactionData.sender,
          usedIds
        })
      );
    })
  );
  const mergedCoins = /* @__PURE__ */ new Map();
  mergedCoins.set("gas", { $kind: "GasCoin", GasCoin: true });
  for (const [index, transaction] of transactionData.commands.entries()) {
    if (transaction.$kind !== "$Intent" || transaction.$Intent.name !== COIN_WITH_BALANCE) {
      continue;
    }
    const { type, balance } = transaction.$Intent.data;
    if (balance === 0n) {
      transactionData.replaceCommand(
        index,
        Commands.MoveCall({ target: "0x2::coin::zero", typeArguments: [type] })
      );
      continue;
    }
    const commands = [];
    if (!mergedCoins.has(type)) {
      const [first, ...rest] = coinsByType.get(type).map(
        (coin) => transactionData.addInput(
          "object",
          Inputs.ObjectRef({
            objectId: coin.coinObjectId,
            digest: coin.digest,
            version: coin.version
          })
        )
      );
      if (rest.length > 0) {
        commands.push(Commands.MergeCoins(first, rest));
      }
      mergedCoins.set(type, first);
    }
    commands.push(
      Commands.SplitCoins(mergedCoins.get(type), [
        transactionData.addInput("pure", Inputs.Pure(bcs.u64().serialize(balance)))
      ])
    );
    transactionData.replaceCommand(index, commands);
    transactionData.mapArguments((arg) => {
      if (arg.$kind === "Result" && arg.Result === index) {
        return {
          $kind: "NestedResult",
          NestedResult: [index + commands.length - 1, 0]
        };
      }
      return arg;
    });
  }
  return next();
}
async function getCoinsOfType({
  coinType,
  balance,
  client,
  owner,
  usedIds
}) {
  let remainingBalance = balance;
  const coins = [];
  return loadMoreCoins();
  async function loadMoreCoins(cursor = null) {
    const { data, hasNextPage, nextCursor } = await client.getCoins({
      owner,
      coinType,
      cursor
    });
    const sortedCoins = data.sort((a, b) => Number(BigInt(b.balance) - BigInt(a.balance)));
    for (const coin of sortedCoins) {
      if (usedIds.has(coin.coinObjectId)) {
        continue;
      }
      const coinBalance = BigInt(coin.balance);
      coins.push(coin);
      remainingBalance -= coinBalance;
      if (remainingBalance <= 0) {
        return coins;
      }
    }
    if (hasNextPage) {
      return loadMoreCoins(nextCursor);
    }
    throw new Error(`Not enough coins of type ${coinType} to satisfy requested balance`);
  }
}
export {
  coinWithBalance
};
//# sourceMappingURL=CoinWithBalance.js.map

Выполнить команду


Для локальной разработки. Не используйте в интернете!