Skip to content

Commit d1fd0dc

Browse files
committed
Only run the new test when appropriate.
The first version had it running two forkserver and one spawn tests underneath each of the _fork, _forkserver, and _spawn test suites that build off the generic one. This adds to the existing complexity of the multiprocessing test suite by offering BaseTestCase classes another attribute to control which suites they are invoked under. :/ Net result: we don't over-run the new test.
1 parent 9d08423 commit d1fd0dc

File tree

1 file changed

+29
-23
lines changed

1 file changed

+29
-23
lines changed

Lib/test/_test_multiprocessing.py

Lines changed: 29 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -258,6 +258,9 @@ def __call__(self, *args, **kwds):
258258
class BaseTestCase(object):
259259

260260
ALLOWED_TYPES = ('processes', 'manager', 'threads')
261+
# If not empty, limit which start method suits run this class.
262+
START_METHODS: set[str] = set()
263+
start_method = None # set by install_tests_in_module_dict()
261264

262265
def assertTimingAlmostEqual(self, a, b):
263266
if CHECK_TIMINGS:
@@ -6404,6 +6407,8 @@ class _TestSpawnedSysPath(BaseTestCase):
64046407
"""Test that sys.path is setup in forkserver and spawn processes."""
64056408

64066409
ALLOWED_TYPES = ('processes',)
6410+
# Not applicable to fork which inherits everything from the process as is.
6411+
START_METHODS = {"forkserver", "spawn"}
64076412

64086413
def setUp(self):
64096414
self._orig_sys_path = list(sys.path)
@@ -6415,6 +6420,8 @@ def setUp(self):
64156420
sys.path[:] = [p for p in sys.path if p] # remove any existing ""s
64166421
sys.path.insert(0, self._temp_dir)
64176422
sys.path.insert(0, "") # Replaced with an abspath in child.
6423+
self.assertIn(self.start_method, self.START_METHODS)
6424+
self._ctx = multiprocessing.get_context(self.start_method)
64186425
try:
64196426
self._ctx_forkserver = multiprocessing.get_context("forkserver")
64206427
except ValueError:
@@ -6430,15 +6437,15 @@ def enq_imported_module_names(queue):
64306437
queue.put(tuple(sys.modules))
64316438

64326439
def test_forkserver_preload_imports_sys_path(self):
6433-
ctx = self._ctx_forkserver
6434-
if not ctx:
6435-
self.skipTest("requires forkserver start method.")
6440+
if self._ctx.get_start_method() != "forkserver":
6441+
self.skipTest("forkserver specific test.")
64366442
self.assertNotIn(self._mod_name, sys.modules)
64376443
multiprocessing.forkserver._forkserver._stop() # Must be fresh.
6438-
ctx.set_forkserver_preload(
6444+
self._ctx.set_forkserver_preload(
64396445
["test.test_multiprocessing_forkserver", self._mod_name])
6440-
q = ctx.Queue()
6441-
proc = ctx.Process(target=self.enq_imported_module_names, args=(q,))
6446+
q = self._ctx.Queue()
6447+
proc = self._ctx.Process(
6448+
target=self.enq_imported_module_names, args=(q,))
64426449
proc.start()
64436450
proc.join()
64446451
child_imported_modules = q.get()
@@ -6456,23 +6463,19 @@ def enq_sys_path_and_import(queue, mod_name):
64566463
queue.put(None)
64576464

64586465
def test_child_sys_path(self):
6459-
for ctx in (self._ctx_spawn, self._ctx_forkserver):
6460-
if not ctx:
6461-
continue
6462-
with self.subTest(f"{ctx.get_start_method()} start method"):
6463-
q = ctx.Queue()
6464-
proc = ctx.Process(target=self.enq_sys_path_and_import,
6465-
args=(q, self._mod_name))
6466-
proc.start()
6467-
proc.join()
6468-
child_sys_path = q.get()
6469-
import_error = q.get()
6470-
q.close()
6471-
self.assertNotIn("", child_sys_path) # replaced by an abspath
6472-
self.assertIn(self._temp_dir, child_sys_path) # our addition
6473-
# ignore the first element, it is the absolute "" replacement
6474-
self.assertEqual(child_sys_path[1:], sys.path[1:])
6475-
self.assertIsNone(import_error, msg=f"child could not import {self._mod_name}")
6466+
q = self._ctx.Queue()
6467+
proc = self._ctx.Process(
6468+
target=self.enq_sys_path_and_import, args=(q, self._mod_name))
6469+
proc.start()
6470+
proc.join()
6471+
child_sys_path = q.get()
6472+
import_error = q.get()
6473+
q.close()
6474+
self.assertNotIn("", child_sys_path) # replaced by an abspath
6475+
self.assertIn(self._temp_dir, child_sys_path) # our addition
6476+
# ignore the first element, it is the absolute "" replacement
6477+
self.assertEqual(child_sys_path[1:], sys.path[1:])
6478+
self.assertIsNone(import_error, msg=f"child could not import {self._mod_name}")
64766479

64776480

64786481
class MiscTestCase(unittest.TestCase):
@@ -6669,6 +6672,8 @@ def install_tests_in_module_dict(remote_globs, start_method,
66696672
if base is BaseTestCase:
66706673
continue
66716674
assert set(base.ALLOWED_TYPES) <= ALL_TYPES, base.ALLOWED_TYPES
6675+
if base.START_METHODS and start_method not in base.START_METHODS:
6676+
continue # class not intended for this start method.
66726677
for type_ in base.ALLOWED_TYPES:
66736678
if only_type and type_ != only_type:
66746679
continue
@@ -6682,6 +6687,7 @@ class Temp(base, Mixin, unittest.TestCase):
66826687
Temp = hashlib_helper.requires_hashdigest('sha256')(Temp)
66836688
Temp.__name__ = Temp.__qualname__ = newname
66846689
Temp.__module__ = __module__
6690+
Temp.start_method = start_method
66856691
remote_globs[newname] = Temp
66866692
elif issubclass(base, unittest.TestCase):
66876693
if only_type:

0 commit comments

Comments
 (0)