Skip to content

Commit

Permalink
feat: better msg signing disp
Browse files Browse the repository at this point in the history
  • Loading branch information
antazoey committed Dec 6, 2023
1 parent f292af3 commit 6c80283
Show file tree
Hide file tree
Showing 2 changed files with 59 additions and 2 deletions.
38 changes: 37 additions & 1 deletion src/ape/types/signatures.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
from typing import Iterator, Union
from typing import Iterator, Optional, Union

from eth_account import Account
from eth_account.messages import SignableMessage
from eth_utils import to_bytes, to_hex
from hexbytes import HexBytes
from pydantic.dataclasses import dataclass

from ape.types import AddressType
Expand All @@ -13,6 +14,41 @@
)


# Improve repr to force hexstr for body instead of raw bytes.
def signable_message_repr(msg: SignableMessage) -> str:
name = getattr(SignableMessage, "__name__", "SignableMessage")
default_value = "<unknown!>" # Shouldn't happen
version_str = _bytes_to_human_str(msg.version) or default_value
header_str = _bytes_to_human_str(msg.header) or default_value
body_str = _bytes_to_human_str(msg.body) or default_value
return f"{name}(" f'version="{version_str}", header="{header_str}", body="{body_str}")'


SignableMessage.__repr__ = signable_message_repr


def _bytes_to_human_str(bytes_value: bytes) -> Optional[str]:
try:
# Try as text
return bytes_value.decode("utf8")
except Exception:
pass

try:
# Try as hex
return HexBytes(bytes_value).hex()
except Exception:
pass

try:
# Try normal str
return str(bytes_value)
except Exception:
pass

return None


def _left_pad_bytes(val: bytes, num_bytes: int) -> bytes:
return b"\x00" * (num_bytes - len(val)) + val if len(val) < num_bytes else val

Expand Down
23 changes: 22 additions & 1 deletion tests/functional/test_types.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
from eth_utils import to_hex
from ethpm_types.abi import EventABI

from ape.types import ContractLog, LogFilter, TransactionSignature
from ape.types import ContractLog, LogFilter, SignableMessage, TransactionSignature
from ape.utils import ZERO_ADDRESS

TXN_HASH = "0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa222222222222222222222222"
Expand Down Expand Up @@ -110,3 +110,24 @@ def test_topic_filter_encoding():
def test_signature_repr():
signature = TransactionSignature(v=0, r=b"123", s=b"456")
assert repr(signature) == "<TransactionSignature v=0 r=0x313233 s=0x343536>"


def test_signable_message_repr():
version = b"E"
header = b"thereum Signed Message:\n32"
body = (
b"\x86\x05\x99\xc6\xfa\x0f\x05|po(\x1f\xe3\x84\xc0\x0f"
b"\x13\xb2\xa6\x91\xa3\xb8\x90\x01\xc0z\xa8\x17\xbe'\xf3\x13"
)
message = SignableMessage(version=version, header=header, body=body)

actual = repr(message)
expected_version = "E"
expected_header = "thereum Signed Message:\n32"
expected_body = "0x860599c6fa0f057c706f281fe384c00f13b2a691a3b89001c07aa817be27f313"
expected = (
f'SignableMessage(version="{expected_version}", header="{expected_header}", '
f'body="{expected_body}")'
)

assert actual == expected

0 comments on commit 6c80283

Please sign in to comment.