import sys from typing import ( TYPE_CHECKING, Type, Union, cast, overload, ) from ._utils import ( to_bytes, ) if TYPE_CHECKING: from typing import ( SupportsIndex, ) BytesLike = Union[bool, bytearray, bytes, int, str, memoryview] class HexBytes(bytes): """ HexBytes is a *very* thin wrapper around the python built-in :class:`bytes` class. It has these three changes: 1. Accepts more initializing values, like hex strings, non-negative integers, and booleans 2. Returns hex with prefix '0x' from :meth:`HexBytes.hex` 3. The representation at console is in hex """ def __new__(cls: Type[bytes], val: BytesLike) -> "HexBytes": bytesval = to_bytes(val) return cast(HexBytes, super().__new__(cls, bytesval)) # type: ignore # https://github.com/python/typeshed/issues/2630 # noqa: E501 def hex( self, sep: Union[str, bytes] = None, bytes_per_sep: "SupportsIndex" = 1 ) -> str: """ Output hex-encoded bytes, with an "0x" prefix. Everything following the "0x" is output exactly like :meth:`bytes.hex`. """ return "0x" + super().hex() @overload def __getitem__(self, key: "SupportsIndex") -> int: # noqa: F811 ... @overload # noqa: F811 def __getitem__(self, key: slice) -> "HexBytes": # noqa: F811 ... def __getitem__( # noqa: F811 self, key: Union["SupportsIndex", slice] ) -> Union[int, bytes, "HexBytes"]: result = super().__getitem__(key) if hasattr(result, "hex"): return type(self)(result) else: return result def __repr__(self) -> str: return f"HexBytes({self.hex()!r})"