Skip to content

Commit

Permalink
plugin.py electrum backports
Browse files Browse the repository at this point in the history
This is a backport of
> plugins: when loading plugins, use newer importlib mechanism
spesmilo@e04e8d2

> plugins: on some systems plugins with relative imports failed to load
spesmilo@811169d

It fixes the windows binary which was broken when upgrading pyinstaller to 4.10.
  • Loading branch information
PiRK committed Jan 11, 2023
1 parent 7466ca0 commit 989e161
Showing 1 changed file with 28 additions and 19 deletions.
47 changes: 28 additions & 19 deletions electroncash/plugins.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
# It is no longer needed for python 3.8+.
import concurrent
import concurrent.futures
import importlib.util
import json
import os
import pkgutil
Expand Down Expand Up @@ -169,14 +170,20 @@ def load_internal_plugins(self):
for loader, name, ispkg in pkgutil.iter_modules(
[self.internal_plugins_pkgpath]
):
# do not load deprecated plugins
if name in ["plot", "exchange_rate"]:
continue
# do not load plugins that rely on untrusted servers, for now
if name in ["labels", "cosigner_pool"]:
continue
m = loader.find_module(name).load_module(name)
d = m.__dict__
full_name = f"electroncash_plugins.{name}"
spec = importlib.util.find_spec(full_name)
# pkgutil found it but importlib can't ?!
if spec is None:
raise Exception(f"Error pre-loading {full_name}: no spec")
try:
module = importlib.util.module_from_spec(spec)
# sys.modules needs to be modified for relative imports to work
# see https://stackoverflow.com/a/50395128
sys.modules[spec.name] = module
spec.loader.exec_module(module)
except Exception as e:
raise Exception(f"Error pre-loading {full_name}: {repr(e)}") from e
d = module.__dict__
if not self.register_plugin(name, d):
continue
self.internal_plugin_metadata[name] = d
Expand Down Expand Up @@ -257,14 +264,15 @@ def load_internal_plugin(self, name):
if name in self.internal_plugins:
return self.internal_plugins[name]

full_name = "electroncash_plugins." + name + "." + self.gui_name
loader = pkgutil.find_loader(full_name)
if not loader:
full_name = f"electroncash_plugins.{name}.{self.gui_name}"
spec = importlib.util.find_spec(full_name)
if spec is None:
raise RuntimeError(
"%s implementation for %s plugin not found" % (self.gui_name, name)
)
p = loader.load_module(full_name)
plugin = p.Plugin(self, self.config, name)
module = importlib.util.module_from_spec(spec)
spec.loader.exec_module(module)
plugin = module.Plugin(self, self.config, name)
plugin.set_enabled_prefix(INTERNAL_USE_PREFIX)
self.add_jobs(plugin.thread_jobs())
self.internal_plugins[name] = plugin
Expand Down Expand Up @@ -298,16 +306,17 @@ def load_external_plugin(self, name):
)
return

sys.modules["electroncash_external_plugins." + name] = module
sys.modules[f"electroncash_external_plugins.{name}"] = module

full_name = "electroncash_external_plugins." + name + "." + self.gui_name
loader = pkgutil.find_loader(full_name)
if not loader:
full_name = f"electroncash_external_plugins.{name}.{self.gui_name}"
spec = importlib.util.find_spec(full_name)
if spec is None:
raise RuntimeError(
"%s implementation for %s plugin not found" % (self.gui_name, name)
)
p = loader.load_module(full_name)
plugin = p.Plugin(self, self.config, name)
module = importlib.util.module_from_spec(spec)
spec.loader.exec_module(module)
plugin = module.Plugin(self, self.config, name)
plugin.set_enabled_prefix(EXTERNAL_USE_PREFIX)
self.add_jobs(plugin.thread_jobs())
self.external_plugins[name] = plugin
Expand Down

0 comments on commit 989e161

Please sign in to comment.