@usebutr/evm
EIP-6963 and injected discovery, the EIP-1193 adapter builder, and the EIP-1193 types.
Discovery
discoverEvmAdapters(onAdapter, options?): () => void
Subscribes to EIP-6963
announcements and calls onAdapter(adapter, info) once per wallet,
deduplicated by info.rdns. The listener stays attached, so wallets that
boot late still register. options.target overrides window (tests). It is a
WalletSource as-is:
import type { WalletManagerConfig } from "@usebutr/core";
import { discoverEvmAdapters } from "@usebutr/evm";
const config: WalletManagerConfig = { sources: [discoverEvmAdapters] };discoverInjectedAdapter(onAdapter, options?): () => void
The last-resort path for wallets that expose only window.ethereum and never
announce through EIP-6963. It waits settleMs, then emits one adapter with
the id injected:legacy, unless hasAnyEip6963Adapter() says the standard
path already found a wallet.
InjectedDiscoveryOptions: hasAnyEip6963Adapter?: () => boolean,
settleMs?: number (default 150), target? (overrides window).
evmDiscoverer: PlatformDiscoverer
EIP-6963 as the primary channel, discoverInjectedAdapter as the fallback.
autoDiscovery() from @usebutr/wallets composes it.
Constants: ANNOUNCE_EVENT and REQUEST_EVENT (the EIP-6963 event names),
GENERIC_INJECTED_ICON (the legacy adapter's icon).
Adapter builder
buildEvmAdapter(info: Eip6963ProviderInfo, provider: Eip1193Provider): EvmAdapter
Wraps any EIP-1193 provider. info.rdns becomes the adapter id. The adapter
always defines disconnect, subscribe, requestAccounts, switchChain,
signMessage, sendTx, getBalance and getTransactionReceipt, and
getSigner() resolves { kind: "eip1193", provider }. See the
injected EVM connector for how each behaves.
isEip1193Provider(value: unknown): value is Eip1193Provider
A structural check for a provider of unknown origin, such as
window.ethereum. A butr signer narrows on kind === "eip1193" instead.
Helpers
chainIdHexToDecimal(hex: string): stringchainIdDecimalToHex(decimal: string): stringformatEther(wei: bigint): string: trims trailing zeros.
Byte helpers (bytesToHex, hexToBytes, …) and the EVM chain registry
(EVM_CHAINS, EVM_CHAINS_LIST) live in @usebutr/core.
Signer
Importing the package registers the eip1193 signer kind:
type Eip1193Signer = { kind: "eip1193"; provider: Eip1193Provider };The WalletConnect EVM namespace resolves the same kind.
Types
Eip1193Provider (request, on, removeListener), Eip1193RequestArgs,
Eip1193Listener, Eip1193Value, Eip1193Object, Eip6963ProviderInfo,
Eip6963ProviderDetail, Eip6963AnnounceEvent, InjectedDiscoveryOptions.
Eip1193Provider.request returns Promise<Eip1193Value | undefined>: loose
on purpose, so the package takes no dependency on viem. viem's custom()
transport accepts it directly.
Source: packages/evm/src/index.ts.