Skip to content

Commit f45ef5e

Browse files
authored
[3.11] gh-109625: Move _ready_to_import() from test_import to support.import_helper (GH-109626) (#109718)
[3.11] gh-109625: Move _ready_to_import() from test_import to support.import_helper (GH-109626). (cherry picked from commit 115c49a)
1 parent 74978ae commit f45ef5e

File tree

3 files changed

+35
-34
lines changed

3 files changed

+35
-34
lines changed

Lib/test/support/import_helper.py

+24-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
import unittest
99
import warnings
1010

11-
from .os_helper import unlink
11+
from .os_helper import unlink, temp_dir
1212

1313

1414
@contextlib.contextmanager
@@ -246,3 +246,26 @@ def modules_cleanup(oldmodules):
246246
# do currently). Implicitly imported *real* modules should be left alone
247247
# (see issue 10556).
248248
sys.modules.update(oldmodules)
249+
250+
251+
@contextlib.contextmanager
252+
def ready_to_import(name=None, source=""):
253+
from test.support import script_helper
254+
255+
# 1. Sets up a temporary directory and removes it afterwards
256+
# 2. Creates the module file
257+
# 3. Temporarily clears the module from sys.modules (if any)
258+
# 4. Reverts or removes the module when cleaning up
259+
name = name or "spam"
260+
with temp_dir() as tempdir:
261+
path = script_helper.make_script(tempdir, name, source)
262+
old_module = sys.modules.pop(name, None)
263+
try:
264+
sys.path.insert(0, tempdir)
265+
yield name, path
266+
sys.path.remove(tempdir)
267+
finally:
268+
if old_module is not None:
269+
sys.modules[name] = old_module
270+
else:
271+
sys.modules.pop(name, None)

Lib/test/test_import/__init__.py

+9-29
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,10 @@
2424
STDLIB_DIR, is_jython, swap_attr, swap_item, cpython_only, is_emscripten,
2525
is_wasi)
2626
from test.support.import_helper import (
27-
forget, make_legacy_pyc, unlink, unload, DirsOnSysPath, CleanImport)
27+
forget, make_legacy_pyc, unlink, unload, ready_to_import,
28+
DirsOnSysPath, CleanImport)
2829
from test.support.os_helper import (
29-
TESTFN, rmtree, temp_umask, TESTFN_UNENCODABLE, temp_dir)
30+
TESTFN, rmtree, temp_umask, TESTFN_UNENCODABLE)
3031
from test.support import script_helper
3132
from test.support import threading_helper
3233
from test.test_importlib.util import uncache
@@ -46,27 +47,6 @@ def remove_files(name):
4647
rmtree('__pycache__')
4748

4849

49-
@contextlib.contextmanager
50-
def _ready_to_import(name=None, source=""):
51-
# sets up a temporary directory and removes it
52-
# creates the module file
53-
# temporarily clears the module from sys.modules (if any)
54-
# reverts or removes the module when cleaning up
55-
name = name or "spam"
56-
with temp_dir() as tempdir:
57-
path = script_helper.make_script(tempdir, name, source)
58-
old_module = sys.modules.pop(name, None)
59-
try:
60-
sys.path.insert(0, tempdir)
61-
yield name, path
62-
sys.path.remove(tempdir)
63-
finally:
64-
if old_module is not None:
65-
sys.modules[name] = old_module
66-
elif name in sys.modules:
67-
del sys.modules[name]
68-
69-
7050
class ImportTests(unittest.TestCase):
7151

7252
def setUp(self):
@@ -130,7 +110,7 @@ def test_from_import_missing_attr_path_is_canonical(self):
130110

131111
def test_from_import_star_invalid_type(self):
132112
import re
133-
with _ready_to_import() as (name, path):
113+
with ready_to_import() as (name, path):
134114
with open(path, 'w', encoding='utf-8') as f:
135115
f.write("__all__ = [b'invalid_type']")
136116
globals = {}
@@ -139,7 +119,7 @@ def test_from_import_star_invalid_type(self):
139119
):
140120
exec(f"from {name} import *", globals)
141121
self.assertNotIn(b"invalid_type", globals)
142-
with _ready_to_import() as (name, path):
122+
with ready_to_import() as (name, path):
143123
with open(path, 'w', encoding='utf-8') as f:
144124
f.write("globals()[b'invalid_type'] = object()")
145125
globals = {}
@@ -550,7 +530,7 @@ class FilePermissionTests(unittest.TestCase):
550530
)
551531
def test_creation_mode(self):
552532
mask = 0o022
553-
with temp_umask(mask), _ready_to_import() as (name, path):
533+
with temp_umask(mask), ready_to_import() as (name, path):
554534
cached_path = importlib.util.cache_from_source(path)
555535
module = __import__(name)
556536
if not os.path.exists(cached_path):
@@ -569,7 +549,7 @@ def test_creation_mode(self):
569549
def test_cached_mode_issue_2051(self):
570550
# permissions of .pyc should match those of .py, regardless of mask
571551
mode = 0o600
572-
with temp_umask(0o022), _ready_to_import() as (name, path):
552+
with temp_umask(0o022), ready_to_import() as (name, path):
573553
cached_path = importlib.util.cache_from_source(path)
574554
os.chmod(path, mode)
575555
__import__(name)
@@ -585,7 +565,7 @@ def test_cached_mode_issue_2051(self):
585565
@os_helper.skip_unless_working_chmod
586566
def test_cached_readonly(self):
587567
mode = 0o400
588-
with temp_umask(0o022), _ready_to_import() as (name, path):
568+
with temp_umask(0o022), ready_to_import() as (name, path):
589569
cached_path = importlib.util.cache_from_source(path)
590570
os.chmod(path, mode)
591571
__import__(name)
@@ -600,7 +580,7 @@ def test_cached_readonly(self):
600580
def test_pyc_always_writable(self):
601581
# Initially read-only .pyc files on Windows used to cause problems
602582
# with later updates, see issue #6074 for details
603-
with _ready_to_import() as (name, path):
583+
with ready_to_import() as (name, path):
604584
# Write a Python file, make it read-only and import it
605585
with open(path, 'w', encoding='utf-8') as f:
606586
f.write("x = 'original'\n")

Lib/test/test_inspect.py

+2-4
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@
2727

2828
from test.support import cpython_only
2929
from test.support import MISSING_C_DOCSTRINGS, ALWAYS_EQ
30-
from test.support.import_helper import DirsOnSysPath
30+
from test.support.import_helper import DirsOnSysPath, ready_to_import
3131
from test.support.os_helper import TESTFN
3232
from test.support.script_helper import assert_python_ok, assert_python_failure
3333
from test import inspect_fodder as mod
@@ -37,8 +37,6 @@
3737
from test import inspect_stringized_annotations
3838
from test import inspect_stringized_annotations_2
3939

40-
from test.test_import import _ready_to_import
41-
4240

4341
# Functions tested in this suite:
4442
# ismodule, isclass, ismethod, isfunction, istraceback, isframe, iscode,
@@ -4505,7 +4503,7 @@ def assertInspectEqual(self, path, source):
45054503

45064504
def test_getsource_reload(self):
45074505
# see issue 1218234
4508-
with _ready_to_import('reload_bug', self.src_before) as (name, path):
4506+
with ready_to_import('reload_bug', self.src_before) as (name, path):
45094507
module = importlib.import_module(name)
45104508
self.assertInspectEqual(path, module)
45114509
with open(path, 'w', encoding='utf-8') as src:

0 commit comments

Comments
 (0)