Merge bitcoin/bitcoin#29283: test: ensure output is large enough to pay for its fees

3bfc5bd36e38ca07306a41a3f56ea102ffe02b67 test: ensure output is large enough to pay for its fees (stickies-v)

Pull request description:

  Fixes a (rare) intermittency issue in wallet_import_rescan.py

  Since we [use](03752444cd/test/functional/wallet_import_rescan.py (L296)) `subtract_fee_from_outputs=[0]` in the `send` command, the output amount must at least be as large as the fee we're paying.

  Example in CI: https://api.cirrus-ci.com/v1/task/6107972259020800/logs/ci.log

  ```
  2024-01-18T22:16:12.383000Z TestFramework (INFO): Test that the mempool is rescanned as well if the rescan parameter is set to true
  2024-01-18T22:16:20.187000Z TestFramework (ERROR): JSONRPC error
  Traceback (most recent call last):
    File "/ci_container_base/ci/scratch/build/bitcoin-x86_64-pc-linux-gnu/test/functional/test_framework/test_framework.py", line 131, in main
      self.run_test()
    File "/ci_container_base/ci/scratch/build/bitcoin-x86_64-pc-linux-gnu/test/functional/wallet_import_rescan.py", line 292, in run_test
      child = self.nodes[1].send(
    File "/ci_container_base/ci/scratch/build/bitcoin-x86_64-pc-linux-gnu/test/functional/test_framework/coverage.py", line 50, in __call__
      return_val = self.auth_service_proxy_instance.__call__(*args, **kwargs)
    File "/ci_container_base/ci/scratch/build/bitcoin-x86_64-pc-linux-gnu/test/functional/test_framework/authproxy.py", line 129, in __call__
      raise JSONRPCException(response['error'], status)
  test_framework.authproxy.JSONRPCException: The transaction amount is too small to pay the fee (-4)
  ```

  Can be reproduced locally by forcing usage of the lowest possible value produced by `get_rand_amount()` ([thanks furszy](https://github.com/bitcoin/bitcoin/pull/29283#pullrequestreview-1832956095)):

  <details>
  <summary>git diff on 5f3a0574c4</summary>

  ```diff
  diff --git a/test/functional/wallet_import_rescan.py b/test/functional/wallet_import_rescan.py
  index 7f01d23941..925849d5c0 100755
  --- a/test/functional/wallet_import_rescan.py
  +++ b/test/functional/wallet_import_rescan.py
  @@ -270,7 +270,7 @@ class ImportRescanTest(BitcoinTestFramework):
                   address_type=variant.address_type.value,
               ))
               variant.key = self.nodes[1].dumpprivkey(variant.address["address"])
  -            variant.initial_amount = get_rand_amount() * 2
  +            variant.initial_amount = Decimal(str(round(AMOUNT_DUST, 8))) * 2
               variant.initial_txid = self.nodes[0].sendtoaddress(variant.address["address"], variant.initial_amount)
               variant.confirmation_height = 0
               variant.timestamp = timestamp

  ```
  </details>

ACKs for top commit:
  achow101:
    ACK 3bfc5bd36e38ca07306a41a3f56ea102ffe02b67
  glozow:
    utACK 3bfc5bd36e38ca07306a41a3f56ea102ffe02b67, didn't experience this issue but in theory a minimum of `AMOUNT_DUST` could be too low to pay the fees
  furszy:
    utACK 3bfc5bd36

Tree-SHA512: 821ab94a510772e90528b2cef368bbf70309d8fd1dcda53dce75dd1bf91622358e80fea4d9fc68249b9d598892306c66f6c843b4a6855a9f9a9175f7b41109c6
This commit is contained in:
Ava Chow 2024-01-26 18:33:33 -05:00
commit ff0eac055f
No known key found for this signature in database
GPG Key ID: 17565732E08E5E41

View File

@ -24,6 +24,7 @@ from test_framework.address import (
AddressType,
ADDRESS_BCRT1_UNSPENDABLE,
)
from test_framework.messages import COIN
from test_framework.util import (
assert_equal,
set_node_times,
@ -270,7 +271,9 @@ class ImportRescanTest(BitcoinTestFramework):
address_type=variant.address_type.value,
))
variant.key = self.nodes[1].dumpprivkey(variant.address["address"])
variant.initial_amount = get_rand_amount() * 2
# Ensure output is large enough to pay for fees: conservatively assuming txsize of
# 500 vbytes and feerate of 20 sats/vbytes
variant.initial_amount = max(get_rand_amount(), (500 * 20 / COIN) + AMOUNT_DUST)
variant.initial_txid = self.nodes[0].sendtoaddress(variant.address["address"], variant.initial_amount)
variant.confirmation_height = 0
variant.timestamp = timestamp