From d5dbb2bae97f5372f3c4a17b303182bedbf24da0 Mon Sep 17 00:00:00 2001 From: zebra-lucky Date: Mon, 13 Oct 2025 16:31:22 +0300 Subject: [PATCH] Qt: fix async JMQtMessageBox usage part3 --- scripts/joinmarket-qt.py | 177 ++++++++++++++++++++++----------------- 1 file changed, 100 insertions(+), 77 deletions(-) diff --git a/scripts/joinmarket-qt.py b/scripts/joinmarket-qt.py index 9b8c23a..daac580 100755 --- a/scripts/joinmarket-qt.py +++ b/scripts/joinmarket-qt.py @@ -1336,7 +1336,8 @@ class TxHistoryTab(QWidget): hf = jm_single().config.get("GUI", "history_file") if not os.path.isfile(hf): if mainWindow: - mainWindow.statusBar().showMessage("No transaction history found.") + mainWindow.statusBar().showMessage( + "No transaction history found.") return [] txhist = [] with open(hf, 'rb') as f: @@ -1344,11 +1345,13 @@ class TxHistoryTab(QWidget): for tl in txlines: txhist.append(tl.decode('utf-8').strip().split(',')) if not len(txhist[-1]) == 4: - JMQtMessageBox(self, - "Incorrectedly formatted file " + hf, - mbtype='warn', - title="Error") - mainWindow.statusBar().showMessage("No transaction history found.") + asyncio.ensure_future( + JMQtMessageBox(self, + "Incorrectedly formatted file " + hf, + mbtype='warn', + title="Error")) + mainWindow.statusBar().showMessage( + "No transaction history found.") return [] return txhist[::-1 ] #appended to file in date order, window shows reverse @@ -1801,10 +1804,11 @@ class JMMainWindow(QMainWindow): """ Initializes BIP78 workflow with modal dialog. """ if not self.wallet_service: - JMQtMessageBox(self, - "No wallet loaded.", - mbtype='crit', - title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, + "No wallet loaded.", + mbtype='crit', + title="Error")) return self.receiver_bip78_dialog = ReceiveBIP78Dialog( self.startReceiver, self.stopReceiver) @@ -1822,14 +1826,17 @@ class JMMainWindow(QMainWindow): self.receiver_bip78_dialog.get_amount_text()) mixdepth = self.receiver_bip78_dialog.get_mixdepth() if mixdepth > self.wallet_service.mixdepth: - JMQtMessageBox(self, - "Wallet does not have mixdepth " + str(mixdepth), - mbtype='crit', title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, + "Wallet does not have mixdepth " + + str(mixdepth), + mbtype='crit', title="Error")) return False if self.wallet_service.get_balance_by_mixdepth(minconfs=1)[mixdepth] == 0: - JMQtMessageBox(self, "Mixdepth " + str(mixdepth) + \ - " has no confirmed coins.", - mbtype='crit', title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, "Mixdepth " + str(mixdepth) + + " has no confirmed coins.", + mbtype='crit', title="Error")) return False self.backend_receiver = JMBIP78ReceiverManager(self.wallet_service, mixdepth, amount, 80, self.receiver_bip78_dialog.info_update, @@ -1885,10 +1892,11 @@ class JMMainWindow(QMainWindow): async def exportPrivkeysJson(self): if not self.wallet_service: - JMQtMessageBox(self, - "No wallet loaded.", - mbtype='crit', - title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, + "No wallet loaded.", + mbtype='crit', + title="Error")) return #TODO add password protection; too critical d = QDialog(self) @@ -1969,25 +1977,34 @@ class JMMainWindow(QMainWindow): # sanity check rawpriv, _ = BTCEngine.wif_to_privkey(pk) if not addr == self.wallet_service._ENGINE.privkey_to_address(rawpriv): - JMQtMessageBox(None, "Failed to create privkey export -" +\ - " critical error in key parsing.", - mbtype='crit') + asyncio.ensure_future( + JMQtMessageBox( + None, + "Failed to create privkey export -" + " critical error in key parsing.", + mbtype='crit')) return f.write(json.dumps(private_keys, indent=4).encode('utf-8')) except (IOError, os.error) as reason: export_error_label = "JoinmarketQt was unable to produce a private key-export." - JMQtMessageBox(None, - export_error_label + "\n" + str(reason), - mbtype='crit', - title="Unable to create json file") + asyncio.ensure_future( + JMQtMessageBox(None, + export_error_label + "\n" + str(reason), + mbtype='crit', + title="Unable to create json file")) except Exception as er: - JMQtMessageBox(self, str(er), mbtype='crit', title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, str(er), mbtype='crit', title="Error")) return - JMQtMessageBox(self, - "Private keys exported to: " + os.path.join(jm_single().datadir, - privkeys_fn) + '.json', title="Success") + asyncio.ensure_future( + JMQtMessageBox(self, + "Private keys exported to: " + + os.path.join( + jm_single().datadir, privkeys_fn) + + '.json', + title="Success")) def seedEntry(self) -> Tuple[Optional[str], Optional[str]]: d = QDialog(self) @@ -2036,12 +2053,14 @@ class JMMainWindow(QMainWindow): msg = "New utxo has been automatically " +\ "frozen to prevent forced address reuse:\n" + utxostr +\ "\n You can unfreeze this utxo via the Coins tab." - JMQtMessageBox(self, msg, mbtype='info', - title="New utxo frozen") + asyncio.ensure_future( + JMQtMessageBox(self, msg, mbtype='info', + title="New utxo frozen")) def restartWithMsg(self, msg): - JMQtMessageBox(self, msg, mbtype='info', - title="Restart") + asyncio.ensure_future( + JMQtMessageBox(self, msg, mbtype='info', + title="Restart")) self.close() async def recoverWallet(self): @@ -2057,17 +2076,16 @@ class JMMainWindow(QMainWindow): enter_seed_extension_callback=None, enter_do_support_fidelity_bonds=lambda: False) if not success: - JMQtMessageBox(self, - "Failed to recover wallet.", - mbtype='warn', - title="Error") + await JMQtMessageBox(self, + "Failed to recover wallet.", + mbtype='warn', title="Error") return except Exception as e: - JMQtMessageBox(self, e.args[0], title="Error", mbtype="warn") + await JMQtMessageBox(self, e.args[0], title="Error", mbtype="warn") return - JMQtMessageBox(self, 'Wallet saved to ' + self.walletname, - title="Wallet created") + await JMQtMessageBox(self, 'Wallet saved to ' + self.walletname, + title="Wallet created") await self.initWallet(seed=self.walletname) async def openWallet(self): @@ -2119,10 +2137,8 @@ class JMMainWindow(QMainWindow): decrypted = await self.loadWalletFromBlockchain( firstarg[0], pwd) except Exception as e: - JMQtMessageBox(self, - str(e), - mbtype='warn', - title="Error") + await JMQtMessageBox(self, str(e), + mbtype='warn', title="Error") return if decrypted == "error": # special case, not a failure to decrypt the file but @@ -2154,10 +2170,8 @@ class JMMainWindow(QMainWindow): if rethrow: raise e else: - JMQtMessageBox(self, - str(e), - mbtype='warn', - title="Error") + await JMQtMessageBox(self, str(e), + mbtype='warn', title="Error") return False # only used for GUI display on regtest: self.testwalletname = wallet.seed = str(firstarg) @@ -2177,8 +2191,8 @@ class JMMainWindow(QMainWindow): # in case an RPC error occurs in the constructor: if self.wallet_service.rpc_error: - JMQtMessageBox(self,self.wallet_service.rpc_error, - mbtype='warn',title="Error") + await JMQtMessageBox(self,self.wallet_service.rpc_error, + mbtype='warn',title="Error") return "error" if jm_single().bc_interface is None: @@ -2209,11 +2223,12 @@ class JMMainWindow(QMainWindow): if not self.wallet_service: #failure to sync in constructor means object is not created newsyncmsg = "Unable to sync wallet - see error in console." elif not self.wallet_service.isRunning(): - JMQtMessageBox(self, - "The Joinmarket wallet service has stopped; this is usually caused " - "by a Bitcoin Core RPC connection failure. Is your node running?", - mbtype='crit', - title="Error") + await JMQtMessageBox( + self, + "The Joinmarket wallet service has stopped; this is usually " + "caused by a Bitcoin Core RPC connection failure. " + "Is your node running?", + mbtype='crit', title="Error") qApp.exit(EXIT_FAILURE) return elif not self.wallet_service.synced: @@ -2261,48 +2276,56 @@ class JMMainWindow(QMainWindow): pwd = str(text).strip().encode('utf-8') match = self.wallet_service.check_wallet_passphrase(pwd) if not match: - JMQtMessageBox(self, - "Wrong passphrase.", mbtype='warn', title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, "Wrong passphrase.", + mbtype='warn', title="Error")) return True def changePassphrase(self): if not self.wallet_service: - JMQtMessageBox(self, "Cannot change passphrase without loaded wallet.", - mbtype="crit", title="Error") + asyncio.ensure_future( + JMQtMessageBox( + self, "Cannot change passphrase without loaded wallet.", + mbtype="crit", title="Error")) return if not (self.checkPassphrase() and wallet_change_passphrase(self.wallet_service, self.getPassword)): - JMQtMessageBox(self, "Failed to change passphrase.", - title="Error", mbtype="warn") + asyncio.ensure_future( + JMQtMessageBox(self, "Failed to change passphrase.", + title="Error", mbtype="warn")) return - JMQtMessageBox(self, "Passphrase changed successfully.", - title="Passphrase changed") + asyncio.ensure_future( + JMQtMessageBox(self, "Passphrase changed successfully.", + title="Passphrase changed")) def getTestnetSeed(self): text, ok = QInputDialog.getText( self, 'Testnet seed', 'Enter a 32 char hex string as seed:') if not ok or not text: - JMQtMessageBox(self, - "No seed entered, aborting", - mbtype='warn', - title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, + "No seed entered, aborting", + mbtype='warn', + title="Error")) return return str(text).strip() def showSeedDialog(self): if not self.wallet_service: - JMQtMessageBox(self, - "No wallet loaded.", - mbtype='crit', - title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, + "No wallet loaded.", + mbtype='crit', + title="Error")) return try: self.displayWords(*self.wallet_service.get_mnemonic_words()) except NotImplementedError: - JMQtMessageBox(self, - "Wallet does not support seed phrases", - mbtype='info', - title="Error") + asyncio.ensure_future( + JMQtMessageBox(self, + "Wallet does not support seed phrases", + mbtype='info', + title="Error")) def getPassword(self) -> str: pd = PasswordDialog()