If trampoline is enabled, do not add non-trampoline nodes to invoices
Rationale: The sender should not assume that they share the same list of hardcoded trampolines as the receiver.
This commit is contained in:
@@ -41,7 +41,6 @@ MSG_CAPITAL_GAINS = _(
|
||||
)
|
||||
|
||||
MSG_NON_TRAMPOLINE_CHANNEL_FROZEN_WITHOUT_GOSSIP = _(
|
||||
"""Trampoline routing is enabled, but this channel is with a non-trampoline node.
|
||||
This channel may still be used for receiving, but it is frozen for sending.
|
||||
"""This channel is with a non-trampoline node; it cannot be used if trampoline is enabled.
|
||||
If you want to keep using this channel, you need to disable trampoline routing in your preferences."""
|
||||
)
|
||||
|
||||
@@ -193,9 +193,12 @@ class ChannelsList(MyTreeView):
|
||||
return self.network.run_from_another_thread(coro)
|
||||
WaitingDialog(self, 'please wait..', task, self.on_request_sent, self.on_failure)
|
||||
|
||||
def freeze_channel_for_sending(self, chan, b):
|
||||
def set_frozen(self, chan, *, for_sending, value):
|
||||
if not self.lnworker.uses_trampoline() or self.lnworker.is_trampoline_peer(chan.node_id):
|
||||
chan.set_frozen_for_sending(b)
|
||||
if for_sending:
|
||||
chan.set_frozen_for_sending(value)
|
||||
else:
|
||||
chan.set_frozen_for_receiving(value)
|
||||
else:
|
||||
msg = messages.MSG_NON_TRAMPOLINE_CHANNEL_FROZEN_WITHOUT_GOSSIP
|
||||
self.main_window.show_warning(msg, title=_('Channel is frozen for sending'))
|
||||
@@ -258,13 +261,13 @@ class ChannelsList(MyTreeView):
|
||||
if not chan.is_backup() and not chan.is_closed():
|
||||
fm = menu.addMenu(_("Freeze"))
|
||||
if not chan.is_frozen_for_sending():
|
||||
fm.addAction(_("Freeze for sending"), lambda: self.freeze_channel_for_sending(chan, True))
|
||||
fm.addAction(_("Freeze for sending"), lambda: self.set_frozen(chan, for_sending=True, value=True))
|
||||
else:
|
||||
fm.addAction(_("Unfreeze for sending"), lambda: self.freeze_channel_for_sending(chan, False))
|
||||
fm.addAction(_("Unfreeze for sending"), lambda: self.set_frozen(chan, for_sending=True, value=False))
|
||||
if not chan.is_frozen_for_receiving():
|
||||
fm.addAction(_("Freeze for receiving"), lambda: chan.set_frozen_for_receiving(True))
|
||||
fm.addAction(_("Freeze for receiving"), lambda: self.set_frozen(chan, for_sending=False, value=True))
|
||||
else:
|
||||
fm.addAction(_("Unfreeze for receiving"), lambda: chan.set_frozen_for_receiving(False))
|
||||
fm.addAction(_("Unfreeze for receiving"), lambda: self.set_frozen(chan, for_sending=False, value=False))
|
||||
if close_opts := chan.get_close_options():
|
||||
cm = menu.addMenu(_("Close"))
|
||||
if ChanCloseOption.COOP_CLOSE in close_opts:
|
||||
|
||||
@@ -921,6 +921,8 @@ class Channel(AbstractChannel):
|
||||
util.trigger_callback('channel', self.lnworker.wallet, self)
|
||||
|
||||
def is_frozen_for_receiving(self) -> bool:
|
||||
if self.lnworker and self.lnworker.uses_trampoline() and not self.lnworker.is_trampoline_peer(self.node_id):
|
||||
return True
|
||||
return self.storage.get('frozen_for_receiving', False)
|
||||
|
||||
def set_frozen_for_receiving(self, b: bool) -> None:
|
||||
|
||||
@@ -2068,6 +2068,8 @@ class LNWallet(LNWorker):
|
||||
routing_hints = self.calc_routing_hints_for_invoice(amount_msat, channels=channels)
|
||||
self.logger.info(f"creating bolt11 invoice with routing_hints: {routing_hints}")
|
||||
invoice_features = self.features.for_invoice()
|
||||
if not self.uses_trampoline():
|
||||
invoice_features &= ~ LnFeatures.OPTION_TRAMPOLINE_ROUTING_OPT_ELECTRUM
|
||||
payment_secret = self.get_payment_secret(payment_hash)
|
||||
amount_btc = amount_msat/Decimal(COIN*1000) if amount_msat else None
|
||||
if expiry == 0:
|
||||
|
||||
@@ -143,7 +143,7 @@ def is_legacy_relay(invoice_features, r_tags) -> Tuple[bool, Set[bytes]]:
|
||||
# endpoints connected to T1 and T2, and sender only has send-capacity with T1, while
|
||||
# recipient only has recv-capacity with T2.
|
||||
singlehop_r_tags = [x for x in r_tags if len(x) == 1]
|
||||
invoice_trampolines = [x[0][0] for x in singlehop_r_tags if is_hardcoded_trampoline(x[0][0])]
|
||||
invoice_trampolines = [x[0][0] for x in singlehop_r_tags]
|
||||
invoice_trampolines = set(invoice_trampolines)
|
||||
if invoice_trampolines:
|
||||
return False, invoice_trampolines
|
||||
|
||||
Reference in New Issue
Block a user