summaryrefslogtreecommitdiffstats
path: root/Lib/test/_test_multiprocessing.py
diff options
context:
space:
mode:
authorSerhiy Storchaka <storchaka@gmail.com>2015-03-13 06:30:33 (GMT)
committerSerhiy Storchaka <storchaka@gmail.com>2015-03-13 06:30:33 (GMT)
commit63623ac2529ce9f293784c06215b018664c74491 (patch)
treeb0420f59515afa599c4597b7abe3dee2f28f39e6 /Lib/test/_test_multiprocessing.py
parent38dae173d11c0f87cec46d137df9180e1f43d01c (diff)
parent79fbeee2378dc31a5edebc9a5aa8f3fe9726933e (diff)
downloadcpython-63623ac2529ce9f293784c06215b018664c74491.zip
cpython-63623ac2529ce9f293784c06215b018664c74491.tar.gz
cpython-63623ac2529ce9f293784c06215b018664c74491.tar.bz2
Issue #23051: multiprocessing.Pool methods imap() and imap_unordered() now
handle exceptions raised by an iterator. Patch by Alon Diamant and Davin Potts.
Diffstat (limited to 'Lib/test/_test_multiprocessing.py')
-rw-r--r--Lib/test/_test_multiprocessing.py46
1 files changed, 46 insertions, 0 deletions
diff --git a/Lib/test/_test_multiprocessing.py b/Lib/test/_test_multiprocessing.py
index 4520c6a..6cff4fc 100644
--- a/Lib/test/_test_multiprocessing.py
+++ b/Lib/test/_test_multiprocessing.py
@@ -1660,6 +1660,14 @@ def sqr(x, wait=0.0):
def mul(x, y):
return x*y
+class SayWhenError(ValueError): pass
+
+def exception_throwing_generator(total, when):
+ for i in range(total):
+ if i == when:
+ raise SayWhenError("Somebody said when")
+ yield i
+
class _TestPool(BaseTestCase):
@classmethod
@@ -1758,6 +1766,25 @@ class _TestPool(BaseTestCase):
self.assertEqual(next(it), i*i)
self.assertRaises(StopIteration, it.__next__)
+ def test_imap_handle_iterable_exception(self):
+ if self.TYPE == 'manager':
+ self.skipTest('test not appropriate for {}'.format(self.TYPE))
+
+ it = self.pool.imap(sqr, exception_throwing_generator(10, 3), 1)
+ for i in range(3):
+ self.assertEqual(next(it), i*i)
+ self.assertRaises(SayWhenError, it.__next__)
+
+ # SayWhenError seen at start of problematic chunk's results
+ it = self.pool.imap(sqr, exception_throwing_generator(20, 7), 2)
+ for i in range(6):
+ self.assertEqual(next(it), i*i)
+ self.assertRaises(SayWhenError, it.__next__)
+ it = self.pool.imap(sqr, exception_throwing_generator(20, 7), 4)
+ for i in range(4):
+ self.assertEqual(next(it), i*i)
+ self.assertRaises(SayWhenError, it.__next__)
+
def test_imap_unordered(self):
it = self.pool.imap_unordered(sqr, list(range(1000)))
self.assertEqual(sorted(it), list(map(sqr, list(range(1000)))))
@@ -1765,6 +1792,25 @@ class _TestPool(BaseTestCase):
it = self.pool.imap_unordered(sqr, list(range(1000)), chunksize=53)
self.assertEqual(sorted(it), list(map(sqr, list(range(1000)))))
+ def test_imap_unordered_handle_iterable_exception(self):
+ if self.TYPE == 'manager':
+ self.skipTest('test not appropriate for {}'.format(self.TYPE))
+
+ it = self.pool.imap_unordered(sqr,
+ exception_throwing_generator(10, 3),
+ 1)
+ with self.assertRaises(SayWhenError):
+ # imap_unordered makes it difficult to anticipate the SayWhenError
+ for i in range(10):
+ self.assertEqual(next(it), i*i)
+
+ it = self.pool.imap_unordered(sqr,
+ exception_throwing_generator(20, 7),
+ 2)
+ with self.assertRaises(SayWhenError):
+ for i in range(20):
+ self.assertEqual(next(it), i*i)
+
def test_make_pool(self):
self.assertRaises(ValueError, multiprocessing.Pool, -1)
self.assertRaises(ValueError, multiprocessing.Pool, 0)