UNPKG

ox

Version:

Ethereum Standard Library

521 lines 16.4 kB
import * as abitype from 'abitype'; import * as Bytes from './Bytes.js'; import * as Errors from './Errors.js'; import * as Hex from './Hex.js'; import * as formatAbiParameters from './internal/human-readable/formatAbiParameters.js'; import * as parseAbiParameters from './internal/human-readable/parseAbiParameters.js'; import * as internal from './internal/abiParameters.js'; /** Root type for ABI parameters. */ export type AbiParameters = readonly abitype.AbiParameter[]; /** A parameter on an {@link ox#AbiParameters.AbiParameters}. */ export type Parameter = abitype.AbiParameter; export { InvalidAbiParametersError, InvalidAbiTypeParameterError, InvalidFunctionModifierError, InvalidModifierError, InvalidParameterError, SolidityProtectedKeywordError, } from './internal/human-readable/errors.js'; export { InvalidParenthesisError } from './internal/human-readable/errors.js'; /** A packed ABI type. */ export type PackedAbiType = abitype.SolidityAddress | abitype.SolidityBool | abitype.SolidityBytes | abitype.SolidityInt | abitype.SolidityString | abitype.SolidityArrayWithoutTuple; /** * Decodes ABI-encoded data into its respective primitive values based on ABI Parameters. * * @example * ```ts twoslash * import { AbiParameters } from 'ox' * * const data = AbiParameters.decode( * AbiParameters.from(['string', 'uint', 'bool']), * '0x000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000001a4000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000057761676d69000000000000000000000000000000000000000000000000000000' * ) * // @log: ['wagmi', 420n, true] * ``` * * @example * ### JSON Parameters * * You can pass **JSON ABI** Parameters: * * ```ts twoslash * import { AbiParameters } from 'ox' * * const data = AbiParameters.decode( * [ * { name: 'x', type: 'string' }, * { name: 'y', type: 'uint' }, * { name: 'z', type: 'bool' } * ], * '0x000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000001a4000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000057761676d69000000000000000000000000000000000000000000000000000000' * ) * // @log: ['wagmi', 420n, true] * ``` * * @param parameters - The set of ABI parameters to decode, in the shape of the `inputs` or `outputs` attribute of an ABI Item. These parameters must include valid [ABI types](https://docs.soliditylang.org/en/latest/types.html). * @param data - ABI encoded data. * @param options - Decoding options. * @returns Array of decoded values. */ export declare function decode<const parameters extends AbiParameters, as extends 'Object' | 'Array' = 'Array'>(parameters: parameters, data: Bytes.Bytes | Hex.Hex, options?: decode.Options<as>): decode.ReturnType<parameters, as>; export declare namespace decode { type Options<as extends 'Object' | 'Array'> = { /** * Whether the decoded values should be returned as an `Object` or `Array`. * * @default "Array" */ as?: as | 'Object' | 'Array' | undefined; /** * Whether decoded addresses should be checksummed. * * @default true */ checksumAddress?: boolean | undefined; }; type ReturnType<parameters extends AbiParameters = AbiParameters, as extends 'Object' | 'Array' = 'Array'> = parameters extends readonly [] ? as extends 'Object' ? {} : [] : as extends 'Object' ? internal.ToObject<parameters> : internal.ToPrimitiveTypes<parameters>; type ErrorType = Bytes.fromHex.ErrorType | internal.decodeParameter.ErrorType | ZeroDataError | DataSizeTooSmallError | Errors.GlobalErrorType; } /** * Encodes primitive values into ABI encoded data as per the [Application Binary Interface (ABI) Specification](https://docs.soliditylang.org/en/latest/abi-spec). * * @example * ```ts twoslash * import { AbiParameters } from 'ox' * * const data = AbiParameters.encode( * AbiParameters.from(['string', 'uint', 'bool']), * ['wagmi', 420n, true] * ) * ``` * * @example * ### JSON Parameters * * Specify **JSON ABI** Parameters as schema: * * ```ts twoslash * import { AbiParameters } from 'ox' * * const data = AbiParameters.encode( * [ * { type: 'string', name: 'name' }, * { type: 'uint', name: 'age' }, * { type: 'bool', name: 'isOwner' } * ], * ['wagmi', 420n, true] * ) * ``` * * @param parameters - The set of ABI parameters to encode, in the shape of the `inputs` or `outputs` attribute of an ABI Item. These parameters must include valid [ABI types](https://docs.soliditylang.org/en/latest/types.html). * @param values - The set of primitive values that correspond to the ABI types defined in `parameters`. * @returns ABI encoded data. */ export declare function encode<const parameters extends AbiParameters | readonly unknown[]>(parameters: parameters, values: parameters extends AbiParameters ? internal.ToPrimitiveTypes<parameters> : never, options?: encode.Options): Hex.Hex; export declare namespace encode { type ErrorType = LengthMismatchError | internal.encode.ErrorType | internal.prepareParameters.ErrorType | Errors.GlobalErrorType; type Options = { /** * Whether addresses should be checked against their checksum. * * @default false */ checksumAddress?: boolean | undefined; }; } /** * Encodes an array of primitive values to a [packed ABI encoding](https://docs.soliditylang.org/en/latest/abi-spec.html#non-standard-packed-mode). * * @example * ```ts twoslash * import { AbiParameters } from 'ox' * * const encoded = AbiParameters.encodePacked( * ['address', 'string'], * [ * '0xd8da6bf26964af9d7eed9e03e53415d37aa96045', * 'hello world' * ] * ) * // @log: '0xd8da6bf26964af9d7eed9e03e53415d37aa9604568656c6c6f20776f726c64' * ``` * * @param types - Set of ABI types to pack encode. * @param values - The set of primitive values that correspond to the ABI types defined in `types`. * @returns The encoded packed data. */ export declare function encodePacked<const packedAbiTypes extends readonly PackedAbiType[] | readonly unknown[]>(types: packedAbiTypes, values: encodePacked.Values<packedAbiTypes>): Hex.Hex; export declare namespace encodePacked { type ErrorType = Hex.concat.ErrorType | LengthMismatchError | Errors.GlobalErrorType; type Values<packedAbiTypes extends readonly PackedAbiType[] | readonly unknown[]> = { [key in keyof packedAbiTypes]: packedAbiTypes[key] extends abitype.AbiType ? abitype.AbiParameterToPrimitiveType<{ type: packedAbiTypes[key]; }> : unknown; }; function encode<const packedAbiType extends PackedAbiType | unknown>(type: packedAbiType, value: Values<[packedAbiType]>[0], isArray?: boolean): Hex.Hex; } /** * Formats {@link ox#AbiParameters.AbiParameters} into **Human Readable ABI Parameters**. * * @example * ```ts twoslash * import { AbiParameters } from 'ox' * * const formatted = AbiParameters.format([ * { * name: 'spender', * type: 'address' * }, * { * name: 'amount', * type: 'uint256' * } * ]) * * formatted * // ^? * ``` * * @param parameters - The ABI Parameters to format. * @returns The formatted ABI Parameters . */ export declare function format<const parameters extends readonly [ Parameter | abitype.AbiEventParameter, ...(readonly (Parameter | abitype.AbiEventParameter)[]) ]>(parameters: parameters | readonly [ Parameter | abitype.AbiEventParameter, ...(readonly (Parameter | abitype.AbiEventParameter)[]) ]): format.ReturnType<parameters>; export declare namespace format { type ReturnType<parameters extends readonly [ Parameter | abitype.AbiEventParameter, ...(readonly (Parameter | abitype.AbiEventParameter)[]) ] = readonly [Parameter, ...(readonly Parameter[])]> = formatAbiParameters.FormatAbiParameters<parameters>; type ErrorType = Errors.GlobalErrorType; } /** * Parses arbitrary **JSON ABI Parameters** or **Human Readable ABI Parameters** into typed {@link ox#AbiParameters.AbiParameters}. * * @example * ### JSON Parameters * * ```ts twoslash * import { AbiParameters } from 'ox' * * const parameters = AbiParameters.from([ * { * name: 'spender', * type: 'address' * }, * { * name: 'amount', * type: 'uint256' * } * ]) * * parameters * //^? * // * // * // * // * // * // * // * // * // * // * // * // * // * // * // * // * ``` * * @example * ### Human Readable Parameters * * Human Readable ABI Parameters can be parsed into a typed {@link ox#AbiParameters.AbiParameters}: * * ```ts twoslash * import { AbiParameters } from 'ox' * * const parameters = AbiParameters.from( * 'address spender, uint256 amount' * ) * * parameters * //^? * // * // * // * // * // * // * // * // * // * // * // * // * // * // * // * // * ``` * * @example * It is possible to specify `struct`s along with your definitions: * * ```ts twoslash * import { AbiParameters } from 'ox' * * const parameters = AbiParameters.from([ * 'struct Foo { address spender; uint256 amount; }', // [!code hl] * 'Foo foo, address bar' * ]) * * parameters * //^? * // * // * // * // * // * // * // * // * // * // * // * // * // * // * // * // * ``` * * * * @param parameters - The ABI Parameters to parse. * @returns The typed ABI Parameters. */ export declare function from<const parameters extends AbiParameters | string | readonly string[]>(parameters: parameters | AbiParameters | string | readonly string[]): from.ReturnType<parameters>; export declare namespace from { type ReturnType<parameters extends AbiParameters | string | readonly string[]> = parameters extends string ? parseAbiParameters.ParseAbiParameters<parameters> : parameters extends readonly string[] ? parseAbiParameters.ParseAbiParameters<parameters> : parameters; type ErrorType = Errors.GlobalErrorType; } /** * Throws when the data size is too small for the given parameters. * * @example * ```ts twoslash * import { AbiParameters } from 'ox' * * AbiParameters.decode([{ type: 'uint256' }], '0x010f') * // ↑ ❌ 2 bytes * // @error: AbiParameters.DataSizeTooSmallError: Data size of 2 bytes is too small for given parameters. * // @error: Params: (uint256) * // @error: Data: 0x010f (2 bytes) * ``` * * ### Solution * * Pass a valid data size. * * ```ts twoslash * import { AbiParameters } from 'ox' * * AbiParameters.decode( * [{ type: 'uint256' }], * '0x00000000000000000000000000000000000000000000000000000000000010f' * ) * // ↑ ✅ 32 bytes * ``` */ export declare class DataSizeTooSmallError extends Errors.BaseError { readonly name = "AbiParameters.DataSizeTooSmallError"; constructor({ data, parameters, size, }: { data: Hex.Hex; parameters: readonly Parameter[]; size: number; }); } /** * Throws when zero data is provided, but data is expected. * * @example * ```ts twoslash * import { AbiParameters } from 'ox' * * AbiParameters.decode([{ type: 'uint256' }], '0x') * // ↑ ❌ zero data * // @error: AbiParameters.DataSizeTooSmallError: Data size of 2 bytes is too small for given parameters. * // @error: Params: (uint256) * // @error: Data: 0x010f (2 bytes) * ``` * * ### Solution * * Pass valid data. * * ```ts twoslash * import { AbiParameters } from 'ox' * * AbiParameters.decode( * [{ type: 'uint256' }], * '0x00000000000000000000000000000000000000000000000000000000000010f' * ) * // ↑ ✅ 32 bytes * ``` */ export declare class ZeroDataError extends Errors.BaseError { readonly name = "AbiParameters.ZeroDataError"; constructor(); } /** * The length of the array value does not match the length specified in the corresponding ABI parameter. * * ### Example * * ```ts twoslash * // @noErrors * import { AbiParameters } from 'ox' * // ---cut--- * AbiParameters.encode(AbiParameters.from('uint256[3]'), [ * [69n, 420n] * ]) * // ↑ expected: 3 ↑ ❌ length: 2 * // @error: AbiParameters.ArrayLengthMismatchError: ABI encoding array length mismatch * // @error: for type `uint256[3]`. Expected: `3`. Given: `2`. * ``` * * ### Solution * * Pass an array of the correct length. * * ```ts twoslash * import { AbiParameters } from 'ox' * // ---cut--- * AbiParameters.encode(AbiParameters.from(['uint256[3]']), [ * [69n, 420n, 69n] * ]) * // ↑ ✅ length: 3 * ``` */ export declare class ArrayLengthMismatchError extends Errors.BaseError { readonly name = "AbiParameters.ArrayLengthMismatchError"; constructor({ expectedLength, givenLength, type, }: { expectedLength: number; givenLength: number; type: string; }); } /** * The size of the bytes value does not match the size specified in the corresponding ABI parameter. * * ### Example * * ```ts twoslash * // @noErrors * import { AbiParameters } from 'ox' * // ---cut--- * AbiParameters.encode(AbiParameters.from('bytes8'), [ * ['0xdeadbeefdeadbeefdeadbeef'] * ]) * // ↑ expected: 8 bytes ↑ ❌ size: 12 bytes * // @error: BytesSizeMismatchError: Size of bytes "0xdeadbeefdeadbeefdeadbeef" * // @error: (bytes12) does not match expected size (bytes8). * ``` * * ### Solution * * Pass a bytes value of the correct size. * * ```ts twoslash * import { AbiParameters } from 'ox' * // ---cut--- * AbiParameters.encode(AbiParameters.from(['bytes8']), [ * '0xdeadbeefdeadbeef' * ]) * // ↑ ✅ size: 8 bytes * ``` */ export declare class BytesSizeMismatchError extends Errors.BaseError { readonly name = "AbiParameters.BytesSizeMismatchError"; constructor({ expectedSize, value, }: { expectedSize: number; value: Hex.Hex; }); } /** * The length of the values to encode does not match the length of the ABI parameters. * * ### Example * * ```ts twoslash * // @noErrors * import { AbiParameters } from 'ox' * // ---cut--- * AbiParameters.encode( * AbiParameters.from(['string', 'uint256']), * ['hello'] * ) * // @error: LengthMismatchError: ABI encoding params/values length mismatch. * // @error: Expected length (params): 2 * // @error: Given length (values): 1 * ``` * * ### Solution * * Pass the correct number of values to encode. * * ### Solution * * Pass a [valid ABI type](https://docs.soliditylang.org/en/develop/abi-spec.html#types). */ export declare class LengthMismatchError extends Errors.BaseError { readonly name = "AbiParameters.LengthMismatchError"; constructor({ expectedLength, givenLength, }: { expectedLength: number; givenLength: number; }); } /** * The value provided is not a valid array as specified in the corresponding ABI parameter. * * ### Example * * ```ts twoslash * // @noErrors * import { AbiParameters } from 'ox' * // ---cut--- * AbiParameters.encode( * AbiParameters.from(['uint256[3]']), * [69] * ) * ``` * * ### Solution * * Pass an array value. */ export declare class InvalidArrayError extends Errors.BaseError { readonly name = "AbiParameters.InvalidArrayError"; constructor(value: unknown); } /** * Throws when the ABI parameter type is invalid. * * @example * ```ts twoslash * import { AbiParameters } from 'ox' * * AbiParameters.decode( * [{ type: 'lol' }], * '0x00000000000000000000000000000000000000000000000000000000000010f' * ) * // ↑ ❌ invalid type * // @error: AbiParameters.InvalidTypeError: Type `lol` is not a valid ABI Type. * ``` */ export declare class InvalidTypeError extends Errors.BaseError { readonly name = "AbiParameters.InvalidTypeError"; constructor(type: string); } //# sourceMappingURL=AbiParameters.d.ts.map