URI: 
       trename lnworker._pay to pay_invoice, call it directly from GUIs - electrum - Electrum Bitcoin wallet
  HTML git clone https://git.parazyd.org/electrum
   DIR Log
   DIR Files
   DIR Refs
   DIR Submodules
       ---
   DIR commit 0c933945131a014420553b99c276c790dd099278
   DIR parent 9c4807644bf8bb0d2b777e9d02573e9b94db7c0f
  HTML Author: ThomasV <thomasv@electrum.org>
       Date:   Sun,  7 Feb 2021 12:09:37 +0100
       
       rename lnworker._pay to pay_invoice, call it directly from GUIs
       
       Diffstat:
         M electrum/commands.py                |       2 +-
         M electrum/gui/kivy/uix/screens.py    |       4 +++-
         M electrum/gui/qt/main_window.py      |       5 +++--
         M electrum/lnworker.py                |      10 +---------
         M electrum/submarine_swaps.py         |       4 ++--
         M electrum/tests/test_lnpeer.py       |      18 +++++++++---------
       
       6 files changed, 19 insertions(+), 24 deletions(-)
       ---
   DIR diff --git a/electrum/commands.py b/electrum/commands.py
       t@@ -1011,7 +1011,7 @@ class Commands:
                lnaddr = lnworker._check_invoice(invoice)
                payment_hash = lnaddr.paymenthash
                wallet.save_invoice(LNInvoice.from_bech32(invoice))
       -        success, log = await lnworker._pay(invoice, attempts=attempts)
       +        success, log = await lnworker.pay_invoice(invoice, attempts=attempts)
                return {
                    'payment_hash': payment_hash.hex(),
                    'success': success,
   DIR diff --git a/electrum/gui/kivy/uix/screens.py b/electrum/gui/kivy/uix/screens.py
       t@@ -367,7 +367,9 @@ class SendScreen(CScreen, Logger):
            def _do_pay_lightning(self, invoice: LNInvoice, pw) -> None:
                def pay_thread():
                    try:
       -                self.app.wallet.lnworker.pay(invoice.invoice, attempts=10)
       +                coro = self.app.wallet.lnworker.pay_invoice(invoice.invoice, attempts=10)
       +                fut = asyncio.run_coroutine_threadsafe(coro, self.app.network.asyncio_loop)
       +                fut.result()
                    except Exception as e:
                        self.app.show_error(repr(e))
                self.save_invoice(invoice)
   DIR diff --git a/electrum/gui/qt/main_window.py b/electrum/gui/qt/main_window.py
       t@@ -1523,9 +1523,10 @@ class ElectrumWindow(QMainWindow, MessageBoxMixin, Logger):
                if not self.question(msg):
                    return
                self.save_pending_invoice()
       -        attempts = LN_NUM_PAYMENT_ATTEMPTS
                def task():
       -            self.wallet.lnworker.pay(invoice, amount_msat=amount_msat, attempts=attempts)
       +            coro = self.wallet.lnworker.pay_invoice(invoice, amount_msat=amount_msat, attempts=LN_NUM_PAYMENT_ATTEMPTS)
       +            fut = asyncio.run_coroutine_threadsafe(coro, self.network.asyncio_loop)
       +            return fut.result()
                self.wallet.thread.add(task)
        
            def on_request_status(self, wallet, key, status):
   DIR diff --git a/electrum/lnworker.py b/electrum/lnworker.py
       t@@ -930,21 +930,13 @@ class LNWallet(LNWorker):
        
                return chan, funding_tx
        
       -    def pay(self, invoice: str, *, amount_msat: int = None, attempts: int = 1) -> Tuple[bool, List[HtlcLog]]:
       -        """
       -        Can be called from other threads
       -        """
       -        coro = self._pay(invoice, amount_msat=amount_msat, attempts=attempts)
       -        fut = asyncio.run_coroutine_threadsafe(coro, self.network.asyncio_loop)
       -        return fut.result()
       -
            def get_channel_by_short_id(self, short_channel_id: bytes) -> Optional[Channel]:
                for chan in self.channels.values():
                    if chan.short_channel_id == short_channel_id:
                        return chan
        
            @log_exceptions
       -    async def _pay(
       +    async def pay_invoice(
                    self, invoice: str, *,
                    amount_msat: int = None,
                    attempts: int = 1,
   DIR diff --git a/electrum/submarine_swaps.py b/electrum/submarine_swaps.py
       t@@ -418,9 +418,9 @@ class SwapManager(Logger):
                # initiate payment.
                if fee_invoice:
                    self.prepayments[prepay_hash] = preimage_hash
       -            asyncio.ensure_future(self.lnworker._pay(fee_invoice, attempts=10))
       +            asyncio.ensure_future(self.lnworker.pay_invoice(fee_invoice, attempts=10))
                # initiate payment.
       -        success, log = await self.lnworker._pay(invoice, attempts=10)
       +        success, log = await self.lnworker.pay_invoice(invoice, attempts=10)
                return success
        
            async def get_pairs(self) -> None:
   DIR diff --git a/electrum/tests/test_lnpeer.py b/electrum/tests/test_lnpeer.py
       t@@ -178,7 +178,7 @@ class MockLNWallet(Logger, NetworkRetryManager[LNPeerAddr]):
            create_routes_from_invoice = LNWallet.create_routes_from_invoice
            _check_invoice = staticmethod(LNWallet._check_invoice)
            pay_to_route = LNWallet.pay_to_route
       -    _pay = LNWallet._pay
       +    pay_invoice = LNWallet.pay_invoice
            force_close_channel = LNWallet.force_close_channel
            try_force_closing = LNWallet.try_force_closing
            get_first_timestamp = lambda self: 0
       t@@ -422,7 +422,7 @@ class TestPeer(ElectrumTestCase):
                p1, p2, w1, w2, _q1, _q2 = self.prepare_peers(alice_channel, bob_channel)
                pay_req = run(self.prepare_invoice(w2))
                async def pay():
       -            result, log = await w1._pay(pay_req)
       +            result, log = await w1.pay_invoice(pay_req)
                    self.assertEqual(result, True)
                    gath.cancel()
                gath = asyncio.gather(pay(), p1._message_loop(), p2._message_loop(), p1.htlc_switch(), p2.htlc_switch())
       t@@ -454,7 +454,7 @@ class TestPeer(ElectrumTestCase):
                alice_channel, bob_channel = create_test_channels()
                p1, p2, w1, w2, _q1, _q2 = self.prepare_peers(alice_channel, bob_channel)
                async def pay(pay_req):
       -            result, log = await w1._pay(pay_req)
       +            result, log = await w1.pay_invoice(pay_req)
                    self.assertTrue(result)
                    raise PaymentDone()
                async def f():
       t@@ -547,7 +547,7 @@ class TestPeer(ElectrumTestCase):
                max_htlcs_in_flight = asyncio.Semaphore(5)
                async def single_payment(pay_req):
                    async with max_htlcs_in_flight:
       -                await w1._pay(pay_req)
       +                await w1.pay_invoice(pay_req)
                async def many_payments():
                    async with TaskGroup() as group:
                        pay_reqs_tasks = [await group.spawn(self.prepare_invoice(w2, amount_msat=payment_value_msat))
       t@@ -572,7 +572,7 @@ class TestPeer(ElectrumTestCase):
                graph = self.prepare_chans_and_peers_in_square()
                peers = graph.all_peers()
                async def pay(pay_req):
       -            result, log = await graph.w_a._pay(pay_req)
       +            result, log = await graph.w_a.pay_invoice(pay_req)
                    self.assertTrue(result)
                    raise PaymentDone()
                async def f():
       t@@ -595,15 +595,15 @@ class TestPeer(ElectrumTestCase):
                        path = [PathEdge(node_id=graph.w_c.node_keypair.pubkey, short_channel_id=graph.chan_ab.short_channel_id),
                                PathEdge(node_id=graph.w_d.node_keypair.pubkey, short_channel_id=graph.chan_bd.short_channel_id)]
                        with self.assertRaises(LNPathInconsistent):
       -                    await graph.w_a._pay(pay_req, full_path=path)
       +                    await graph.w_a.pay_invoice(pay_req, full_path=path)
                    with self.subTest(msg="bad path: last node id differs from invoice pubkey"):
                        path = [PathEdge(node_id=graph.w_b.node_keypair.pubkey, short_channel_id=graph.chan_ab.short_channel_id)]
                        with self.assertRaises(LNPathInconsistent):
       -                    await graph.w_a._pay(pay_req, full_path=path)
       +                    await graph.w_a.pay_invoice(pay_req, full_path=path)
                    with self.subTest(msg="good path"):
                        path = [PathEdge(node_id=graph.w_b.node_keypair.pubkey, short_channel_id=graph.chan_ab.short_channel_id),
                                PathEdge(node_id=graph.w_d.node_keypair.pubkey, short_channel_id=graph.chan_bd.short_channel_id)]
       -                result, log = await graph.w_a._pay(pay_req, full_path=path)
       +                result, log = await graph.w_a.pay_invoice(pay_req, full_path=path)
                        self.assertTrue(result)
                        self.assertEqual(
                            [edge.short_channel_id for edge in path],
       t@@ -627,7 +627,7 @@ class TestPeer(ElectrumTestCase):
                graph.w_c.network.config.set_key('test_fail_htlcs_with_temp_node_failure', True)
                peers = graph.all_peers()
                async def pay(pay_req):
       -            result, log = await graph.w_a._pay(pay_req)
       +            result, log = await graph.w_a.pay_invoice(pay_req)
                    self.assertFalse(result)
                    self.assertEqual(OnionFailureCode.TEMPORARY_NODE_FAILURE, log[0].failure_msg.code)
                    raise PaymentDone()