UNPKG

ox

Version:

Ethereum Standard Library

238 lines (218 loc) 6.88 kB
import type * as Errors from './Errors.js' import * as Hex from './Hex.js' import type { Compute, OneOf } from './internal/types.js' export type FeeHistory<bigintType = bigint> = Compute<{ /** * An array of block base fees per gas (in wei). This includes the next block after * the newest of the returned range, because this value can be derived from the newest block. * Zeroes are returned for pre-EIP-1559 blocks. */ baseFeePerGas: bigintType[] /** An array of block gas used ratios. These are calculated as the ratio of gasUsed and gasLimit. */ gasUsedRatio: number[] /** Lowest number block of the returned range. */ oldestBlock: bigintType /** An array of effective priority fees (in wei) per gas data points from a single block. All zeroes are returned if the block is empty. */ reward?: bigintType[][] | undefined }> export type FeeHistoryRpc = FeeHistory<Hex.Hex> export type FeeValuesLegacy<bigintType = bigint> = { /** Base fee per gas. */ gasPrice: bigintType } export type FeeValuesLegacyRpc = FeeValuesLegacy<Hex.Hex> export type FeeValuesEip1559<bigintType = bigint> = { /** Total fee per gas in wei (gasPrice/baseFeePerGas + maxPriorityFeePerGas). */ maxFeePerGas: bigintType /** Max priority fee per gas (in wei). */ maxPriorityFeePerGas: bigintType } export type FeeValuesEip1559Rpc = FeeValuesEip1559<Hex.Hex> export type FeeValuesEip4844<bigintType = bigint> = { /** Maximum total fee per gas sender is willing to pay for blob gas (in wei). */ maxFeePerBlobGas: bigintType /** Total fee per gas in wei (gasPrice/baseFeePerGas + maxPriorityFeePerGas). */ maxFeePerGas: bigintType /** Max priority fee per gas (in wei). */ maxPriorityFeePerGas: bigintType } export type FeeValuesEip4844Rpc = FeeValuesEip4844<Hex.Hex> export type FeeValues<bigintType = bigint> = OneOf< | FeeValuesLegacy<bigintType> | FeeValuesEip1559<bigintType> | FeeValuesEip4844<bigintType> > export type FeeValuesRpc = OneOf< FeeValuesLegacyRpc | FeeValuesEip1559Rpc | FeeValuesEip4844Rpc > export type FeeValuesType = 'legacy' | 'eip1559' | 'eip4844' /** * Converts a {@link ox#Fee.FeeHistoryRpc} to a {@link ox#Fee.FeeHistory}. * * @example * ```ts twoslash * import { Fee } from 'ox' * * const history = Fee.fromHistoryRpc({ * baseFeePerGas: ['0x01', '0x02'], * gasUsedRatio: [0.5, 0.6], * oldestBlock: '0x10', * reward: [['0x01']] * }) * // @log: { baseFeePerGas: [1n, 2n], gasUsedRatio: [0.5, 0.6], oldestBlock: 16n, reward: [[1n]] } * ``` * * @param history - The RPC fee history to convert. * @returns An instantiated {@link ox#Fee.FeeHistory}. */ export function fromHistoryRpc(history: FeeHistoryRpc): FeeHistory { return { baseFeePerGas: history.baseFeePerGas.map((value) => BigInt(value)), gasUsedRatio: history.gasUsedRatio, oldestBlock: BigInt(history.oldestBlock), ...(history.reward ? { reward: history.reward.map((row) => row.map((value) => BigInt(value)), ), } : {}), } } export declare namespace fromHistoryRpc { type ErrorType = Errors.GlobalErrorType } /** * Converts a {@link ox#Fee.FeeHistory} to a {@link ox#Fee.FeeHistoryRpc}. * * @example * ```ts twoslash * import { Fee } from 'ox' * * const rpc = Fee.toHistoryRpc({ * baseFeePerGas: [1n, 2n], * gasUsedRatio: [0.5, 0.6], * oldestBlock: 16n, * reward: [[1n]] * }) * ``` * * @param history - The fee history to convert. * @returns An RPC fee history. */ export function toHistoryRpc(history: FeeHistory): FeeHistoryRpc { return { baseFeePerGas: history.baseFeePerGas.map((value) => Hex.fromNumber(value)), gasUsedRatio: history.gasUsedRatio, oldestBlock: Hex.fromNumber(history.oldestBlock), ...(history.reward ? { reward: history.reward.map((row) => row.map((value) => Hex.fromNumber(value)), ), } : {}), } } export declare namespace toHistoryRpc { type ErrorType = Errors.GlobalErrorType } /** * Estimates a `maxFeePerGas` from a base fee, a priority tip, and a multiplier * applied to the base fee: * * ``` * maxFeePerGas = baseFeePerGas * multiplier + maxPriorityFeePerGas * ``` * * The multiplier is supplied as `multiplierNumerator / multiplierDenominator` * to keep the math in `bigint`. The default is `2 / 1` (i.e. 2x), matching the * common wallet/relay heuristic for headroom against base-fee bumps. * * @example * ```ts twoslash * import { Fee } from 'ox' * * Fee.estimateMaxFeePerGas({ * baseFeePerGas: 100n, * maxPriorityFeePerGas: 5n * }) * // @log: 205n * * Fee.estimateMaxFeePerGas({ * baseFeePerGas: 100n, * maxPriorityFeePerGas: 5n, * multiplierNumerator: 3n, * multiplierDenominator: 2n * }) * // @log: 155n (= 100n * 3n / 2n + 5n) * ``` * * @param args.baseFeePerGas - Block base fee per gas. * @param args.maxPriorityFeePerGas - Tip per gas. * @param args.multiplierNumerator - Numerator of the base-fee multiplier (default `2n`). * @param args.multiplierDenominator - Denominator of the base-fee multiplier (default `1n`). * @returns Suggested `maxFeePerGas`. */ export function estimateMaxFeePerGas(args: { baseFeePerGas: bigint maxPriorityFeePerGas: bigint multiplierNumerator?: bigint | undefined multiplierDenominator?: bigint | undefined }): bigint { const { baseFeePerGas, maxPriorityFeePerGas, multiplierNumerator = 2n, multiplierDenominator = 1n, } = args return ( (baseFeePerGas * multiplierNumerator) / multiplierDenominator + maxPriorityFeePerGas ) } export declare namespace estimateMaxFeePerGas { type ErrorType = Errors.GlobalErrorType } /** * Computes the effective gas price an EIP-1559 transaction will pay: * * ``` * effective = min(maxFeePerGas, baseFeePerGas + maxPriorityFeePerGas) * ``` * * @example * ```ts twoslash * import { Fee } from 'ox' * * Fee.effectiveGasPrice({ * baseFeePerGas: 100n, * maxFeePerGas: 200n, * maxPriorityFeePerGas: 50n * }) * // @log: 150n (= 100n + 50n) * * Fee.effectiveGasPrice({ * baseFeePerGas: 100n, * maxFeePerGas: 120n, * maxPriorityFeePerGas: 50n * }) * // @log: 120n (capped at maxFeePerGas) * ``` * * @param args.baseFeePerGas - Block base fee per gas. * @param args.maxFeePerGas - Sender-supplied `maxFeePerGas`. * @param args.maxPriorityFeePerGas - Sender-supplied tip. * @returns Effective gas price (in wei). */ export function effectiveGasPrice(args: { baseFeePerGas: bigint maxFeePerGas: bigint maxPriorityFeePerGas: bigint }): bigint { const { baseFeePerGas, maxFeePerGas, maxPriorityFeePerGas } = args const ceiling = baseFeePerGas + maxPriorityFeePerGas return ceiling < maxFeePerGas ? ceiling : maxFeePerGas } export declare namespace effectiveGasPrice { type ErrorType = Errors.GlobalErrorType }