##// END OF EJS Templates
Fix a number of bugs with %history, add proper tests....
Fernando Perez -
Show More
@@ -1,5 +1,4 b''
1 1 # -*- coding: utf-8 -*-
2
3 2 """ History related magics and functionality """
4 3
5 4 # Stdlib imports
@@ -7,7 +6,7 b' import fnmatch'
7 6 import os
8 7
9 8 # IPython imports
10 from IPython.genutils import Term, ask_yes_no
9 from IPython.genutils import Term, ask_yes_no, warn
11 10 import IPython.ipapi
12 11
13 12 def magic_history(self, parameter_s = ''):
@@ -47,8 +46,6 b" def magic_history(self, parameter_s = ''):"
47 46 -f FILENAME: instead of printing the output to the screen, redirect it to
48 47 the given file. The file is always overwritten, though IPython asks for
49 48 confirmation first if it already exists.
50
51
52 49 """
53 50
54 51 ip = self.api
@@ -62,31 +59,28 b" def magic_history(self, parameter_s = ''):"
62 59 try:
63 60 outfname = opts['f']
64 61 except KeyError:
65 outfile = Term.cout
62 outfile = Term.cout # default
66 63 # We don't want to close stdout at the end!
67 64 close_at_end = False
68 65 else:
69 66 if os.path.exists(outfname):
70 ans = ask_yes_no("File %r exists. Overwrite?" % outfname)
71 if not ans:
67 if not ask_yes_no("File %r exists. Overwrite?" % outfname):
72 68 print 'Aborting.'
73 69 return
74 else:
75 outfile = open(outfname,'w')
76 close_at_end = True
77
78 70
79 if opts.has_key('t'):
71 outfile = open(outfname,'w')
72 close_at_end = True
73
74 if 't' in opts:
80 75 input_hist = shell.input_hist
81 elif opts.has_key('r'):
76 elif 'r' in opts:
82 77 input_hist = shell.input_hist_raw
83 78 else:
84 79 input_hist = shell.input_hist
85
86
80
87 81 default_length = 40
88 82 pattern = None
89 if opts.has_key('g'):
83 if 'g' in opts:
90 84 init = 1
91 85 final = len(input_hist)
92 86 parts = parameter_s.split(None,1)
@@ -138,13 +132,11 b" def magic_history(self, parameter_s = ''):"
138 132 outfile.close()
139 133
140 134
141
142 135 def magic_hist(self, parameter_s=''):
143 136 """Alternate name for %history."""
144 137 return self.magic_history(parameter_s)
145 138
146 139
147
148 140 def rep_f(self, arg):
149 141 r""" Repeat a command, or get command to input line for editing
150 142
@@ -173,11 +165,9 b' def rep_f(self, arg):'
173 165 %rep foo
174 166
175 167 Place the most recent line that has the substring "foo" to next input.
176 (e.g. 'svn ci -m foobar').
177
168 (e.g. 'svn ci -m foobar').
178 169 """
179 170
180
181 171 opts,args = self.parse_options(arg,'',mode='list')
182 172 ip = self.api
183 173 if not args:
@@ -206,7 +196,6 b' def rep_f(self, arg):'
206 196 ip.set_next_input(str(h).rstrip())
207 197 return
208 198
209
210 199 try:
211 200 lines = self.extract_input_slices(args, True)
212 201 print "lines",lines
@@ -215,7 +204,6 b' def rep_f(self, arg):'
215 204 print "Not found in recent history:", args
216 205
217 206
218
219 207 _sentinel = object()
220 208
221 209 class ShadowHist:
@@ -259,23 +247,12 b' class ShadowHist:'
259 247 if k == idx:
260 248 return v
261 249
262 def test_shist():
263 from IPython.Extensions import pickleshare
264 db = pickleshare.PickleShareDB('~/shist')
265 s = ShadowHist(db)
266 s.add('hello')
267 s.add('world')
268 s.add('hello')
269 s.add('hello')
270 s.add('karhu')
271 print "all",s.all()
272 print s.get(2)
273 250
274 251 def init_ipython(ip):
252 import ipy_completers
253
275 254 ip.expose_magic("rep",rep_f)
276 255 ip.expose_magic("hist",magic_hist)
277 256 ip.expose_magic("history",magic_history)
278 257
279 import ipy_completers
280 258 ipy_completers.quick_completer('%hist' ,'-g -t -r -n')
281 #test_shist()
@@ -65,13 +65,28 b' log = logging.getLogger(__name__)'
65 65 # test globals. Once we move over to a clean magic system, this will be done
66 66 # with much less ugliness.
67 67
68 class py_file_finder(object):
69 def __init__(self,test_filename):
70 self.test_filename = test_filename
71
72 def __call__(self,name):
73 from IPython.genutils import get_py_filename
74 try:
75 get_py_filename(name)
76 except IOError:
77 test_dir = os.path.dirname(self.test_filename)
78 new_path = os.path.join(test_dir,name)
79 return get_py_filename(new_path)
80
81
68 82 def _run_ns_sync(self,arg_s,runner=None):
69 83 """Modified version of %run that syncs testing namespaces.
70 84
71 85 This is strictly needed for running doctests that call %run.
72 86 """
73 87
74 out = _ip.IP.magic_run_ori(arg_s,runner)
88 finder = py_file_finder(_run_ns_sync.test_filename)
89 out = _ip.IP.magic_run_ori(arg_s,runner,finder)
75 90 _run_ns_sync.test_globs.update(_ip.user_ns)
76 91 return out
77 92
@@ -129,8 +144,7 b' def start_ipython():'
129 144
130 145 # Start IPython instance. We customize it to start with minimal frills.
131 146 user_ns,global_ns = IPython.ipapi.make_user_namespaces(ipnsdict(),dict())
132
133 IPython.Shell.IPShell(['--classic','--noterm_title'],
147 IPython.Shell.IPShell(['--colors=NoColor','--noterm_title'],
134 148 user_ns,global_ns)
135 149
136 150 # Deactivate the various python system hooks added by ipython for
@@ -638,7 +652,8 b' class IPDocTestRunner(doctest.DocTestRunner,object):'
638 652 # when called (rather than unconconditionally updating test.globs here
639 653 # for all examples, most of which won't be calling %run anyway).
640 654 _run_ns_sync.test_globs = test.globs
641
655 _run_ns_sync.test_filename = test.filename
656
642 657 return super(IPDocTestRunner,self).run(test,
643 658 compileflags,out,clear_globs)
644 659
@@ -1,8 +1,10 b''
1 1 """ Tests for various magic functions
2 2
3 3 Needs to be run by nose (to make ipython session available)
4
5 4 """
5
6 from IPython.testing import decorators as dec
7
6 8 def test_rehashx():
7 9 # clear up everything
8 10 _ip.IP.alias_table.clear()
@@ -19,3 +21,72 b' def test_rehashx():'
19 21 # rehashx must fill up syscmdlist
20 22 scoms = _ip.db['syscmdlist']
21 23 assert len(scoms) > 10
24
25
26 def doctest_run_ns():
27 """Classes declared %run scripts must be instantiable afterwards.
28
29 In [3]: run tclass.py
30
31 In [4]: f()
32 """
33 pass # doctest only
34
35
36 def doctest_hist_f():
37 """Test %hist -f with temporary filename.
38
39 In [9]: import tempfile
40
41 In [10]: tfile = tempfile.mktemp('.py','tmp-ipython-')
42
43 In [11]: %history -n -f $tfile 3
44 """
45
46
47 def doctest_hist_r():
48 """Test %hist -r
49
50 XXX - This test is not recording the output correctly. Not sure why...
51
52 In [6]: x=1
53
54 In [7]: hist -n -r 2
55 x=1 # random
56 hist -n -r 2 # random
57 """
58
59
60 def test_shist():
61 # Simple tests of ShadowHist class
62 import os, shutil, tempfile
63 import nose.tools as nt
64
65 from IPython.Extensions import pickleshare
66 from IPython.history import ShadowHist
67
68
69 tfile = tempfile.mktemp('','tmp-ipython-')
70
71 db = pickleshare.PickleShareDB(tfile)
72 s = ShadowHist(db)
73 s.add('hello')
74 s.add('world')
75 s.add('hello')
76 s.add('hello')
77 s.add('karhu')
78
79 yield nt.assert_equals,s.all(),[(1, 'hello'), (2, 'world'), (3, 'karhu')]
80
81 yield nt.assert_equal,s.get(2),'world'
82
83 shutil.rmtree(tfile)
84
85
86 @dec.skip_numpy_not_avail
87 def doctest_clear_array():
88 """Check that array clearing works.
89
90 >>> 1/0
91 """
92 pass # doctest only
General Comments 0
You need to be logged in to leave comments. Login now