| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153 | /** *  [[link-ankr]] provides a third-party service for connecting to *  various blockchains over JSON-RPC. * *  **Supported Networks** * *  - Ethereum Mainnet (``mainnet``) *  - Goerli Testnet (``goerli``) *  - Sepolia Testnet (``sepolia``) *  - Arbitrum (``arbitrum``) *  - Base (``base``) *  - Base Goerlia Testnet (``base-goerli``) *  - Base Sepolia Testnet (``base-sepolia``) *  - BNB (``bnb``) *  - BNB Testnet (``bnbt``) *  - Optimism (``optimism``) *  - Optimism Goerli Testnet (``optimism-goerli``) *  - Optimism Sepolia Testnet (``optimism-sepolia``) *  - Polygon (``matic``) *  - Polygon Mumbai Testnet (``matic-mumbai``) * *  @_subsection: api/providers/thirdparty:Ankr  [providers-ankr] */import {    defineProperties, FetchRequest, assertArgument} from "../utils/index.js";import { AbstractProvider } from "./abstract-provider.js";import { showThrottleMessage } from "./community.js";import { Network } from "./network.js";import { JsonRpcProvider } from "./provider-jsonrpc.js";import type { CommunityResourcable } from "./community.js";import type { Networkish } from "./network.js";import type { JsonRpcError, JsonRpcPayload } from "./provider-jsonrpc.js";const defaultApiKey = "9f7d929b018cdffb338517efa06f58359e86ff1ffd350bc889738523659e7972";function getHost(name: string): string {    switch (name) {        case "mainnet":            return "rpc.ankr.com/eth";        case "goerli":            return "rpc.ankr.com/eth_goerli";        case "sepolia":            return "rpc.ankr.com/eth_sepolia";        case "arbitrum":            return "rpc.ankr.com/arbitrum";        case "base":            return "rpc.ankr.com/base";        case "base-goerli":            return "rpc.ankr.com/base_goerli";        case "base-sepolia":            return "rpc.ankr.com/base_sepolia";        case "bnb":            return "rpc.ankr.com/bsc";        case "bnbt":            return "rpc.ankr.com/bsc_testnet_chapel";        case "matic":            return "rpc.ankr.com/polygon";        case "matic-mumbai":            return "rpc.ankr.com/polygon_mumbai";        case "optimism":            return "rpc.ankr.com/optimism";        case "optimism-goerli":            return "rpc.ankr.com/optimism_testnet";        case "optimism-sepolia":            return "rpc.ankr.com/optimism_sepolia";    }    assertArgument(false, "unsupported network", "network", name);}/** *  The **AnkrProvider** connects to the [[link-ankr]] *  JSON-RPC end-points. * *  By default, a highly-throttled API key is used, which is *  appropriate for quick prototypes and simple scripts. To *  gain access to an increased rate-limit, it is highly *  recommended to [sign up here](link-ankr-signup). */export class AnkrProvider extends JsonRpcProvider implements CommunityResourcable {    /**     *  The API key for the Ankr connection.     */    readonly apiKey!: string;    /**     *  Create a new **AnkrProvider**.     *     *  By default connecting to ``mainnet`` with a highly throttled     *  API key.     */    constructor(_network?: Networkish, apiKey?: null | string) {        if (_network == null) { _network = "mainnet"; }        const network = Network.from(_network);        if (apiKey == null) { apiKey = defaultApiKey; }        // Ankr does not support filterId, so we force polling        const options = { polling: true, staticNetwork: network };        const request = AnkrProvider.getRequest(network, apiKey);        super(request, network, options);        defineProperties<AnkrProvider>(this, { apiKey });    }    _getProvider(chainId: number): AbstractProvider {        try {            return new AnkrProvider(chainId, this.apiKey);        } catch (error) { }        return super._getProvider(chainId);    }    /**     *  Returns a prepared request for connecting to %%network%% with     *  %%apiKey%%.     */    static getRequest(network: Network, apiKey?: null | string): FetchRequest {        if (apiKey == null) { apiKey = defaultApiKey; }        const request = new FetchRequest(`https:/\/${ getHost(network.name) }/${ apiKey }`);        request.allowGzip = true;        if (apiKey === defaultApiKey) {            request.retryFunc = async (request, response, attempt) => {                showThrottleMessage("AnkrProvider");                return true;            };        }        return request;    }    getRpcError(payload: JsonRpcPayload, error: JsonRpcError): Error {        if (payload.method === "eth_sendRawTransaction") {            if (error && error.error && error.error.message === "INTERNAL_ERROR: could not replace existing tx") {                error.error.message = "replacement transaction underpriced";            }        }        return super.getRpcError(payload, error);    }    isCommunityResource(): boolean {        return (this.apiKey === defaultApiKey);    }}
 |