Added utilities for dealing with ABIs and contract data that do not require a w3 instance.
ABIElement is a type in web3.py which is composed of ABIFunctions and ABIEvents. These represent fragments of an ABI which are useful when decoding/encoding contract data. These utilities will make it easier to work with contract logs.
The codec is using the default registry which may not be desired. The idea is to eliminate the need to pass in a codec when retrieving event data from a log. web3._utils.events.get_event_data() requires a codec, but the new parse_transaction_for_event is set up with an argument to enable strict.
I'm not totally sure if this is the correct way to enable strict mode for encoding/decoding. Does the codec itself need to be initialized with the proper registry, or is the flag all that is needed?
ABI utils tests to be added in tests/core/abi-utils.
The following methods are now available for the ABI utility API.
Public ABI Utils
def encode_transaction(
address: ChecksumAddress,
abi: Optional[ABI] = None,
function_identifier: Union[str, Type[FallbackFn], Type[ReceiveFn]] = None,
function_args: Optional[Sequence[Any]] = None,
function_kwargs: Optional[Any] = None,
transaction: Optional[TxParams] = None,
) -> TxParams:
"""
Return encoded transaction data without sending a transaction.
"""
def encode_transaction_data(
abi: Optional[ABI],
function_identifier: Union[str, Type[FallbackFn], Type[ReceiveFn]],
function_args: Optional[Sequence[Any]] = None,
function_kwargs: Optional[Any] = None,
is_async: bool = False,
provider: BaseProvider = HTTPProvider(),
abi_codec: ABICodec = ABICodec(default_registry),
) -> HexStr:
"""
Return encoded data to be used in a transaction.
"""
def encode_abi(
function_abi: ABIFunction,
data: Optional[HexStr] = None,
arguments: Sequence[Any] = None,
is_async: bool = False,
provider: HTTPProvider = HTTPProvider(),
abi_codec: ABICodec = ABICodec(default_registry),
) -> HexStr:
"""
Return encoded data from a function ABI and arguments.
"""
def encode_event_filter_params(
event_abi: ABIEvent,
contract_address: Optional[ChecksumAddress] = None,
argument_filters: Optional[Dict[str, Any]] = None,
topics: Optional[Sequence[HexStr]] = None,
fromBlock: Optional[BlockIdentifier] = None,
toBlock: Optional[BlockIdentifier] = None,
address: Optional[ChecksumAddress] = None,
abi_codec: ABICodec = ABICodec(default_registry),
) -> Tuple[List[List[Optional[HexStr]]], FilterParams]:
"""
Return a raw event filter for a JSON-RPC query.
"""
def encode_event_filter_topics(
event_abi: ABIEvent,
arguments: Optional[Union[Sequence[Any], Dict[str, Any]]] = None,
abi_codec: ABICodec = ABICodec(default_registry),
) -> List[HexStr]:
"""
Return encoded filter topics for an event.
"""
def encode_event_arguments(
event_abi: ABIEvent,
arguments: Optional[Union[Sequence[Any], Dict[str, Any]]] = None,
abi_codec: ABICodec = ABICodec(default_registry),
) -> List[List[Optional[HexStr]]]:
"""
Return encoded arguments for transaction data.
"""
def decode_transaction_data_for_event(
event_abi: ABIEvent,
log: Optional[LogReceipt] = None,
abi_codec: ABICodec = ABICodec(default_registry),
) -> EventData:
"""
Return decoded event data from a log in a transaction.
"""
def decode_data_for_transaction(
function_abi: ABIFunction,
log: Optional[LogReceipt] = None,
abi_codec: ABICodec = ABICodec(default_registry),
) -> TxParams:
"""
Return decoded transaction parameters from a log in a transaction.
"""
def decode_event_args(
event_abi: ABIEvent,
data: HexBytes = None,
topics: Optional[Sequence[HexBytes]] = None,
abi_codec: Optional[ABICodec] = ABICodec(default_registry),
) -> EventDataArgs:
"""
Return the name and arguments of an event.
Recommend using `web3.utils.parse_log_for_event` which takes a LogReceipt and
returns all event data.
"""
def decode_function_outputs(
function_abi: ABIFunction,
data: HexStr,
normalizers: Sequence[Callable[[TypeStr, Any], Tuple[TypeStr, Any]]] = None,
abi_codec: ABICodec = ABICodec(default_registry),
) -> Dict[str, Any]:
"""
Return result inputs and outputs from a function.
"""
def get_abi_input_names(abi_element: ABIElement) -> List[str]:
"""
Return names for each input from the function or event ABI.
"""
def get_abi_input_types(abi_element: ABIElement) -> List[str]:
"""
Return types for each input from the function or event ABI.
"""
def get_abi_output_names(function_abi: ABIFunction) -> List[str]:
"""
Return names for each output from the function ABI.
"""
def get_abi_output_types(function_abi: ABIFunction) -> List[str]:
"""
Return types for each output from the function ABI.
"""
def get_all_event_abis(abi: ABI) -> ABIEvent:
"""
Return interfaces for each event in the contract ABI.
"""
def get_event_abi(
abi: ABI,
event_name: Optional[str] = None,
argument_names: Optional[Sequence[str]] = None,
) -> ABIEvent:
"""
Find the event interface with the given name and arguments.
"""
def get_event_log_topics(
event_abi: ABIEvent,
topics: Optional[Sequence[HexBytes]] = None,
) -> Sequence[HexBytes]:
"""
Return topics from an event ABI.
"""
def get_all_function_abis(abi: ABI) -> ABIFunction:
"""
Return interfaces for each function in the contract ABI.
"""
def get_function_abi(
abi: ABI,
function_identifier: Optional[Union[str, Type[FallbackFn], Type[ReceiveFn]]] = None,
args: Optional[Sequence[Any]] = None,
kwargs: Optional[Any] = None,
abi_codec: ABICodec = ABICodec(default_registry),
) -> ABIFunction:
"""
Return the interface for a contract function.
"""
def get_function_info(
abi: ABI,
function_identifier: Union[str, Type[FallbackFn], Type[ReceiveFn]],
args: Optional[Sequence[Any]] = None,
kwargs: Optional[Any] = None,
) -> ABIFunctionInfo:
"""
Return the function ABI, selector and input arguments.
"""
What was wrong?
This PR is a redesign from #3286
Related to #1596, #3036, #3279
How was it fixed?
Added utilities for dealing with ABIs and contract data that do not require a w3 instance.
ABIElement
is a type in web3.py which is composed ofABIFunction
s andABIEvents
. These represent fragments of an ABI which are useful when decoding/encoding contract data. These utilities will make it easier to work with contract logs.The codec is using the default registry which may not be desired. The idea is to eliminate the need to pass in a codec when retrieving event data from a log.
web3._utils.events.get_event_data()
requires a codec, but the newparse_transaction_for_event
is set up with an argument to enablestrict
.I'm not totally sure if this is the correct way to enable
strict
mode for encoding/decoding. Does the codec itself need to be initialized with the proper registry, or is the flag all that is needed?ABI utils tests to be added in
tests/core/abi-utils
.The following methods are now available for the ABI utility API.
Public ABI Utils
Todo:
Cute Animal Picture