import { createPublicClient, createWalletClient, defineChain, http, webSocket, Account, Chain, publicActions, Client, RpcSchema, WalletActions, PublicActions, WebSocketTransport, HttpTransport, Transport, } from "viem"; import { mnemonicToAccount } from "viem/accounts"; import * as chains from "viem/chains"; import { isWsEndpoint } from "../utils"; const UNKNOWN_CHAIN_CONFIG = { name: "Unknown", nativeCurrency: { name: "Unknown", symbol: "Unknown", decimals: 18, }, rpcUrls: { default: { http: [], }, }, }; export type SuperWalletClient = Client< Transport, Chain, Account, RpcSchema, PublicActions & WalletActions >; // Get the transport based on the endpoint const getTransport = (endpoint: string): WebSocketTransport | HttpTransport => isWsEndpoint(endpoint) ? webSocket(endpoint) : http(endpoint); // Get the chain corresponding to the chainId. If the chain is not found, it will return // an unknown chain which should work fine in most of the cases. We might need to update // the viem package to support new chains if they don't work as expected with the unknown // chain. const getChainById = (chainId: number): Chain => Object.values(chains).find((chain) => chain.id === chainId) || defineChain({ id: chainId, ...UNKNOWN_CHAIN_CONFIG }); export const createClient = async ( endpoint: string, mnemonic: string ): Promise => { const transport = getTransport(endpoint); const chainId = await createPublicClient({ transport, }).getChainId(); return createWalletClient({ transport, account: mnemonicToAccount(mnemonic), chain: getChainById(chainId), }).extend(publicActions); };