mirror of
https://github.com/bitcoin/bitcoin.git
synced 2025-03-12 02:07:39 +01:00
wallet: introduce "tx amount exceeds balance when fees are included" error
This was previously implemented at the GUI level but has been broken since #20640
This commit is contained in:
parent
a786fd2041
commit
900e5ed51b
2 changed files with 31 additions and 2 deletions
|
@ -1131,7 +1131,19 @@ static util::Result<CreatedTransactionResult> CreateTransactionInternal(
|
|||
if (!select_coins_res) {
|
||||
// 'SelectCoins' either returns a specific error message or, if empty, means a general "Insufficient funds".
|
||||
const bilingual_str& err = util::ErrorString(select_coins_res);
|
||||
return util::Error{err.empty() ?_("Insufficient funds") : err};
|
||||
if (!err.empty()) return util::Error{err};
|
||||
|
||||
// Check if we have enough balance but cannot cover the fees
|
||||
CAmount available_balance = preset_inputs.total_amount + available_coins.GetTotalAmount();
|
||||
if (available_balance >= recipients_sum) {
|
||||
CAmount available_effective_balance = preset_inputs.total_amount + available_coins.GetEffectiveTotalAmount().value_or(available_coins.GetTotalAmount());
|
||||
if (available_effective_balance < selection_target) {
|
||||
return util::Error{_("The total transaction amount exceeds your balance when fees are included")};
|
||||
}
|
||||
}
|
||||
|
||||
// General failure description
|
||||
return util::Error{_("Insufficient funds")};
|
||||
}
|
||||
const SelectionResult& result = *select_coins_res;
|
||||
TRACE5(coin_selection, selected_coins,
|
||||
|
|
|
@ -150,6 +150,7 @@ class RawTransactionsTest(BitcoinTestFramework):
|
|||
self.test_feerate_rounding()
|
||||
self.test_input_confs_control()
|
||||
self.test_duplicate_outputs()
|
||||
self.test_cannot_cover_fees()
|
||||
|
||||
def test_duplicate_outputs(self):
|
||||
self.log.info("Test deserializing and funding a transaction with duplicate outputs")
|
||||
|
@ -1426,7 +1427,8 @@ class RawTransactionsTest(BitcoinTestFramework):
|
|||
# To test this does not happen, we subtract 202 sats from the input value. If working correctly, this should
|
||||
# fail with insufficient funds rather than bitcoind asserting.
|
||||
rawtx = w.createrawtransaction(inputs=[], outputs=[{self.nodes[0].getnewaddress(address_type="bech32"): 1 - 0.00000202}])
|
||||
assert_raises_rpc_error(-4, "Insufficient funds", w.fundrawtransaction, rawtx, fee_rate=1.85)
|
||||
expected_err_msg = "The total transaction amount exceeds your balance when fees are included"
|
||||
assert_raises_rpc_error(-4, expected_err_msg, w.fundrawtransaction, rawtx, fee_rate=1.85)
|
||||
|
||||
def test_input_confs_control(self):
|
||||
self.nodes[0].createwallet("minconf")
|
||||
|
@ -1489,5 +1491,20 @@ class RawTransactionsTest(BitcoinTestFramework):
|
|||
|
||||
wallet.unloadwallet()
|
||||
|
||||
def test_cannot_cover_fees(self):
|
||||
self.log.info("Test tx amount exceeds available balance when fees are included")
|
||||
|
||||
self.nodes[1].createwallet("cannot_cover_fees")
|
||||
wallet = self.nodes[1].get_wallet_rpc("cannot_cover_fees")
|
||||
|
||||
self.nodes[0].sendtoaddress(wallet.getnewaddress(), 0.3)
|
||||
self.generate(self.nodes[0], 1)
|
||||
|
||||
rawtx = wallet.createrawtransaction(inputs=[], outputs=[{self.nodes[0].getnewaddress(): 0.3}])
|
||||
expected_err_msg = "The total transaction amount exceeds your balance when fees are included"
|
||||
assert_raises_rpc_error(-4, expected_err_msg, wallet.fundrawtransaction, rawtx)
|
||||
wallet.unloadwallet()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
RawTransactionsTest().main()
|
||||
|
|
Loading…
Add table
Reference in a new issue