commit 386e0d560eee1ad82380c4000d2afa8e6a07963c
parent 4f7283a3b0b3301195f68cca915db2c49d410a15
Author: SomberNight <somber.night@protonmail.com>
Date: Wed, 31 Oct 2018 17:58:47 +0100
wizard,hw: tell user about errors during plugin init
see #4817 (issuecomment-434765570)
Diffstat:
3 files changed, 42 insertions(+), 20 deletions(-)
diff --git a/electrum/base_wizard.py b/electrum/base_wizard.py
@@ -228,14 +228,7 @@ class BaseWizard(object):
def choose_hw_device(self, purpose=HWD_SETUP_NEW_WALLET):
title = _('Hardware Keystore')
# check available plugins
- support = self.plugins.get_hardware_support()
- if not support:
- msg = '\n'.join([
- _('No hardware wallet support found on your system.'),
- _('Please install the relevant libraries (eg python-trezor for Trezor).'),
- ])
- self.confirm_dialog(title=title, message=msg, run_next= lambda x: self.choose_hw_device(purpose))
- return
+ supported_plugins = self.plugins.get_hardware_support()
# scan devices
devices = []
devmgr = self.plugins.device_manager
@@ -246,14 +239,24 @@ class BaseWizard(object):
debug_msg = ' {}:\n {}'.format(_('Error scanning devices'), e)
else:
debug_msg = ''
- for name, description, plugin in support:
+ for splugin in supported_plugins:
+ name, plugin = splugin.name, splugin.plugin
+ # plugin init errored?
+ if not plugin:
+ e = splugin.exception
+ indented_error_msg = ' '.join([''] + str(e).splitlines(keepends=True))
+ debug_msg += f' {name}: (error during plugin init)\n'
+ debug_msg += ' {}\n'.format(_('You might have an incompatible library.'))
+ debug_msg += f'{indented_error_msg}\n'
+ continue
+ # see if plugin recognizes 'scanned_devices'
try:
# FIXME: side-effect: unpaired_device_info sets client.handler
u = devmgr.unpaired_device_infos(None, plugin, devices=scanned_devices)
except BaseException as e:
- devmgr.print_error('error getting device infos for {}: {}'.format(name, e))
+ devmgr.print_error(f'error getting device infos for {name}: {e}')
indented_error_msg = ' '.join([''] + str(e).splitlines(keepends=True))
- debug_msg += ' {}:\n{}\n'.format(plugin.name, indented_error_msg)
+ debug_msg += f' {name}: (error getting device infos)\n{indented_error_msg}\n'
continue
devices += list(map(lambda x: (name, x), u))
if not debug_msg:
diff --git a/electrum/plugin.py b/electrum/plugin.py
@@ -28,7 +28,7 @@ import os
import pkgutil
import time
import threading
-from typing import NamedTuple, Any, Union
+from typing import NamedTuple, Any, Union, TYPE_CHECKING, Optional
from .i18n import _
from .util import (profiler, PrintError, DaemonThread, UserCancelled,
@@ -37,6 +37,9 @@ from . import bip32
from . import plugins
from .simple_config import SimpleConfig
+if TYPE_CHECKING:
+ from .plugins.hw_wallet import HW_PluginBase
+
plugin_loaders = {}
hook_names = set()
@@ -148,10 +151,17 @@ class Plugins(DaemonThread):
try:
p = self.get_plugin(name)
if p.is_enabled():
- out.append([name, details[2], p])
- except:
+ out.append(HardwarePluginToScan(name=name,
+ description=details[2],
+ plugin=p,
+ exception=None))
+ except Exception as e:
traceback.print_exc()
self.print_error("cannot load plugin for:", name)
+ out.append(HardwarePluginToScan(name=name,
+ description=details[2],
+ plugin=None,
+ exception=e))
return out
def register_wallet_type(self, name, gui_good, wallet_type):
@@ -277,6 +287,13 @@ class DeviceInfo(NamedTuple):
initialized: bool
+class HardwarePluginToScan(NamedTuple):
+ name: str
+ description: str
+ plugin: Optional['HW_PluginBase']
+ exception: Optional[Exception]
+
+
class DeviceMgr(ThreadJob, PrintError):
'''Manages hardware clients. A client communicates over a hardware
channel with the device.
diff --git a/run_electrum b/run_electrum
@@ -165,18 +165,20 @@ def init_cmdline(config_options, server):
def get_connected_hw_devices(plugins):
- support = plugins.get_hardware_support()
- if not support:
- print_msg('No hardware wallet support found on your system.')
- sys.exit(1)
+ supported_plugins = plugins.get_hardware_support()
# scan devices
devices = []
devmgr = plugins.device_manager
- for name, description, plugin in support:
+ for splugin in supported_plugins:
+ name, plugin = splugin.name, splugin.plugin
+ if not plugin:
+ e = splugin.exception
+ print_stderr(f"{name}: error during plugin init: {repr(e)}")
+ continue
try:
u = devmgr.unpaired_device_infos(None, plugin)
except:
- devmgr.print_error("error", name)
+ devmgr.print_error(f'error getting device infos for {name}: {e}')
continue
devices += list(map(lambda x: (name, x), u))
return devices