diff options
author | Barry Warsaw <barry@python.org> | 2017-12-30 20:18:06 (GMT) |
---|---|---|
committer | GitHub <noreply@github.com> | 2017-12-30 20:18:06 (GMT) |
commit | deae6b451fefd5fd3143dd65051e1d341e5a5f84 (patch) | |
tree | 21d0732eb5dd8f7d5ca469b39a1f3b703f3f83f3 /Lib/test/test_importlib/util.py | |
parent | ffcb4c0165827d0a48ea973cc88bc134c74879fb (diff) | |
download | cpython-deae6b451fefd5fd3143dd65051e1d341e5a5f84.zip cpython-deae6b451fefd5fd3143dd65051e1d341e5a5f84.tar.gz cpython-deae6b451fefd5fd3143dd65051e1d341e5a5f84.tar.bz2 |
bpo-32248 - Implement importlib.resources (#4911)
Port importlib_resources to importlib.resources
Diffstat (limited to 'Lib/test/test_importlib/util.py')
-rw-r--r-- | Lib/test/test_importlib/util.py | 163 |
1 files changed, 163 insertions, 0 deletions
diff --git a/Lib/test/test_importlib/util.py b/Lib/test/test_importlib/util.py index 64e039e..bfb7cad 100644 --- a/Lib/test/test_importlib/util.py +++ b/Lib/test/test_importlib/util.py @@ -1,17 +1,24 @@ +import abc import builtins import contextlib import errno import functools import importlib from importlib import machinery, util, invalidate_caches +from importlib.abc import ResourceReader +import io import os import os.path +from pathlib import Path, PurePath from test import support import unittest import sys import tempfile import types +from . import data01 +from . import zipdata01 + BUILTINS = types.SimpleNamespace() BUILTINS.good_name = None @@ -386,3 +393,159 @@ class CASEOKTestBase: if any(x in self.importlib._bootstrap_external._os.environ for x in possibilities) != should_exist: self.skipTest('os.environ changes not reflected in _os.environ') + + +def create_package(file, path, is_package=True, contents=()): + class Reader(ResourceReader): + def open_resource(self, path): + self._path = path + if isinstance(file, Exception): + raise file + else: + return file + + def resource_path(self, path_): + self._path = path_ + if isinstance(path, Exception): + raise path + else: + return path + + def is_resource(self, path_): + self._path = path_ + if isinstance(path, Exception): + raise path + for entry in contents: + parts = entry.split('/') + if len(parts) == 1 and parts[0] == path_: + return True + return False + + def contents(self): + if isinstance(path, Exception): + raise path + # There's no yield from in baseball, er, Python 2. + for entry in contents: + yield entry + + name = 'testingpackage' + # Unforunately importlib.util.module_from_spec() was not introduced until + # Python 3.5. + module = types.ModuleType(name) + loader = Reader() + spec = machinery.ModuleSpec( + name, loader, + origin='does-not-exist', + is_package=is_package) + module.__spec__ = spec + module.__loader__ = loader + return module + + +class CommonResourceTests(abc.ABC): + @abc.abstractmethod + def execute(self, package, path): + raise NotImplementedError + + def test_package_name(self): + # Passing in the package name should succeed. + self.execute(data01.__name__, 'utf-8.file') + + def test_package_object(self): + # Passing in the package itself should succeed. + self.execute(data01, 'utf-8.file') + + def test_string_path(self): + # Passing in a string for the path should succeed. + path = 'utf-8.file' + self.execute(data01, path) + + @unittest.skipIf(sys.version_info < (3, 6), 'requires os.PathLike support') + def test_pathlib_path(self): + # Passing in a pathlib.PurePath object for the path should succeed. + path = PurePath('utf-8.file') + self.execute(data01, path) + + def test_absolute_path(self): + # An absolute path is a ValueError. + path = Path(__file__) + full_path = path.parent/'utf-8.file' + with self.assertRaises(ValueError): + self.execute(data01, full_path) + + def test_relative_path(self): + # A reative path is a ValueError. + with self.assertRaises(ValueError): + self.execute(data01, '../data01/utf-8.file') + + def test_importing_module_as_side_effect(self): + # The anchor package can already be imported. + del sys.modules[data01.__name__] + self.execute(data01.__name__, 'utf-8.file') + + def test_non_package_by_name(self): + # The anchor package cannot be a module. + with self.assertRaises(TypeError): + self.execute(__name__, 'utf-8.file') + + def test_non_package_by_package(self): + # The anchor package cannot be a module. + with self.assertRaises(TypeError): + module = sys.modules['test.test_importlib.util'] + self.execute(module, 'utf-8.file') + + @unittest.skipIf(sys.version_info < (3,), 'No ResourceReader in Python 2') + def test_resource_opener(self): + bytes_data = io.BytesIO(b'Hello, world!') + package = create_package(file=bytes_data, path=FileNotFoundError()) + self.execute(package, 'utf-8.file') + self.assertEqual(package.__loader__._path, 'utf-8.file') + + @unittest.skipIf(sys.version_info < (3,), 'No ResourceReader in Python 2') + def test_resource_path(self): + bytes_data = io.BytesIO(b'Hello, world!') + path = __file__ + package = create_package(file=bytes_data, path=path) + self.execute(package, 'utf-8.file') + self.assertEqual(package.__loader__._path, 'utf-8.file') + + def test_useless_loader(self): + package = create_package(file=FileNotFoundError(), + path=FileNotFoundError()) + with self.assertRaises(FileNotFoundError): + self.execute(package, 'utf-8.file') + + +class ZipSetupBase: + ZIP_MODULE = None + + @classmethod + def setUpClass(cls): + data_path = Path(cls.ZIP_MODULE.__file__) + data_dir = data_path.parent + cls._zip_path = str(data_dir / 'ziptestdata.zip') + sys.path.append(cls._zip_path) + cls.data = importlib.import_module('ziptestdata') + + @classmethod + def tearDownClass(cls): + try: + sys.path.remove(cls._zip_path) + except ValueError: + pass + + try: + del sys.path_importer_cache[cls._zip_path] + del sys.modules[cls.data.__name__] + except KeyError: + pass + + try: + del cls.data + del cls._zip_path + except AttributeError: + pass + + +class ZipSetup(ZipSetupBase): + ZIP_MODULE = zipdata01 # type: ignore |