import { BigNumber, ContractFactory, ContractReceipt, ContractTransaction, PopulatedTransaction, Signer, providers } from 'ethers';
import { Logger } from 'pino';
import { Address } from '@hyperlane-xyz/utils';
import { ChainMetadataManager } from '../metadata/ChainMetadataManager.js';
import { ChainMetadata } from '../metadata/chainMetadataTypes.js';
import { ChainMap, ChainName, ChainNameOrId } from '../types.js';
import { AnnotatedEV5Transaction } from './ProviderType.js';
import { ProviderBuilderFn } from './providerBuilders.js';
type Provider = providers.Provider;
export interface MultiProviderOptions {
    logger?: Logger;
    providers?: ChainMap<Provider>;
    providerBuilder?: ProviderBuilderFn<Provider>;
    signers?: ChainMap<Signer>;
}
/**
 * A utility class to create and manage providers and signers for multiple chains
 * @typeParam MetaExt - Extra metadata fields for chains (such as contract addresses)
 */
export declare class MultiProvider<MetaExt = {}> extends ChainMetadataManager<MetaExt> {
    readonly options: MultiProviderOptions;
    readonly providers: ChainMap<Provider>;
    readonly providerBuilder: ProviderBuilderFn<Provider>;
    signers: ChainMap<Signer>;
    useSharedSigner: boolean;
    readonly logger: Logger;
    /**
     * Create a new MultiProvider with the given chainMetadata,
     * or the SDK's default metadata if not provided
     */
    constructor(chainMetadata: ChainMap<ChainMetadata<MetaExt>>, options?: MultiProviderOptions);
    addChain(metadata: ChainMetadata<MetaExt>): void;
    extendChainMetadata<NewExt = {}>(additionalMetadata: ChainMap<NewExt>): MultiProvider<MetaExt & NewExt>;
    /**
     * Get an Ethers provider for a given chain name or domain id
     */
    tryGetProvider(chainNameOrId: ChainNameOrId): Provider | null;
    /**
     * Get an Ethers provider for a given chain name or domain id
     * @throws if chain's metadata has not been set
     */
    getProvider(chainNameOrId: ChainNameOrId): Provider;
    /**
     * Sets an Ethers provider for a given chain name or domain id
     * @throws if chain's metadata has not been set
     */
    setProvider(chainNameOrId: ChainNameOrId, provider: Provider): Provider;
    /**
     * Sets Ethers providers for a set of chains
     * @throws if chain's metadata has not been set
     */
    setProviders(providers: ChainMap<Provider>): void;
    /**
     * Get an Ethers signer for a given chain name or domain id
     * If signer is not yet connected, it will be connected
     */
    tryGetSigner(chainNameOrId: ChainNameOrId): Signer | null;
    /**
     * Get an Ethers signer for a given chain name or domain id
     * If signer is not yet connected, it will be connected
     * @throws if chain's metadata or signer has not been set
     */
    getSigner(chainNameOrId: ChainNameOrId): Signer;
    /**
     * Get an Ethers signer for a given chain name or domain id
     * @throws if chain's metadata or signer has not been set
     */
    getSignerAddress(chainNameOrId: ChainNameOrId): Promise<Address>;
    /**
     * Sets an Ethers Signer for a given chain name or domain id
     * @throws if chain's metadata has not been set or shared signer has already been set
     */
    setSigner(chainNameOrId: ChainNameOrId, signer: Signer): Signer;
    /**
     * Sets Ethers Signers for a set of chains
     * @throws if chain's metadata has not been set or shared signer has already been set
     */
    setSigners(signers: ChainMap<Signer>): void;
    /**
     * Gets the Signer if it's been set, otherwise the provider
     */
    tryGetSignerOrProvider(chainNameOrId: ChainNameOrId): Signer | Provider | null;
    /**
     * Gets the Signer if it's been set, otherwise the provider
     * @throws if chain metadata has not been set
     */
    getSignerOrProvider(chainNameOrId: ChainNameOrId): Signer | Provider;
    /**
     * Sets Ethers Signers to be used for all chains
     * Any subsequent calls to getSigner will return given signer
     * Setting sharedSigner to null clears all signers
     */
    setSharedSigner(sharedSigner: Signer | null): Signer | null;
    /**
     * Create a new MultiProvider from the intersection
     * of current's chains and the provided chain list
     */
    intersect(chains: ChainName[], throwIfNotSubset?: boolean): {
        intersection: ChainName[];
        result: MultiProvider<MetaExt>;
    };
    /**
     * Get a block explorer URL for given chain's address
     */
    tryGetExplorerAddressUrl(chainNameOrId: ChainNameOrId, address?: string): Promise<string | null>;
    /**
     * Get the latest block range for a given chain's RPC provider
     */
    getLatestBlockRange(chainNameOrId: ChainNameOrId, rangeSize?: number): Promise<{
        fromBlock: number;
        toBlock: number;
    }>;
    /**
     * Get the transaction overrides for a given chain name or domain id
     * @throws if chain's metadata has not been set
     */
    getTransactionOverrides(chainNameOrId: ChainNameOrId): Partial<providers.TransactionRequest>;
    /**
     * Wait for deploy tx to be confirmed
     * @throws if chain's metadata or signer has not been set or tx fails
     */
    handleDeploy<F extends ContractFactory>(chainNameOrId: ChainNameOrId, factory: F, params: Parameters<F['deploy']>): Promise<Awaited<ReturnType<F['deploy']>>>;
    /**
     * Wait for given tx to be confirmed
     * @throws if chain's metadata or signer has not been set or tx fails
     */
    handleTx(chainNameOrId: ChainNameOrId, tx: ContractTransaction | Promise<ContractTransaction>): Promise<ContractReceipt>;
    /**
     * Populate a transaction's fields using signer address and overrides
     * @throws if chain's metadata has not been set or tx fails
     */
    prepareTx(chainNameOrId: ChainNameOrId, tx: PopulatedTransaction, from?: string): Promise<providers.TransactionRequest>;
    /**
     * Estimate gas for given tx
     * @throws if chain's metadata has not been set or tx fails
     */
    estimateGas(chainNameOrId: ChainNameOrId, tx: PopulatedTransaction, from?: string): Promise<BigNumber>;
    /**
     * Send a transaction and wait for confirmation
     * @throws if chain's metadata or signer has not been set or tx fails
     */
    sendTransaction(chainNameOrId: ChainNameOrId, txProm: AnnotatedEV5Transaction | Promise<AnnotatedEV5Transaction>): Promise<ContractReceipt>;
    /**
     * Creates a MultiProvider using the given signer for all test networks
     */
    static createTestMultiProvider(params?: {
        signer?: Signer;
        provider?: Provider;
    }, chains?: ChainName[]): MultiProvider;
}
export {};
//# sourceMappingURL=MultiProvider.d.ts.map