##// END OF EJS Templates
Sort and unique %config results
Sang Min Park -
Show More
@@ -1,157 +1,158 b''
1 1 """Implementation of configuration-related magic functions.
2 2 """
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2012 The IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 # Stdlib
16 16 import re
17 17
18 18 # Our own packages
19 19 from IPython.core.error import UsageError
20 20 from IPython.core.magic import Magics, magics_class, line_magic
21 21 from logging import error
22 22
23 23 #-----------------------------------------------------------------------------
24 24 # Magic implementation classes
25 25 #-----------------------------------------------------------------------------
26 26
27 27 reg = re.compile('^\w+\.\w+$')
28 28 @magics_class
29 29 class ConfigMagics(Magics):
30 30
31 31 def __init__(self, shell):
32 32 super(ConfigMagics, self).__init__(shell)
33 33 self.configurables = []
34 34
35 35 @line_magic
36 36 def config(self, s):
37 37 """configure IPython
38 38
39 39 %config Class[.trait=value]
40 40
41 41 This magic exposes most of the IPython config system. Any
42 42 Configurable class should be able to be configured with the simple
43 43 line::
44 44
45 45 %config Class.trait=value
46 46
47 47 Where `value` will be resolved in the user's namespace, if it is an
48 48 expression or variable name.
49 49
50 50 Examples
51 51 --------
52 52
53 53 To see what classes are available for config, pass no arguments::
54 54
55 55 In [1]: %config
56 56 Available objects for config:
57 57 TerminalInteractiveShell
58 58 HistoryManager
59 59 PrefilterManager
60 60 AliasManager
61 61 IPCompleter
62 62 DisplayFormatter
63 63
64 64 To view what is configurable on a given class, just pass the class
65 65 name::
66 66
67 67 In [2]: %config IPCompleter
68 68 IPCompleter options
69 69 -----------------
70 70 IPCompleter.omit__names=<Enum>
71 71 Current: 2
72 72 Choices: (0, 1, 2)
73 73 Instruct the completer to omit private method names
74 74 Specifically, when completing on ``object.<tab>``.
75 75 When 2 [default]: all names that start with '_' will be excluded.
76 76 When 1: all 'magic' names (``__foo__``) will be excluded.
77 77 When 0: nothing will be excluded.
78 78 IPCompleter.merge_completions=<CBool>
79 79 Current: True
80 80 Whether to merge completion results into a single list
81 81 If False, only the completion results from the first non-empty
82 82 completer will be returned.
83 83 IPCompleter.limit_to__all__=<CBool>
84 84 Current: False
85 85 Instruct the completer to use __all__ for the completion
86 86 Specifically, when completing on ``object.<tab>``.
87 87 When True: only those names in obj.__all__ will be included.
88 88 When False [default]: the __all__ attribute is ignored
89 89 IPCompleter.greedy=<CBool>
90 90 Current: False
91 91 Activate greedy completion
92 92 This will enable completion on elements of lists, results of
93 93 function calls, etc., but can be unsafe because the code is
94 94 actually evaluated on TAB.
95 95
96 96 but the real use is in setting values::
97 97
98 98 In [3]: %config IPCompleter.greedy = True
99 99
100 100 and these values are read from the user_ns if they are variables::
101 101
102 102 In [4]: feeling_greedy=False
103 103
104 104 In [5]: %config IPCompleter.greedy = feeling_greedy
105 105
106 106 """
107 107 from traitlets.config.loader import Config
108 108 # some IPython objects are Configurable, but do not yet have
109 109 # any configurable traits. Exclude them from the effects of
110 110 # this magic, as their presence is just noise:
111 configurables = [ c for c in self.shell.configurables
112 if c.__class__.class_traits(config=True) ]
111 configurables = sorted(set([ c for c in self.shell.configurables
112 if c.__class__.class_traits(config=True)
113 ]), key=lambda x: x.__class__.__name__)
113 114 classnames = [ c.__class__.__name__ for c in configurables ]
114 115
115 116 line = s.strip()
116 117 if not line:
117 118 # print available configurable names
118 119 print("Available objects for config:")
119 120 for name in classnames:
120 121 print(" ", name)
121 122 return
122 123 elif line in classnames:
123 124 # `%config TerminalInteractiveShell` will print trait info for
124 125 # TerminalInteractiveShell
125 126 c = configurables[classnames.index(line)]
126 127 cls = c.__class__
127 128 help = cls.class_get_help(c)
128 129 # strip leading '--' from cl-args:
129 130 help = re.sub(re.compile(r'^--', re.MULTILINE), '', help)
130 131 print(help)
131 132 return
132 133 elif reg.match(line):
133 134 cls, attr = line.split('.')
134 135 return getattr(configurables[classnames.index(cls)],attr)
135 136 elif '=' not in line:
136 137 msg = "Invalid config statement: %r, "\
137 138 "should be `Class.trait = value`."
138 139
139 140 ll = line.lower()
140 141 for classname in classnames:
141 142 if ll == classname.lower():
142 143 msg = msg + '\nDid you mean %s (note the case)?' % classname
143 144 break
144 145
145 146 raise UsageError( msg % line)
146 147
147 148 # otherwise, assume we are setting configurables.
148 149 # leave quotes on args when splitting, because we want
149 150 # unquoted args to eval in user_ns
150 151 cfg = Config()
151 152 exec("cfg."+line, locals(), self.shell.user_ns)
152 153
153 154 for configurable in configurables:
154 155 try:
155 156 configurable.update_config(cfg)
156 157 except Exception as e:
157 158 error(e)
@@ -1,979 +1,997 b''
1 1 # -*- coding: utf-8 -*-
2 2 """Tests for various magic functions.
3 3
4 4 Needs to be run by nose (to make ipython session available).
5 5 """
6 6
7 7 import io
8 8 import os
9 9 import sys
10 10 import warnings
11 11 from unittest import TestCase
12 12 from importlib import invalidate_caches
13 13 from io import StringIO
14 14
15 15 import nose.tools as nt
16 16
17 17 from IPython import get_ipython
18 18 from IPython.core import magic
19 19 from IPython.core.error import UsageError
20 20 from IPython.core.magic import (Magics, magics_class, line_magic,
21 21 cell_magic,
22 22 register_line_magic, register_cell_magic)
23 23 from IPython.core.magics import execution, script, code
24 24 from IPython.testing import decorators as dec
25 25 from IPython.testing import tools as tt
26 26 from IPython.utils import py3compat
27 27 from IPython.utils.io import capture_output
28 28 from IPython.utils.tempdir import TemporaryDirectory
29 29 from IPython.utils.process import find_cmd
30 30
31 31
32 32
33 33 _ip = get_ipython()
34 34
35 35 @magic.magics_class
36 36 class DummyMagics(magic.Magics): pass
37 37
38 38 def test_extract_code_ranges():
39 39 instr = "1 3 5-6 7-9 10:15 17: :10 10- -13 :"
40 40 expected = [(0, 1),
41 41 (2, 3),
42 42 (4, 6),
43 43 (6, 9),
44 44 (9, 14),
45 45 (16, None),
46 46 (None, 9),
47 47 (9, None),
48 48 (None, 13),
49 49 (None, None)]
50 50 actual = list(code.extract_code_ranges(instr))
51 51 nt.assert_equal(actual, expected)
52 52
53 53 def test_extract_symbols():
54 54 source = """import foo\na = 10\ndef b():\n return 42\n\n\nclass A: pass\n\n\n"""
55 55 symbols_args = ["a", "b", "A", "A,b", "A,a", "z"]
56 56 expected = [([], ['a']),
57 57 (["def b():\n return 42\n"], []),
58 58 (["class A: pass\n"], []),
59 59 (["class A: pass\n", "def b():\n return 42\n"], []),
60 60 (["class A: pass\n"], ['a']),
61 61 ([], ['z'])]
62 62 for symbols, exp in zip(symbols_args, expected):
63 63 nt.assert_equal(code.extract_symbols(source, symbols), exp)
64 64
65 65
66 66 def test_extract_symbols_raises_exception_with_non_python_code():
67 67 source = ("=begin A Ruby program :)=end\n"
68 68 "def hello\n"
69 69 "puts 'Hello world'\n"
70 70 "end")
71 71 with nt.assert_raises(SyntaxError):
72 72 code.extract_symbols(source, "hello")
73 73
74 74 def test_config():
75 75 """ test that config magic does not raise
76 76 can happen if Configurable init is moved too early into
77 77 Magics.__init__ as then a Config object will be registerd as a
78 78 magic.
79 79 """
80 80 ## should not raise.
81 81 _ip.magic('config')
82 82
83 def test_config_available_configs():
84 """ test that config magic prints available configs in unique and
85 sorted order. """
86 with capture_output() as captured:
87 _ip.magic('config')
88
89 stdout = captured.stdout
90 config_classes = stdout.strip().split('\n')[1:]
91 nt.assert_list_equal(config_classes, sorted(set(config_classes)))
92
93 def test_config_print_class():
94 """ test that config with a classname prints the class's options. """
95 with capture_output() as captured:
96 _ip.magic('config TerminalInteractiveShell')
97
98 stdout = captured.stdout
99 nt.assert_in("TerminalInteractiveShell options", stdout)
100
83 101 def test_rehashx():
84 102 # clear up everything
85 103 _ip.alias_manager.clear_aliases()
86 104 del _ip.db['syscmdlist']
87 105
88 106 _ip.magic('rehashx')
89 107 # Practically ALL ipython development systems will have more than 10 aliases
90 108
91 109 nt.assert_true(len(_ip.alias_manager.aliases) > 10)
92 110 for name, cmd in _ip.alias_manager.aliases:
93 111 # we must strip dots from alias names
94 112 nt.assert_not_in('.', name)
95 113
96 114 # rehashx must fill up syscmdlist
97 115 scoms = _ip.db['syscmdlist']
98 116 nt.assert_true(len(scoms) > 10)
99 117
100 118
101 119 def test_magic_parse_options():
102 120 """Test that we don't mangle paths when parsing magic options."""
103 121 ip = get_ipython()
104 122 path = 'c:\\x'
105 123 m = DummyMagics(ip)
106 124 opts = m.parse_options('-f %s' % path,'f:')[0]
107 125 # argv splitting is os-dependent
108 126 if os.name == 'posix':
109 127 expected = 'c:x'
110 128 else:
111 129 expected = path
112 130 nt.assert_equal(opts['f'], expected)
113 131
114 132 def test_magic_parse_long_options():
115 133 """Magic.parse_options can handle --foo=bar long options"""
116 134 ip = get_ipython()
117 135 m = DummyMagics(ip)
118 136 opts, _ = m.parse_options('--foo --bar=bubble', 'a', 'foo', 'bar=')
119 137 nt.assert_in('foo', opts)
120 138 nt.assert_in('bar', opts)
121 139 nt.assert_equal(opts['bar'], "bubble")
122 140
123 141
124 142 @dec.skip_without('sqlite3')
125 143 def doctest_hist_f():
126 144 """Test %hist -f with temporary filename.
127 145
128 146 In [9]: import tempfile
129 147
130 148 In [10]: tfile = tempfile.mktemp('.py','tmp-ipython-')
131 149
132 150 In [11]: %hist -nl -f $tfile 3
133 151
134 152 In [13]: import os; os.unlink(tfile)
135 153 """
136 154
137 155
138 156 @dec.skip_without('sqlite3')
139 157 def doctest_hist_r():
140 158 """Test %hist -r
141 159
142 160 XXX - This test is not recording the output correctly. For some reason, in
143 161 testing mode the raw history isn't getting populated. No idea why.
144 162 Disabling the output checking for now, though at least we do run it.
145 163
146 164 In [1]: 'hist' in _ip.lsmagic()
147 165 Out[1]: True
148 166
149 167 In [2]: x=1
150 168
151 169 In [3]: %hist -rl 2
152 170 x=1 # random
153 171 %hist -r 2
154 172 """
155 173
156 174
157 175 @dec.skip_without('sqlite3')
158 176 def doctest_hist_op():
159 177 """Test %hist -op
160 178
161 179 In [1]: class b(float):
162 180 ...: pass
163 181 ...:
164 182
165 183 In [2]: class s(object):
166 184 ...: def __str__(self):
167 185 ...: return 's'
168 186 ...:
169 187
170 188 In [3]:
171 189
172 190 In [4]: class r(b):
173 191 ...: def __repr__(self):
174 192 ...: return 'r'
175 193 ...:
176 194
177 195 In [5]: class sr(s,r): pass
178 196 ...:
179 197
180 198 In [6]:
181 199
182 200 In [7]: bb=b()
183 201
184 202 In [8]: ss=s()
185 203
186 204 In [9]: rr=r()
187 205
188 206 In [10]: ssrr=sr()
189 207
190 208 In [11]: 4.5
191 209 Out[11]: 4.5
192 210
193 211 In [12]: str(ss)
194 212 Out[12]: 's'
195 213
196 214 In [13]:
197 215
198 216 In [14]: %hist -op
199 217 >>> class b:
200 218 ... pass
201 219 ...
202 220 >>> class s(b):
203 221 ... def __str__(self):
204 222 ... return 's'
205 223 ...
206 224 >>>
207 225 >>> class r(b):
208 226 ... def __repr__(self):
209 227 ... return 'r'
210 228 ...
211 229 >>> class sr(s,r): pass
212 230 >>>
213 231 >>> bb=b()
214 232 >>> ss=s()
215 233 >>> rr=r()
216 234 >>> ssrr=sr()
217 235 >>> 4.5
218 236 4.5
219 237 >>> str(ss)
220 238 's'
221 239 >>>
222 240 """
223 241
224 242 def test_hist_pof():
225 243 ip = get_ipython()
226 244 ip.run_cell(u"1+2", store_history=True)
227 245 #raise Exception(ip.history_manager.session_number)
228 246 #raise Exception(list(ip.history_manager._get_range_session()))
229 247 with TemporaryDirectory() as td:
230 248 tf = os.path.join(td, 'hist.py')
231 249 ip.run_line_magic('history', '-pof %s' % tf)
232 250 assert os.path.isfile(tf)
233 251
234 252
235 253 @dec.skip_without('sqlite3')
236 254 def test_macro():
237 255 ip = get_ipython()
238 256 ip.history_manager.reset() # Clear any existing history.
239 257 cmds = ["a=1", "def b():\n return a**2", "print(a,b())"]
240 258 for i, cmd in enumerate(cmds, start=1):
241 259 ip.history_manager.store_inputs(i, cmd)
242 260 ip.magic("macro test 1-3")
243 261 nt.assert_equal(ip.user_ns["test"].value, "\n".join(cmds)+"\n")
244 262
245 263 # List macros
246 264 nt.assert_in("test", ip.magic("macro"))
247 265
248 266
249 267 @dec.skip_without('sqlite3')
250 268 def test_macro_run():
251 269 """Test that we can run a multi-line macro successfully."""
252 270 ip = get_ipython()
253 271 ip.history_manager.reset()
254 272 cmds = ["a=10", "a+=1", py3compat.doctest_refactor_print("print a"),
255 273 "%macro test 2-3"]
256 274 for cmd in cmds:
257 275 ip.run_cell(cmd, store_history=True)
258 276 nt.assert_equal(ip.user_ns["test"].value,
259 277 py3compat.doctest_refactor_print("a+=1\nprint a\n"))
260 278 with tt.AssertPrints("12"):
261 279 ip.run_cell("test")
262 280 with tt.AssertPrints("13"):
263 281 ip.run_cell("test")
264 282
265 283
266 284 def test_magic_magic():
267 285 """Test %magic"""
268 286 ip = get_ipython()
269 287 with capture_output() as captured:
270 288 ip.magic("magic")
271 289
272 290 stdout = captured.stdout
273 291 nt.assert_in('%magic', stdout)
274 292 nt.assert_in('IPython', stdout)
275 293 nt.assert_in('Available', stdout)
276 294
277 295
278 296 @dec.skipif_not_numpy
279 297 def test_numpy_reset_array_undec():
280 298 "Test '%reset array' functionality"
281 299 _ip.ex('import numpy as np')
282 300 _ip.ex('a = np.empty(2)')
283 301 nt.assert_in('a', _ip.user_ns)
284 302 _ip.magic('reset -f array')
285 303 nt.assert_not_in('a', _ip.user_ns)
286 304
287 305 def test_reset_out():
288 306 "Test '%reset out' magic"
289 307 _ip.run_cell("parrot = 'dead'", store_history=True)
290 308 # test '%reset -f out', make an Out prompt
291 309 _ip.run_cell("parrot", store_history=True)
292 310 nt.assert_true('dead' in [_ip.user_ns[x] for x in ('_','__','___')])
293 311 _ip.magic('reset -f out')
294 312 nt.assert_false('dead' in [_ip.user_ns[x] for x in ('_','__','___')])
295 313 nt.assert_equal(len(_ip.user_ns['Out']), 0)
296 314
297 315 def test_reset_in():
298 316 "Test '%reset in' magic"
299 317 # test '%reset -f in'
300 318 _ip.run_cell("parrot", store_history=True)
301 319 nt.assert_true('parrot' in [_ip.user_ns[x] for x in ('_i','_ii','_iii')])
302 320 _ip.magic('%reset -f in')
303 321 nt.assert_false('parrot' in [_ip.user_ns[x] for x in ('_i','_ii','_iii')])
304 322 nt.assert_equal(len(set(_ip.user_ns['In'])), 1)
305 323
306 324 def test_reset_dhist():
307 325 "Test '%reset dhist' magic"
308 326 _ip.run_cell("tmp = [d for d in _dh]") # copy before clearing
309 327 _ip.magic('cd ' + os.path.dirname(nt.__file__))
310 328 _ip.magic('cd -')
311 329 nt.assert_true(len(_ip.user_ns['_dh']) > 0)
312 330 _ip.magic('reset -f dhist')
313 331 nt.assert_equal(len(_ip.user_ns['_dh']), 0)
314 332 _ip.run_cell("_dh = [d for d in tmp]") #restore
315 333
316 334 def test_reset_in_length():
317 335 "Test that '%reset in' preserves In[] length"
318 336 _ip.run_cell("print 'foo'")
319 337 _ip.run_cell("reset -f in")
320 338 nt.assert_equal(len(_ip.user_ns['In']), _ip.displayhook.prompt_count+1)
321 339
322 340 def test_tb_syntaxerror():
323 341 """test %tb after a SyntaxError"""
324 342 ip = get_ipython()
325 343 ip.run_cell("for")
326 344
327 345 # trap and validate stdout
328 346 save_stdout = sys.stdout
329 347 try:
330 348 sys.stdout = StringIO()
331 349 ip.run_cell("%tb")
332 350 out = sys.stdout.getvalue()
333 351 finally:
334 352 sys.stdout = save_stdout
335 353 # trim output, and only check the last line
336 354 last_line = out.rstrip().splitlines()[-1].strip()
337 355 nt.assert_equal(last_line, "SyntaxError: invalid syntax")
338 356
339 357
340 358 def test_time():
341 359 ip = get_ipython()
342 360
343 361 with tt.AssertPrints("Wall time: "):
344 362 ip.run_cell("%time None")
345 363
346 364 ip.run_cell("def f(kmjy):\n"
347 365 " %time print (2*kmjy)")
348 366
349 367 with tt.AssertPrints("Wall time: "):
350 368 with tt.AssertPrints("hihi", suppress=False):
351 369 ip.run_cell("f('hi')")
352 370
353 371
354 372 @dec.skip_win32
355 373 def test_time2():
356 374 ip = get_ipython()
357 375
358 376 with tt.AssertPrints("CPU times: user "):
359 377 ip.run_cell("%time None")
360 378
361 379 def test_time3():
362 380 """Erroneous magic function calls, issue gh-3334"""
363 381 ip = get_ipython()
364 382 ip.user_ns.pop('run', None)
365 383
366 384 with tt.AssertNotPrints("not found", channel='stderr'):
367 385 ip.run_cell("%%time\n"
368 386 "run = 0\n"
369 387 "run += 1")
370 388
371 389 def test_doctest_mode():
372 390 "Toggle doctest_mode twice, it should be a no-op and run without error"
373 391 _ip.magic('doctest_mode')
374 392 _ip.magic('doctest_mode')
375 393
376 394
377 395 def test_parse_options():
378 396 """Tests for basic options parsing in magics."""
379 397 # These are only the most minimal of tests, more should be added later. At
380 398 # the very least we check that basic text/unicode calls work OK.
381 399 m = DummyMagics(_ip)
382 400 nt.assert_equal(m.parse_options('foo', '')[1], 'foo')
383 401 nt.assert_equal(m.parse_options(u'foo', '')[1], u'foo')
384 402
385 403
386 404 def test_dirops():
387 405 """Test various directory handling operations."""
388 406 # curpath = lambda :os.path.splitdrive(os.getcwd())[1].replace('\\','/')
389 407 curpath = os.getcwd
390 408 startdir = os.getcwd()
391 409 ipdir = os.path.realpath(_ip.ipython_dir)
392 410 try:
393 411 _ip.magic('cd "%s"' % ipdir)
394 412 nt.assert_equal(curpath(), ipdir)
395 413 _ip.magic('cd -')
396 414 nt.assert_equal(curpath(), startdir)
397 415 _ip.magic('pushd "%s"' % ipdir)
398 416 nt.assert_equal(curpath(), ipdir)
399 417 _ip.magic('popd')
400 418 nt.assert_equal(curpath(), startdir)
401 419 finally:
402 420 os.chdir(startdir)
403 421
404 422
405 423 def test_xmode():
406 424 # Calling xmode three times should be a no-op
407 425 xmode = _ip.InteractiveTB.mode
408 426 for i in range(3):
409 427 _ip.magic("xmode")
410 428 nt.assert_equal(_ip.InteractiveTB.mode, xmode)
411 429
412 430 def test_reset_hard():
413 431 monitor = []
414 432 class A(object):
415 433 def __del__(self):
416 434 monitor.append(1)
417 435 def __repr__(self):
418 436 return "<A instance>"
419 437
420 438 _ip.user_ns["a"] = A()
421 439 _ip.run_cell("a")
422 440
423 441 nt.assert_equal(monitor, [])
424 442 _ip.magic("reset -f")
425 443 nt.assert_equal(monitor, [1])
426 444
427 445 class TestXdel(tt.TempFileMixin):
428 446 def test_xdel(self):
429 447 """Test that references from %run are cleared by xdel."""
430 448 src = ("class A(object):\n"
431 449 " monitor = []\n"
432 450 " def __del__(self):\n"
433 451 " self.monitor.append(1)\n"
434 452 "a = A()\n")
435 453 self.mktmp(src)
436 454 # %run creates some hidden references...
437 455 _ip.magic("run %s" % self.fname)
438 456 # ... as does the displayhook.
439 457 _ip.run_cell("a")
440 458
441 459 monitor = _ip.user_ns["A"].monitor
442 460 nt.assert_equal(monitor, [])
443 461
444 462 _ip.magic("xdel a")
445 463
446 464 # Check that a's __del__ method has been called.
447 465 nt.assert_equal(monitor, [1])
448 466
449 467 def doctest_who():
450 468 """doctest for %who
451 469
452 470 In [1]: %reset -f
453 471
454 472 In [2]: alpha = 123
455 473
456 474 In [3]: beta = 'beta'
457 475
458 476 In [4]: %who int
459 477 alpha
460 478
461 479 In [5]: %who str
462 480 beta
463 481
464 482 In [6]: %whos
465 483 Variable Type Data/Info
466 484 ----------------------------
467 485 alpha int 123
468 486 beta str beta
469 487
470 488 In [7]: %who_ls
471 489 Out[7]: ['alpha', 'beta']
472 490 """
473 491
474 492 def test_whos():
475 493 """Check that whos is protected against objects where repr() fails."""
476 494 class A(object):
477 495 def __repr__(self):
478 496 raise Exception()
479 497 _ip.user_ns['a'] = A()
480 498 _ip.magic("whos")
481 499
482 500 @py3compat.u_format
483 501 def doctest_precision():
484 502 """doctest for %precision
485 503
486 504 In [1]: f = get_ipython().display_formatter.formatters['text/plain']
487 505
488 506 In [2]: %precision 5
489 507 Out[2]: {u}'%.5f'
490 508
491 509 In [3]: f.float_format
492 510 Out[3]: {u}'%.5f'
493 511
494 512 In [4]: %precision %e
495 513 Out[4]: {u}'%e'
496 514
497 515 In [5]: f(3.1415927)
498 516 Out[5]: {u}'3.141593e+00'
499 517 """
500 518
501 519 def test_psearch():
502 520 with tt.AssertPrints("dict.fromkeys"):
503 521 _ip.run_cell("dict.fr*?")
504 522
505 523 def test_timeit_shlex():
506 524 """test shlex issues with timeit (#1109)"""
507 525 _ip.ex("def f(*a,**kw): pass")
508 526 _ip.magic('timeit -n1 "this is a bug".count(" ")')
509 527 _ip.magic('timeit -r1 -n1 f(" ", 1)')
510 528 _ip.magic('timeit -r1 -n1 f(" ", 1, " ", 2, " ")')
511 529 _ip.magic('timeit -r1 -n1 ("a " + "b")')
512 530 _ip.magic('timeit -r1 -n1 f("a " + "b")')
513 531 _ip.magic('timeit -r1 -n1 f("a " + "b ")')
514 532
515 533
516 534 def test_timeit_arguments():
517 535 "Test valid timeit arguments, should not cause SyntaxError (GH #1269)"
518 536 _ip.magic("timeit ('#')")
519 537
520 538
521 539 def test_timeit_special_syntax():
522 540 "Test %%timeit with IPython special syntax"
523 541 @register_line_magic
524 542 def lmagic(line):
525 543 ip = get_ipython()
526 544 ip.user_ns['lmagic_out'] = line
527 545
528 546 # line mode test
529 547 _ip.run_line_magic('timeit', '-n1 -r1 %lmagic my line')
530 548 nt.assert_equal(_ip.user_ns['lmagic_out'], 'my line')
531 549 # cell mode test
532 550 _ip.run_cell_magic('timeit', '-n1 -r1', '%lmagic my line2')
533 551 nt.assert_equal(_ip.user_ns['lmagic_out'], 'my line2')
534 552
535 553 def test_timeit_return():
536 554 """
537 555 test wether timeit -o return object
538 556 """
539 557
540 558 res = _ip.run_line_magic('timeit','-n10 -r10 -o 1')
541 559 assert(res is not None)
542 560
543 561 def test_timeit_quiet():
544 562 """
545 563 test quiet option of timeit magic
546 564 """
547 565 with tt.AssertNotPrints("loops"):
548 566 _ip.run_cell("%timeit -n1 -r1 -q 1")
549 567
550 568 def test_timeit_return_quiet():
551 569 with tt.AssertNotPrints("loops"):
552 570 res = _ip.run_line_magic('timeit', '-n1 -r1 -q -o 1')
553 571 assert (res is not None)
554 572
555 573 @dec.skipif(execution.profile is None)
556 574 def test_prun_special_syntax():
557 575 "Test %%prun with IPython special syntax"
558 576 @register_line_magic
559 577 def lmagic(line):
560 578 ip = get_ipython()
561 579 ip.user_ns['lmagic_out'] = line
562 580
563 581 # line mode test
564 582 _ip.run_line_magic('prun', '-q %lmagic my line')
565 583 nt.assert_equal(_ip.user_ns['lmagic_out'], 'my line')
566 584 # cell mode test
567 585 _ip.run_cell_magic('prun', '-q', '%lmagic my line2')
568 586 nt.assert_equal(_ip.user_ns['lmagic_out'], 'my line2')
569 587
570 588 @dec.skipif(execution.profile is None)
571 589 def test_prun_quotes():
572 590 "Test that prun does not clobber string escapes (GH #1302)"
573 591 _ip.magic(r"prun -q x = '\t'")
574 592 nt.assert_equal(_ip.user_ns['x'], '\t')
575 593
576 594 def test_extension():
577 595 # Debugging information for failures of this test
578 596 print('sys.path:')
579 597 for p in sys.path:
580 598 print(' ', p)
581 599 print('CWD', os.getcwd())
582 600
583 601 nt.assert_raises(ImportError, _ip.magic, "load_ext daft_extension")
584 602 daft_path = os.path.join(os.path.dirname(__file__), "daft_extension")
585 603 sys.path.insert(0, daft_path)
586 604 try:
587 605 _ip.user_ns.pop('arq', None)
588 606 invalidate_caches() # Clear import caches
589 607 _ip.magic("load_ext daft_extension")
590 608 nt.assert_equal(_ip.user_ns['arq'], 185)
591 609 _ip.magic("unload_ext daft_extension")
592 610 assert 'arq' not in _ip.user_ns
593 611 finally:
594 612 sys.path.remove(daft_path)
595 613
596 614
597 615 def test_notebook_export_json():
598 616 _ip = get_ipython()
599 617 _ip.history_manager.reset() # Clear any existing history.
600 618 cmds = [u"a=1", u"def b():\n return a**2", u"print('noΓ«l, Γ©tΓ©', b())"]
601 619 for i, cmd in enumerate(cmds, start=1):
602 620 _ip.history_manager.store_inputs(i, cmd)
603 621 with TemporaryDirectory() as td:
604 622 outfile = os.path.join(td, "nb.ipynb")
605 623 _ip.magic("notebook -e %s" % outfile)
606 624
607 625
608 626 class TestEnv(TestCase):
609 627
610 628 def test_env(self):
611 629 env = _ip.magic("env")
612 630 self.assertTrue(isinstance(env, dict))
613 631
614 632 def test_env_get_set_simple(self):
615 633 env = _ip.magic("env var val1")
616 634 self.assertEqual(env, None)
617 635 self.assertEqual(os.environ['var'], 'val1')
618 636 self.assertEqual(_ip.magic("env var"), 'val1')
619 637 env = _ip.magic("env var=val2")
620 638 self.assertEqual(env, None)
621 639 self.assertEqual(os.environ['var'], 'val2')
622 640
623 641 def test_env_get_set_complex(self):
624 642 env = _ip.magic("env var 'val1 '' 'val2")
625 643 self.assertEqual(env, None)
626 644 self.assertEqual(os.environ['var'], "'val1 '' 'val2")
627 645 self.assertEqual(_ip.magic("env var"), "'val1 '' 'val2")
628 646 env = _ip.magic('env var=val2 val3="val4')
629 647 self.assertEqual(env, None)
630 648 self.assertEqual(os.environ['var'], 'val2 val3="val4')
631 649
632 650 def test_env_set_bad_input(self):
633 651 self.assertRaises(UsageError, lambda: _ip.magic("set_env var"))
634 652
635 653 def test_env_set_whitespace(self):
636 654 self.assertRaises(UsageError, lambda: _ip.magic("env var A=B"))
637 655
638 656
639 657 class CellMagicTestCase(TestCase):
640 658
641 659 def check_ident(self, magic):
642 660 # Manually called, we get the result
643 661 out = _ip.run_cell_magic(magic, 'a', 'b')
644 662 nt.assert_equal(out, ('a','b'))
645 663 # Via run_cell, it goes into the user's namespace via displayhook
646 664 _ip.run_cell('%%' + magic +' c\nd')
647 665 nt.assert_equal(_ip.user_ns['_'], ('c','d'))
648 666
649 667 def test_cell_magic_func_deco(self):
650 668 "Cell magic using simple decorator"
651 669 @register_cell_magic
652 670 def cellm(line, cell):
653 671 return line, cell
654 672
655 673 self.check_ident('cellm')
656 674
657 675 def test_cell_magic_reg(self):
658 676 "Cell magic manually registered"
659 677 def cellm(line, cell):
660 678 return line, cell
661 679
662 680 _ip.register_magic_function(cellm, 'cell', 'cellm2')
663 681 self.check_ident('cellm2')
664 682
665 683 def test_cell_magic_class(self):
666 684 "Cell magics declared via a class"
667 685 @magics_class
668 686 class MyMagics(Magics):
669 687
670 688 @cell_magic
671 689 def cellm3(self, line, cell):
672 690 return line, cell
673 691
674 692 _ip.register_magics(MyMagics)
675 693 self.check_ident('cellm3')
676 694
677 695 def test_cell_magic_class2(self):
678 696 "Cell magics declared via a class, #2"
679 697 @magics_class
680 698 class MyMagics2(Magics):
681 699
682 700 @cell_magic('cellm4')
683 701 def cellm33(self, line, cell):
684 702 return line, cell
685 703
686 704 _ip.register_magics(MyMagics2)
687 705 self.check_ident('cellm4')
688 706 # Check that nothing is registered as 'cellm33'
689 707 c33 = _ip.find_cell_magic('cellm33')
690 708 nt.assert_equal(c33, None)
691 709
692 710 def test_file():
693 711 """Basic %%file"""
694 712 ip = get_ipython()
695 713 with TemporaryDirectory() as td:
696 714 fname = os.path.join(td, 'file1')
697 715 ip.run_cell_magic("file", fname, u'\n'.join([
698 716 'line1',
699 717 'line2',
700 718 ]))
701 719 with open(fname) as f:
702 720 s = f.read()
703 721 nt.assert_in('line1\n', s)
704 722 nt.assert_in('line2', s)
705 723
706 724 def test_file_var_expand():
707 725 """%%file $filename"""
708 726 ip = get_ipython()
709 727 with TemporaryDirectory() as td:
710 728 fname = os.path.join(td, 'file1')
711 729 ip.user_ns['filename'] = fname
712 730 ip.run_cell_magic("file", '$filename', u'\n'.join([
713 731 'line1',
714 732 'line2',
715 733 ]))
716 734 with open(fname) as f:
717 735 s = f.read()
718 736 nt.assert_in('line1\n', s)
719 737 nt.assert_in('line2', s)
720 738
721 739 def test_file_unicode():
722 740 """%%file with unicode cell"""
723 741 ip = get_ipython()
724 742 with TemporaryDirectory() as td:
725 743 fname = os.path.join(td, 'file1')
726 744 ip.run_cell_magic("file", fname, u'\n'.join([
727 745 u'linΓ©1',
728 746 u'linΓ©2',
729 747 ]))
730 748 with io.open(fname, encoding='utf-8') as f:
731 749 s = f.read()
732 750 nt.assert_in(u'linΓ©1\n', s)
733 751 nt.assert_in(u'linΓ©2', s)
734 752
735 753 def test_file_amend():
736 754 """%%file -a amends files"""
737 755 ip = get_ipython()
738 756 with TemporaryDirectory() as td:
739 757 fname = os.path.join(td, 'file2')
740 758 ip.run_cell_magic("file", fname, u'\n'.join([
741 759 'line1',
742 760 'line2',
743 761 ]))
744 762 ip.run_cell_magic("file", "-a %s" % fname, u'\n'.join([
745 763 'line3',
746 764 'line4',
747 765 ]))
748 766 with open(fname) as f:
749 767 s = f.read()
750 768 nt.assert_in('line1\n', s)
751 769 nt.assert_in('line3\n', s)
752 770
753 771
754 772 def test_script_config():
755 773 ip = get_ipython()
756 774 ip.config.ScriptMagics.script_magics = ['whoda']
757 775 sm = script.ScriptMagics(shell=ip)
758 776 nt.assert_in('whoda', sm.magics['cell'])
759 777
760 778 @dec.skip_win32
761 779 def test_script_out():
762 780 ip = get_ipython()
763 781 ip.run_cell_magic("script", "--out output sh", "echo 'hi'")
764 782 nt.assert_equal(ip.user_ns['output'], 'hi\n')
765 783
766 784 @dec.skip_win32
767 785 def test_script_err():
768 786 ip = get_ipython()
769 787 ip.run_cell_magic("script", "--err error sh", "echo 'hello' >&2")
770 788 nt.assert_equal(ip.user_ns['error'], 'hello\n')
771 789
772 790 @dec.skip_win32
773 791 def test_script_out_err():
774 792 ip = get_ipython()
775 793 ip.run_cell_magic("script", "--out output --err error sh", "echo 'hi'\necho 'hello' >&2")
776 794 nt.assert_equal(ip.user_ns['output'], 'hi\n')
777 795 nt.assert_equal(ip.user_ns['error'], 'hello\n')
778 796
779 797 @dec.skip_win32
780 798 def test_script_bg_out():
781 799 ip = get_ipython()
782 800 ip.run_cell_magic("script", "--bg --out output sh", "echo 'hi'")
783 801 nt.assert_equal(ip.user_ns['output'].read(), b'hi\n')
784 802
785 803 @dec.skip_win32
786 804 def test_script_bg_err():
787 805 ip = get_ipython()
788 806 ip.run_cell_magic("script", "--bg --err error sh", "echo 'hello' >&2")
789 807 nt.assert_equal(ip.user_ns['error'].read(), b'hello\n')
790 808
791 809 @dec.skip_win32
792 810 def test_script_bg_out_err():
793 811 ip = get_ipython()
794 812 ip.run_cell_magic("script", "--bg --out output --err error sh", "echo 'hi'\necho 'hello' >&2")
795 813 nt.assert_equal(ip.user_ns['output'].read(), b'hi\n')
796 814 nt.assert_equal(ip.user_ns['error'].read(), b'hello\n')
797 815
798 816 def test_script_defaults():
799 817 ip = get_ipython()
800 818 for cmd in ['sh', 'bash', 'perl', 'ruby']:
801 819 try:
802 820 find_cmd(cmd)
803 821 except Exception:
804 822 pass
805 823 else:
806 824 nt.assert_in(cmd, ip.magics_manager.magics['cell'])
807 825
808 826
809 827 @magics_class
810 828 class FooFoo(Magics):
811 829 """class with both %foo and %%foo magics"""
812 830 @line_magic('foo')
813 831 def line_foo(self, line):
814 832 "I am line foo"
815 833 pass
816 834
817 835 @cell_magic("foo")
818 836 def cell_foo(self, line, cell):
819 837 "I am cell foo, not line foo"
820 838 pass
821 839
822 840 def test_line_cell_info():
823 841 """%%foo and %foo magics are distinguishable to inspect"""
824 842 ip = get_ipython()
825 843 ip.magics_manager.register(FooFoo)
826 844 oinfo = ip.object_inspect('foo')
827 845 nt.assert_true(oinfo['found'])
828 846 nt.assert_true(oinfo['ismagic'])
829 847
830 848 oinfo = ip.object_inspect('%%foo')
831 849 nt.assert_true(oinfo['found'])
832 850 nt.assert_true(oinfo['ismagic'])
833 851 nt.assert_equal(oinfo['docstring'], FooFoo.cell_foo.__doc__)
834 852
835 853 oinfo = ip.object_inspect('%foo')
836 854 nt.assert_true(oinfo['found'])
837 855 nt.assert_true(oinfo['ismagic'])
838 856 nt.assert_equal(oinfo['docstring'], FooFoo.line_foo.__doc__)
839 857
840 858 def test_multiple_magics():
841 859 ip = get_ipython()
842 860 foo1 = FooFoo(ip)
843 861 foo2 = FooFoo(ip)
844 862 mm = ip.magics_manager
845 863 mm.register(foo1)
846 864 nt.assert_true(mm.magics['line']['foo'].__self__ is foo1)
847 865 mm.register(foo2)
848 866 nt.assert_true(mm.magics['line']['foo'].__self__ is foo2)
849 867
850 868 def test_alias_magic():
851 869 """Test %alias_magic."""
852 870 ip = get_ipython()
853 871 mm = ip.magics_manager
854 872
855 873 # Basic operation: both cell and line magics are created, if possible.
856 874 ip.run_line_magic('alias_magic', 'timeit_alias timeit')
857 875 nt.assert_in('timeit_alias', mm.magics['line'])
858 876 nt.assert_in('timeit_alias', mm.magics['cell'])
859 877
860 878 # --cell is specified, line magic not created.
861 879 ip.run_line_magic('alias_magic', '--cell timeit_cell_alias timeit')
862 880 nt.assert_not_in('timeit_cell_alias', mm.magics['line'])
863 881 nt.assert_in('timeit_cell_alias', mm.magics['cell'])
864 882
865 883 # Test that line alias is created successfully.
866 884 ip.run_line_magic('alias_magic', '--line env_alias env')
867 885 nt.assert_equal(ip.run_line_magic('env', ''),
868 886 ip.run_line_magic('env_alias', ''))
869 887
870 888 def test_save():
871 889 """Test %save."""
872 890 ip = get_ipython()
873 891 ip.history_manager.reset() # Clear any existing history.
874 892 cmds = [u"a=1", u"def b():\n return a**2", u"print(a, b())"]
875 893 for i, cmd in enumerate(cmds, start=1):
876 894 ip.history_manager.store_inputs(i, cmd)
877 895 with TemporaryDirectory() as tmpdir:
878 896 file = os.path.join(tmpdir, "testsave.py")
879 897 ip.run_line_magic("save", "%s 1-10" % file)
880 898 with open(file) as f:
881 899 content = f.read()
882 900 nt.assert_equal(content.count(cmds[0]), 1)
883 901 nt.assert_in('coding: utf-8', content)
884 902 ip.run_line_magic("save", "-a %s 1-10" % file)
885 903 with open(file) as f:
886 904 content = f.read()
887 905 nt.assert_equal(content.count(cmds[0]), 2)
888 906 nt.assert_in('coding: utf-8', content)
889 907
890 908
891 909 def test_store():
892 910 """Test %store."""
893 911 ip = get_ipython()
894 912 ip.run_line_magic('load_ext', 'storemagic')
895 913
896 914 # make sure the storage is empty
897 915 ip.run_line_magic('store', '-z')
898 916 ip.user_ns['var'] = 42
899 917 ip.run_line_magic('store', 'var')
900 918 ip.user_ns['var'] = 39
901 919 ip.run_line_magic('store', '-r')
902 920 nt.assert_equal(ip.user_ns['var'], 42)
903 921
904 922 ip.run_line_magic('store', '-d var')
905 923 ip.user_ns['var'] = 39
906 924 ip.run_line_magic('store' , '-r')
907 925 nt.assert_equal(ip.user_ns['var'], 39)
908 926
909 927
910 928 def _run_edit_test(arg_s, exp_filename=None,
911 929 exp_lineno=-1,
912 930 exp_contents=None,
913 931 exp_is_temp=None):
914 932 ip = get_ipython()
915 933 M = code.CodeMagics(ip)
916 934 last_call = ['','']
917 935 opts,args = M.parse_options(arg_s,'prxn:')
918 936 filename, lineno, is_temp = M._find_edit_target(ip, args, opts, last_call)
919 937
920 938 if exp_filename is not None:
921 939 nt.assert_equal(exp_filename, filename)
922 940 if exp_contents is not None:
923 941 with io.open(filename, 'r', encoding='utf-8') as f:
924 942 contents = f.read()
925 943 nt.assert_equal(exp_contents, contents)
926 944 if exp_lineno != -1:
927 945 nt.assert_equal(exp_lineno, lineno)
928 946 if exp_is_temp is not None:
929 947 nt.assert_equal(exp_is_temp, is_temp)
930 948
931 949
932 950 def test_edit_interactive():
933 951 """%edit on interactively defined objects"""
934 952 ip = get_ipython()
935 953 n = ip.execution_count
936 954 ip.run_cell(u"def foo(): return 1", store_history=True)
937 955
938 956 try:
939 957 _run_edit_test("foo")
940 958 except code.InteractivelyDefined as e:
941 959 nt.assert_equal(e.index, n)
942 960 else:
943 961 raise AssertionError("Should have raised InteractivelyDefined")
944 962
945 963
946 964 def test_edit_cell():
947 965 """%edit [cell id]"""
948 966 ip = get_ipython()
949 967
950 968 ip.run_cell(u"def foo(): return 1", store_history=True)
951 969
952 970 # test
953 971 _run_edit_test("1", exp_contents=ip.user_ns['In'][1], exp_is_temp=True)
954 972
955 973 def test_bookmark():
956 974 ip = get_ipython()
957 975 ip.run_line_magic('bookmark', 'bmname')
958 976 with tt.AssertPrints('bmname'):
959 977 ip.run_line_magic('bookmark', '-l')
960 978 ip.run_line_magic('bookmark', '-d bmname')
961 979
962 980 def test_ls_magic():
963 981 ip = get_ipython()
964 982 json_formatter = ip.display_formatter.formatters['application/json']
965 983 json_formatter.enabled = True
966 984 lsmagic = ip.magic('lsmagic')
967 985 with warnings.catch_warnings(record=True) as w:
968 986 j = json_formatter(lsmagic)
969 987 nt.assert_equal(sorted(j), ['cell', 'line'])
970 988 nt.assert_equal(w, []) # no warnings
971 989
972 990 def test_strip_initial_indent():
973 991 def sii(s):
974 992 lines = s.splitlines()
975 993 return '\n'.join(code.strip_initial_indent(lines))
976 994
977 995 nt.assert_equal(sii(" a = 1\nb = 2"), "a = 1\nb = 2")
978 996 nt.assert_equal(sii(" a\n b\nc"), "a\n b\nc")
979 997 nt.assert_equal(sii("a\n b"), "a\n b")
General Comments 0
You need to be logged in to leave comments. Login now