erc20/v1.ts

import { ethers } from "ethers";
import ringABI from "@evo/config/abi/common/abi-ring.json";
import type { ContractNameType } from "@evo/types";
import type { CallbackType } from "@evo/utils/ethers/contractHelper";
import {
  triggerContractByContractName,
  viewContractByContractName,
  triggerContract,
  viewContract,
  getContract,
} from "@evo/utils/ethers/contractHelper";
import { LandId } from "@evo/config/constants";
import { TransactionResponse } from "@ethersproject/providers";

/**
 * ERC20 Allowance
 * @param provider Ethers provider
 * @param contractName Contract name
 * @param from From, account address
 * @param spender Spender
 * @param callback Callback
 * @returns String amount
 */
export const erc20Allowance = async (
  landId: LandId,
  provider: ethers.providers.Provider,
  contractName: ContractNameType,
  from: string,
  spender: string,
  callback?: CallbackType
): Promise<string> => {
  const results = await viewContractByContractName(
    landId,
    provider,
    contractName,
    "allowance",
    [from, spender],
    callback
  );
  return results.length ? (results[0] as ethers.BigNumber).toHexString() : ethers.utils.hexValue(0);
};

/**
 * ERC20 Allowance By Contract Address
 * @param provider Ethers provider
 * @param contractAddress Contract address
 * @param from From
 * @param spender Spender
 * @param callback Callback
 * @returns String amount
 */
export const erc20AllowanceByContractAddress = async (
  provider: ethers.providers.Provider,
  contractAddress: string,
  from: string,
  spender: string,
  callback?: CallbackType
): Promise<string> => {
  const contract = await getContract(provider, contractAddress, ringABI);
  if (contract) {
    const results = await viewContract(contract, "allowance", [from, spender], callback);
    return results.length ? (results[0] as ethers.BigNumber).toHexString() : ethers.utils.hexValue(0);
  } else {
    callback && callback.errorCallback({ error: new Error(`erc20AllowanceByContractAddress failed to get contract.`) });
    return ethers.utils.hexValue(0);
  }
};

/**
 * ERC20 Approve
 * @param signer Ethers signer
 * @param contractName Contract name
 * @param spender Spender
 * @param value Value
 * @param callback Callback
 */
export const erc20Approve = (
  landId: LandId,
  signer: ethers.Signer,
  contractName: ContractNameType,
  spender: string,
  value = "0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
  callback?: CallbackType
): Promise<TransactionResponse> => {
  return triggerContractByContractName(
    landId,
    signer,
    contractName,
    "approve(address,uint256)",
    [spender, value],
    callback
  );
};

/**
 * ERC20 Approve By Contract Address
 * @param signer Ethers signer
 * @param contractAddress Contract address
 * @param spender Spender
 * @param value Value
 * @param callback Callback
 */
export const erc20ApproveByContractAddress = async (
  signer: ethers.Signer,
  contractAddress: string,
  spender: string,
  value = "0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
  callback?: CallbackType
): Promise<TransactionResponse> => {
  const contract = await getContract(signer, contractAddress, ringABI);
  // if (contract) {
  return triggerContract(contract, "approve(address,uint256)", [spender, value], callback);
  // } else {
  //   callback && callback.errorCallback({ error: new Error(`erc20ApproveByContractAddress failed to get contract.`) });
  // }
};

/**
 * ERC20 Transfer
 * @param signer Signer
 * @param contractAddress Token contract address
 * @param dst Recipient
 * @param wad Amount
 * @param callback Callback
 * @returns any
 */
export const erc20TransferByContractAddress = async (
  signer: ethers.Signer,
  contractAddress: string,
  dst: string,
  wad: string,
  callback?: CallbackType
): Promise<TransactionResponse> => {
  const contract = await getContract(signer, contractAddress, ringABI);
  // if (contract) {
  return triggerContract(contract, "transfer(address,uint256)", [dst, wad], callback);
  // } else {
  //   callback && callback.errorCallback({ error: new Error(`erc20TransferByContractAddress failed to get contract.`) });
  // }
};

/**
 * Get token balance by address
 * @param provider Provider
 * @param tokenAddress ERC20 contract address
 * @param account Address
 * @param callback Callbcak
 * @returns any
 */
export const erc20BalanceOf = async (
  provider: ethers.providers.Provider,
  tokenAddress: string,
  account: string,
  callback?: CallbackType
): Promise<string> => {
  const contract = await getContract(provider, tokenAddress, ringABI);

  const results = await viewContract(contract, "balanceOf(address)", [account], callback);
  return results.length ? (results[0] as ethers.BigNumber).toHexString() : ethers.utils.hexValue(0);
};

/**
 * Get token total supply
 * @param provider Provider
 * @param tokenAddress ERC20 contract address
 * @param callback Callback
 * @returns any
 */
export const erc20TotalSupply = async (
  provider: ethers.providers.Provider,
  tokenAddress: string,
  callback?: CallbackType
): Promise<string> => {
  const contract = await getContract(provider, tokenAddress, ringABI);

  const results = await viewContract(contract, "totalSupply", [], callback);
  return results.length ? (results[0] as ethers.BigNumber).toHexString() : ethers.utils.hexValue(0);
};