import { ERC20 } from "@tracer-protocol/perpetual-pools-contracts/types";
import BigNumber from "bignumber.js";
import { providers as MCProvider } from '@0xsequence/multicall';
import { ethers } from "ethers";
import { IContract } from "../types";
/**
 * Token class constructor inputs
 */
export interface IToken extends IContract, TokenInfo {
}
/**
 * Token constructor props
 * Only `address` is required, additional props are encouraged
 * 	to reduce the number of RPC calls
 */
export interface TokenInfo {
    address: string;
    name?: string;
    symbol?: string;
    decimals?: number;
}
/**
 * Token class for interacting with ERC20 tokens
 * The constructor is private so must be instantiated with {@linkcode Token.Create}
 */
export default class Token {
    _contract?: ERC20;
    address: string;
    provider: ethers.providers.Provider | ethers.Signer | undefined;
    multicallProvider: MCProvider.MulticallProvider | ethers.Signer | undefined;
    name: string;
    symbol: string;
    decimals: number;
    /**
     * @private
     */
    private constructor();
    /**
     * Replacement constructor pattern to support async initialisations
     * @param tokenINfo {@link IToken | IToken interface props}
     * @returns a Promise containing an initialised Token class ready to be used
     */
    static Create: (tokenInfo: IToken) => Promise<Token>;
    /**
     * Creates an empty Token that can be used as a default
     * @returns default constructed token
     */
    static CreateDefault: () => Token;
    /**
     * Private initialisation function called in {@link Token.Create}
     * @private
     * @param tokenInfo {@link IToken | IToken interface props}
     */
    private init;
    /**
     * Fetch an accounts balance for this token
     * @param account Account to check balance of
     * @returns The accounts balance formatted in a BigNumber
     */
    fetchBalance: (account: string) => Promise<BigNumber>;
    /**
     * Fetch an accounts allowance for a given spender
     * @param account Account to check allowance
     * @param spender Spender of the accounts tokens
     * @returns the allowance the account has given to the spender address to spend this token
     */
    fetchAllowance: (spender: string, account: string) => Promise<BigNumber>;
    /**
     * Approve a spender to spend the signers accounts tokens
     * @param spender the address of the contract that will spend the tokens
     * @param amount the amount the signer is allowing the spender to spend
     * @returns an ethers transaction
     */
    approve: (spender: string, amount: number | BigNumber) => Promise<ethers.ContractTransaction>;
    /**
     * Replaces the provider and connects the contract instance
     * @param provider The new provider to connect to
     */
    connect: (provider: ethers.providers.Provider | ethers.Signer) => void;
}
