Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[v6] Rename Contract.encodeABI -> Contract.encode_abi #3280

Merged
merged 3 commits into from
Mar 13, 2024
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion docs/overview.rst
Original file line number Diff line number Diff line change
Expand Up @@ -258,7 +258,7 @@ API
- :attr:`Contract.events <web3.contract.Contract.events>`
- :attr:`Contract.fallback <web3.contract.Contract.fallback.call>`
- :meth:`Contract.constructor() <web3.contract.Contract.constructor>`
- :meth:`Contract.encodeABI() <web3.contract.Contract.encodeABI>`
- :meth:`Contract.encode_abi() <web3.contract.Contract.encode_abi>`
- :attr:`web3.contract.ContractFunction <web3.contract.ContractFunction>`
- :attr:`web3.contract.ContractEvents <web3.contract.ContractEvents>`

Expand Down
17 changes: 11 additions & 6 deletions docs/web3.contract.rst
Original file line number Diff line number Diff line change
Expand Up @@ -302,17 +302,22 @@ Each Contract Factory exposes the following methods.
filter_builder.fromBlock = 0 # raises a ValueError


.. py:classmethod:: Contract.encodeABI(fn_name, args=None, kwargs=None, data=None)
.. py:classmethod:: Contract.encode_abi(fn_name, args=None, kwargs=None, data=None)

Encodes the arguments using the Ethereum ABI for the contract function that
matches the given ``fn_name`` and arguments ``args``. The ``data`` parameter
defaults to the function selector.
Encodes the arguments using the Ethereum ABI for the contract function that
matches the given ``fn_name`` and arguments ``args``. The ``data`` parameter
defaults to the function selector.

.. code-block:: python
.. code-block:: python

>>> contract.encodeABI(fn_name="register", args=["rainbows", 10])
>>> contract.encode_abi(fn_name="register", args=["rainbows", 10])
"0xea87152b0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000a00000000000000000000000000000000000000000000000000000000000000087261696e626f7773000000000000000000000000000000000000000000000000"

.. py:classmethod:: Contract.encodeABI(fn_name, args=None, kwargs=None, data=None)

.. deprecated:: 7.0
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is nice! TIL

Use :meth:`Contract.encode_abi` instead.

.. py:classmethod:: Contract.all_functions()

Returns a list of all the functions present in a Contract where every function is
Expand Down
2 changes: 1 addition & 1 deletion ens/async_ens.py
Original file line number Diff line number Diff line change
Expand Up @@ -490,7 +490,7 @@ async def _resolve(
):
contract_func_with_args = (fn_name, [node])

