https://github.com/python/cpython/commit/b48c208bb03ec50e5f41672037aa5fd0adbdb987
commit: b48c208bb03ec50e5f41672037aa5fd0adbdb987
branch: 3.15
author: sobolevn <[email protected]>
committer: sobolevn <[email protected]>
date: 2026-06-05T08:43:27Z
summary:
[3.15] gh-150899: Do not reset custom `-Xlazy_imports` mode in
`test_lazy_imports` (GH-150900) (#150947)
(cherry picked from commit 2f064fbc0b427f0e1c83fe9b9036531ed16e95e8)
files:
M Lib/test/test_lazy_import/__init__.py
diff --git a/Lib/test/test_lazy_import/__init__.py
b/Lib/test/test_lazy_import/__init__.py
index 4340efd31095ea6..2a82ac78fb90fb8 100644
--- a/Lib/test/test_lazy_import/__init__.py
+++ b/Lib/test/test_lazy_import/__init__.py
@@ -21,8 +21,10 @@
_testcapi = None
-class LazyImportTests(unittest.TestCase):
- """Tests for basic lazy import functionality."""
+class LazyImportTestCase(unittest.TestCase):
+ def setUp(self):
+ self.lazy_imports_filter = sys.get_lazy_imports_filter()
+ self.lazy_imports = sys.get_lazy_imports()
def tearDown(self):
"""Clean up any test modules from sys.modules."""
@@ -30,10 +32,14 @@ def tearDown(self):
if key.startswith('test.test_lazy_import.data'):
del sys.modules[key]
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
+ sys.set_lazy_imports_filter(self.lazy_imports_filter)
+ sys.set_lazy_imports(self.lazy_imports)
sys.lazy_modules.clear()
+
+class LazyImportTests(LazyImportTestCase):
+ """Tests for basic lazy import functionality."""
+
def test_basic_unused(self):
"""Lazy imported module should not be loaded if never accessed."""
import test.test_lazy_import.data.basic_unused
@@ -162,17 +168,9 @@ def test_from_import_with_imported_module_getattr(self):
assert_python_ok("-c", code)
-class GlobalLazyImportModeTests(unittest.TestCase):
+class GlobalLazyImportModeTests(LazyImportTestCase):
"""Tests for sys.set_lazy_imports() global mode control."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_global_off(self):
"""Mode 'none' should disable lazy imports entirely."""
import test.test_lazy_import.data.global_off
@@ -204,17 +202,9 @@ def test_global_filter_from_true(self):
self.assertNotIn("test.test_lazy_import.data.basic2", sys.modules)
-class CompatibilityModeTests(unittest.TestCase):
+class CompatibilityModeTests(LazyImportTestCase):
"""Tests for __lazy_modules__ compatibility mode."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_compatibility_mode(self):
"""__lazy_modules__ should enable lazy imports for listed modules."""
import test.test_lazy_import.data.basic_compatibility_mode
@@ -241,17 +231,9 @@ def test_compatibility_mode_relative(self):
self.assertNotIn("test.test_lazy_import.data.basic2", sys.modules)
-class ModuleIntrospectionTests(unittest.TestCase):
+class ModuleIntrospectionTests(LazyImportTestCase):
"""Tests for module dict and getattr behavior with lazy imports."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_modules_dict(self):
"""Accessing module.__dict__ should not trigger reification."""
import test.test_lazy_import.data.modules_dict
@@ -268,17 +250,9 @@ def test_modules_getattr_other(self):
self.assertNotIn("test.test_lazy_import.data.basic2", sys.modules)
-class LazyImportTypeTests(unittest.TestCase):
+class LazyImportTypeTests(LazyImportTestCase):
"""Tests for the LazyImportType and its resolve() method."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_lazy_value_resolve(self):
"""resolve() method should force the lazy import to load."""
import test.test_lazy_import.data.lazy_get_value
@@ -304,17 +278,9 @@ def test_lazy_import_type_attributes_accessible(self):
self.assertIn(b"<built-in method resolve of lazy_import object at",
proc.out)
-class SyntaxRestrictionTests(unittest.TestCase):
+class SyntaxRestrictionTests(LazyImportTestCase):
"""Tests for syntax restrictions on lazy imports."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_lazy_try_except(self):
"""lazy import inside try/except should raise SyntaxError."""
with self.assertRaises(SyntaxError):
@@ -383,17 +349,9 @@ def test_lazy_import_exec_at_module_level(self):
self.assertIn("OK", result.stdout)
-class EagerImportInLazyModeTests(unittest.TestCase):
+class EagerImportInLazyModeTests(LazyImportTestCase):
"""Tests for imports that should remain eager even in lazy mode."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_try_except_eager(self):
"""Imports in try/except should be eager even with mode='all'."""
sys.set_lazy_imports("all")
@@ -459,17 +417,9 @@ class C:
del globals()["__lazy_modules__"]
-class WithStatementTests(unittest.TestCase):
+class WithStatementTests(LazyImportTestCase):
"""Tests for lazy imports in with statement context."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_lazy_with(self):
"""lazy import with 'with' statement should work."""
import test.test_lazy_import.data.lazy_with
@@ -481,17 +431,9 @@ def test_lazy_with_from(self):
self.assertNotIn("test.test_lazy_import.data.basic2", sys.modules)
-class PackageTests(unittest.TestCase):
+class PackageTests(LazyImportTestCase):
"""Tests for lazy imports with packages."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_lazy_import_pkg(self):
"""lazy import of package submodule should load the package."""
out = io.StringIO()
@@ -600,17 +542,9 @@ def test_package_from_import_with_module_getattr(self):
assert_python_ok("-c", code)
-class DunderLazyImportTests(unittest.TestCase):
+class DunderLazyImportTests(LazyImportTestCase):
"""Tests for __lazy_import__ builtin function."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_dunder_lazy_import(self):
"""__lazy_import__ should create lazy import proxy."""
import test.test_lazy_import.data.dunder_lazy_import
@@ -645,17 +579,9 @@ def test_dunder_lazy_import_builtins(self):
self.assertEqual(dunder_lazy_import_builtins.basic.basic2, 42)
-class SysLazyImportsAPITests(unittest.TestCase):
+class SysLazyImportsAPITests(LazyImportTestCase):
"""Tests for sys lazy imports API functions."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_set_lazy_imports_requires_string(self):
"""set_lazy_imports should reject non-string arguments."""
with self.assertRaises(TypeError):
@@ -723,21 +649,13 @@ def test_lazy_modules_tracks_lazy_imports(self):
@support.requires_subprocess()
-class ErrorHandlingTests(unittest.TestCase):
+class ErrorHandlingTests(LazyImportTestCase):
"""Tests for error handling during lazy import reification.
PEP 810: Errors during reification should show exception chaining with
both the lazy import definition location and the access location.
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_import_error_shows_chained_traceback(self):
"""Accessing a nonexistent lazy submodule via parent attr raises
AttributeError."""
code = textwrap.dedent("""
@@ -870,7 +788,7 @@ def hello():
@support.requires_subprocess()
-class GlobalsAndDictTests(unittest.TestCase):
+class GlobalsAndDictTests(LazyImportTestCase):
"""Tests for globals() and __dict__ behavior with lazy imports.
PEP 810: "Calling globals() or accessing a module's __dict__ does not
trigger
@@ -878,14 +796,6 @@ class GlobalsAndDictTests(unittest.TestCase):
through that dictionary still returns lazy proxy objects."
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_globals_returns_lazy_proxy_when_accessed_from_function(self):
"""globals() accessed from a function should return lazy proxy without
reification.
@@ -1040,7 +950,7 @@ def f():
@support.requires_subprocess()
-class MultipleNameFromImportTests(unittest.TestCase):
+class MultipleNameFromImportTests(LazyImportTestCase):
"""Tests for lazy from ... import with multiple names.
PEP 810: "When using lazy from ... import, each imported name is bound to a
@@ -1049,14 +959,6 @@ class MultipleNameFromImportTests(unittest.TestCase):
Other names remain as lazy proxies until they are accessed."
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_accessing_one_name_leaves_others_as_proxies(self):
"""Accessing one name from multi-name import should leave others
lazy."""
code = textwrap.dedent("""
@@ -1121,20 +1023,12 @@ def test_all_names_reified_after_all_accessed(self):
@support.requires_subprocess()
-class SysLazyModulesTrackingTests(unittest.TestCase):
+class SysLazyModulesTrackingTests(LazyImportTestCase):
"""Tests for sys.lazy_modules tracking behavior.
PEP 810: "When the module is reified, it's removed from sys.lazy_modules"
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_module_added_to_lazy_modules_on_lazy_import(self):
"""Module should be added to sys.lazy_modules when lazily imported."""
# PEP 810 states lazy_modules tracks modules that have been lazily
imported
@@ -1433,20 +1327,12 @@ def test_sys_set_lazy_imports_overrides_cli(self):
@support.requires_subprocess()
-class FilterFunctionSignatureTests(unittest.TestCase):
+class FilterFunctionSignatureTests(LazyImportTestCase):
"""Tests for the filter function signature per PEP 810.
PEP 810: func(importer: str, name: str, fromlist: tuple[str, ...] | None)
-> bool
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def _run_subprocess_with_modules(self, code, files):
with tempfile.TemporaryDirectory() as tmpdir:
for relpath, contents in files.items():
@@ -1716,17 +1602,9 @@ def my_filter(importer, name, fromlist):
self.assertIn("OK", result.stdout)
-class AdditionalSyntaxRestrictionTests(unittest.TestCase):
+class AdditionalSyntaxRestrictionTests(LazyImportTestCase):
"""Additional syntax restriction tests per PEP 810."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_lazy_import_inside_class_raises_syntax_error(self):
"""lazy import inside class body should raise SyntaxError."""
# PEP 810: "The soft keyword is only allowed at the global (module)
level,
@@ -1736,7 +1614,7 @@ def
test_lazy_import_inside_class_raises_syntax_error(self):
@support.requires_subprocess()
-class MixedLazyEagerImportTests(unittest.TestCase):
+class MixedLazyEagerImportTests(LazyImportTestCase):
"""Tests for mixing lazy and eager imports of the same module.
PEP 810: "If module foo is imported both lazily and eagerly in the same
@@ -1744,14 +1622,6 @@ class MixedLazyEagerImportTests(unittest.TestCase):
the same module object."
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_eager_import_before_lazy_resolves_to_same_module(self):
"""Eager import before lazy should make lazy resolve to same module."""
code = textwrap.dedent("""
@@ -1797,17 +1667,9 @@ def
test_lazy_import_before_eager_resolves_to_same_module(self):
self.assertIn("OK", result.stdout)
-class RelativeImportTests(unittest.TestCase):
+class RelativeImportTests(LazyImportTestCase):
"""Tests for relative imports with lazy keyword."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_relative_lazy_import(self):
"""lazy from . import submodule should work."""
from test.test_lazy_import.data import relative_lazy
@@ -1832,21 +1694,13 @@ def test_relative_lazy_from_import(self):
self.assertIn("test.test_lazy_import.data.basic2", sys.modules)
-class LazyModulesCompatibilityFromImportTests(unittest.TestCase):
+class LazyModulesCompatibilityFromImportTests(LazyImportTestCase):
"""Tests for __lazy_modules__ with from imports.
PEP 810: "When a module is made lazy this way, from-imports using that
module are also lazy"
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_lazy_modules_makes_from_imports_lazy(self):
"""__lazy_modules__ should make from imports of listed modules lazy."""
from test.test_lazy_import.data import lazy_compat_from
@@ -1861,7 +1715,7 @@ def test_lazy_modules_makes_from_imports_lazy(self):
@support.requires_subprocess()
-class ImportStateAtReificationTests(unittest.TestCase):
+class ImportStateAtReificationTests(LazyImportTestCase):
"""Tests for import system state at reification time.
PEP 810: "Reification still calls __import__ to resolve the import, which
uses
@@ -1870,14 +1724,6 @@ class ImportStateAtReificationTests(unittest.TestCase):
statement was evaluated."
"""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_sys_path_at_reification_time_is_used(self):
"""sys.path changes after lazy import should affect reification."""
code = textwrap.dedent("""
@@ -1920,17 +1766,9 @@ def test_sys_path_at_reification_time_is_used(self):
@support.requires_subprocess()
-class ThreadSafetyTests(unittest.TestCase):
+class ThreadSafetyTests(LazyImportTestCase):
"""Tests for thread-safety of lazy imports."""
- def tearDown(self):
- for key in list(sys.modules.keys()):
- if key.startswith('test.test_lazy_import.data'):
- del sys.modules[key]
-
- sys.set_lazy_imports_filter(None)
- sys.set_lazy_imports("normal")
-
def test_concurrent_lazy_import_reification(self):
"""Multiple threads racing to reify the same lazy import should
succeed."""
from test.test_lazy_import.data import basic_unused
@@ -2192,11 +2030,7 @@ def test_normal_import_dis(self):
@unittest.skipIf(_testcapi is None, 'need the _testcapi module')
-class LazyCApiTests(unittest.TestCase):
- def tearDown(self):
- sys.set_lazy_imports("normal")
- sys.set_lazy_imports_filter(None)
-
+class LazyCApiTests(LazyImportTestCase):
def test_set_matches_sys(self):
self.assertEqual(_testcapi.PyImport_GetLazyImportsMode(),
sys.get_lazy_imports())
for mode in ("normal", "all", "none"):
_______________________________________________
Python-checkins mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3//lists/python-checkins.python.org
Member address: [email protected]