From e2338581eb5f0aa2320a793e96db8ee38de2517f Mon Sep 17 00:00:00 2001 From: SomberNight Date: Mon, 10 Sep 2018 18:39:10 +0200 Subject: [PATCH] broadcast_transaction: introduce async variant --- electrum/commands.py | 2 +- electrum/gui/kivy/main_window.py | 2 +- electrum/gui/qt/main_window.py | 2 +- electrum/gui/stdio.py | 2 +- electrum/gui/text.py | 2 +- electrum/network.py | 10 +++++++--- 6 files changed, 12 insertions(+), 8 deletions(-) diff --git a/electrum/commands.py b/electrum/commands.py index e2cf87a26..1e38b1024 100644 --- a/electrum/commands.py +++ b/electrum/commands.py @@ -255,7 +255,7 @@ class Commands: def broadcast(self, tx): """Broadcast a transaction to the network. """ tx = Transaction(tx) - return self.network.broadcast_transaction(tx) + return self.network.broadcast_transaction_from_non_network_thread(tx) @command('') def createmultisig(self, num, pubkeys): diff --git a/electrum/gui/kivy/main_window.py b/electrum/gui/kivy/main_window.py index e100fba18..9ccabfbb8 100644 --- a/electrum/gui/kivy/main_window.py +++ b/electrum/gui/kivy/main_window.py @@ -880,7 +880,7 @@ class ElectrumWindow(App): Clock.schedule_once(lambda dt: on_success(tx)) def _broadcast_thread(self, tx, on_complete): - ok, txid = self.network.broadcast_transaction(tx) + ok, txid = self.network.broadcast_transaction_from_non_network_thread(tx) Clock.schedule_once(lambda dt: on_complete(ok, txid)) def broadcast(self, tx, pr=None): diff --git a/electrum/gui/qt/main_window.py b/electrum/gui/qt/main_window.py index 539b72293..22d7144e8 100644 --- a/electrum/gui/qt/main_window.py +++ b/electrum/gui/qt/main_window.py @@ -1616,7 +1616,7 @@ class ElectrumWindow(QMainWindow, MessageBoxMixin, PrintError): if pr and pr.has_expired(): self.payment_request = None return False, _("Payment request has expired") - status, msg = self.network.broadcast_transaction(tx) + status, msg = self.network.broadcast_transaction_from_non_network_thread(tx) if pr and status is True: self.invoices.set_paid(pr, tx.txid()) self.invoices.save() diff --git a/electrum/gui/stdio.py b/electrum/gui/stdio.py index d155efb08..d3d16342c 100644 --- a/electrum/gui/stdio.py +++ b/electrum/gui/stdio.py @@ -200,7 +200,7 @@ class ElectrumGui: self.wallet.labels[tx.txid()] = self.str_description print(_("Please wait...")) - status, msg = self.network.broadcast_transaction(tx) + status, msg = self.network.broadcast_transaction_from_non_network_thread(tx) if status: print(_('Payment sent.')) diff --git a/electrum/gui/text.py b/electrum/gui/text.py index c27eb2df0..d00528ccc 100644 --- a/electrum/gui/text.py +++ b/electrum/gui/text.py @@ -354,7 +354,7 @@ class ElectrumGui: self.wallet.labels[tx.txid()] = self.str_description self.show_message(_("Please wait..."), getchar=False) - status, msg = self.network.broadcast_transaction(tx) + status, msg = self.network.broadcast_transaction_from_non_network_thread(tx) if status: self.show_message(_('Payment sent.')) diff --git a/electrum/network.py b/electrum/network.py index e6f77d614..89ab8ff64 100644 --- a/electrum/network.py +++ b/electrum/network.py @@ -671,10 +671,14 @@ class Network(PrintError): async def get_merkle_for_transaction(self, tx_hash, tx_height): return await self.interface.session.send_request('blockchain.transaction.get_merkle', [tx_hash, tx_height]) - def broadcast_transaction(self, tx, timeout=5): - fut = asyncio.run_coroutine_threadsafe(self.interface.session.send_request('blockchain.transaction.broadcast', [str(tx)]), self.asyncio_loop) + def broadcast_transaction_from_non_network_thread(self, tx, timeout=10): + # note: calling this from the network thread will deadlock it + fut = asyncio.run_coroutine_threadsafe(self.broadcast_transaction(tx, timeout=timeout), self.asyncio_loop) + return fut.result() + + async def broadcast_transaction(self, tx, timeout=10): try: - out = fut.result(timeout) + out = await self.interface.session.send_request('blockchain.transaction.broadcast', [str(tx)], timeout=timeout) except asyncio.TimeoutError as e: return False, "error: operation timed out" except Exception as e: