Skip to content

Commit 896a9d0

Browse files
committed
Merge #13022: [qa] Attach node index to test_node AssertionError and print messages
80a5e59 [qa] Attach node index to test_node AssertionError and print messages (James O'Beirne) Pull request description: In the midst of fighting with #12873 it became apparent that there're a number of assertions and print statements which are emitted by test nodes but don't identify the node in question. This change makes debugging a bit easier by adding identifying information to non-logger test_node-related error messages. Tree-SHA512: 7cc86f2c81f4b3fdba15ec9a2d21a84c4b083629e845e82288087c3affbbdc5c68e74067621856cc97fe84fbc8cb4f5ca4977a51ef381e5d74515df8eb001239
2 parents 569e381 + 80a5e59 commit 896a9d0

File tree

1 file changed

+24
-13
lines changed

1 file changed

+24
-13
lines changed

test/functional/test_framework/test_node.py

Lines changed: 24 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,6 @@
1919
from .authproxy import JSONRPCException
2020
from .util import (
2121
append_config,
22-
assert_equal,
2322
delete_cookie_file,
2423
get_rpc_proxy,
2524
rpc_url,
@@ -103,22 +102,30 @@ def __init__(self, i, datadir, rpchost, timewait, binary, stderr, mocktime, cove
103102

104103
self.p2ps = []
105104

105+
def _node_msg(self, msg: str) -> str:
106+
"""Return a modified msg that identifies this node by its index as a debugging aid."""
107+
return "[node %d] %s" % (self.index, msg)
108+
109+
def _raise_assertion_error(self, msg: str):
110+
"""Raise an AssertionError with msg modified to identify this node."""
111+
raise AssertionError(self._node_msg(msg))
112+
106113
def __del__(self):
107114
# Ensure that we don't leave any bitcoind processes lying around after
108115
# the test ends
109116
if self.process and self.cleanup_on_exit:
110117
# Should only happen on test failure
111118
# Avoid using logger, as that may have already been shutdown when
112119
# this destructor is called.
113-
print("Cleaning up leftover process")
120+
print(self._node_msg("Cleaning up leftover process"))
114121
self.process.kill()
115122

116123
def __getattr__(self, name):
117124
"""Dispatches any unrecognised messages to the RPC connection or a CLI instance."""
118125
if self.use_cli:
119126
return getattr(self.cli, name)
120127
else:
121-
assert self.rpc_connected and self.rpc is not None, "Error: no RPC connection"
128+
assert self.rpc_connected and self.rpc is not None, self._node_msg("Error: no RPC connection")
122129
return getattr(self.rpc, name)
123130

124131
def start(self, extra_args=None, stderr=None, *args, **kwargs):
@@ -141,7 +148,8 @@ def wait_for_rpc_connection(self):
141148
poll_per_s = 4
142149
for _ in range(poll_per_s * self.rpc_timeout):
143150
if self.process.poll() is not None:
144-
raise FailedToStartError('bitcoind exited with status {} during initialization'.format(self.process.returncode))
151+
raise FailedToStartError(self._node_msg(
152+
'bitcoind exited with status {} during initialization'.format(self.process.returncode)))
145153
try:
146154
self.rpc = get_rpc_proxy(rpc_url(self.datadir, self.index, self.rpchost), self.index, timeout=self.rpc_timeout, coveragedir=self.coverage_dir)
147155
self.rpc.getblockcount()
@@ -160,14 +168,13 @@ def wait_for_rpc_connection(self):
160168
if "No RPC credentials" not in str(e):
161169
raise
162170
time.sleep(1.0 / poll_per_s)
163-
raise AssertionError("Unable to connect to bitcoind")
171+
self._raise_assertion_error("Unable to connect to bitcoind")
164172

165173
def get_wallet_rpc(self, wallet_name):
166174
if self.use_cli:
167175
return self.cli("-rpcwallet={}".format(wallet_name))
168176
else:
169-
assert self.rpc_connected
170-
assert self.rpc
177+
assert self.rpc_connected and self.rpc, self._node_msg("RPC not connected")
171178
wallet_path = "wallet/%s" % wallet_name
172179
return self.rpc / wallet_path
173180

@@ -194,7 +201,8 @@ def is_node_stopped(self):
194201
return False
195202

196203
# process has stopped. Assert that it didn't return an error code.
197-
assert_equal(return_code, 0)
204+
assert return_code == 0, self._node_msg(
205+
"Node returned non-zero exit code (%d) when stopping" % return_code)
198206
self.running = False
199207
self.process = None
200208
self.rpc_connected = False
@@ -229,19 +237,22 @@ def assert_start_raises_init_error(self, extra_args=None, expected_msg=None, mat
229237
stderr = log_stderr.read().decode('utf-8').strip()
230238
if match == ErrorMatch.PARTIAL_REGEX:
231239
if re.search(expected_msg, stderr, flags=re.MULTILINE) is None:
232-
raise AssertionError('Expected message "{}" does not partially match stderr:\n"{}"'.format(expected_msg, stderr))
240+
self._raise_assertion_error(
241+
'Expected message "{}" does not partially match stderr:\n"{}"'.format(expected_msg, stderr))
233242
elif match == ErrorMatch.FULL_REGEX:
234243
if re.fullmatch(expected_msg, stderr) is None:
235-
raise AssertionError('Expected message "{}" does not fully match stderr:\n"{}"'.format(expected_msg, stderr))
244+
self._raise_assertion_error(
245+
'Expected message "{}" does not fully match stderr:\n"{}"'.format(expected_msg, stderr))
236246
elif match == ErrorMatch.FULL_TEXT:
237247
if expected_msg != stderr:
238-
raise AssertionError('Expected message "{}" does not fully match stderr:\n"{}"'.format(expected_msg, stderr))
248+
self._raise_assertion_error(
249+
'Expected message "{}" does not fully match stderr:\n"{}"'.format(expected_msg, stderr))
239250
else:
240251
if expected_msg is None:
241252
assert_msg = "bitcoind should have exited with an error"
242253
else:
243254
assert_msg = "bitcoind should have exited with expected error " + expected_msg
244-
raise AssertionError(assert_msg)
255+
self._raise_assertion_error(assert_msg)
245256

246257
def node_encrypt_wallet(self, passphrase):
247258
""""Encrypts the wallet.
@@ -272,7 +283,7 @@ def p2p(self):
272283
273284
Convenience property - most tests only use a single p2p connection to each
274285
node, so this saves having to write node.p2ps[0] many times."""
275-
assert self.p2ps, "No p2p connection"
286+
assert self.p2ps, self._node_msg("No p2p connection")
276287
return self.p2ps[0]
277288

278289
def disconnect_p2ps(self):

0 commit comments

Comments
 (0)