PY-32005 Importing matplotlib 3.0.0 crashes Python Console

Wait for full pyplot import to get access to `matplotlib.rcParams` attribute, which was changed in version 3
This commit is contained in:
Elizaveta Shashkova
2018-10-22 12:50:54 +03:00
parent 9621ea78cb
commit 7b2b8e5466
2 changed files with 19 additions and 2 deletions
@@ -8,6 +8,7 @@ class ImportHookManager(ModuleType):
ModuleType.__init__(self, name)
self._system_import = system_import
self._modules_to_patch = {}
self.inside_activation = False
def add_module_name(self, module_name, activate_function):
self._modules_to_patch[module_name] = activate_function
@@ -19,11 +20,13 @@ class ImportHookManager(ModuleType):
module = self._system_import(name, *args, **kwargs)
try:
if activate_func:
if activate_func and not self.inside_activation:
self.inside_activation = True
succeeded = activate_func()
if succeeded and name in self._modules_to_patch:
# Remove if only it was executed correctly
self._modules_to_patch.pop(name)
self.inside_activation = False
except:
sys.stderr.write("Matplotlib support failed\n")
traceback.print_exc()
@@ -38,4 +41,4 @@ else:
import_hook_manager = ImportHookManager(__name__ + '.import_hook', builtins.__import__)
builtins.__import__ = import_hook_manager.do_import
sys.modules[import_hook_manager.__name__] = import_hook_manager
del builtins
del builtins
@@ -85,6 +85,10 @@ def patch_is_interactive():
matplotlib.is_interactive = patched_is_interactive
def _get_major_version(module):
return int(module.__version__.split('.')[0])
def activate_matplotlib(enable_gui_function):
"""Set interactive to True for interactive backends.
enable_gui_function - Function which enables gui, should be run in the main thread.
@@ -93,6 +97,16 @@ def activate_matplotlib(enable_gui_function):
if not hasattr(matplotlib, 'rcParams'):
# matplotlib module wasn't fully imported, try later
return False
if _get_major_version(matplotlib) >= 3:
# since matplotlib 3.0, accessing `matplotlib.rcParams` lead to pyplot import,
# so we need to wait until necessary pyplot attributes will be imported as well
if 'matplotlib.pyplot' not in sys.modules:
return False
pyplot = sys.modules['matplotlib.pyplot']
if not hasattr(pyplot, 'switch_backend'):
return False
gui, backend = find_gui_and_backend()
is_interactive = is_interactive_backend(backend)
if is_interactive: