content: import pytest
  import asyncio
  import threading
  import time
  from typing import (
      TYPE_CHECKING,
      Any,
      NoReturn,
      Sequence,
      cast,
  )
  
  from eth_typing import (
      Address,
      ChecksumAddress,
      HexAddress,
      HexStr,
      TypeStr,
  )
  from hexbytes import (
      HexBytes,
  )
  
  from web3 import (
      AsyncWeb3,
      Web3,
  )
  from web3._utils.ens import (
      ens_addresses,
  )
  from web3.contract import (
      Contract,
  )
  from web3.exceptions import (
      InvalidAddress,
      MethodNotSupported,
      Web3ValueError,
  )
  from web3.types import (
      BlockData,
  )
  
  if TYPE_CHECKING:
      from web3.contract import (  # noqa: F401
          AsyncContract,
      )
  
  
  SOME_BLOCK_KEYS = {"number", "hash", "parentHash", "stateRoot", "transactions"}
  
  
  class Web3ModuleTest:
      def test_web3_client_version(self, w3: Web3) -> None:
          client_version = w3.client_version
          self._check_web3_client_version(client_version)
  
      def _check_web3_client_version(self, client_version: str) -> NoReturn:
          raise NotImplementedError("Must be implemented by subclasses")
  
      # Contract that calculated test values can be found at
      # https://kovan.etherscan.io/address/0xb9be06f5b99372cf9afbccadbbb9954ccaf7f4bb#code
      @pytest.mark.parametrize(
          "types,values,expected",
          (
              (
                  ["bool"],
                  [True],
                  HexBytes(
                      "0x5fe7f977e71dba2ea1a68e21057beebb9be2ac30c6410aa38d4f3fbe41dcffd2"
                  ),
              ),
              (
                  ["uint8", "uint8", "uint8"],
                  [97, 98, 99],
                  HexBytes(
                      "0x4e03657aea45a94fc7d47ba826c8d667c0d1e6e33a64a036ec44f58fa12d6c45"
                  ),
              ),
              (
                  ["uint248"],
                  [30],
                  HexBytes(
                      "0x30f95d210785601eb33ae4d53d405b26f920e765dff87cca8e9a4aec99f82671"
                  ),
              ),
              (
                  ["bool", "uint16"],
                  [True, 299],
                  HexBytes(
                      "0xed18599ccd80ee9fae9a28b0e34a5573c3233d7468f808fd659bc171cf0b43bd"
                  ),
              ),
              (
                  ["int256"],
                  [-10],
                  HexBytes(
                      "0xd6fb717f7e270a360f5093ce6a7a3752183e89c9a9afe5c0cb54b458a304d3d5"
                  ),
              ),
              (
                  ["int256"],
                  [10],
                  HexBytes(
                      "0xc65a7bb8d6351c1cf70c95a316cc6a92839c986682d98bc35f958f4883f9d2a8"
                  ),
              ),
              (
                  ["int8", "uint8"],
                  [-10, 18],
                  HexBytes(
                      "0x5c6ab1e634c08d9c0f4df4d789e8727943ef010dd7ca8e3c89de197a26d148be"
                  ),
              ),
              (
                  ["address"],
                  ["0x49eddd3769c0712032808d86597b84ac5c2f5614"],
                  InvalidAddress,
              ),
              (
                  ["address"],
                  ["0x49EdDD3769c0712032808D86597B84ac5c2F5614"],
                  HexBytes(
                      "0x2ff37b5607484cd4eecf6d13292e22bd6e5401eaffcc07e279583bc742c68882"
                  ),
              ),
              (
                  ["bytes2"],
                  ["0x5402"],
                  HexBytes(
                      "0x4ed9171bda52fca71ab28e7f452bd6eacc3e5a568a47e0fa53b503159a9b8910"
                  ),
              ),
              (
                  ["bytes3"],
                  ["0x5402"],
                  HexBytes(
                      "0x4ed9171bda52fca71ab28e7f452bd6eacc3e5a568a47e0fa53b503159a9b8910"
                  ),
              ),
              (
                  ["bytes"],
                  [
                      "0x636865636b6c6f6e6762797465737472696e676167"
                      "61696e7374736f6c6964697479736861336861736866756e6374696f6e"
                  ],
                  HexBytes(
                      "0xd78a84d65721b67e4011b10c99dafdedcdcd7cb30153064f773e210b4762e22f"
                  ),
              ),
              (
                  ["string"],
                  ["testing a string!"],
                  HexBytes(
                      "0xe8c275c0b4070a5ec6cfcb83f0ba394b30ddd283de785d43f2eabfb04bd96747"
                  ),
              ),
              (
                  ["string", "bool", "uint16", "bytes2", "address"],
                  [
                      "testing a string!",
                      False,
                      299,
                      "0x5402",
                      "0x49eddd3769c0712032808d86597b84ac5c2f5614",
                  ],
                  InvalidAddress,
              ),
              (
                  ["string", "bool", "uint16", "bytes2", "address"],
                  [
                      "testing a string!",
                      False,
                      299,
                      "0x5402",
                      "0x49EdDD3769c0712032808D86597B84ac5c2F5614",
                  ],
                  HexBytes(
                      "0x8cc6eabb25b842715e8ca39e2524ed946759aa37bfb7d4b81829cf5a7e266103"
                  ),
              ),
              (
                  ["bool[2][]"],
                  [[[True, False], [False, True]]],
                  HexBytes(
                      "0x1eef261f2eb51a8c736d52be3f91ff79e78a9ec5df2b7f50d0c6f98ed1e2bc06"
                  ),
              ),
              (
                  ["bool[]"],
                  [[True, False, True]],
                  HexBytes(
                      "0x5c6090c0461491a2941743bda5c3658bf1ea53bbd3edcde54e16205e18b45792"
                  ),
              ),
              (
                  ["uint24[]"],
                  [[1, 0, 1]],
                  HexBytes(
                      "0x5c6090c0461491a2941743bda5c3658bf1ea53bbd3edcde54e16205e18b45792"
                  ),
              ),
              (
                  ["uint8[2]"],
                  [[8, 9]],
                  HexBytes(
                      "0xc7694af312c4f286114180fd0ba6a52461fcee8a381636770b19a343af92538a"
                  ),
              ),
              (
                  ["uint256[2]"],
                  [[8, 9]],
                  HexBytes(
                      "0xc7694af312c4f286114180fd0ba6a52461fcee8a381636770b19a343af92538a"
                  ),
              ),
              (
                  ["uint8[]"],
                  [[8]],
                  HexBytes(
                      "0xf3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee3"
                  ),
              ),
              (
                  ["address[]"],
                  [
                      [
                          "0x49EdDD3769c0712032808D86597B84ac5c2F5614",
                          "0xA6b759bBbf4B59D24acf7E06e79f3a5D104fdCE5",
                      ]
                  ],
                  HexBytes(
                      "0xb98565c0c26a962fd54d93b0ed6fb9296e03e9da29d2281ed3e3473109ef7dde"
                  ),
              ),
              (
                  ["address[]"],
                  [
                      [
                          "0x49EdDD3769c0712032808D86597B84ac5c2F5614",
                          "0xa6b759bbbf4b59d24acf7e06e79f3a5d104fdce5",
                      ]
                  ],
                  InvalidAddress,
              ),
          ),
      )
      def test_solidity_keccak(
          self,
          w3: "Web3",
          types: Sequence[TypeStr],
          values: Sequence[Any],
          expected: HexBytes,
      ) -> None:
          if isinstance(expected, type) and issubclass(expected, Exception):
              with pytest.raises(expected):
                  w3.solidity_keccak(types, values)
              return
  
          actual = w3.solidity_keccak(types, values)
          assert actual == expected
  
      @pytest.mark.parametrize(
          "types, values, expected",
          (
              (
                  ["address"],
                  ["one.eth"],
                  HexBytes(
                      "0x2ff37b5607484cd4eecf6d13292e22bd6e5401eaffcc07e279583bc742c68882"
                  ),
              ),
              (
                  ["address[]"],
                  [["one.eth", "two.eth"]],
                  HexBytes(
                      "0xb98565c0c26a962fd54d93b0ed6fb9296e03e9da29d2281ed3e3473109ef7dde"
                  ),
              ),
          ),
      )
      def test_solidity_keccak_ens(
          self,
          w3: "Web3",
          types: Sequence[TypeStr],
          values: Sequence[str],
          expected: HexBytes,
      ) -> None:
          with ens_addresses(
              w3,
              {
                  "one.eth": ChecksumAddress(
                      HexAddress(HexStr("0x49EdDD3769c0712032808D86597B84ac5c2F5614"))
                  ),
                  "two.eth": ChecksumAddress(
                      HexAddress(HexStr("0xA6b759bBbf4B59D24acf7E06e79f3a5D104fdCE5"))
                  ),
              },
          ):
              # when called as class method, any name lookup attempt will fail
              with pytest.raises(InvalidAddress):
                  Web3.solidity_keccak(types, values)
  
              # when called as instance method, ens lookups can succeed
              actual = w3.solidity_keccak(types, values)
              assert actual == expected
  
      @pytest.mark.parametrize(
          "types,values",
          (
              (["address"], ["0xA6b759bBbf4B59D24acf7E06e79f3a5D104fdCE5", True]),
              (["address", "bool"], ["0xA6b759bBbf4B59D24acf7E06e79f3a5D104fdCE5"]),
              ([], ["0xA6b759bBbf4B59D24acf7E06e79f3a5D104fdCE5"]),
          ),
      )
      def test_solidity_keccak_same_number_of_types_and_values(
          self, w3: "Web3", types: Sequence[TypeStr], values: Sequence[Any]
      ) -> None:
          with pytest.raises(ValueError):
              w3.solidity_keccak(types, values)
  
      def test_is_connected(self, w3: "Web3") -> None:
          assert w3.is_connected()
  
      def test_batch_requests(self, w3: "Web3", math_contract: Contract) -> None:
          with w3.batch_requests() as batch:
              batch.add(w3.eth.get_block(6))
              batch.add(w3.eth.get_block(4))
              batch.add(w3.eth.get_block(2))
              batch.add(w3.eth.get_block(0))
              batch.add(math_contract.functions.multiply7(0))
  
              batch.add_mapping(
                  {
                      math_contract.functions.multiply7: [1, 2, 3],
                      w3.eth.get_block: [1, 3, 5],
                  }
              )
  
              assert len(batch._requests_info) == 11
              responses = batch.execute()
              assert len(responses) == 11
  
              # assert proper batch cleanup after execution
              assert batch._requests_info == []
              assert not w3.provider._is_batching
  
              # assert batch cannot be added to after execution
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  batch.add(w3.eth.get_block(5))
  
              # assert batch cannot be executed again
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  batch.execute()
  
          # assert can make a request after executing
          block_num = w3.eth.block_number
          assert isinstance(block_num, int)
  
          first_four_responses: Sequence[BlockData] = cast(
              Sequence[BlockData], responses[:4]
          )
          assert first_four_responses[0]["number"] == 6
          assert first_four_responses[1]["number"] == 4
          assert first_four_responses[2]["number"] == 2
          assert first_four_responses[3]["number"] == 0
  
          responses_five_through_eight: Sequence[int] = cast(
              Sequence[int], responses[4:8]
          )
          assert responses_five_through_eight[0] == 0
          assert responses_five_through_eight[1] == 7
          assert responses_five_through_eight[2] == 14
          assert responses_five_through_eight[3] == 21
  
          last_three_responses: Sequence[BlockData] = cast(
              Sequence[BlockData], responses[8:]
          )
          assert last_three_responses[0]["number"] == 1
          assert last_three_responses[1]["number"] == 3
          assert last_three_responses[2]["number"] == 5
  
      def test_batch_requests_initialized_as_object(
          self, w3: "Web3", math_contract: Contract
      ) -> None:
          batch = w3.batch_requests()
          batch.add(w3.eth.get_block(1))
          batch.add(w3.eth.get_block(2))
          batch.add(math_contract.functions.multiply7(0))
          batch.add_mapping(
              {math_contract.functions.multiply7: [1, 2], w3.eth.get_block: [3, 4]}
          )
  
          assert len(batch._requests_info) == 7
          b1, b2, m0, m1, m2, b3, b4 = batch.execute()
  
          # assert proper batch cleanup after execution
          assert batch._requests_info == []
          assert not w3.provider._is_batching
  
          # assert batch cannot be added to after execution
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              batch.add(w3.eth.get_block(5))
  
          # assert batch cannot be executed again
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              batch.execute()
  
          # assert can make a request after executing
          block_num = w3.eth.block_number
          assert isinstance(block_num, int)
  
          assert cast(BlockData, b1)["number"] == 1
          assert cast(BlockData, b2)["number"] == 2
          assert cast(int, m0) == 0
          assert cast(int, m1) == 7
          assert cast(int, m2) == 14
          assert cast(BlockData, b3)["number"] == 3
          assert cast(BlockData, b4)["number"] == 4
  
      def test_batch_requests_clear(self, w3: "Web3") -> None:
          with w3.batch_requests() as batch:
              batch.add(w3.eth.get_block(1))
              batch.add(w3.eth.get_block(2))
  
              assert len(batch._requests_info) == 2
              batch.clear()
              assert batch._requests_info == []
  
              batch.add(w3.eth.get_block(3))
              batch.add(w3.eth.get_block(4))
  
              r1, r2 = batch.execute()
  
              assert cast(BlockData, r1)["number"] == 3
              assert cast(BlockData, r2)["number"] == 4
  
          new_batch = w3.batch_requests()
          new_batch.add(w3.eth.get_block(5))
  
          assert len(new_batch._requests_info) == 1
          new_batch.clear()
          assert new_batch._requests_info == []
  
          new_batch.add(w3.eth.get_block(6))
          (r3,) = new_batch.execute()
          assert cast(BlockData, r3)["number"] == 6
  
      def test_batch_requests_cancel(self, w3: "Web3") -> None:
          # as context manager
          with w3.batch_requests() as batch:
              batch.add(w3.eth.get_block(1))
              batch.cancel()
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  batch.add(w3.eth.get_block(2))
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  batch.execute()
  
          # can make a request after cancelling
          block_num = w3.eth.block_number
          assert isinstance(block_num, int)
  
          # as obj
          new_batch = w3.batch_requests()
          new_batch.add(w3.eth.get_block(1))
          new_batch.cancel()
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              new_batch.add(w3.eth.get_block(2))
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              new_batch.execute()
  
          # assert can make a request after cancelling
          block_num = w3.eth.block_number
          assert isinstance(block_num, int)
  
      def test_batch_requests_raises_for_common_unsupported_methods(
          self, w3: "Web3", math_contract: Contract
      ) -> None:
          with w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sendTransaction"):
                  batch.add(w3.eth.send_transaction({}))
                  batch.execute()
  
          with w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sendTransaction"):
                  batch.add(math_contract.functions.multiply7(1).transact({}))
                  batch.execute()
  
          with w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sendRawTransaction"):
                  batch.add(w3.eth.send_raw_transaction(b""))
                  batch.execute()
  
          with w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sign"):
                  batch.add(w3.eth.sign(Address(b"\x00" * 20)))
                  batch.execute()
  
      def test_batch_requests_concurrently_with_regular_requests(
          self, w3: "Web3"
      ) -> None:
          num_requests = 40
          responses = []
          batch_response = []
  
          def make_regular_requests() -> None:
              for _ in range(num_requests):
                  responses.append(w3.eth.get_block(0))
                  time.sleep(0.01)
  
          def make_batch_request() -> None:
              with w3.batch_requests() as batch:
                  for _ in range(num_requests):
                      batch.add(w3.eth.get_block(0))
                      time.sleep(0.01)
                  batch_response.extend(batch.execute())
  
          # split into threads
          regular_thread = threading.Thread(target=make_regular_requests)
          batch_thread = threading.Thread(target=make_batch_request)
  
          regular_thread.start()
          batch_thread.start()
  
          # wait for threads to finish
          regular_thread.join()
          batch_thread.join()
          assert not regular_thread.is_alive()
          assert not batch_thread.is_alive()
  
          assert len(responses) == num_requests
          assert len(batch_response) == num_requests
          assert all(SOME_BLOCK_KEYS.issubset(response.keys()) for response in responses)
          assert set(responses) == set(batch_response)
  
  
  # -- async -- #
  
  
  class AsyncWeb3ModuleTest(Web3ModuleTest):
      # Note: Any test that overrides the synchronous test from `Web3ModuleTest` with
      # an asynchronous test should have the exact same name.
  
      @pytest.mark.asyncio
      async def test_web3_client_version(self, async_w3: AsyncWeb3[Any]) -> None:
          client_version = await async_w3.client_version
          self._check_web3_client_version(client_version)
  
      @pytest.mark.asyncio
      async def test_batch_requests(
          self, async_w3: AsyncWeb3[Any], async_math_contract: "AsyncContract"
      ) -> None:
          async with async_w3.batch_requests() as batch:
              batch.add(async_w3.eth.get_block(6))
              batch.add(async_w3.eth.get_block(4))
              batch.add(async_w3.eth.get_block(2))
              batch.add(async_w3.eth.get_block(0))
  
              batch.add(async_math_contract.functions.multiply7(0))
  
              batch.add_mapping(
                  {
                      async_math_contract.functions.multiply7: [1, 2, 3],
                      async_w3.eth.get_block: [1, 3, 5],
                  }
              )
  
              assert len(batch._async_requests_info) == 11
              responses = await batch.async_execute()
              assert len(responses) == 11
  
              # assert proper batch cleanup after execution
              assert batch._async_requests_info == []
              assert not async_w3.provider._is_batching
  
              # assert batch cannot be added to after execution
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  batch.add(async_w3.eth.get_block(5))
  
              # assert batch cannot be executed again
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  await batch.async_execute()
  
          # assert can make a request after executing
          block_num = await async_w3.eth.block_number
          assert isinstance(block_num, int)
  
          first_four_responses: Sequence[BlockData] = cast(
              Sequence[BlockData], responses[:4]
          )
          assert first_four_responses[0]["number"] == 6
          assert first_four_responses[1]["number"] == 4
          assert first_four_responses[2]["number"] == 2
          assert first_four_responses[3]["number"] == 0
  
          responses_five_through_eight: Sequence[int] = cast(
              Sequence[int], responses[4:8]
          )
          assert responses_five_through_eight[0] == 0
          assert responses_five_through_eight[1] == 7
          assert responses_five_through_eight[2] == 14
          assert responses_five_through_eight[3] == 21
  
          last_three_responses: Sequence[BlockData] = cast(
              Sequence[BlockData], responses[8:]
          )
          assert last_three_responses[0]["number"] == 1
          assert last_three_responses[1]["number"] == 3
          assert last_three_responses[2]["number"] == 5
  
      @pytest.mark.asyncio
      async def test_batch_requests_initialized_as_object(
          self,
          async_w3: AsyncWeb3[Any],
          async_math_contract: "AsyncContract",
      ) -> None:
          batch = async_w3.batch_requests()
          batch.add(async_w3.eth.get_block(1))
          batch.add(async_w3.eth.get_block(2))
          batch.add(async_math_contract.functions.multiply7(0))
          batch.add_mapping(
              {
                  async_math_contract.functions.multiply7: [1, 2],
                  async_w3.eth.get_block: [3, 4],
              }
          )
  
          assert len(batch._async_requests_info) == 7
          b1, b2, m0, m1, m2, b3, b4 = await batch.async_execute()
  
          # assert proper batch cleanup after execution
          assert batch._async_requests_info == []
          assert not async_w3.provider._is_batching
  
          # assert batch cannot be added to after execution
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              batch.add(async_w3.eth.get_block(5))
  
          # assert batch cannot be executed again
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              await batch.async_execute()
  
          # assert can make a request after executing
          block_num = await async_w3.eth.block_number
          assert isinstance(block_num, int)
  
          assert cast(BlockData, b1)["number"] == 1
          assert cast(BlockData, b2)["number"] == 2
          assert cast(int, m0) == 0
          assert cast(int, m1) == 7
          assert cast(int, m2) == 14
          assert cast(BlockData, b3)["number"] == 3
          assert cast(BlockData, b4)["number"] == 4
  
      @pytest.mark.asyncio
      async def test_batch_requests_clear(self, async_w3: AsyncWeb3[Any]) -> None:
          async with async_w3.batch_requests() as batch:
              batch.add(async_w3.eth.get_block(1))
              batch.add(async_w3.eth.get_block(2))
  
              assert len(batch._async_requests_info) == 2
              batch.clear()
              assert batch._async_requests_info == []
  
              batch.add(async_w3.eth.get_block(3))
              batch.add(async_w3.eth.get_block(4))
  
              r1, r2 = await batch.async_execute()
  
              assert cast(BlockData, r1)["number"] == 3
              assert cast(BlockData, r2)["number"] == 4
  
          new_batch = async_w3.batch_requests()
          new_batch.add(async_w3.eth.get_block(5))
  
          assert len(new_batch._async_requests_info) == 1
          new_batch.clear()
          assert new_batch._async_requests_info == []
  
          new_batch.add(async_w3.eth.get_block(6))
          (r3,) = await new_batch.async_execute()
          assert cast(BlockData, r3)["number"] == 6
  
      @pytest.mark.asyncio
      async def test_batch_requests_cancel(self, async_w3: AsyncWeb3[Any]) -> None:
          # as context manager
          async with async_w3.batch_requests() as batch:
              batch.add(async_w3.eth.get_block(1))
              batch.cancel()
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  batch.add(async_w3.eth.get_block(2))
              with pytest.raises(
                  Web3ValueError,
                  match="Batch has already been executed or cancelled",
              ):
                  await batch.async_execute()
  
          # can make a request after cancelling
          block_num = await async_w3.eth.block_number
          assert isinstance(block_num, int)
  
          # as obj
          new_batch = async_w3.batch_requests()
          new_batch.add(async_w3.eth.get_block(1))
          new_batch.cancel()
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              new_batch.add(async_w3.eth.get_block(2))
          with pytest.raises(
              Web3ValueError,
              match="Batch has already been executed or cancelled",
          ):
              await new_batch.async_execute()
  
          # can make a request after cancelling
          block_num = await async_w3.eth.block_number
          assert isinstance(block_num, int)
  
      @pytest.mark.asyncio
      async def test_batch_requests_raises_for_common_unsupported_methods(
          self,
          async_w3: AsyncWeb3[Any],
          async_math_contract: "AsyncContract",
      ) -> None:
          async with async_w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sendTransaction"):
                  batch.add(async_w3.eth.send_transaction({}))
                  await batch.async_execute()
  
          async with async_w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sendTransaction"):
                  batch.add(async_math_contract.functions.multiply7(1).transact({}))
                  await batch.async_execute()
  
          async with async_w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sendRawTransaction"):
                  batch.add(async_w3.eth.send_raw_transaction(b""))
                  await batch.async_execute()
  
          async with async_w3.batch_requests() as batch:
              with pytest.raises(MethodNotSupported, match="eth_sign"):
                  batch.add(async_w3.eth.sign(Address(b"\x00" * 20)))
                  await batch.async_execute()
  
      @pytest.mark.asyncio
      async def test_batch_requests_concurrently_with_regular_requests(
          self, async_w3: AsyncWeb3[Any]
      ) -> None:
          responses = []
          batch_response = []
  
          num_blocks = await async_w3.eth.block_number
  
          async def make_regular_requests() -> None:
              for i in range(num_blocks):
                  responses.append(await async_w3.eth.get_block(i))
                  await asyncio.sleep(0.01)
  
          async def make_batch_request() -> None:
              async with async_w3.batch_requests() as batch:
                  for i in range(num_blocks):
                      batch.add(async_w3.eth.get_block(i))
                      await asyncio.sleep(0.01)
                  batch_response.extend(await batch.async_execute())
  
          await asyncio.gather(
              make_regular_requests(),
              make_batch_request(),
          )
  
          assert len(responses) == num_blocks
          assert len(batch_response) == num_blocks
          assert all(SOME_BLOCK_KEYS.issubset(response.keys()) for response in responses)
          assert set(responses) == set(batch_response)
  