← Files AgentBrokoARCHIVED FILE
.venv/Lib/site-packages/eth_abi/codec.py
5 KB · Sep 30, 2026 · 23:15 UTC
from collections.abc import (
Iterable,
)
from typing import (
Any,
cast,
)
from eth_typing.abi import (
Decodable,
TypeStr,
)
from eth_abi.decoding import (
ContextFramesBytesIO,
TupleDecoder,
)
from eth_abi.encoding import (
TupleEncoder,
)
from eth_abi.exceptions import (
EncodingError,
)
from eth_abi.registry import (
ABIRegistry,
)
from eth_abi.utils.validation import (
validate_bytes_param,
validate_list_like_param,
)
class BaseABICoder:
"""
Base class for porcelain coding APIs. These are classes which wrap
instances of :class:`~eth_abi.registry.ABIRegistry` to provide last-mile
coding functionality.
"""
def __init__(self, registry: ABIRegistry):
"""
Constructor.
:param registry: The registry providing the encoders to be used when
encoding values.
"""
self._registry = registry
class ABIEncoder(BaseABICoder):
"""
Wraps a registry to provide last-mile encoding functionality.
"""
def encode(self, types: Iterable[TypeStr], args: Iterable[Any]) -> bytes:
"""
Encodes the python values in ``args`` as a sequence of binary values of
the ABI types in ``types`` via the head-tail mechanism.
:param types: A list or tuple of string representations of the ABI types
that will be used for encoding e.g. ``('uint256', 'bytes[]',
'(int,int)')``
:param args: A list or tuple of python values to be encoded.
:returns: The head-tail encoded binary representation of the python
values in ``args`` as values of the ABI types in ``types``.
"""
# validate encode types and args
validate_list_like_param(types, "types")
validate_list_like_param(args, "args")
encoders = [self._registry.get_encoder(type_str) for type_str in types]
encoder = TupleEncoder(encoders=encoders)
return encoder(args)
def is_encodable(self, typ: TypeStr, arg: Any) -> bool:
"""
Determines if the python value ``arg`` is encodable as a value of the
ABI type ``typ``.
:param typ: A string representation for the ABI type against which the
python value ``arg`` will be checked e.g. ``'uint256'``,
``'bytes[]'``, ``'(int,int)'``, etc.
:param arg: The python value whose encodability should be checked.
:returns: ``True`` if ``arg`` is encodable as a value of the ABI type
``typ``. Otherwise, ``False``.
"""
if not self.is_encodable_type(typ):
return False
encoder = self._registry.get_encoder(typ)
try:
encoder.validate_value(arg)
except EncodingError:
return False
except AttributeError:
try:
encoder(arg)
except EncodingError:
return False
return True
def is_encodable_type(self, typ: TypeStr) -> bool:
"""
Returns ``True`` if values for the ABI type ``typ`` can be encoded by
this codec.
:param typ: A string representation for the ABI type that will be
checked for encodability e.g. ``'uint256'``, ``'bytes[]'``,
``'(int,int)'``, etc.
:returns: ``True`` if values for ``typ`` can be encoded by this codec.
Otherwise, ``False``.
"""
return self._registry.has_encoder(typ)
class ABIDecoder(BaseABICoder):
"""
Wraps a registry to provide last-mile decoding functionality.
"""
stream_class = ContextFramesBytesIO
def decode(
self,
types: Iterable[TypeStr],
data: Decodable,
strict: bool = True,
) -> tuple[Any, ...]:
"""
Decodes the binary value ``data`` as a sequence of values of the ABI types
in ``types`` via the head-tail mechanism into a tuple of equivalent python
values.
:param types: A list or tuple of string representations of the ABI types that
will be used for decoding e.g. ``('uint256', 'bytes[]', '(int,int)')``
:param data: The binary value to be decoded.
:param strict: If ``False``, dynamic-type decoders will ignore validations such
as making sure the data is padded to a multiple of 32 bytes or checking that
padding bytes are zero / empty. ``False`` is how the Solidity ABI decoder
currently works. However, ``True`` is the default for the eth-abi library.
:returns: A tuple of equivalent python values for the ABI values
represented in ``data``.
"""
# validate decode types and data
validate_list_like_param(types, "types")
validate_bytes_param(data, "data")
decoders = [
self._registry.get_decoder(type_str, strict=strict) for type_str in types
]
decoder = TupleDecoder(decoders=decoders)
stream = self.stream_class(data)
return cast(tuple[Any, ...], decoder(stream))
class ABICodec(ABIEncoder, ABIDecoder):
pass
SHA-256: 64cb51ec3d5e2dc5399722a97dab344910b944d169545d93e6987f73a5db6aa9