Files
bitcoin/test/functional/test_framework
merge-script 142e86a65c Merge bitcoin/bitcoin#35458: qa: Avoid extra tracebacks when exception is raised
472b950b7f qa: Use custom assert_greater_than() over naked assert (Hodlinator)
f42226d526 qa: Silence socket.timeout exception when substituting it for a JSONRPCException (Hodlinator)
659671ac3d qa: Avoid cleanup when exception is raised (Hodlinator)

Pull request description:

  Clean up some cases in which we would trigger multiple tracebacks, which makes it unclear what issue is occuring (https://github.com/bitcoin/bitcoin/issues/31894#issuecomment-4616130031).

  CI log of this occurring: https://github.com/bitcoin/bitcoin/actions/runs/26907239657/job/79375388058?pr=35179

  <details><summary>Relevant log excerpt</summary>

  ```
   test  2026-06-03T19:28:28.119804Z TestFramework.node0 (DEBUG): TestNode.generate() dispatches `generate` call to `generatetoaddress`
   test  2026-06-03T19:28:28.120483Z TestFramework (ERROR): Unexpected exception:
                                     Traceback (most recent call last):
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/authproxy.py", line 165, in _get_response
                                         http_response = self.__conn.getresponse()
                                                         ^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/usr/lib/python3.12/http/client.py", line 1448, in getresponse
                                         response.begin()
                                       File "/usr/lib/python3.12/http/client.py", line 336, in begin
                                         version, status, reason = self._read_status()
                                                                   ^^^^^^^^^^^^^^^^^^^
                                       File "/usr/lib/python3.12/http/client.py", line 297, in _read_status
                                         line = str(self.fp.readline(_MAXLINE + 1), "iso-8859-1")
                                                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/usr/lib/python3.12/socket.py", line 707, in readinto
                                         return self._sock.recv_into(b)
                                                ^^^^^^^^^^^^^^^^^^^^^^^
                                     TimeoutError: timed out
                                     During handling of the above exception, another exception occurred:
                                     Traceback (most recent call last):
                                       File "/home/runner/work/bitcoin/bitcoin/ci_build/test/functional/p2p_orphan_handling.py", line 54, in wrapper
                                         func(self)
                                       File "/home/runner/work/bitcoin/bitcoin/ci_build/test/functional/p2p_orphan_handling.py", line 633, in test_maximal_package_protected
                                         testres = node.testmempoolaccept([large_orphan.serialize().hex()])
                                                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/coverage.py", line 50, in __call__
                                         return_val = self.auth_service_proxy_instance.__call__(*args, **kwargs)
                                                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/authproxy.py", line 128, in __call__
                                         response, status = self._request('POST', self.__url.path, postdata.encode('utf-8'))
                                                            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/authproxy.py", line 102, in _request
                                         return self._get_response()
                                                ^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/authproxy.py", line 167, in _get_response
                                         raise JSONRPCException({
                                     test_framework.util.JSONRPCException: 'testmempoolaccept' RPC took longer than 30.000000 seconds. Consider using larger timeout for calls that take longer to return. (-344)  [http_status=None]
                                     During handling of the above exception, another exception occurred:
                                     Traceback (most recent call last):
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/test_framework.py", line 143, in main
                                         self.run_test()
                                       File "/home/runner/work/bitcoin/bitcoin/ci_build/test/functional/p2p_orphan_handling.py", line 837, in run_test
                                         self.test_maximal_package_protected()
                                       File "/home/runner/work/bitcoin/bitcoin/ci_build/test/functional/p2p_orphan_handling.py", line 57, in wrapper
                                         self.generate(self.nodes[0], 1)
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/test_framework.py", line 666, in generate
                                         blocks = generator.generate(*args, called_by_framework=True, **kwargs)
                                                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/test_node.py", line 445, in generate
                                         return self.generatetoaddress(nblocks=nblocks, address=self.get_deterministic_priv_key().address, maxtries=maxtries, **kwargs)
                                                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/test_node.py", line 453, in generatetoaddress
                                         return self.__getattr__('generatetoaddress')(*args, **kwargs)
                                                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/coverage.py", line 50, in __call__
                                         return_val = self.auth_service_proxy_instance.__call__(*args, **kwargs)
                                                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/authproxy.py", line 128, in __call__
                                         response, status = self._request('POST', self.__url.path, postdata.encode('utf-8'))
                                                            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
                                       File "/home/runner/work/bitcoin/bitcoin/test/functional/test_framework/authproxy.py", line 101, in _request
                                         self.__conn.request(method, path, postdata, headers)
                                       File "/usr/lib/python3.12/http/client.py", line 1356, in request
                                         self._send_request(method, url, body, headers, encode_chunked)
                                       File "/usr/lib/python3.12/http/client.py", line 1367, in _send_request
                                         self.putrequest(method, url, **skips)
                                       File "/usr/lib/python3.12/http/client.py", line 1193, in putrequest
                                         raise CannotSendRequest(self.__state)
                                     http.client.CannotSendRequest: Request-sent
   test  2026-06-03T19:28:28.124908Z TestFramework (DEBUG): Closing down network thread
  ```

  </details>

  Fix in authproxy.py can be verified through applying the below diff with/without PR changes and running `./build/test/functional/p2p_orphan_handling.py`:

  ```diff
  --- a/test/functional/test_framework/authproxy.py
  +++ b/test/functional/test_framework/authproxy.py
  @@ -162,6 +162,8 @@ class AuthServiceProxy():
       def _get_response(self):
           req_start_time = time.time()
           try:
  +            if AuthServiceProxy.__id_count > 55:
  +                raise socket.timeout()
               http_response = self.__conn.getresponse()
           except socket.timeout:
               raise JSONRPCException({
  ```

ACKs for top commit:
  maflcko:
    review ACK 472b950b7f 🔼
  polespinasa:
    reACK 472b950b7f

Tree-SHA512: ec1ede0340da9d1338643980e7f2e4646f0aed2e64f339f8b41a447cbbfb4da8158c1cbcb22f2d0cc383c2dd945075602d02b07a47b33b44cc6215f3292c1d46
2026-06-12 10:51:47 +02:00
..
2026-06-04 21:58:56 +10:00
2026-06-04 21:58:56 +10:00
2026-06-04 21:58:56 +10:00