1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185
|
#------------------------------------------------------------------------------
# Copyright (c) 2018-2024, Nucleic Development Team.
#
# Distributed under the terms of the Modified BSD License.
#
# The full license is in the file LICENSE, distributed with this software.
#------------------------------------------------------------------------------
import importlib
import os
import sys
import time
from importlib.machinery import ModuleSpec
from enaml.core.import_hooks import (AbstractEnamlImporter, EnamlImporter,
imports)
import pytest
# Test handling wrong loader type
class WrongEnamlImporter(AbstractEnamlImporter):
@classmethod
def locate_module(cls, fullname, path=None):
return object()
def get_code(self):
pass
@pytest.mark.parametrize('method', ('find_spec',))
def test_handling_wrong_locate_module_implementation(method):
"""Test handling a poorly implemented locate_module method.
"""
loader = WrongEnamlImporter()
with pytest.raises(ImportError):
getattr(loader, method)('module_name')
SOURCE =\
"""
from enaml.widgets.api import *
enamldef Main(Window):
Field: fd:
name = 'content'
"""
@pytest.fixture()
def enaml_module(tmpdir):
"""Create an enaml module in a tempdir and add it to sys.path.
"""
name = '__enaml_test_module__'
folder = str(tmpdir)
path = os.path.join(folder, name + '.enaml')
with open(path, 'w') as f:
f.write(SOURCE)
sys.path.append(folder)
yield name, folder, path
sys.path.remove(folder)
if name in sys.modules:
del sys.modules[name]
def test_import_and_cache_generation(enaml_module):
"""Test importing a module and checking that the cache was generated.
"""
name, folder, _ = enaml_module
with imports():
importlib.import_module(name)
assert name in sys.modules
# Check that the module attributes are properly populated
mod = sys.modules[name]
assert mod.__name__ == name
assert mod.__file__ == os.path.join(folder, name + ".enaml")
assert os.path.join(folder, "__enamlcache__") in mod.__cached__
assert isinstance(mod.__loader__, EnamlImporter)
assert isinstance(mod.__spec__, ModuleSpec)
cache_folder = os.path.join(folder, '__enamlcache__')
assert os.path.isdir(cache_folder)
cache_name = os.listdir(cache_folder)[0]
assert name in cache_name
assert '.enamlc' in cache_name
def test_import_when_cache_exists(enaml_module):
"""Test importing a module when the cache exists.
"""
name, folder, _ = enaml_module
assert name not in sys.modules
with imports():
importlib.import_module(name)
assert name in sys.modules
del sys.modules[name]
cache_folder = os.path.join(folder, '__enamlcache__')
assert os.path.isdir(cache_folder)
cache_name = os.listdir(cache_folder)[0]
cache_path = os.path.join(cache_folder, cache_name)
cache_time = os.path.getmtime(cache_path)
with imports():
importlib.import_module(name)
assert os.path.getmtime(cache_path) == cache_time
assert name in sys.modules
def test_import_cache_only(enaml_module):
"""Test importing a module for which we have no sources.
"""
name, _, path = enaml_module
with imports():
importlib.import_module(name)
assert name in sys.modules
del sys.modules[name]
os.remove(path)
with imports():
importlib.import_module(name)
assert name in sys.modules
def test_handling_importing_a_bugged_module(enaml_module):
"""Test that when importing a bugged module it does not stay in sys.modules
"""
name, _, path = enaml_module
with open(path, 'a') as f:
f.write('\nraise RuntimeError()')
assert name not in sys.modules
with imports():
with pytest.raises(RuntimeError):
importlib.import_module(name)
assert name not in sys.modules
@pytest.fixture
def enaml_importer():
"""Standard enaml importer whose state is restored after testing.
"""
print(imports, dir(imports))
old = imports.get_importers()
yield imports
imports._imports__importers = old
def test_importer_management(enaml_importer):
"""Test managing manually enaml importers.
"""
standard_importers_numbers = len(enaml_importer.get_importers())
enaml_importer.add_importer(WrongEnamlImporter)
assert WrongEnamlImporter in enaml_importer.get_importers()
enaml_importer.add_importer(WrongEnamlImporter)
assert (len(enaml_importer.get_importers()) ==
standard_importers_numbers + 1)
enaml_importer.remove_importer(WrongEnamlImporter)
# Test removing twice
enaml_importer.remove_importer(WrongEnamlImporter)
with pytest.raises(TypeError):
enaml_importer.add_importer(object)
|