17db96d56Sopenharmony_ciimport sys
27db96d56Sopenharmony_ciimport unittest
37db96d56Sopenharmony_ciimport uuid
47db96d56Sopenharmony_ciimport pathlib
57db96d56Sopenharmony_ci
67db96d56Sopenharmony_cifrom . import data01
77db96d56Sopenharmony_cifrom . import zipdata01, zipdata02
87db96d56Sopenharmony_cifrom .resources import util
97db96d56Sopenharmony_cifrom importlib import resources, import_module
107db96d56Sopenharmony_cifrom test.support import import_helper
117db96d56Sopenharmony_cifrom test.support.os_helper import unlink
127db96d56Sopenharmony_ci
137db96d56Sopenharmony_ci
147db96d56Sopenharmony_ciclass ResourceTests:
157db96d56Sopenharmony_ci    # Subclasses are expected to set the `data` attribute.
167db96d56Sopenharmony_ci
177db96d56Sopenharmony_ci    def test_is_file_exists(self):
187db96d56Sopenharmony_ci        target = resources.files(self.data) / 'binary.file'
197db96d56Sopenharmony_ci        self.assertTrue(target.is_file())
207db96d56Sopenharmony_ci
217db96d56Sopenharmony_ci    def test_is_file_missing(self):
227db96d56Sopenharmony_ci        target = resources.files(self.data) / 'not-a-file'
237db96d56Sopenharmony_ci        self.assertFalse(target.is_file())
247db96d56Sopenharmony_ci
257db96d56Sopenharmony_ci    def test_is_dir(self):
267db96d56Sopenharmony_ci        target = resources.files(self.data) / 'subdirectory'
277db96d56Sopenharmony_ci        self.assertFalse(target.is_file())
287db96d56Sopenharmony_ci        self.assertTrue(target.is_dir())
297db96d56Sopenharmony_ci
307db96d56Sopenharmony_ci
317db96d56Sopenharmony_ciclass ResourceDiskTests(ResourceTests, unittest.TestCase):
327db96d56Sopenharmony_ci    def setUp(self):
337db96d56Sopenharmony_ci        self.data = data01
347db96d56Sopenharmony_ci
357db96d56Sopenharmony_ci
367db96d56Sopenharmony_ciclass ResourceZipTests(ResourceTests, util.ZipSetup, unittest.TestCase):
377db96d56Sopenharmony_ci    pass
387db96d56Sopenharmony_ci
397db96d56Sopenharmony_ci
407db96d56Sopenharmony_cidef names(traversable):
417db96d56Sopenharmony_ci    return {item.name for item in traversable.iterdir()}
427db96d56Sopenharmony_ci
437db96d56Sopenharmony_ci
447db96d56Sopenharmony_ciclass ResourceLoaderTests(unittest.TestCase):
457db96d56Sopenharmony_ci    def test_resource_contents(self):
467db96d56Sopenharmony_ci        package = util.create_package(
477db96d56Sopenharmony_ci            file=data01, path=data01.__file__, contents=['A', 'B', 'C']
487db96d56Sopenharmony_ci        )
497db96d56Sopenharmony_ci        self.assertEqual(names(resources.files(package)), {'A', 'B', 'C'})
507db96d56Sopenharmony_ci
517db96d56Sopenharmony_ci    def test_is_file(self):
527db96d56Sopenharmony_ci        package = util.create_package(
537db96d56Sopenharmony_ci            file=data01, path=data01.__file__, contents=['A', 'B', 'C', 'D/E', 'D/F']
547db96d56Sopenharmony_ci        )
557db96d56Sopenharmony_ci        self.assertTrue(resources.files(package).joinpath('B').is_file())
567db96d56Sopenharmony_ci
577db96d56Sopenharmony_ci    def test_is_dir(self):
587db96d56Sopenharmony_ci        package = util.create_package(
597db96d56Sopenharmony_ci            file=data01, path=data01.__file__, contents=['A', 'B', 'C', 'D/E', 'D/F']
607db96d56Sopenharmony_ci        )
617db96d56Sopenharmony_ci        self.assertTrue(resources.files(package).joinpath('D').is_dir())
627db96d56Sopenharmony_ci
637db96d56Sopenharmony_ci    def test_resource_missing(self):
647db96d56Sopenharmony_ci        package = util.create_package(
657db96d56Sopenharmony_ci            file=data01, path=data01.__file__, contents=['A', 'B', 'C', 'D/E', 'D/F']
667db96d56Sopenharmony_ci        )
677db96d56Sopenharmony_ci        self.assertFalse(resources.files(package).joinpath('Z').is_file())
687db96d56Sopenharmony_ci
697db96d56Sopenharmony_ci
707db96d56Sopenharmony_ciclass ResourceCornerCaseTests(unittest.TestCase):
717db96d56Sopenharmony_ci    def test_package_has_no_reader_fallback(self):
727db96d56Sopenharmony_ci        # Test odd ball packages which:
737db96d56Sopenharmony_ci        # 1. Do not have a ResourceReader as a loader
747db96d56Sopenharmony_ci        # 2. Are not on the file system
757db96d56Sopenharmony_ci        # 3. Are not in a zip file
767db96d56Sopenharmony_ci        module = util.create_package(
777db96d56Sopenharmony_ci            file=data01, path=data01.__file__, contents=['A', 'B', 'C']
787db96d56Sopenharmony_ci        )
797db96d56Sopenharmony_ci        # Give the module a dummy loader.
807db96d56Sopenharmony_ci        module.__loader__ = object()
817db96d56Sopenharmony_ci        # Give the module a dummy origin.
827db96d56Sopenharmony_ci        module.__file__ = '/path/which/shall/not/be/named'
837db96d56Sopenharmony_ci        module.__spec__.loader = module.__loader__
847db96d56Sopenharmony_ci        module.__spec__.origin = module.__file__
857db96d56Sopenharmony_ci        self.assertFalse(resources.files(module).joinpath('A').is_file())
867db96d56Sopenharmony_ci
877db96d56Sopenharmony_ci
887db96d56Sopenharmony_ciclass ResourceFromZipsTest01(util.ZipSetupBase, unittest.TestCase):
897db96d56Sopenharmony_ci    ZIP_MODULE = zipdata01  # type: ignore
907db96d56Sopenharmony_ci
917db96d56Sopenharmony_ci    def test_is_submodule_resource(self):
927db96d56Sopenharmony_ci        submodule = import_module('ziptestdata.subdirectory')
937db96d56Sopenharmony_ci        self.assertTrue(resources.files(submodule).joinpath('binary.file').is_file())
947db96d56Sopenharmony_ci
957db96d56Sopenharmony_ci    def test_read_submodule_resource_by_name(self):
967db96d56Sopenharmony_ci        self.assertTrue(
977db96d56Sopenharmony_ci            resources.files('ziptestdata.subdirectory')
987db96d56Sopenharmony_ci            .joinpath('binary.file')
997db96d56Sopenharmony_ci            .is_file()
1007db96d56Sopenharmony_ci        )
1017db96d56Sopenharmony_ci
1027db96d56Sopenharmony_ci    def test_submodule_contents(self):
1037db96d56Sopenharmony_ci        submodule = import_module('ziptestdata.subdirectory')
1047db96d56Sopenharmony_ci        self.assertEqual(
1057db96d56Sopenharmony_ci            names(resources.files(submodule)), {'__init__.py', 'binary.file'}
1067db96d56Sopenharmony_ci        )
1077db96d56Sopenharmony_ci
1087db96d56Sopenharmony_ci    def test_submodule_contents_by_name(self):
1097db96d56Sopenharmony_ci        self.assertEqual(
1107db96d56Sopenharmony_ci            names(resources.files('ziptestdata.subdirectory')),
1117db96d56Sopenharmony_ci            {'__init__.py', 'binary.file'},
1127db96d56Sopenharmony_ci        )
1137db96d56Sopenharmony_ci
1147db96d56Sopenharmony_ci
1157db96d56Sopenharmony_ciclass ResourceFromZipsTest02(util.ZipSetupBase, unittest.TestCase):
1167db96d56Sopenharmony_ci    ZIP_MODULE = zipdata02  # type: ignore
1177db96d56Sopenharmony_ci
1187db96d56Sopenharmony_ci    def test_unrelated_contents(self):
1197db96d56Sopenharmony_ci        """
1207db96d56Sopenharmony_ci        Test thata zip with two unrelated subpackages return
1217db96d56Sopenharmony_ci        distinct resources. Ref python/importlib_resources#44.
1227db96d56Sopenharmony_ci        """
1237db96d56Sopenharmony_ci        self.assertEqual(
1247db96d56Sopenharmony_ci            names(resources.files('ziptestdata.one')),
1257db96d56Sopenharmony_ci            {'__init__.py', 'resource1.txt'},
1267db96d56Sopenharmony_ci        )
1277db96d56Sopenharmony_ci        self.assertEqual(
1287db96d56Sopenharmony_ci            names(resources.files('ziptestdata.two')),
1297db96d56Sopenharmony_ci            {'__init__.py', 'resource2.txt'},
1307db96d56Sopenharmony_ci        )
1317db96d56Sopenharmony_ci
1327db96d56Sopenharmony_ci
1337db96d56Sopenharmony_ciclass DeletingZipsTest(unittest.TestCase):
1347db96d56Sopenharmony_ci    """Having accessed resources in a zip file should not keep an open
1357db96d56Sopenharmony_ci    reference to the zip.
1367db96d56Sopenharmony_ci    """
1377db96d56Sopenharmony_ci
1387db96d56Sopenharmony_ci    ZIP_MODULE = zipdata01
1397db96d56Sopenharmony_ci
1407db96d56Sopenharmony_ci    def setUp(self):
1417db96d56Sopenharmony_ci        modules = import_helper.modules_setup()
1427db96d56Sopenharmony_ci        self.addCleanup(import_helper.modules_cleanup, *modules)
1437db96d56Sopenharmony_ci
1447db96d56Sopenharmony_ci        data_path = pathlib.Path(self.ZIP_MODULE.__file__)
1457db96d56Sopenharmony_ci        data_dir = data_path.parent
1467db96d56Sopenharmony_ci        self.source_zip_path = data_dir / 'ziptestdata.zip'
1477db96d56Sopenharmony_ci        self.zip_path = pathlib.Path(f'{uuid.uuid4()}.zip').absolute()
1487db96d56Sopenharmony_ci        self.zip_path.write_bytes(self.source_zip_path.read_bytes())
1497db96d56Sopenharmony_ci        sys.path.append(str(self.zip_path))
1507db96d56Sopenharmony_ci        self.data = import_module('ziptestdata')
1517db96d56Sopenharmony_ci
1527db96d56Sopenharmony_ci    def tearDown(self):
1537db96d56Sopenharmony_ci        try:
1547db96d56Sopenharmony_ci            sys.path.remove(str(self.zip_path))
1557db96d56Sopenharmony_ci        except ValueError:
1567db96d56Sopenharmony_ci            pass
1577db96d56Sopenharmony_ci
1587db96d56Sopenharmony_ci        try:
1597db96d56Sopenharmony_ci            del sys.path_importer_cache[str(self.zip_path)]
1607db96d56Sopenharmony_ci            del sys.modules[self.data.__name__]
1617db96d56Sopenharmony_ci        except KeyError:
1627db96d56Sopenharmony_ci            pass
1637db96d56Sopenharmony_ci
1647db96d56Sopenharmony_ci        try:
1657db96d56Sopenharmony_ci            unlink(self.zip_path)
1667db96d56Sopenharmony_ci        except OSError:
1677db96d56Sopenharmony_ci            # If the test fails, this will probably fail too
1687db96d56Sopenharmony_ci            pass
1697db96d56Sopenharmony_ci
1707db96d56Sopenharmony_ci    def test_iterdir_does_not_keep_open(self):
1717db96d56Sopenharmony_ci        c = [item.name for item in resources.files('ziptestdata').iterdir()]
1727db96d56Sopenharmony_ci        self.zip_path.unlink()
1737db96d56Sopenharmony_ci        del c
1747db96d56Sopenharmony_ci
1757db96d56Sopenharmony_ci    def test_is_file_does_not_keep_open(self):
1767db96d56Sopenharmony_ci        c = resources.files('ziptestdata').joinpath('binary.file').is_file()
1777db96d56Sopenharmony_ci        self.zip_path.unlink()
1787db96d56Sopenharmony_ci        del c
1797db96d56Sopenharmony_ci
1807db96d56Sopenharmony_ci    def test_is_file_failure_does_not_keep_open(self):
1817db96d56Sopenharmony_ci        c = resources.files('ziptestdata').joinpath('not-present').is_file()
1827db96d56Sopenharmony_ci        self.zip_path.unlink()
1837db96d56Sopenharmony_ci        del c
1847db96d56Sopenharmony_ci
1857db96d56Sopenharmony_ci    @unittest.skip("Desired but not supported.")
1867db96d56Sopenharmony_ci    def test_as_file_does_not_keep_open(self):  # pragma: no cover
1877db96d56Sopenharmony_ci        c = resources.as_file(resources.files('ziptestdata') / 'binary.file')
1887db96d56Sopenharmony_ci        self.zip_path.unlink()
1897db96d56Sopenharmony_ci        del c
1907db96d56Sopenharmony_ci
1917db96d56Sopenharmony_ci    def test_entered_path_does_not_keep_open(self):
1927db96d56Sopenharmony_ci        # This is what certifi does on import to make its bundle
1937db96d56Sopenharmony_ci        # available for the process duration.
1947db96d56Sopenharmony_ci        c = resources.as_file(
1957db96d56Sopenharmony_ci            resources.files('ziptestdata') / 'binary.file'
1967db96d56Sopenharmony_ci        ).__enter__()
1977db96d56Sopenharmony_ci        self.zip_path.unlink()
1987db96d56Sopenharmony_ci        del c
1997db96d56Sopenharmony_ci
2007db96d56Sopenharmony_ci    def test_read_binary_does_not_keep_open(self):
2017db96d56Sopenharmony_ci        c = resources.files('ziptestdata').joinpath('binary.file').read_bytes()
2027db96d56Sopenharmony_ci        self.zip_path.unlink()
2037db96d56Sopenharmony_ci        del c
2047db96d56Sopenharmony_ci
2057db96d56Sopenharmony_ci    def test_read_text_does_not_keep_open(self):
2067db96d56Sopenharmony_ci        c = resources.files('ziptestdata').joinpath('utf-8.file').read_text()
2077db96d56Sopenharmony_ci        self.zip_path.unlink()
2087db96d56Sopenharmony_ci        del c
2097db96d56Sopenharmony_ci
2107db96d56Sopenharmony_ci
2117db96d56Sopenharmony_ciclass ResourceFromNamespaceTest01(unittest.TestCase):
2127db96d56Sopenharmony_ci    site_dir = str(pathlib.Path(__file__).parent)
2137db96d56Sopenharmony_ci
2147db96d56Sopenharmony_ci    @classmethod
2157db96d56Sopenharmony_ci    def setUpClass(cls):
2167db96d56Sopenharmony_ci        sys.path.append(cls.site_dir)
2177db96d56Sopenharmony_ci
2187db96d56Sopenharmony_ci    @classmethod
2197db96d56Sopenharmony_ci    def tearDownClass(cls):
2207db96d56Sopenharmony_ci        sys.path.remove(cls.site_dir)
2217db96d56Sopenharmony_ci
2227db96d56Sopenharmony_ci    def test_is_submodule_resource(self):
2237db96d56Sopenharmony_ci        self.assertTrue(
2247db96d56Sopenharmony_ci            resources.files(import_module('namespacedata01'))
2257db96d56Sopenharmony_ci            .joinpath('binary.file')
2267db96d56Sopenharmony_ci            .is_file()
2277db96d56Sopenharmony_ci        )
2287db96d56Sopenharmony_ci
2297db96d56Sopenharmony_ci    def test_read_submodule_resource_by_name(self):
2307db96d56Sopenharmony_ci        self.assertTrue(
2317db96d56Sopenharmony_ci            resources.files('namespacedata01').joinpath('binary.file').is_file()
2327db96d56Sopenharmony_ci        )
2337db96d56Sopenharmony_ci
2347db96d56Sopenharmony_ci    def test_submodule_contents(self):
2357db96d56Sopenharmony_ci        contents = names(resources.files(import_module('namespacedata01')))
2367db96d56Sopenharmony_ci        try:
2377db96d56Sopenharmony_ci            contents.remove('__pycache__')
2387db96d56Sopenharmony_ci        except KeyError:
2397db96d56Sopenharmony_ci            pass
2407db96d56Sopenharmony_ci        self.assertEqual(contents, {'binary.file', 'utf-8.file', 'utf-16.file'})
2417db96d56Sopenharmony_ci
2427db96d56Sopenharmony_ci    def test_submodule_contents_by_name(self):
2437db96d56Sopenharmony_ci        contents = names(resources.files('namespacedata01'))
2447db96d56Sopenharmony_ci        try:
2457db96d56Sopenharmony_ci            contents.remove('__pycache__')
2467db96d56Sopenharmony_ci        except KeyError:
2477db96d56Sopenharmony_ci            pass
2487db96d56Sopenharmony_ci        self.assertEqual(contents, {'binary.file', 'utf-8.file', 'utf-16.file'})
2497db96d56Sopenharmony_ci
2507db96d56Sopenharmony_ci
2517db96d56Sopenharmony_ciif __name__ == '__main__':
2527db96d56Sopenharmony_ci    unittest.main()
253