From 466783319599ff1b1c2a2fcb20ffd101d16bc11b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mike=20F=C3=A4hrmann?= Date: Thu, 17 Oct 2024 21:01:34 +0200 Subject: [PATCH] [util] add 'std' object to global eval namespace (#6330) allows accessing standard library modules (and other external modules) in a more straightforward manner than '__import__(...)' * std.os.getcwd() * std["os"].getcwd() --- gallery_dl/util.py | 20 ++++++++++++++++++++ test/test_util.py | 28 ++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+) diff --git a/gallery_dl/util.py b/gallery_dl/util.py index 80c53cb8..6cdd9946 100644 --- a/gallery_dl/util.py +++ b/gallery_dl/util.py @@ -532,6 +532,24 @@ class HTTPBasicAuth(): return request +class ModuleProxy(): + __slots__ = () + + def __getitem__(self, key, modules=sys.modules): + try: + return modules[key] + except KeyError: + pass + try: + __import__(key) + except ImportError: + modules[key] = NONE + return NONE + return modules[key] + + __getattr__ = __getitem__ + + class LazyPrompt(): __slots__ = () @@ -540,6 +558,7 @@ class LazyPrompt(): class NullContext(): + __slots__ = () def __enter__(self): return None @@ -646,6 +665,7 @@ GLOBALS = { "restart" : raises(exception.RestartExtraction), "hash_sha1": sha1, "hash_md5" : md5, + "std" : ModuleProxy(), "re" : re, } diff --git a/test/test_util.py b/test/test_util.py index b630ffbc..888a70a0 100644 --- a/test/test_util.py +++ b/test/test_util.py @@ -830,6 +830,34 @@ def hash(value): i += 1 self.assertEqual(i, 0) + def test_module_proxy(self): + proxy = util.ModuleProxy() + + self.assertIs(proxy.os, os) + self.assertIs(proxy.os.path, os.path) + self.assertIs(proxy["os"], os) + self.assertIs(proxy["os.path"], os.path) + self.assertIs(proxy["os"].path, os.path) + + self.assertIs(proxy.abcdefghi, util.NONE) + self.assertIs(proxy["abcdefghi"], util.NONE) + self.assertIs(proxy["abc.def.ghi"], util.NONE) + self.assertIs(proxy["os.path2"], util.NONE) + + def test_null_context(self): + with util.NullContext(): + pass + + with util.NullContext() as ctx: + self.assertIs(ctx, None) + + try: + with util.NullContext() as ctx: + exc_orig = ValueError() + raise exc_orig + except ValueError as exc: + self.assertIs(exc, exc_orig) + class TestExtractor(): category = "test_category"