qt: TxEditor: extend messages for send change to ln
What changed, and why it matters
This commit only improves user-facing messages in Electrum's Qt transaction confirmation dialog. It explains when the 'send change to Lightning' feature will or won't be used, including reasons such as Lightning not being enabled, channel limits, or swap provider minimum/maximum amounts. There is no security-relevant code change.
No security action needed. This is a routine UX/message improvement.
Security signals we found
No strong security signals were identified.
Evidence from the diff
The patch extends TxEditor.get_messages() in electrum/gui/qt/confirm_tx_dialog.py to provide clearer messaging around submarine swaps and the ‘WALLET_SEND_CHANGE_TO_LIGHTNING’ configuration. It replaces a simple static message with dynamic messages that include swap fees and reasons why change might not be sent to Lightning. No logic affecting transaction construction, signing, validation, or security boundaries is modified.
Changed components
electrum/gui/qt/confirm_tx_dialog.pyInspect captured patch +29 / −2
diff --git a/electrum/gui/qt/confirm_tx_dialog.py b/electrum/gui/qt/confirm_tx_dialog.py
index 3e7fc48..ce908c5 100644
--- a/electrum/gui/qt/confirm_tx_dialog.py
+++ b/electrum/gui/qt/confirm_tx_dialog.py
@@ -667,8 +667,35 @@ class TxEditor(WindowModalDialog, QtEventListener, Logger):
messages.append(long_warning)
if self.no_dynfee_estimates:
self.error = _('Fee estimates not available. Please set a fixed fee or feerate.')
- if self.tx.get_dummy_output(DummyAddress.SWAP):
- messages.append(_('This transaction will send funds to a submarine swap.'))
+ if dummy_output := self.tx.get_dummy_output(DummyAddress.SWAP):
+ swap_msg = _('Will send change to lightning')
+ swap_fee_msg = "."
+ if self.swap_manager and self.swap_manager.is_initialized.is_set() and isinstance(dummy_output.value, int):
+ ln_amount_we_recv = self.swap_manager.get_recv_amount(send_amount=dummy_output.value, is_reverse=False)
+ if ln_amount_we_recv:
+ swap_fees = dummy_output.value - ln_amount_we_recv
+ swap_fee_msg = " [" + _("Swap fees:") + " " + self.main_window.format_amount_and_units(swap_fees) + "]."
+ messages.append(swap_msg + swap_fee_msg)
+ elif self.config.WALLET_SEND_CHANGE_TO_LIGHTNING and self.tx.has_change():
+ swap_msg = _('Will not send change to Lightning')
+ swap_msg_reason = None
+ change_amount = sum(c.value for c in self.tx.get_change_outputs() if isinstance(c.value, int))
+ if not self.wallet.has_lightning():
+ swap_msg_reason = _('Lightning is not enabled.')
+ elif change_amount > int(self.wallet.lnworker.num_sats_can_receive()):
+ swap_msg_reason = _("Your channels cannot receive this amount.")
+ elif self.wallet.lnworker.swap_manager.is_initialized.is_set():
+ min_amount = self.wallet.lnworker.swap_manager.get_min_amount()
+ max_amount = self.wallet.lnworker.swap_manager.get_provider_max_reverse_amount()
+ if change_amount < min_amount:
+ swap_msg_reason = _("Below the swap providers minimum value of {}.").format(
+ self.main_window.format_amount_and_units(min_amount)
+ )
+ else:
+ swap_msg_reason = _('Change amount exceeds the swap providers maximum value of {}.').format(
+ self.main_window.format_amount_and_units(max_amount)
+ )
+ messages.append(swap_msg + f": {swap_msg_reason}" if swap_msg_reason else '')
# warn if spending unconf
if any((txin.block_height is not None and txin.block_height<=0) for txin in self.tx.inputs()):
messages.append(_('This transaction will spend unconfirmed coins.'))
Why this scored 14/100
Community notes
Notes can correct, qualify, or add evidence to the AI analysis. Every note shown here has been validated by a human moderator.
The AI analysis stands alone for now. Submit a note if you can add evidence or important context.