##// END OF EJS Templates
Merge pull request #4107 from minrk/parallel-magics-fix...
Thomas Kluyver -
r12304:f0e4a0f0 merge
parent child Browse files
Show More
@@ -1,385 +1,380 b''
1 1 # -*- coding: utf-8 -*-
2 2 """Test Parallel magics
3 3
4 4 Authors:
5 5
6 6 * Min RK
7 7 """
8 8 #-------------------------------------------------------------------------------
9 9 # Copyright (C) 2011 The IPython Development Team
10 10 #
11 11 # Distributed under the terms of the BSD License. The full license is in
12 12 # the file COPYING, distributed as part of this software.
13 13 #-------------------------------------------------------------------------------
14 14
15 15 #-------------------------------------------------------------------------------
16 16 # Imports
17 17 #-------------------------------------------------------------------------------
18 18
19 19 import re
20 20 import sys
21 21 import time
22 22
23 23 import zmq
24 24 from nose import SkipTest
25 25
26 26 from IPython.testing import decorators as dec
27 27 from IPython.testing.ipunittest import ParametricTestCase
28 28 from IPython.utils.io import capture_output
29 29
30 30 from IPython import parallel as pmod
31 31 from IPython.parallel import error
32 32 from IPython.parallel import AsyncResult
33 33 from IPython.parallel.util import interactive
34 34
35 35 from IPython.parallel.tests import add_engines
36 36
37 37 from .clienttest import ClusterTestCase, generate_output
38 38
39 39 def setup():
40 40 add_engines(3, total=True)
41 41
42 42 class TestParallelMagics(ClusterTestCase, ParametricTestCase):
43 43
44 44 def test_px_blocking(self):
45 45 ip = get_ipython()
46 46 v = self.client[-1:]
47 47 v.activate()
48 48 v.block=True
49 49
50 50 ip.magic('px a=5')
51 51 self.assertEqual(v['a'], [5])
52 52 ip.magic('px a=10')
53 53 self.assertEqual(v['a'], [10])
54 54 # just 'print a' works ~99% of the time, but this ensures that
55 55 # the stdout message has arrived when the result is finished:
56 56 with capture_output() as io:
57 57 ip.magic(
58 58 'px import sys,time;print(a);sys.stdout.flush();time.sleep(0.2)'
59 59 )
60 out = io.stdout
61 self.assertTrue('[stdout:' in out, out)
62 self.assertFalse('\n\n' in out)
63 self.assertTrue(out.rstrip().endswith('10'))
60 self.assertIn('[stdout:', io.stdout)
61 self.assertNotIn('\n\n', io.stdout)
62 assert io.stdout.rstrip().endswith('10')
64 63 self.assertRaisesRemote(ZeroDivisionError, ip.magic, 'px 1/0')
65 64
66 65 def _check_generated_stderr(self, stderr, n):
67 66 expected = [
68 67 r'\[stderr:\d+\]',
69 68 '^stderr$',
70 69 '^stderr2$',
71 70 ] * n
72 71
73 self.assertFalse('\n\n' in stderr, stderr)
72 self.assertNotIn('\n\n', stderr)
74 73 lines = stderr.splitlines()
75 74 self.assertEqual(len(lines), len(expected), stderr)
76 75 for line,expect in zip(lines, expected):
77 76 if isinstance(expect, str):
78 77 expect = [expect]
79 78 for ex in expect:
80 self.assertTrue(re.search(ex, line) is not None, "Expected %r in %r" % (ex, line))
79 assert re.search(ex, line) is not None, "Expected %r in %r" % (ex, line)
81 80
82 81 def test_cellpx_block_args(self):
83 82 """%%px --[no]block flags work"""
84 83 ip = get_ipython()
85 84 v = self.client[-1:]
86 85 v.activate()
87 86 v.block=False
88 87
89 88 for block in (True, False):
90 89 v.block = block
91 90 ip.magic("pxconfig --verbose")
92 with capture_output() as io:
91 with capture_output(display=False) as io:
93 92 ip.run_cell_magic("px", "", "1")
94 93 if block:
95 self.assertTrue(io.stdout.startswith("Parallel"), io.stdout)
94 assert io.stdout.startswith("Parallel"), io.stdout
96 95 else:
97 self.assertTrue(io.stdout.startswith("Async"), io.stdout)
96 assert io.stdout.startswith("Async"), io.stdout
98 97
99 with capture_output() as io:
98 with capture_output(display=False) as io:
100 99 ip.run_cell_magic("px", "--block", "1")
101 self.assertTrue(io.stdout.startswith("Parallel"), io.stdout)
100 assert io.stdout.startswith("Parallel"), io.stdout
102 101
103 with capture_output() as io:
102 with capture_output(display=False) as io:
104 103 ip.run_cell_magic("px", "--noblock", "1")
105 self.assertTrue(io.stdout.startswith("Async"), io.stdout)
104 assert io.stdout.startswith("Async"), io.stdout
106 105
107 106 def test_cellpx_groupby_engine(self):
108 107 """%%px --group-outputs=engine"""
109 108 ip = get_ipython()
110 109 v = self.client[:]
111 110 v.block = True
112 111 v.activate()
113 112
114 113 v['generate_output'] = generate_output
115 114
116 with capture_output() as io:
115 with capture_output(display=False) as io:
117 116 ip.run_cell_magic('px', '--group-outputs=engine', 'generate_output()')
118 117
119 self.assertFalse('\n\n' in io.stdout)
118 self.assertNotIn('\n\n', io.stdout)
120 119 lines = io.stdout.splitlines()
121 120 expected = [
122 121 r'\[stdout:\d+\]',
123 122 'stdout',
124 123 'stdout2',
125 124 r'\[output:\d+\]',
126 125 r'IPython\.core\.display\.HTML',
127 126 r'IPython\.core\.display\.Math',
128 127 r'Out\[\d+:\d+\]:.*IPython\.core\.display\.Math',
129 128 ] * len(v)
130 129
131 130 self.assertEqual(len(lines), len(expected), io.stdout)
132 131 for line,expect in zip(lines, expected):
133 132 if isinstance(expect, str):
134 133 expect = [expect]
135 134 for ex in expect:
136 self.assertTrue(re.search(ex, line) is not None, "Expected %r in %r" % (ex, line))
135 assert re.search(ex, line) is not None, "Expected %r in %r" % (ex, line)
137 136
138 137 self._check_generated_stderr(io.stderr, len(v))
139 138
140 139
141 140 def test_cellpx_groupby_order(self):
142 141 """%%px --group-outputs=order"""
143 142 ip = get_ipython()
144 143 v = self.client[:]
145 144 v.block = True
146 145 v.activate()
147 146
148 147 v['generate_output'] = generate_output
149 148
150 with capture_output() as io:
149 with capture_output(display=False) as io:
151 150 ip.run_cell_magic('px', '--group-outputs=order', 'generate_output()')
152 151
153 self.assertFalse('\n\n' in io.stdout)
152 self.assertNotIn('\n\n', io.stdout)
154 153 lines = io.stdout.splitlines()
155 154 expected = []
156 155 expected.extend([
157 156 r'\[stdout:\d+\]',
158 157 'stdout',
159 158 'stdout2',
160 159 ] * len(v))
161 160 expected.extend([
162 161 r'\[output:\d+\]',
163 162 'IPython.core.display.HTML',
164 163 ] * len(v))
165 164 expected.extend([
166 165 r'\[output:\d+\]',
167 166 'IPython.core.display.Math',
168 167 ] * len(v))
169 168 expected.extend([
170 169 r'Out\[\d+:\d+\]:.*IPython\.core\.display\.Math'
171 170 ] * len(v))
172 171
173 172 self.assertEqual(len(lines), len(expected), io.stdout)
174 173 for line,expect in zip(lines, expected):
175 174 if isinstance(expect, str):
176 175 expect = [expect]
177 176 for ex in expect:
178 self.assertTrue(re.search(ex, line) is not None, "Expected %r in %r" % (ex, line))
177 assert re.search(ex, line) is not None, "Expected %r in %r" % (ex, line)
179 178
180 179 self._check_generated_stderr(io.stderr, len(v))
181 180
182 181 def test_cellpx_groupby_type(self):
183 182 """%%px --group-outputs=type"""
184 183 ip = get_ipython()
185 184 v = self.client[:]
186 185 v.block = True
187 186 v.activate()
188 187
189 188 v['generate_output'] = generate_output
190 189
191 with capture_output() as io:
190 with capture_output(display=False) as io:
192 191 ip.run_cell_magic('px', '--group-outputs=type', 'generate_output()')
193 192
194 self.assertFalse('\n\n' in io.stdout)
193 self.assertNotIn('\n\n', io.stdout)
195 194 lines = io.stdout.splitlines()
196 195
197 196 expected = []
198 197 expected.extend([
199 198 r'\[stdout:\d+\]',
200 199 'stdout',
201 200 'stdout2',
202 201 ] * len(v))
203 202 expected.extend([
204 203 r'\[output:\d+\]',
205 204 r'IPython\.core\.display\.HTML',
206 205 r'IPython\.core\.display\.Math',
207 206 ] * len(v))
208 207 expected.extend([
209 208 (r'Out\[\d+:\d+\]', r'IPython\.core\.display\.Math')
210 209 ] * len(v))
211 210
212 211 self.assertEqual(len(lines), len(expected), io.stdout)
213 212 for line,expect in zip(lines, expected):
214 213 if isinstance(expect, str):
215 214 expect = [expect]
216 215 for ex in expect:
217 self.assertTrue(re.search(ex, line) is not None, "Expected %r in %r" % (ex, line))
216 assert re.search(ex, line) is not None, "Expected %r in %r" % (ex, line)
218 217
219 218 self._check_generated_stderr(io.stderr, len(v))
220 219
221 220
222 221 def test_px_nonblocking(self):
223 222 ip = get_ipython()
224 223 v = self.client[-1:]
225 224 v.activate()
226 225 v.block=False
227 226
228 227 ip.magic('px a=5')
229 228 self.assertEqual(v['a'], [5])
230 229 ip.magic('px a=10')
231 230 self.assertEqual(v['a'], [10])
232 231 ip.magic('pxconfig --verbose')
233 232 with capture_output() as io:
234 233 ar = ip.magic('px print (a)')
235 self.assertTrue(isinstance(ar, AsyncResult))
236 self.assertTrue('Async' in io.stdout)
237 self.assertFalse('[stdout:' in io.stdout)
238 self.assertFalse('\n\n' in io.stdout)
234 self.assertIsInstance(ar, AsyncResult)
235 self.assertIn('Async', io.stdout)
236 self.assertNotIn('[stdout:', io.stdout)
237 self.assertNotIn('\n\n', io.stdout)
239 238
240 239 ar = ip.magic('px 1/0')
241 240 self.assertRaisesRemote(ZeroDivisionError, ar.get)
242 241
243 242 def test_autopx_blocking(self):
244 243 ip = get_ipython()
245 244 v = self.client[-1]
246 245 v.activate()
247 246 v.block=True
248 247
249 with capture_output() as io:
248 with capture_output(display=False) as io:
250 249 ip.magic('autopx')
251 250 ip.run_cell('\n'.join(('a=5','b=12345','c=0')))
252 251 ip.run_cell('b*=2')
253 252 ip.run_cell('print (b)')
254 253 ip.run_cell('b')
255 254 ip.run_cell("b/c")
256 255 ip.magic('autopx')
257 256
258 257 output = io.stdout
259 258
260 self.assertTrue(output.startswith('%autopx enabled'), output)
261 self.assertTrue(output.rstrip().endswith('%autopx disabled'), output)
262 self.assertTrue('ZeroDivisionError' in output, output)
263 self.assertTrue('\nOut[' in output, output)
264 self.assertTrue(': 24690' in output, output)
259 assert output.startswith('%autopx enabled'), output
260 assert output.rstrip().endswith('%autopx disabled'), output
261 self.assertIn('ZeroDivisionError', output)
262 self.assertIn('\nOut[', output)
263 self.assertIn(': 24690', output)
265 264 ar = v.get_result(-1)
266 265 self.assertEqual(v['a'], 5)
267 266 self.assertEqual(v['b'], 24690)
268 267 self.assertRaisesRemote(ZeroDivisionError, ar.get)
269 268
270 269 def test_autopx_nonblocking(self):
271 270 ip = get_ipython()
272 271 v = self.client[-1]
273 272 v.activate()
274 273 v.block=False
275 274
276 275 with capture_output() as io:
277 276 ip.magic('autopx')
278 277 ip.run_cell('\n'.join(('a=5','b=10','c=0')))
279 278 ip.run_cell('print (b)')
280 279 ip.run_cell('import time; time.sleep(0.1)')
281 280 ip.run_cell("b/c")
282 281 ip.run_cell('b*=2')
283 282 ip.magic('autopx')
284 283
285 284 output = io.stdout.rstrip()
286 285
287 self.assertTrue(output.startswith('%autopx enabled'))
288 self.assertTrue(output.endswith('%autopx disabled'))
289 self.assertFalse('ZeroDivisionError' in output)
286 assert output.startswith('%autopx enabled'), output
287 assert output.endswith('%autopx disabled'), output
288 self.assertNotIn('ZeroDivisionError', output)
290 289 ar = v.get_result(-2)
291 290 self.assertRaisesRemote(ZeroDivisionError, ar.get)
292 291 # prevent TaskAborted on pulls, due to ZeroDivisionError
293 292 time.sleep(0.5)
294 293 self.assertEqual(v['a'], 5)
295 294 # b*=2 will not fire, due to abort
296 295 self.assertEqual(v['b'], 10)
297 296
298 297 def test_result(self):
299 298 ip = get_ipython()
300 299 v = self.client[-1]
301 300 v.activate()
302 301 data = dict(a=111,b=222)
303 302 v.push(data, block=True)
304 303
305 304 for name in ('a', 'b'):
306 305 ip.magic('px ' + name)
307 with capture_output() as io:
306 with capture_output(display=False) as io:
308 307 ip.magic('pxresult')
309 output = io.stdout
310 msg = "expected %s output to include %s, but got: %s" % \
311 ('%pxresult', str(data[name]), output)
312 self.assertTrue(str(data[name]) in output, msg)
308 self.assertIn(str(data[name]), io.stdout)
313 309
314 310 @dec.skipif_not_matplotlib
315 311 def test_px_pylab(self):
316 312 """%pylab works on engines"""
317 313 ip = get_ipython()
318 314 v = self.client[-1]
319 315 v.block = True
320 316 v.activate()
321 317
322 318 with capture_output() as io:
323 319 ip.magic("px %pylab inline")
324 320
325 self.assertTrue("Populating the interactive namespace from numpy and matplotlib" in io.stdout, io.stdout)
321 self.assertIn("Populating the interactive namespace from numpy and matplotlib", io.stdout)
326 322
327 with capture_output() as io:
323 with capture_output(display=False) as io:
328 324 ip.magic("px plot(rand(100))")
329
330 self.assertTrue('Out[' in io.stdout, io.stdout)
331 self.assertTrue('matplotlib.lines' in io.stdout, io.stdout)
325 self.assertIn('Out[', io.stdout)
326 self.assertIn('matplotlib.lines', io.stdout)
332 327
333 328 def test_pxconfig(self):
334 329 ip = get_ipython()
335 330 rc = self.client
336 331 v = rc.activate(-1, '_tst')
337 332 self.assertEqual(v.targets, rc.ids[-1])
338 333 ip.magic("%pxconfig_tst -t :")
339 334 self.assertEqual(v.targets, rc.ids)
340 335 ip.magic("%pxconfig_tst -t ::2")
341 336 self.assertEqual(v.targets, rc.ids[::2])
342 337 ip.magic("%pxconfig_tst -t 1::2")
343 338 self.assertEqual(v.targets, rc.ids[1::2])
344 339 ip.magic("%pxconfig_tst -t 1")
345 340 self.assertEqual(v.targets, 1)
346 341 ip.magic("%pxconfig_tst --block")
347 342 self.assertEqual(v.block, True)
348 343 ip.magic("%pxconfig_tst --noblock")
349 344 self.assertEqual(v.block, False)
350 345
351 346 def test_cellpx_targets(self):
352 347 """%%px --targets doesn't change defaults"""
353 348 ip = get_ipython()
354 349 rc = self.client
355 350 view = rc.activate(rc.ids)
356 351 self.assertEqual(view.targets, rc.ids)
357 352 ip.magic('pxconfig --verbose')
358 353 for cell in ("pass", "1/0"):
359 with capture_output() as io:
354 with capture_output(display=False) as io:
360 355 try:
361 356 ip.run_cell_magic("px", "--targets all", cell)
362 357 except pmod.RemoteError:
363 358 pass
364 self.assertTrue('engine(s): all' in io.stdout)
359 self.assertIn('engine(s): all', io.stdout)
365 360 self.assertEqual(view.targets, rc.ids)
366 361
367 362
368 363 def test_cellpx_block(self):
369 364 """%%px --block doesn't change default"""
370 365 ip = get_ipython()
371 366 rc = self.client
372 367 view = rc.activate(rc.ids)
373 368 view.block = False
374 369 self.assertEqual(view.targets, rc.ids)
375 370 ip.magic('pxconfig --verbose')
376 371 for cell in ("pass", "1/0"):
377 with capture_output() as io:
372 with capture_output(display=False) as io:
378 373 try:
379 374 ip.run_cell_magic("px", "--block", cell)
380 375 except pmod.RemoteError:
381 376 pass
382 self.assertFalse('Async' in io.stdout)
383 self.assertFalse(view.block)
377 self.assertNotIn('Async', io.stdout)
378 self.assertEqual(view.block, False)
384 379
385 380
General Comments 0
You need to be logged in to leave comments. Login now