calldata = resolver.encodeABI(*contract_func_with_args)
calldata = resolver.encode_abi(*contract_func_with_args)
contract_call_result = await resolver.caller.resolve(
ens_encode_name(normal_name),
calldata,
Expand Down
2 changes: 1 addition & 1 deletion ens/ens.py
Original file line number Diff line number Diff line change
Expand Up @@ -475,7 +475,7 @@ def _resolve(
if _resolver_supports_interface(resolver, ENS_EXTENDED_RESOLVER_INTERFACE_ID):
contract_func_with_args = (fn_name, [node])

calldata = resolver.encodeABI(*contract_func_with_args)
calldata = resolver.encode_abi(*contract_func_with_args)
contract_call_result = resolver.caller.resolve(
ens_encode_name(normal_name),
calldata,
Expand Down
1 change: 1 addition & 0 deletions newsfragments/3280.deprecation.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Deprecated ``Contract.encodeABI()`` in favor of ``Contract.encode_abi()``.
50 changes: 46 additions & 4 deletions tests/core/contracts/test_contract_method_abi_encoding.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
import json
import pytest
from unittest.mock import (
patch,
)

from web3 import (
constants,
Expand Down Expand Up @@ -64,7 +67,7 @@
)
def test_contract_abi_encoding(w3, abi, arguments, data, expected):
contract = w3.eth.contract(abi=abi)
actual = contract.encodeABI("a", arguments, data=data)
actual = contract.encode_abi("a", arguments, data=data)
assert actual == expected


Expand Down Expand Up @@ -116,7 +119,7 @@ def test_contract_abi_encoding_non_strict(
w3_non_strict_abi, abi, arguments, data, expected
):
contract = w3_non_strict_abi.eth.contract(abi=abi)
actual = contract.encodeABI("a", arguments, data=data)
actual = contract.encode_abi("a", arguments, data=data)
assert actual == expected


Expand All @@ -128,7 +131,7 @@ def test_contract_abi_encoding_kwargs(w3):
"0x6f8d2fa18448afbfe4f82143c384484ad09a0271f3a3c0eb9f629e703f883125",
],
}
actual = contract.encodeABI("byte_array", kwargs=kwargs)
actual = contract.encode_abi("byte_array", kwargs=kwargs)
assert (
actual
== "0xf166d6f8000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000025595c210956e7721f9b692e702708556aa9aabb14ea163e96afa56ffbe9fa8096f8d2fa18448afbfe4f82143c384484ad09a0271f3a3c0eb9f629e703f883125" # noqa: E501
Expand All @@ -146,7 +149,7 @@ def test_contract_abi_encoding_kwargs(w3):
def test_contract_abi_encoding_strict_with_error(w3, arguments):
contract = w3.eth.contract(abi=ABI_C)
with pytest.raises(Web3ValidationError):
contract.encodeABI("a", arguments, data=None)
contract.encode_abi("a", arguments, data=None)


@pytest.mark.parametrize(
Expand Down Expand Up @@ -195,5 +198,44 @@ def test_contract_abi_encoding_strict_with_error(w3, arguments):
)
def test_contract_abi_encoding_strict(w3, abi, arguments, data, expected):
contract = w3.eth.contract(abi=abi)
actual = contract.encode_abi("a", arguments, data=data)
assert actual == expected


def test_contract_encodeABI_deprecated(w3):
abi = ABI_B
arguments = [0]

contract = w3.eth.contract(abi=abi)

with pytest.warns(DeprecationWarning):
contract.encodeABI("a", arguments)


def test_contract_encodeABI_deprecated_returns_encoded(w3):
expected = "0xf0fdf8340000000000000000000000000000000000000000000000000000000000000000" # noqa: E501

abi = ABI_B
arguments = [0]
data = None

contract = w3.eth.contract(abi=abi)

actual = contract.encodeABI("a", arguments, data=data)
reedsa marked this conversation as resolved.
Show resolved Hide resolved
assert actual == expected


@patch("web3.eth.Contract.encodeABI", lambda w3, *args, **kwargs: (args, kwargs))
def test_contract_encodeABI_deprecated_calls_encode_abi_with_args(w3):
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this test add any new test vector? It looks like the test above tests kwargs already?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This test expects the new method to be called with all the arguments. The @patch wraps the encode function to be able to check values for each argument.

abi = ABI_B
arguments = [0]
kwargs = {"x": 1}
data = {"secret_code": "12345"}

contract = w3.eth.contract(abi=abi)

passed_on_args, passed_on_kwargs = contract.encodeABI(
"a", arguments, kwargs, data=data
)
assert passed_on_args == ([0], {"x": 1})
assert passed_on_kwargs == {"data": {"secret_code": "12345"}}
12 changes: 6 additions & 6 deletions web3/_utils/module_testing/eth_module.py
Original file line number Diff line number Diff line change
Expand Up @@ -1340,7 +1340,7 @@ async def test_eth_call_revert_custom_error_with_msg(
async_revert_contract: "Contract",
async_unlocked_account: ChecksumAddress,
) -> None:
data = async_revert_contract.encodeABI(
data = async_revert_contract.encode_abi(
fn_name="UnauthorizedWithMessage", args=["You are not authorized"]
)
txn_params = async_revert_contract._prepare_transaction(
Expand All @@ -1360,7 +1360,7 @@ async def test_eth_call_revert_custom_error_without_msg(
async_revert_contract: "Contract",
async_unlocked_account: ChecksumAddress,
) -> None:
data = async_revert_contract.encodeABI(fn_name="Unauthorized")
data = async_revert_contract.encode_abi(fn_name="Unauthorized")
txn_params = async_revert_contract._prepare_transaction(
fn_name="customErrorWithoutMessage",
transaction={
Expand Down Expand Up @@ -3826,7 +3826,7 @@ def test_eth_call_custom_error_revert_with_msg(
revert_contract: "Contract",
unlocked_account: ChecksumAddress,
) -> None:
data = revert_contract.encodeABI(
data = revert_contract.encode_abi(
fn_name="UnauthorizedWithMessage", args=["You are not authorized"]
)
txn_params = revert_contract._prepare_transaction(
Expand All @@ -3846,7 +3846,7 @@ def test_eth_call_custom_error_revert_without_msg(
revert_contract: "Contract",
unlocked_account: ChecksumAddress,
) -> None:
data = revert_contract.encodeABI(fn_name="Unauthorized")
data = revert_contract.encode_abi(fn_name="Unauthorized")
txn_params = revert_contract._prepare_transaction(
fn_name="customErrorWithoutMessage",
transaction={
Expand Down Expand Up @@ -4135,7 +4135,7 @@ def test_eth_estimate_gas_custom_error_revert_with_msg(
revert_contract: "Contract",
unlocked_account: ChecksumAddress,
) -> None:
data = revert_contract.encodeABI(
data = revert_contract.encode_abi(
fn_name="UnauthorizedWithMessage", args=["You are not authorized"]
)
txn_params = revert_contract._prepare_transaction(
Expand All @@ -4155,7 +4155,7 @@ def test_eth_estimate_gas_custom_error_revert_without_msg(
revert_contract: "Contract",
unlocked_account: ChecksumAddress,
) -> None:
data = revert_contract.encodeABI(fn_name="Unauthorized")
data = revert_contract.encode_abi(fn_name="Unauthorized")
txn_params = revert_contract._prepare_transaction(
fn_name="customErrorWithoutMessage",
transaction={
Expand Down
14 changes: 14 additions & 0 deletions web3/contract/base_contract.py
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,9 @@
from web3._utils.datatypes import (
PropertyCheckingFactory,
)
from web3._utils.decorators import (
deprecated_for,
)
from web3._utils.empty import (
empty,
)
Expand Down Expand Up @@ -724,12 +727,23 @@ class BaseContract:
# Public API
#
@combomethod
@deprecated_for("encode_abi()")
def encodeABI(
cls,
fn_name: str,
args: Optional[Any] = None,
kwargs: Optional[Any] = None,
data: Optional[HexStr] = None,
) -> HexStr:
return cls.encode_abi(fn_name, args, kwargs, data)

@combomethod
def encode_abi(
cls,
fn_name: str,
args: Optional[Any] = None,
kwargs: Optional[Any] = None,
data: Optional[HexStr] = None,
) -> HexStr:
"""
Encodes the arguments using the Ethereum ABI for the contract function
Expand Down