##// END OF EJS Templates
Merge in all development done in bzr since February 16 2008....
Fernando Perez -
r1218:6b454030 merge
parent child Browse files
Show More

The requested changes are too big and content was truncated. Show full diff

@@ -0,0 +1,2 b''
1 [LF]
2 *.py
@@ -0,0 +1,244 b''
1 """
2 IPython extension: autoreload modules before executing the next line
3
4 Try::
5
6 %autoreload?
7
8 for documentation.
9 """
10
11 # Pauli Virtanen <pav@iki.fi>, 2008.
12 # Thomas Heller, 2000.
13 #
14 # This IPython module is written by Pauli Virtanen, based on the autoreload
15 # code by Thomas Heller.
16
17 #------------------------------------------------------------------------------
18 # Autoreload functionality
19 #------------------------------------------------------------------------------
20
21 import time, os, threading, sys, types, imp, inspect, traceback, atexit
22
23 def _get_compiled_ext():
24 """Official way to get the extension of compiled files (.pyc or .pyo)"""
25 for ext, mode, typ in imp.get_suffixes():
26 if typ == imp.PY_COMPILED:
27 return ext
28
29 PY_COMPILED_EXT = _get_compiled_ext()
30
31 class ModuleReloader(object):
32 skipped = {}
33 """Modules that failed to reload: {module: mtime-on-failed-reload, ...}"""
34
35 modules = {}
36 """Modules specially marked as autoreloadable."""
37
38 skip_modules = {}
39 """Modules specially marked as not autoreloadable."""
40
41 check_all = True
42 """Autoreload all modules, not just those listed in 'modules'"""
43
44 def check(self, check_all=False):
45 """Check whether some modules need to be reloaded."""
46
47 if check_all or self.check_all:
48 modules = sys.modules.keys()
49 else:
50 modules = self.modules.keys()
51
52 for modname in modules:
53 m = sys.modules.get(modname, None)
54
55 if modname in self.skip_modules:
56 continue
57
58 if not hasattr(m, '__file__'):
59 continue
60
61 if m.__name__ == '__main__':
62 # we cannot reload(__main__)
63 continue
64
65 filename = m.__file__
66 dirname = os.path.dirname(filename)
67 path, ext = os.path.splitext(filename)
68
69 if ext.lower() == '.py':
70 ext = PY_COMPILED_EXT
71 filename = os.path.join(dirname, path + PY_COMPILED_EXT)
72
73 if ext != PY_COMPILED_EXT:
74 continue
75
76 try:
77 pymtime = os.stat(filename[:-1]).st_mtime
78 if pymtime <= os.stat(filename).st_mtime:
79 continue
80 if self.skipped.get(filename[:-1], None) == pymtime:
81 continue
82 except OSError:
83 continue
84
85 try:
86 superreload(m)
87 if filename[:-1] in self.skipped:
88 del self.skipped[filename[:-1]]
89 except:
90 self.skipped[filename[:-1]] = pymtime
91
92 def update_function(old, new, attrnames):
93 for name in attrnames:
94 setattr(old, name, getattr(new, name))
95
96 def superreload(module, reload=reload):
97 """Enhanced version of the builtin reload function.
98
99 superreload replaces the class dictionary of every top-level
100 class in the module with the new one automatically,
101 as well as every function's code object.
102
103 """
104
105 module = reload(module)
106
107 # iterate over all objects and update them
108 count = 0
109 for name, new_obj in module.__dict__.items():
110 key = (module.__name__, name)
111 if _old_objects.has_key(key):
112 for old_obj in _old_objects[key]:
113 if type(new_obj) == types.ClassType:
114 old_obj.__dict__.update(new_obj.__dict__)
115 count += 1
116 elif type(new_obj) == types.FunctionType:
117 update_function(old_obj,
118 new_obj,
119 "func_code func_defaults func_doc".split())
120 count += 1
121 elif type(new_obj) == types.MethodType:
122 update_function(old_obj.im_func,
123 new_obj.im_func,
124 "func_code func_defaults func_doc".split())
125 count += 1
126
127 return module
128
129 reloader = ModuleReloader()
130
131 #------------------------------------------------------------------------------
132 # IPython monkey-patching
133 #------------------------------------------------------------------------------
134
135 import IPython.iplib
136
137 autoreload_enabled = False
138
139 def runcode_hook(self):
140 if not autoreload_enabled:
141 raise IPython.ipapi.TryNext
142 try:
143 reloader.check()
144 except:
145 pass
146
147
148 def enable_autoreload():
149 global autoreload_enabled
150 autoreload_enabled = True
151
152
153 def disable_autoreload():
154 global autoreload_enabled
155 autoreload_enabled = False
156
157 #------------------------------------------------------------------------------
158 # IPython connectivity
159 #------------------------------------------------------------------------------
160
161 import IPython.ipapi
162 ip = IPython.ipapi.get()
163
164 def autoreload_f(self, parameter_s=''):
165 r""" %autoreload => Reload modules automatically
166
167 %autoreload
168 Reload all modules (except thoses excluded by %aimport) automatically now.
169
170 %autoreload 1
171 Reload all modules imported with %aimport every time before executing
172 the Python code typed.
173
174 %autoreload 2
175 Reload all modules (except thoses excluded by %aimport) every time
176 before executing the Python code typed.
177
178 Reloading Python modules in a reliable way is in general
179 difficult, and unexpected things may occur. Some of the common
180 caveats relevant for 'autoreload' are:
181
182 - Modules are not reloaded in any specific order, and no dependency
183 analysis is done. For example, modules with 'from xxx import foo'
184 retain old versions of 'foo' when 'xxx' is autoreloaded.
185 - Functions or objects imported from the autoreloaded module to
186 the interactive namespace are not updated.
187 - C extension modules cannot be reloaded, and so cannot be
188 autoreloaded.
189 """
190 if parameter_s == '':
191 reloader.check(True)
192 elif parameter_s == '0':
193 disable_autoreload()
194 elif parameter_s == '1':
195 reloader.check_all = False
196 enable_autoreload()
197 elif parameter_s == '2':
198 reloader.check_all = True
199 enable_autoreload()
200
201 def aimport_f(self, parameter_s=''):
202 """%aimport => Import modules for automatic reloading.
203
204 %aimport
205 List modules to automatically import and not to import.
206
207 %aimport foo
208 Import module 'foo' and mark it to be autoreloaded for %autoreload 1
209
210 %aimport -foo
211 Mark module 'foo' to not be autoreloaded for %autoreload 1
212
213 """
214
215 modname = parameter_s
216 if not modname:
217 to_reload = reloader.modules.keys()
218 to_reload.sort()
219 to_skip = reloader.skip_modules.keys()
220 to_skip.sort()
221 if reloader.check_all:
222 print "Modules to reload:\nall-expect-skipped"
223 else:
224 print "Modules to reload:\n%s" % ' '.join(to_reload)
225 print "\nModules to skip:\n%s" % ' '.join(to_skip)
226 elif modname.startswith('-'):
227 modname = modname[1:]
228 try: del reloader.modules[modname]
229 except KeyError: pass
230 reloader.skip_modules[modname] = True
231 else:
232 try: del reloader.skip_modules[modname]
233 except KeyError: pass
234 reloader.modules[modname] = True
235
236 mod = __import__(modname)
237 ip.to_user_ns({modname: mod})
238
239 def init():
240 ip.expose_magic('autoreload', autoreload_f)
241 ip.expose_magic('aimport', aimport_f)
242 ip.set_hook('pre_runcode_hook', runcode_hook)
243
244 init() No newline at end of file
@@ -0,0 +1,343 b''
1 """ Extension for bzr command tab completer. Supports comlpeting commands and options
2
3 Unlike the core IPython, you should note that this extension is under GPL, not BSD.
4
5 Based on "shell" bzr plugin by Aaron Bentley, license is below. The IPython additions
6 are at the bottom of the file, the rest is left untouched.
7
8 Must be loaded with ip.load('ipy_bzr')
9
10 """
11
12 # Copyright (C) 2004, 2005 Aaron Bentley
13 # <aaron@aaronbentley.com>
14 #
15 # This program is free software; you can redistribute it and/or modify
16 # it under the terms of the GNU General Public License as published by
17 # the Free Software Foundation; either version 2 of the License, or
18 # (at your option) any later version.
19 #
20 # This program is distributed in the hope that it will be useful,
21 # but WITHOUT ANY WARRANTY; without even the implied warranty of
22 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 # GNU General Public License for more details.
24 #
25 # You should have received a copy of the GNU General Public License
26 # along with this program; if not, write to the Free Software
27 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
28
29 import cmd
30 from itertools import chain
31 import os
32 import shlex
33 import stat
34 import string
35 import sys
36
37 from bzrlib import osutils
38 from bzrlib.branch import Branch
39 from bzrlib.config import config_dir, ensure_config_dir_exists
40 from bzrlib.commands import get_cmd_object, get_all_cmds, get_alias
41 from bzrlib.errors import BzrError
42 from bzrlib.workingtree import WorkingTree
43 import bzrlib.plugin
44
45
46 SHELL_BLACKLIST = set(['rm', 'ls'])
47 COMPLETION_BLACKLIST = set(['shell'])
48
49
50 class BlackListedCommand(BzrError):
51 def __init__(self, command):
52 BzrError.__init__(self, "The command %s is blacklisted for shell use" %
53 command)
54
55
56 class CompletionContext(object):
57 def __init__(self, text, command=None, prev_opt=None, arg_pos=None):
58 self.text = text
59 self.command = command
60 self.prev_opt = prev_opt
61 self.arg_pos = None
62
63 def get_completions(self):
64 try:
65 return self.get_completions_or_raise()
66 except Exception, e:
67 print e, type(e)
68 return []
69
70 def get_option_completions(self):
71 try:
72 command_obj = get_cmd_object(self.command)
73 except BzrError:
74 return []
75 opts = [o+" " for o in iter_opt_completions(command_obj)]
76 return list(filter_completions(opts, self.text))
77
78 def get_completions_or_raise(self):
79 if self.command is None:
80 if '/' in self.text:
81 iter = iter_executables(self.text)
82 else:
83 iter = (c+" " for c in iter_command_names() if
84 c not in COMPLETION_BLACKLIST)
85 return list(filter_completions(iter, self.text))
86 if self.prev_opt is None:
87 completions = self.get_option_completions()
88 if self.command == "cd":
89 iter = iter_dir_completions(self.text)
90 completions.extend(list(filter_completions(iter, self.text)))
91 else:
92 iter = iter_file_completions(self.text)
93 completions.extend(filter_completions(iter, self.text))
94 return completions
95
96
97 class PromptCmd(cmd.Cmd):
98
99 def __init__(self):
100 cmd.Cmd.__init__(self)
101 self.prompt = "bzr> "
102 try:
103 self.tree = WorkingTree.open_containing('.')[0]
104 except:
105 self.tree = None
106 self.set_title()
107 self.set_prompt()
108 self.identchars += '-'
109 ensure_config_dir_exists()
110 self.history_file = osutils.pathjoin(config_dir(), 'shell-history')
111 readline.set_completer_delims(string.whitespace)
112 if os.access(self.history_file, os.R_OK) and \
113 os.path.isfile(self.history_file):
114 readline.read_history_file(self.history_file)
115 self.cwd = os.getcwd()
116
117 def write_history(self):
118 readline.write_history_file(self.history_file)
119
120 def do_quit(self, args):
121 self.write_history()
122 raise StopIteration
123
124 def do_exit(self, args):
125 self.do_quit(args)
126
127 def do_EOF(self, args):
128 print
129 self.do_quit(args)
130
131 def postcmd(self, line, bar):
132 self.set_title()
133 self.set_prompt()
134
135 def set_prompt(self):
136 if self.tree is not None:
137 try:
138 prompt_data = (self.tree.branch.nick, self.tree.branch.revno(),
139 self.tree.relpath('.'))
140 prompt = " %s:%d/%s" % prompt_data
141 except:
142 prompt = ""
143 else:
144 prompt = ""
145 self.prompt = "bzr%s> " % prompt
146
147 def set_title(self, command=None):
148 try:
149 b = Branch.open_containing('.')[0]
150 version = "%s:%d" % (b.nick, b.revno())
151 except:
152 version = "[no version]"
153 if command is None:
154 command = ""
155 sys.stdout.write(terminal.term_title("bzr %s %s" % (command, version)))
156
157 def do_cd(self, line):
158 if line == "":
159 line = "~"
160 line = os.path.expanduser(line)
161 if os.path.isabs(line):
162 newcwd = line
163 else:
164 newcwd = self.cwd+'/'+line
165 newcwd = os.path.normpath(newcwd)
166 try:
167 os.chdir(newcwd)
168 self.cwd = newcwd
169 except Exception, e:
170 print e
171 try:
172 self.tree = WorkingTree.open_containing(".")[0]
173 except:
174 self.tree = None
175
176 def do_help(self, line):
177 self.default("help "+line)
178
179 def default(self, line):
180 args = shlex.split(line)
181 alias_args = get_alias(args[0])
182 if alias_args is not None:
183 args[0] = alias_args.pop(0)
184
185 commandname = args.pop(0)
186 for char in ('|', '<', '>'):
187 commandname = commandname.split(char)[0]
188 if commandname[-1] in ('|', '<', '>'):
189 commandname = commandname[:-1]
190 try:
191 if commandname in SHELL_BLACKLIST:
192 raise BlackListedCommand(commandname)
193 cmd_obj = get_cmd_object(commandname)
194 except (BlackListedCommand, BzrError):
195 return os.system(line)
196
197 try:
198 if too_complicated(line):
199 return os.system("bzr "+line)
200 else:
201 return (cmd_obj.run_argv_aliases(args, alias_args) or 0)
202 except BzrError, e:
203 print e
204 except KeyboardInterrupt, e:
205 print "Interrupted"
206 except Exception, e:
207 # print "Unhandled error:\n%s" % errors.exception_str(e)
208 print "Unhandled error:\n%s" % (e)
209
210
211 def completenames(self, text, line, begidx, endidx):
212 return CompletionContext(text).get_completions()
213
214 def completedefault(self, text, line, begidx, endidx):
215 """Perform completion for native commands.
216
217 :param text: The text to complete
218 :type text: str
219 :param line: The entire line to complete
220 :type line: str
221 :param begidx: The start of the text in the line
222 :type begidx: int
223 :param endidx: The end of the text in the line
224 :type endidx: int
225 """
226 (cmd, args, foo) = self.parseline(line)
227 if cmd == "bzr":
228 cmd = None
229 return CompletionContext(text, command=cmd).get_completions()
230
231
232 def run_shell():
233 try:
234 prompt = PromptCmd()
235 try:
236 prompt.cmdloop()
237 finally:
238 prompt.write_history()
239 except StopIteration:
240 pass
241
242
243 def iter_opt_completions(command_obj):
244 for option_name, option in command_obj.options().items():
245 yield "--" + option_name
246 short_name = option.short_name()
247 if short_name:
248 yield "-" + short_name
249
250
251 def iter_file_completions(arg, only_dirs = False):
252 """Generate an iterator that iterates through filename completions.
253
254 :param arg: The filename fragment to match
255 :type arg: str
256 :param only_dirs: If true, match only directories
257 :type only_dirs: bool
258 """
259 cwd = os.getcwd()
260 if cwd != "/":
261 extras = [".", ".."]
262 else:
263 extras = []
264 (dir, file) = os.path.split(arg)
265 if dir != "":
266 listingdir = os.path.expanduser(dir)
267 else:
268 listingdir = cwd
269 for file in chain(os.listdir(listingdir), extras):
270 if dir != "":
271 userfile = dir+'/'+file
272 else:
273 userfile = file
274 if userfile.startswith(arg):
275 if os.path.isdir(listingdir+'/'+file):
276 userfile+='/'
277 yield userfile
278 elif not only_dirs:
279 yield userfile + ' '
280
281
282 def iter_dir_completions(arg):
283 """Generate an iterator that iterates through directory name completions.
284
285 :param arg: The directory name fragment to match
286 :type arg: str
287 """
288 return iter_file_completions(arg, True)
289
290
291 def iter_command_names(hidden=False):
292 for real_cmd_name, cmd_class in get_all_cmds():
293 if not hidden and cmd_class.hidden:
294 continue
295 for name in [real_cmd_name] + cmd_class.aliases:
296 # Don't complete on aliases that are prefixes of the canonical name
297 if name == real_cmd_name or not real_cmd_name.startswith(name):
298 yield name
299
300
301 def iter_executables(path):
302 dirname, partial = os.path.split(path)
303 for filename in os.listdir(dirname):
304 if not filename.startswith(partial):
305 continue
306 fullpath = os.path.join(dirname, filename)
307 mode=os.lstat(fullpath)[stat.ST_MODE]
308 if stat.S_ISREG(mode) and 0111 & mode:
309 yield fullpath + ' '
310
311
312 def filter_completions(iter, arg):
313 return (c for c in iter if c.startswith(arg))
314
315
316 def iter_munged_completions(iter, arg, text):
317 for completion in iter:
318 completion = str(completion)
319 if completion.startswith(arg):
320 yield completion[len(arg)-len(text):]+" "
321
322
323 def too_complicated(line):
324 for char in '|<>*?':
325 if char in line:
326 return True
327 return False
328
329
330 ### IPython mods start
331
332 def init_ipython(ip):
333 def bzr_completer(self,ev):
334 #print "bzr complete"
335 tup = ev.line.split(None,2)
336 if len(tup) > 2:
337 cmd = tup[1]
338 else:
339 cmd = None
340
341 return CompletionContext(ev.symbol, command = cmd).get_completions()
342 bzrlib.plugin.load_plugins()
343 ip.set_hook('complete_command', bzr_completer, str_key = 'bzr')
@@ -0,0 +1,75 b''
1 """ Greedy completer extension for IPython
2
3 Normal tab completer refuses to evaluate nonsafe stuff. This will evaluate
4 everything, so you need to consider the consequences of pressing tab
5 yourself!
6
7 Note that this extension simplifies readline interaction by setting
8 only whitespace as completer delimiter. If this works well, we will
9 do the same in default completer.
10
11 """
12 from IPython import generics,ipapi
13 from IPython.genutils import dir2
14
15 def attr_matches(self, text):
16 """Compute matches when text contains a dot.
17
18 MONKEYPATCHED VERSION (ipy_greedycompleter.py)
19
20 Assuming the text is of the form NAME.NAME....[NAME], and is
21 evaluatable in self.namespace or self.global_namespace, it will be
22 evaluated and its attributes (as revealed by dir()) are used as
23 possible completions. (For class instances, class members are are
24 also considered.)
25
26 WARNING: this can still invoke arbitrary C code, if an object
27 with a __getattr__ hook is evaluated.
28
29 """
30 import re
31
32 force_complete = 1
33 # Another option, seems to work great. Catches things like ''.<tab>
34 m = re.match(r"(\S+(\.\w+)*)\.(\w*)$", text)
35
36 if m:
37 expr, attr = m.group(1, 3)
38 else:
39 # force match - eval anything that ends with colon
40 if not force_complete:
41 return []
42
43 m2 = re.match(r"(.+)\.(\w*)$", self.lbuf)
44 if not m2:
45 return []
46 expr, attr = m2.group(1,2)
47
48
49 try:
50 obj = eval(expr, self.namespace)
51 except:
52 try:
53 obj = eval(expr, self.global_namespace)
54 except:
55 return []
56
57 words = dir2(obj)
58
59 try:
60 words = generics.complete_object(obj, words)
61 except ipapi.TryNext:
62 pass
63 # Build match list to return
64 n = len(attr)
65 res = ["%s.%s" % (expr, w) for w in words if w[:n] == attr ]
66 return res
67
68 def main():
69 import readline
70 readline.set_completer_delims(" \n\t")
71 # monkeypatch - the code will be folded to normal completer later on
72 import IPython.completer
73 IPython.completer.Completer.attr_matches = attr_matches
74
75 main() No newline at end of file
@@ -0,0 +1,311 b''
1 # -*- coding: utf-8 -*-
2 """
3 %jot magic for lightweight persistence.
4
5 Stores variables in Struct with some notes in PicleShare database
6
7
8 """
9
10 from datetime import datetime
11 import IPython.ipapi
12 ip = IPython.ipapi.get()
13
14 import pickleshare
15
16 import inspect,pickle,os,sys,textwrap
17 from IPython.FakeModule import FakeModule
18 from IPython.ipstruct import Struct
19
20
21 def refresh_variables(ip, key=None):
22 db = ip.db
23 if key is None:
24 keys = db.keys('jot/*')
25 else:
26 keys = db.keys('jot/'+key)
27 for key in keys:
28 # strip autorestore
29 justkey = os.path.basename(key)
30 print "Restoring from", justkey, "..."
31 try:
32 obj = db[key]
33 except KeyError:
34 print "Unable to restore variable '%s', ignoring (use %%jot -d to forget!)" % justkey
35 print "The error was:",sys.exc_info()[0]
36 else:
37 #print "restored",justkey,"=",obj #dbg
38 try:
39 origname = obj.name
40 except:
41 ip.user_ns[justkey] = obj
42 print "Restored", justkey
43 else:
44 ip.user_ns[origname] = obj['val']
45 print "Restored", origname
46
47 def read_variables(ip, key=None):
48 db = ip.db
49 if key is None:
50 return None
51 else:
52 keys = db.keys('jot/'+key)
53 for key in keys:
54 # strip autorestore
55 justkey = os.path.basename(key)
56 print "restoring from ", justkey
57 try:
58 obj = db[key]
59 except KeyError:
60 print "Unable to read variable '%s', ignoring (use %%jot -d to forget!)" % justkey
61 print "The error was:",sys.exc_info()[0]
62 else:
63 return obj
64
65
66 def detail_variables(ip, key=None):
67 db, get = ip.db, ip.db.get
68
69 if key is None:
70 keys = db.keys('jot/*')
71 else:
72 keys = db.keys('jot/'+key)
73 if keys:
74 size = max(map(len,keys))
75 else:
76 size = 0
77
78 fmthead = '%-'+str(size)+'s [%s]'
79 fmtbody = 'Comment:\n %s'
80 fmtdata = 'Data:\n %s, %s'
81 for key in keys:
82 v = get(key,'<unavailable>')
83 justkey = os.path.basename(key)
84 try:
85 print fmthead % (justkey, datetime.ctime(v.get('time','<unavailable>')))
86 print fmtbody % (v.get('comment','<unavailable>'))
87 d = v.get('val','unavailable')
88 print fmtdata % (repr(type(d)), '')
89 print repr(d)[0:200]
90 print
91 print
92 except AttributeError:
93 print fmt % (justkey, '<unavailable>', '<unavailable>', repr(v)[:50])
94
95
96 def intm(n):
97 try:
98 return int(n)
99 except:
100 return 0
101
102 def jot_obj(self, obj, name, comment=''):
103 """
104 write obj data to the note database, with whatever that should be noted.
105 """
106 had = self.db.keys('jot/'+name+'*')
107 # if it the same name but a later version, we stupidly add a number to the
108 # so the name doesn't collide. Any better idea?
109 suffix = ''
110 if len(had)>0:
111 pre = os.path.commonprefix(had)
112 suf = [n.split(pre)[1] for n in had]
113 versions = map(intm, suf)
114 suffix = str(max(versions)+1)
115
116 uname = 'jot/'+name+suffix
117
118 # which one works better?
119 #all = ip.IP.shadowhist.all()
120 all = ip.IP.shell.input_hist
121
122 # We may actually want to make snapshot of files that are run-ned.
123
124 # get the comment
125 try:
126 comment = ip.IP.magic_edit('-x').strip()
127 except:
128 print "No comment is recorded."
129 comment = ''
130
131 self.db[uname] = Struct({'val':obj,
132 'time' : datetime.now(),
133 'hist' : all,
134 'name' : name,
135 'comment' : comment,})
136
137 print "Jotted down notes for '%s' (%s)" % (uname, obj.__class__.__name__)
138
139
140
141 def magic_jot(self, parameter_s=''):
142 """Lightweight persistence for python variables.
143
144 Example:
145
146 ville@badger[~]|1> A = ['hello',10,'world']\\
147 ville@badger[~]|2> %jot A\\
148 ville@badger[~]|3> Exit
149
150 (IPython session is closed and started again...)
151
152 ville@badger:~$ ipython -p pysh\\
153 ville@badger[~]|1> print A
154
155 ['hello', 10, 'world']
156
157 Usage:
158
159 %jot - Show list of all variables and their current values\\
160 %jot -l - Show list of all variables and their current values in detail\\
161 %jot -l <var> - Show one variable and its current values in detail\\
162 %jot <var> - Store the *current* value of the variable to disk\\
163 %jot -d <var> - Remove the variable and its value from storage\\
164 %jot -z - Remove all variables from storage (disabled)\\
165 %jot -r <var> - Refresh/Load variable from jot (delete current vals)\\
166 %jot foo >a.txt - Store value of foo to new file a.txt\\
167 %jot foo >>a.txt - Append value of foo to file a.txt\\
168
169 It should be noted that if you change the value of a variable, you
170 need to %note it again if you want to persist the new value.
171
172 Note also that the variables will need to be pickleable; most basic
173 python types can be safely %stored.
174
175 """
176
177 opts,argsl = self.parse_options(parameter_s,'drzl',mode='string')
178 args = argsl.split(None,1)
179 ip = self.getapi()
180 db = ip.db
181 # delete
182 if opts.has_key('d'):
183 try:
184 todel = args[0]
185 except IndexError:
186 error('You must provide the variable to forget')
187 else:
188 try:
189 del db['jot/' + todel]
190 except:
191 error("Can't delete variable '%s'" % todel)
192 # reset the whole database
193 elif opts.has_key('z'):
194 print "reseting the whole database has been disabled."
195 #for k in db.keys('autorestore/*'):
196 # del db[k]
197
198 elif opts.has_key('r'):
199 try:
200 toret = args[0]
201 except:
202 print "restoring all the variables jotted down..."
203 refresh_variables(ip)
204 else:
205 refresh_variables(ip, toret)
206
207 elif opts.has_key('l'):
208 try:
209 tolist = args[0]
210 except:
211 print "List details for all the items."
212 detail_variables(ip)
213 else:
214 print "Details for", tolist, ":"
215 detail_variables(ip, tolist)
216
217 # run without arguments -> list noted variables & notes
218 elif not args:
219 vars = self.db.keys('jot/*')
220 vars.sort()
221 if vars:
222 size = max(map(len,vars)) - 4
223 else:
224 size = 0
225
226 print 'Variables and their in-db values:'
227 fmt = '%-'+str(size)+'s [%s] -> %s'
228 get = db.get
229 for var in vars:
230 justkey = os.path.basename(var)
231 v = get(var,'<unavailable>')
232 try:
233 print fmt % (justkey,\
234 datetime.ctime(v.get('time','<unavailable>')),\
235 v.get('comment','<unavailable>')[:70].replace('\n',' '),)
236 except AttributeError:
237 print fmt % (justkey, '<unavailable>', '<unavailable>', repr(v)[:50])
238
239
240 # default action - store the variable
241 else:
242 # %store foo >file.txt or >>file.txt
243 if len(args) > 1 and args[1].startswith('>'):
244 fnam = os.path.expanduser(args[1].lstrip('>').lstrip())
245 if args[1].startswith('>>'):
246 fil = open(fnam,'a')
247 else:
248 fil = open(fnam,'w')
249 obj = ip.ev(args[0])
250 print "Writing '%s' (%s) to file '%s'." % (args[0],
251 obj.__class__.__name__, fnam)
252
253
254 if not isinstance (obj,basestring):
255 from pprint import pprint
256 pprint(obj,fil)
257 else:
258 fil.write(obj)
259 if not obj.endswith('\n'):
260 fil.write('\n')
261
262 fil.close()
263 return
264
265 # %note foo
266 try:
267 obj = ip.user_ns[args[0]]
268 except KeyError:
269 # this should not be alias, for aliases, use %store
270 print
271 print "Error: %s doesn't exist." % args[0]
272 print
273 print "Use %note -r <var> to retrieve variables. This should not be used " +\
274 "to store alias, for saving aliases, use %store"
275 return
276 else:
277 if isinstance(inspect.getmodule(obj), FakeModule):
278 print textwrap.dedent("""\
279 Warning:%s is %s
280 Proper storage of interactively declared classes (or instances
281 of those classes) is not possible! Only instances
282 of classes in real modules on file system can be %%store'd.
283 """ % (args[0], obj) )
284 return
285 #pickled = pickle.dumps(obj)
286 #self.db[ 'jot/' + args[0] ] = obj
287 jot_obj(self, obj, args[0])
288
289
290 def magic_read(self, parameter_s=''):
291 """
292 %read <var> - Load variable from data that is jotted down.\\
293
294 """
295
296 opts,argsl = self.parse_options(parameter_s,'drzl',mode='string')
297 args = argsl.split(None,1)
298 ip = self.getapi()
299 db = ip.db
300 #if opts.has_key('r'):
301 try:
302 toret = args[0]
303 except:
304 print "which record do you want to read out?"
305 return
306 else:
307 return read_variables(ip, toret)
308
309
310 ip.expose_magic('jot',magic_jot)
311 ip.expose_magic('read',magic_read)
@@ -0,0 +1,234 b''
1 """
2 IPython extension: %lookfor command for searching docstrings
3
4 """
5 # Pauli Virtanen <pav@iki.fi>, 2008.
6
7 import re, inspect, pkgutil, pydoc
8
9 #------------------------------------------------------------------------------
10 # Lookfor functionality
11 #------------------------------------------------------------------------------
12
13 # Cache for lookfor: {id(module): {name: (docstring, kind, index), ...}...}
14 # where kind: "func", "class", "module", "object"
15 # and index: index in breadth-first namespace traversal
16 _lookfor_caches = {}
17
18 # regexp whose match indicates that the string may contain a function signature
19 _function_signature_re = re.compile(r"[a-z_]+\(.*[,=].*\)", re.I)
20
21 def lookfor(what, modules=None, import_modules=True, regenerate=False):
22 """
23 Search for objects whose documentation contains all given words.
24 Shows a summary of matching objects, sorted roughly by relevance.
25
26 Parameters
27 ----------
28 what : str
29 String containing words to look for.
30
31 module : str, module
32 Module whose docstrings to go through.
33 import_modules : bool
34 Whether to import sub-modules in packages.
35 Will import only modules in __all__
36 regenerate: bool
37 Re-generate the docstring cache
38
39 """
40 # Cache
41 cache = {}
42 for module in modules:
43 try:
44 c = _lookfor_generate_cache(module, import_modules, regenerate)
45 cache.update(c)
46 except ImportError:
47 pass
48
49 # Search
50 # XXX: maybe using a real stemming search engine would be better?
51 found = []
52 whats = str(what).lower().split()
53 if not whats: return
54
55 for name, (docstring, kind, index) in cache.iteritems():
56 if kind in ('module', 'object'):
57 # don't show modules or objects
58 continue
59 ok = True
60 doc = docstring.lower()
61 for w in whats:
62 if w not in doc:
63 ok = False
64 break
65 if ok:
66 found.append(name)
67
68 # Relevance sort
69 # XXX: this is full Harrison-Stetson heuristics now,
70 # XXX: it probably could be improved
71
72 kind_relevance = {'func': 1000, 'class': 1000,
73 'module': -1000, 'object': -1000}
74
75 def relevance(name, docstr, kind, index):
76 r = 0
77 # do the keywords occur within the start of the docstring?
78 first_doc = "\n".join(docstr.lower().strip().split("\n")[:3])
79 r += sum([200 for w in whats if w in first_doc])
80 # do the keywords occur in the function name?
81 r += sum([30 for w in whats if w in name])
82 # is the full name long?
83 r += -len(name) * 5
84 # is the object of bad type?
85 r += kind_relevance.get(kind, -1000)
86 # is the object deep in namespace hierarchy?
87 r += -name.count('.') * 10
88 r += max(-index / 100, -100)
89 return r
90
91 def relevance_sort(a, b):
92 dr = relevance(b, *cache[b]) - relevance(a, *cache[a])
93 if dr != 0: return dr
94 else: return cmp(a, b)
95 found.sort(relevance_sort)
96
97 # Pretty-print
98 s = "Search results for '%s'" % (' '.join(whats))
99 help_text = [s, "-"*len(s)]
100 for name in found:
101 doc, kind, ix = cache[name]
102
103 doclines = [line.strip() for line in doc.strip().split("\n")
104 if line.strip()]
105
106 # find a suitable short description
107 try:
108 first_doc = doclines[0].strip()
109 if _function_signature_re.search(first_doc):
110 first_doc = doclines[1].strip()
111 except IndexError:
112 first_doc = ""
113 help_text.append("%s\n %s" % (name, first_doc))
114
115 # Output
116 if len(help_text) > 10:
117 pager = pydoc.getpager()
118 pager("\n".join(help_text))
119 else:
120 print "\n".join(help_text)
121
122 def _lookfor_generate_cache(module, import_modules, regenerate):
123 """
124 Generate docstring cache for given module.
125
126 Parameters
127 ----------
128 module : str, None, module
129 Module for which to generate docstring cache
130 import_modules : bool
131 Whether to import sub-modules in packages.
132 Will import only modules in __all__
133 regenerate: bool
134 Re-generate the docstring cache
135
136 Returns
137 -------
138 cache : dict {obj_full_name: (docstring, kind, index), ...}
139 Docstring cache for the module, either cached one (regenerate=False)
140 or newly generated.
141
142 """
143 global _lookfor_caches
144
145 if module is None:
146 module = "numpy"
147
148 if isinstance(module, str):
149 module = __import__(module)
150
151 if id(module) in _lookfor_caches and not regenerate:
152 return _lookfor_caches[id(module)]
153
154 # walk items and collect docstrings
155 cache = {}
156 _lookfor_caches[id(module)] = cache
157 seen = {}
158 index = 0
159 stack = [(module.__name__, module)]
160 while stack:
161 name, item = stack.pop(0)
162 if id(item) in seen: continue
163 seen[id(item)] = True
164
165 index += 1
166 kind = "object"
167
168 if inspect.ismodule(item):
169 kind = "module"
170 try:
171 _all = item.__all__
172 except AttributeError:
173 _all = None
174 # import sub-packages
175 if import_modules and hasattr(item, '__path__'):
176 for m in pkgutil.iter_modules(item.__path__):
177 if _all is not None and m[1] not in _all:
178 continue
179 try:
180 __import__("%s.%s" % (name, m[1]))
181 except ImportError:
182 continue
183 for n, v in inspect.getmembers(item):
184 if _all is not None and n not in _all:
185 continue
186 stack.append(("%s.%s" % (name, n), v))
187 elif inspect.isclass(item):
188 kind = "class"
189 for n, v in inspect.getmembers(item):
190 stack.append(("%s.%s" % (name, n), v))
191 elif callable(item):
192 kind = "func"
193
194 doc = inspect.getdoc(item)
195 if doc is not None:
196 cache[name] = (doc, kind, index)
197
198 return cache
199
200 #------------------------------------------------------------------------------
201 # IPython connectivity
202 #------------------------------------------------------------------------------
203
204 import IPython.ipapi
205 ip = IPython.ipapi.get()
206
207 _lookfor_modules = ['numpy', 'scipy']
208
209 def lookfor_f(self, arg=''):
210 r"""
211 Search for objects whose documentation contains all given words.
212 Shows a summary of matching objects, sorted roughly by relevance.
213
214 Usage
215 -----
216 %lookfor +numpy some words
217 Search module 'numpy'
218
219 %lookfor_modules numpy scipy
220 Set default modules whose docstrings to search
221
222 """
223 lookfor(arg, modules=_lookfor_modules)
224
225 def lookfor_modules_f(self, arg=''):
226 global _lookfor_modules
227 if not arg:
228 print "Modules included in %lookfor search:", _lookfor_modules
229 else:
230 _lookfor_modules = arg.split()
231
232 ip.expose_magic('lookfor', lookfor_f)
233 ip.expose_magic('lookfor_modules', lookfor_modules_f)
234
@@ -0,0 +1,239 b''
1 """ Integration with gvim, by Erich Heine
2
3 Provides a %vim magic command, and reuses the same vim session. Uses
4 unix domain sockets for communication between vim and IPython. ipy.vim is
5 available in doc/examples of the IPython distribution.
6
7 Slightly touched up email announcement (and description how to use it) by
8 Erich Heine is here:
9
10 Ive recently been playing with ipython, and like it quite a bit. I did
11 however discover a bit of frustration, namely with editor interaction.
12 I am a gvim user, and using the command edit on a new file causes
13 ipython to try and run that file as soon as the text editor opens
14 up. The -x command of course fixes this, but its still a bit annoying,
15 switching windows to do a run file, then back to the text
16 editor. Being a heavy tab user in gvim, another annoyance is not being
17 able to specify weather a new tab is how I choose to open the file.
18
19 Not being one to shirk my open source duties (and seeing this as a
20 good excuse to poke around ipython internals), Ive created a script
21 for having gvim and ipython work very nicely together. Ive attached
22 both to this email (hoping of course that the mailing list allows such
23 things).
24
25 There are 2 files:
26
27 ipy_vimserver.py -- this file contains the ipython stuff
28 ipy.vim -- this file contains the gvim stuff
29
30 In combination they allow for a few functionalities:
31
32 #1. the vim magic command. This is a fancy wrapper around the edit
33 magic, that allows for a new option, -t, which opens the text in a new
34 gvim tab. Otherwise it works the same as edit -x. (it internally
35 calls edit -x). This magic command also juggles vim server management,
36 so when it is called when there is not a gvim running, it creates a
37 new gvim instance, named after the ipython session name. Once such a
38 gvim instance is running, it will be used for subsequent uses of the
39 vim command.
40
41 #2. ipython - gvim interaction. Once a file has been opened with the
42 vim magic (and a session set up, see below), pressing the F5 key in
43 vim will cause the calling ipython instance to execute run
44 filename.py. (if you typo like I do, this is very useful)
45
46 #3. ipython server - this is a thread wich listens on a unix domain
47 socket, and runs commands sent to that socket.
48
49 Note, this only works on POSIX systems, that allow for AF_UNIX type
50 sockets. It has only been tested on linux (a fairly recent debian
51 testing distro).
52
53 To install it put, the ipserver.py in your favorite locaion for
54 sourcing ipython scripts. I put the ipy.vim in
55 ~/.vim/after/ftplugin/python/.
56
57 To use (this can be scripted im sure, but i usually have 2 or 3
58 ipythons and corresponding gvims open):
59
60 import ipy_vimserver
61 ipy_vimserver.setup('sessionname')
62
63 (Editors note - you can probably add these to your ipy_user_conf.py)
64
65 Then use ipython as you normally would, until you need to edit
66 something. Instead of edit, use the vim magic. Thats it!
67
68 """
69
70 import IPython.ipapi
71 #import ipythonhooks
72 import socket, select
73 import os, threading, subprocess
74 import re
75
76 ERRCONDS = select.POLLHUP|select.POLLERR
77 SERVER = None
78 ip = IPython.ipapi.get()
79
80 # this listens to a unix domain socket in a separate thread, so that comms
81 # between a vim instance and ipython can happen in a fun and productive way
82 class IpyServer(threading.Thread):
83 def __init__(self, sname):
84 super(IpyServer, self).__init__()
85 self.keep_running = True
86 self.__sname = sname
87 self.socket = socket.socket(socket.AF_UNIX)
88 self.poller = select.poll()
89 self.current_conns = dict()
90 self.setDaemon(True)
91
92 def listen(self):
93 self.socket.bind(self.__sname)
94 self.socket.listen(1)
95
96 def __handle_error(self, socket):
97 if socket == self.socket.fileno():
98 self.keep_running = False
99 for a in self.current_conns.values():
100 a.close()
101 return False
102 else:
103 y = self.current_conns[socket]
104 del self.current_conns[socket]
105 y.close()
106 self.poller.unregister(socket)
107
108 def serve_me(self):
109 self.listen()
110 self.poller.register(self.socket,select.POLLIN|ERRCONDS)
111
112 while self.keep_running:
113 try:
114 avail = self.poller.poll(1)
115 except:
116 continue
117
118 if not avail: continue
119
120 for sock, conds in avail:
121 if conds & (ERRCONDS):
122 if self.__handle_error(sock): continue
123 else: break
124
125 if sock == self.socket.fileno():
126 y = self.socket.accept()[0]
127 self.poller.register(y, select.POLLIN|ERRCONDS)
128 self.current_conns[y.fileno()] = y
129 else: y = self.current_conns.get(sock)
130
131 self.handle_request(y)
132
133 os.remove(self.__sname)
134
135 run = serve_me
136
137 def stop(self):
138 self.keep_running = False
139
140 def handle_request(self,sock):
141 sock.settimeout(1)
142 while self.keep_running:
143 try:
144 x = sock.recv(4096)
145 except socket.timeout:
146 pass
147 else:
148 break
149 self.do_it(x)
150
151 def do_it(self, data):
152 data = data.split('\n')
153 cmds = list()
154 for line in data:
155 cmds.append(line)
156 ip.runlines(cmds)
157
158
159 # try to help ensure that the unix domain socket is cleaned up proper
160 def shutdown_server(self):
161 if SERVER:
162 SERVER.stop()
163 SERVER.join(3)
164 raise IPython.ipapi.TryNext
165
166 ip.set_hook('shutdown_hook', shutdown_server, 10)
167
168 # this fun function exists to make setup easier for all, and makes the
169 # vimhook function ready for instance specific communication
170 def setup(sessionname='',socketdir=os.path.expanduser('~/.ipython/')):
171 global SERVER
172
173 if sessionname:
174 session = sessionname
175 elif os.environ.get('IPY_SESSION'):
176 session = os.environ.get('IPY_SESSION')
177 else:
178 session = 'IPYS'
179 vimhook.vimserver=session
180 vimhook.ipyserver = os.path.join(socketdir, session)
181 if not SERVER:
182 SERVER = IpyServer(vimhook.ipyserver)
183 SERVER.start()
184
185
186
187 # calls gvim, with all ops happening on the correct gvim instance for this
188 # ipython instance. it then calls edit -x (since gvim will return right away)
189 # things of note: it sets up a special environment, so that the ipy.vim script
190 # can connect back to the ipython instance and do fun things, like run the file
191 def vimhook(self, fname, line):
192 env = os.environ.copy()
193 vserver = vimhook.vimserver.upper()
194 check = subprocess.Popen('gvim --serverlist', stdout = subprocess.PIPE,
195 shell=True)
196 check.wait()
197 cval = [l for l in check.stdout.readlines() if vserver in l]
198
199 if cval:
200 vimargs = '--remote%s' % (vimhook.extras,)
201 else:
202 vimargs = ''
203 vimhook.extras = ''
204
205 env['IPY_SESSION'] = vimhook.vimserver
206 env['IPY_SERVER'] = vimhook.ipyserver
207
208 if line is None: line = ''
209 else: line = '+' + line
210 vim_cmd = 'gvim --servername %s %s %s %s' % (vimhook.vimserver, vimargs,
211 line, fname)
212 subprocess.call(vim_cmd, env=env, shell=True)
213
214
215 #default values to keep it sane...
216 vimhook.vimserver = ''
217 vimhook.ipyserver = ''
218
219 ip.set_hook('editor',vimhook)
220
221 # this is set up so more vim specific commands can be added, instead of just
222 # the current -t. all thats required is a compiled regex, a call to do_arg(pat)
223 # and the logic to deal with the new feature
224 newtab = re.compile(r'-t(?:\s|$)')
225 def vim(self, argstr):
226 def do_arg(pat, rarg):
227 x = len(pat.findall(argstr))
228 if x:
229 a = pat.sub('',argstr)
230 return rarg, a
231 else: return '', argstr
232
233 t, argstr = do_arg(newtab, '-tab')
234 vimhook.extras = t
235 argstr = 'edit -x ' + argstr
236 ip.magic(argstr)
237
238 ip.expose_magic('vim', vim)
239
@@ -0,0 +1,73 b''
1 """ Debug a script (like %run -d) in IPython process, Using WinPdb
2
3 Usage:
4
5 %wdb test.py
6 run test.py, with a winpdb breakpoint at start of the file
7
8 %wdb pass
9 Change the password (e.g. if you have forgotten the old one)
10 """
11
12 import os
13
14 import IPython.ipapi
15 import rpdb2
16
17 ip = IPython.ipapi.get()
18
19 rpdb_started = False
20
21 def wdb_f(self, arg):
22 """ Debug a script (like %run -d) in IPython process, Using WinPdb
23
24 Usage:
25
26 %wdb test.py
27 run test.py, with a winpdb breakpoint at start of the file
28
29 %wdb pass
30 Change the password (e.g. if you have forgotten the old one)
31
32 Note that after the script has been run, you need to do "Go" (f5)
33 in WinPdb to resume normal IPython operation.
34 """
35
36 global rpdb_started
37 if not arg.strip():
38 print __doc__
39 return
40
41 if arg.strip() == 'pass':
42 passwd = raw_input('Enter new winpdb session password: ')
43 ip.db['winpdb_pass'] = passwd
44 print "Winpdb password changed"
45 if rpdb_started:
46 print "You need to restart IPython to use the new password"
47 return
48
49 path = os.path.abspath(arg)
50 if not os.path.isfile(path):
51 raise IPython.ipapi.UsageError("%%wdb: file %s does not exist" % path)
52 if not rpdb_started:
53 passwd = ip.db.get('winpdb_pass', None)
54 if passwd is None:
55 import textwrap
56 print textwrap.dedent("""\
57 Winpdb sessions need a password that you use for attaching the external
58 winpdb session. IPython will remember this. You can change the password later
59 by '%wpdb pass'
60 """)
61 passwd = raw_input('Enter new winpdb session password: ')
62 ip.db['winpdb_pass'] = passwd
63
64 print "Starting rpdb2 in IPython process"
65 rpdb2.start_embedded_debugger(passwd, timeout = 0)
66 rpdb_started = True
67
68 rpdb2.set_temp_breakpoint(path)
69 print 'It is time to attach with WinPdb (launch WinPdb if needed, File -> Attach)'
70 ip.magic('%run ' + arg)
71
72
73 ip.expose_magic('wdb', wdb_f)
@@ -0,0 +1,460 b''
1 #!/usr/bin/python
2 # -*- coding: iso-8859-15 -*-
3 '''
4 Provides IPython remote instance.
5
6 @author: Laurent Dufrechou
7 laurent.dufrechou _at_ gmail.com
8 @license: BSD
9
10 All rights reserved. This program and the accompanying materials are made
11 available under the terms of the BSD which accompanies this distribution, and
12 is available at U{http://www.opensource.org/licenses/bsd-license.php}
13 '''
14
15 __version__ = 0.9
16 __author__ = "Laurent Dufrechou"
17 __email__ = "laurent.dufrechou _at_ gmail.com"
18 __license__ = "BSD"
19
20 import re
21 import sys
22 import os
23 import locale
24 import time
25 import pydoc,__builtin__,site
26 from thread_ex import ThreadEx
27 from StringIO import StringIO
28
29 try:
30 import IPython
31 except Exception,e:
32 raise "Error importing IPython (%s)" % str(e)
33
34 ##############################################################################
35 class _Helper(object):
36 """Redefine the built-in 'help'.
37 This is a wrapper around pydoc.help (with a twist).
38 """
39
40 def __init__(self,pager):
41 self._pager = pager
42
43 def __repr__(self):
44 return "Type help() for interactive help, " \
45 "or help(object) for help about object."
46
47 def __call__(self, *args, **kwds):
48 class DummyWriter(object):
49 def __init__(self,pager):
50 self._pager = pager
51
52 def write(self,data):
53 self._pager(data)
54
55 import pydoc
56 pydoc.help.output = DummyWriter(self._pager)
57 pydoc.help.interact = lambda :1
58
59 return pydoc.help(*args, **kwds)
60
61
62 ##############################################################################
63 class _CodeExecutor(ThreadEx):
64
65 def __init__(self, instance, after):
66 ThreadEx.__init__(self)
67 self.instance = instance
68 self._afterExecute=after
69
70 def run(self):
71 try:
72 self.instance._doc_text = None
73 self.instance._help_text = None
74 self.instance._execute()
75 # used for uper class to generate event after execution
76 self._afterExecute()
77
78 except KeyboardInterrupt:
79 pass
80
81
82 ##############################################################################
83 class NonBlockingIPShell(object):
84 '''
85 Create an IPython instance, running the commands in a separate,
86 non-blocking thread.
87 This allows embedding in any GUI without blockage.
88
89 Note: The ThreadEx class supports asynchroneous function call
90 via raise_exc()
91 '''
92
93 def __init__(self,argv=[],user_ns={},user_global_ns=None,
94 cin=None, cout=None, cerr=None,
95 ask_exit_handler=None):
96 '''
97 @param argv: Command line options for IPython
98 @type argv: list
99 @param user_ns: User namespace.
100 @type user_ns: dictionary
101 @param user_global_ns: User global namespace.
102 @type user_global_ns: dictionary.
103 @param cin: Console standard input.
104 @type cin: IO stream
105 @param cout: Console standard output.
106 @type cout: IO stream
107 @param cerr: Console standard error.
108 @type cerr: IO stream
109 @param exit_handler: Replacement for builtin exit() function
110 @type exit_handler: function
111 @param time_loop: Define the sleep time between two thread's loop
112 @type int
113 '''
114 #ipython0 initialisation
115 self.initIpython0(argv, user_ns, user_global_ns,
116 cin, cout, cerr,
117 ask_exit_handler)
118
119 #vars used by _execute
120 self._iter_more = 0
121 self._history_level = 0
122 self._complete_sep = re.compile('[\s\{\}\[\]\(\)\=]')
123 self._prompt = str(self._IP.outputcache.prompt1).strip()
124
125 #thread working vars
126 self._line_to_execute = ''
127
128 #vars that will be checked by GUI loop to handle thread states...
129 #will be replaced later by PostEvent GUI funtions...
130 self._doc_text = None
131 self._help_text = None
132 self._add_button = None
133
134 def initIpython0(self, argv=[], user_ns={}, user_global_ns=None,
135 cin=None, cout=None, cerr=None,
136 ask_exit_handler=None):
137 #first we redefine in/out/error functions of IPython
138 if cin:
139 IPython.Shell.Term.cin = cin
140 if cout:
141 IPython.Shell.Term.cout = cout
142 if cerr:
143 IPython.Shell.Term.cerr = cerr
144
145 # This is to get rid of the blockage that accurs during
146 # IPython.Shell.InteractiveShell.user_setup()
147 IPython.iplib.raw_input = lambda x: None
148
149 self._term = IPython.genutils.IOTerm(cin=cin, cout=cout, cerr=cerr)
150
151 excepthook = sys.excepthook
152
153 self._IP = IPython.Shell.make_IPython(
154 argv,user_ns=user_ns,
155 user_global_ns=user_global_ns,
156 embedded=True,
157 shell_class=IPython.Shell.InteractiveShell)
158
159 #we replace IPython default encoding by wx locale encoding
160 loc = locale.getpreferredencoding()
161 if loc:
162 self._IP.stdin_encoding = loc
163 #we replace the ipython default pager by our pager
164 self._IP.set_hook('show_in_pager',self._pager)
165
166 #we replace the ipython default shell command caller by our shell handler
167 self._IP.set_hook('shell_hook',self._shell)
168
169 #we replace the ipython default input command caller by our method
170 IPython.iplib.raw_input_original = self._raw_input
171 #we replace the ipython default exit command by our method
172 self._IP.exit = ask_exit_handler
173 #we replace the help command
174 self._IP.user_ns['help'] = _Helper(self._pager_help)
175
176 #we disable cpase magic... until we found a way to use it properly.
177 #import IPython.ipapi
178 ip = IPython.ipapi.get()
179 def bypassMagic(self, arg):
180 print '%this magic is currently disabled.'
181 ip.expose_magic('cpaste', bypassMagic)
182
183 sys.excepthook = excepthook
184
185 #----------------------- Thread management section ----------------------
186 def doExecute(self,line):
187 """
188 Tell the thread to process the 'line' command
189 """
190
191 self._line_to_execute = line
192 #we launch the ipython line execution in a thread to make it interruptible
193 self.ce = _CodeExecutor(self,self._afterExecute)
194 self.ce.start()
195
196 #----------------------- IPython management section ----------------------
197 def getDocText(self):
198 """
199 Returns the output of the processing that need to be paged (if any)
200
201 @return: The std output string.
202 @rtype: string
203 """
204 return self._doc_text
205
206 def getHelpText(self):
207 """
208 Returns the output of the processing that need to be paged via help pager(if any)
209
210 @return: The std output string.
211 @rtype: string
212 """
213 return self._help_text
214
215 def getBanner(self):
216 """
217 Returns the IPython banner for useful info on IPython instance
218
219 @return: The banner string.
220 @rtype: string
221 """
222 return self._IP.BANNER
223
224 def getPromptCount(self):
225 """
226 Returns the prompt number.
227 Each time a user execute a line in the IPython shell the prompt count is increased
228
229 @return: The prompt number
230 @rtype: int
231 """
232 return self._IP.outputcache.prompt_count
233
234 def getPrompt(self):
235 """
236 Returns current prompt inside IPython instance
237 (Can be In [...]: ot ...:)
238
239 @return: The current prompt.
240 @rtype: string
241 """
242 return self._prompt
243
244 def getIndentation(self):
245 """
246 Returns the current indentation level
247 Usefull to put the caret at the good start position if we want to do autoindentation.
248
249 @return: The indentation level.
250 @rtype: int
251 """
252 return self._IP.indent_current_nsp
253
254 def updateNamespace(self, ns_dict):
255 '''
256 Add the current dictionary to the shell namespace.
257
258 @param ns_dict: A dictionary of symbol-values.
259 @type ns_dict: dictionary
260 '''
261 self._IP.user_ns.update(ns_dict)
262
263 def complete(self, line):
264 '''
265 Returns an auto completed line and/or posibilities for completion.
266
267 @param line: Given line so far.
268 @type line: string
269
270 @return: Line completed as for as possible,
271 and possible further completions.
272 @rtype: tuple
273 '''
274 split_line = self._complete_sep.split(line)
275 possibilities = self._IP.complete(split_line[-1])
276 if possibilities:
277
278 def _commonPrefix(str1, str2):
279 '''
280 Reduction function. returns common prefix of two given strings.
281
282 @param str1: First string.
283 @type str1: string
284 @param str2: Second string
285 @type str2: string
286
287 @return: Common prefix to both strings.
288 @rtype: string
289 '''
290 for i in range(len(str1)):
291 if not str2.startswith(str1[:i+1]):
292 return str1[:i]
293 return str1
294 common_prefix = reduce(_commonPrefix, possibilities)
295 completed = line[:-len(split_line[-1])]+common_prefix
296 else:
297 completed = line
298 return completed, possibilities
299
300 def historyBack(self):
301 '''
302 Provides one history command back.
303
304 @return: The command string.
305 @rtype: string
306 '''
307 history = ''
308 #the below while loop is used to suppress empty history lines
309 while((history == '' or history == '\n') and self._history_level >0):
310 if self._history_level>=1:
311 self._history_level -= 1
312 history = self._getHistory()
313 return history
314
315 def historyForward(self):
316 '''
317 Provides one history command forward.
318
319 @return: The command string.
320 @rtype: string
321 '''
322 history = ''
323 #the below while loop is used to suppress empty history lines
324 while((history == '' or history == '\n') and self._history_level <= self._getHistoryMaxIndex()):
325 if self._history_level < self._getHistoryMaxIndex():
326 self._history_level += 1
327 history = self._getHistory()
328 else:
329 if self._history_level == self._getHistoryMaxIndex():
330 history = self._getHistory()
331 self._history_level += 1
332 else:
333 history = ''
334 return history
335
336 def initHistoryIndex(self):
337 '''
338 set history to last command entered
339 '''
340 self._history_level = self._getHistoryMaxIndex()+1
341
342 #----------------------- IPython PRIVATE management section --------------
343 def _afterExecute(self):
344 '''
345 Can be redefined to generate post event after excution is done
346 '''
347 pass
348
349 #def _askExit(self):
350 # '''
351 # Can be redefined to generate post event to exit the Ipython shell
352 # '''
353 # pass
354
355 def _getHistoryMaxIndex(self):
356 '''
357 returns the max length of the history buffer
358
359 @return: history length
360 @rtype: int
361 '''
362 return len(self._IP.input_hist_raw)-1
363
364 def _getHistory(self):
365 '''
366 Get's the command string of the current history level.
367
368 @return: Historic command stri
369 @rtype: string
370 '''
371 rv = self._IP.input_hist_raw[self._history_level].strip('\n')
372 return rv
373
374 def _pager_help(self,text):
375 '''
376 This function is used as a callback replacment to IPython help pager function
377
378 It puts the 'text' value inside the self._help_text string that can be retrived via getHelpText
379 function.
380 '''
381 if self._help_text == None:
382 self._help_text = text
383 else:
384 self._help_text += text
385
386 def _pager(self,IP,text):
387 '''
388 This function is used as a callback replacment to IPython pager function
389
390 It puts the 'text' value inside the self._doc_text string that can be retrived via getDocText
391 function.
392 '''
393 self._doc_text = text
394
395 def _raw_input(self, prompt=''):
396 '''
397 Custom raw_input() replacement. Get's current line from console buffer.
398
399 @param prompt: Prompt to print. Here for compatability as replacement.
400 @type prompt: string
401
402 @return: The current command line text.
403 @rtype: string
404 '''
405 return self._line_to_execute
406
407 def _execute(self):
408 '''
409 Executes the current line provided by the shell object.
410 '''
411 orig_stdout = sys.stdout
412 sys.stdout = IPython.Shell.Term.cout
413
414 try:
415 line = self._IP.raw_input(None, self._iter_more)
416 if self._IP.autoindent:
417 self._IP.readline_startup_hook(None)
418
419 except KeyboardInterrupt:
420 self._IP.write('\nKeyboardInterrupt\n')
421 self._IP.resetbuffer()
422 # keep cache in sync with the prompt counter:
423 self._IP.outputcache.prompt_count -= 1
424
425 if self._IP.autoindent:
426 self._IP.indent_current_nsp = 0
427 self._iter_more = 0
428 except:
429 self._IP.showtraceback()
430 else:
431 self._iter_more = self._IP.push(line)
432 if (self._IP.SyntaxTB.last_syntax_error and
433 self._IP.rc.autoedit_syntax):
434 self._IP.edit_syntax_error()
435 if self._iter_more:
436 self._prompt = str(self._IP.outputcache.prompt2).strip()
437 if self._IP.autoindent:
438 self._IP.readline_startup_hook(self._IP.pre_readline)
439 else:
440 self._prompt = str(self._IP.outputcache.prompt1).strip()
441 self._IP.indent_current_nsp = 0 #we set indentation to 0
442 sys.stdout = orig_stdout
443
444 def _shell(self, ip, cmd):
445 '''
446 Replacement method to allow shell commands without them blocking.
447
448 @param ip: Ipython instance, same as self._IP
449 @type cmd: Ipython instance
450 @param cmd: Shell command to execute.
451 @type cmd: string
452 '''
453 stdin, stdout = os.popen4(cmd)
454 result = stdout.read().decode('cp437').encode(locale.getpreferredencoding())
455 #we use print command because the shell command is called inside IPython instance and thus is
456 #redirected to thread cout
457 #"\x01\x1b[1;36m\x02" <-- add colour to the text...
458 print "\x01\x1b[1;36m\x02"+result
459 stdout.close()
460 stdin.close()
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100755
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: new file 100644
The requested commit or file is too big and content was truncated. Show full diff
@@ -1,86 +1,86 b''
1 <?xml version='1.0' encoding='iso-8859-1'?>
2 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
3 <html>
4 <head>
5 <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
6 <link rel="stylesheet" href="igrid_help.css" type="text/css" />
7 <title>igrid help</title>
8 </head>
9 <body>
10 <h1>igrid help</h1>
11
12
13 <h2>Commands</h2>
14
15
16 <h3>pick (P)</h3>
17 <p>Pick the whole row (object is available as "_")</p>
18
19 <h3>pickattr (Shift-P)</h3>
20 <p>Pick the attribute under the cursor</p>
21
22 <h3>pickallattrs (Shift-C)</h3>
23 <p>Pick' the complete column under the cursor (i.e. the attribute under the
24 cursor) from all currently fetched objects. These attributes will be returned
25 as a list.</p>
26
27 <h3>enter (E)</h3>
28 <p>Enter the object under the cursor. (what this mean depends on the object
29 itself, i.e. how it implements iteration). This opens a new browser 'level'.</p>
30
31 <h3>enterattr (Shift-E)</h3>
32 <p>Enter the attribute under the cursor.</p>
33
34 <h3>detail (D)</h3>
35 <p>Show a detail view of the object under the cursor. This shows the name,
36 type, doc string and value of the object attributes (and it might show more
37 attributes than in the list view, depending on the object).</p>
38
39 <h3>detailattr (Shift-D)</h3>
40 <p>Show a detail view of the attribute under the cursor.</p>
41
42 <h3>pickrows (M)</h3>
43 <p>Pick multiple selected rows (M)</p>
44
45 <h3>pickrowsattr (CTRL-M)</h3>
46 <p>From multiple selected rows pick the cells matching the attribute the cursor is in (CTRL-M)</p>
47
48 <h3>find (CTRL-F)</h3>
49 <p>Find text</p>
50
51 <h3>find_next (F3)</h3>
52 <p>Find next occurrence of the searchtext</p>
53
54 <h3>find_previous (Shift-F3)</h3>
55 <p>Find previous occurrence of the searchtext </p>
56
57 <h3>sortattrasc (V)</h3>
58 <p>Sort the objects (in ascending order) using the attribute under the cursor as the sort key.</p>
59
60 <h3>sortattrdesc (Shift-V)</h3>
61 <p>Sort the objects (in descending order) using the attribute under the cursor as the sort key.</p>
62
63 <h3>leave (Backspace, DEL, X)</h3>
64 <p>Close current tab (and all the tabs to the right of the current one).</h3>
65
66 <h3>quit (ESC,Q)</h3>
67 <p>Quit igrid and return to the IPython prompt.</p>
68
69
70 <h2>Navigation</h2>
71
72
73 <h3>Jump to the last column of the current row (END, CTRL-E, CTRL-Right)</h3>
74
75 <h3>Jump to the first column of the current row (HOME, CTRL-A, CTRL-Left)</h3>
76
77 <h3>Move the cursor one column to the left (&lt;)</h3>
78
79 <h3>Move the cursor one column to the right (&gt;)</h3>
80
81 <h3>Jump to the first row in the current column (CTRL-Up)</h3>
82
83 <h3>Jump to the last row in the current column (CTRL-Down)</h3>
84
85 </body>
86 </html>
1 <?xml version='1.0' encoding='iso-8859-1'?>
2 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
3 <html>
4 <head>
5 <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
6 <link rel="stylesheet" href="igrid_help.css" type="text/css" />
7 <title>igrid help</title>
8 </head>
9 <body>
10 <h1>igrid help</h1>
11
12
13 <h2>Commands</h2>
14
15
16 <h3>pick (P)</h3>
17 <p>Pick the whole row (object is available as "_")</p>
18
19 <h3>pickattr (Shift-P)</h3>
20 <p>Pick the attribute under the cursor</p>
21
22 <h3>pickallattrs (Shift-C)</h3>
23 <p>Pick' the complete column under the cursor (i.e. the attribute under the
24 cursor) from all currently fetched objects. These attributes will be returned
25 as a list.</p>
26
27 <h3>enter (E)</h3>
28 <p>Enter the object under the cursor. (what this mean depends on the object
29 itself, i.e. how it implements iteration). This opens a new browser 'level'.</p>
30
31 <h3>enterattr (Shift-E)</h3>
32 <p>Enter the attribute under the cursor.</p>
33
34 <h3>detail (D)</h3>
35 <p>Show a detail view of the object under the cursor. This shows the name,
36 type, doc string and value of the object attributes (and it might show more
37 attributes than in the list view, depending on the object).</p>
38
39 <h3>detailattr (Shift-D)</h3>
40 <p>Show a detail view of the attribute under the cursor.</p>
41
42 <h3>pickrows (M)</h3>
43 <p>Pick multiple selected rows (M)</p>
44
45 <h3>pickrowsattr (CTRL-M)</h3>
46 <p>From multiple selected rows pick the cells matching the attribute the cursor is in (CTRL-M)</p>
47
48 <h3>find (CTRL-F)</h3>
49 <p>Find text</p>
50
51 <h3>find_next (F3)</h3>
52 <p>Find next occurrence of the searchtext</p>
53
54 <h3>find_previous (Shift-F3)</h3>
55 <p>Find previous occurrence of the searchtext </p>
56
57 <h3>sortattrasc (V)</h3>
58 <p>Sort the objects (in ascending order) using the attribute under the cursor as the sort key.</p>
59
60 <h3>sortattrdesc (Shift-V)</h3>
61 <p>Sort the objects (in descending order) using the attribute under the cursor as the sort key.</p>
62
63 <h3>leave (Backspace, DEL, X)</h3>
64 <p>Close current tab (and all the tabs to the right of the current one).</h3>
65
66 <h3>quit (ESC,Q)</h3>
67 <p>Quit igrid and return to the IPython prompt.</p>
68
69
70 <h2>Navigation</h2>
71
72
73 <h3>Jump to the last column of the current row (END, CTRL-E, CTRL-Right)</h3>
74
75 <h3>Jump to the first column of the current row (HOME, CTRL-A, CTRL-Left)</h3>
76
77 <h3>Move the cursor one column to the left (&lt;)</h3>
78
79 <h3>Move the cursor one column to the right (&gt;)</h3>
80
81 <h3>Jump to the first row in the current column (CTRL-Up)</h3>
82
83 <h3>Jump to the last row in the current column (CTRL-Down)</h3>
84
85 </body>
86 </html>
@@ -1,17 +1,19 b''
1 1 """ Install various IPython completers
2 2
3 3 IPython extension that installs the completers related to external apps.
4 4
5 5 The actual implementations are in Extensions/ipy_completers.py
6 6
7 7 """
8 8 import IPython.ipapi
9 9
10 10 ip = IPython.ipapi.get()
11 11
12 12 from ipy_completers import *
13 13
14 14 ip.set_hook('complete_command', apt_completer, re_key = '.*apt-get')
15 15 ip.set_hook('complete_command', svn_completer, str_key = 'svn')
16 16 ip.set_hook('complete_command', hg_completer, str_key = 'hg')
17 ip.set_hook('complete_command', bzr_completer, str_key = 'bzr')
17
18 # the old bzr completer is deprecated, we recommend ipy_bzr
19 #ip.set_hook('complete_command', bzr_completer, str_key = 'bzr')
@@ -1,359 +1,386 b''
1 #!/usr/bin/env python
2 1
3 2 """ Implementations for various useful completers
4 3
5 4 See Extensions/ipy_stock_completers.py on examples of how to enable a completer,
6 5 but the basic idea is to do:
7 6
8 7 ip.set_hook('complete_command', svn_completer, str_key = 'svn')
9 8
10 9 """
11 10 import IPython.ipapi
12 11 import glob,os,shlex,sys
13 12 import inspect
14 13 from time import time
14 from zipimport import zipimporter
15 15 ip = IPython.ipapi.get()
16 16
17 17 try:
18 18 set
19 19 except:
20 20 from sets import Set as set
21 21
22 22 TIMEOUT_STORAGE = 3 #Time in seconds after which the rootmodules will be stored
23 23 TIMEOUT_GIVEUP = 20 #Time in seconds after which we give up
24 24
25 25 def quick_completer(cmd, completions):
26 26 """ Easily create a trivial completer for a command.
27 27
28 28 Takes either a list of completions, or all completions in string
29 29 (that will be split on whitespace)
30 30
31 31 Example::
32 32
33 33 [d:\ipython]|1> import ipy_completers
34 34 [d:\ipython]|2> ipy_completers.quick_completer('foo', ['bar','baz'])
35 35 [d:\ipython]|3> foo b<TAB>
36 36 bar baz
37 37 [d:\ipython]|3> foo ba
38 38 """
39 39 if isinstance(completions, basestring):
40 40
41 41 completions = completions.split()
42 42 def do_complete(self,event):
43 43 return completions
44 44
45 45 ip.set_hook('complete_command',do_complete, str_key = cmd)
46 46
47 47 def getRootModules():
48 48 """
49 49 Returns a list containing the names of all the modules available in the
50 50 folders of the pythonpath.
51 51 """
52 52 modules = []
53 53 if ip.db.has_key('rootmodules'):
54 54 return ip.db['rootmodules']
55 55 t = time()
56 56 store = False
57 57 for path in sys.path:
58 58 modules += moduleList(path)
59 59 if time() - t >= TIMEOUT_STORAGE and not store:
60 60 store = True
61 61 print "\nCaching the list of root modules, please wait!"
62 62 print "(This will only be done once - type '%rehashx' to " + \
63 63 "reset cache!)"
64 64 print
65 65 if time() - t > TIMEOUT_GIVEUP:
66 66 print "This is taking too long, we give up."
67 67 print
68 68 ip.db['rootmodules'] = []
69 69 return []
70 70
71 71 modules += sys.builtin_module_names
72 72
73 73 modules = list(set(modules))
74 74 if '__init__' in modules:
75 75 modules.remove('__init__')
76 76 modules = list(set(modules))
77 77 if store:
78 78 ip.db['rootmodules'] = modules
79 79 return modules
80 80
81 81 def moduleList(path):
82 82 """
83 83 Return the list containing the names of the modules available in the given
84 84 folder.
85 85 """
86 86
87 87 if os.path.isdir(path):
88 88 folder_list = os.listdir(path)
89 elif path.endswith('.egg'):
90 try:
91 folder_list = [f for f in zipimporter(path)._files]
92 except:
93 folder_list = []
89 94 else:
90 95 folder_list = []
91 96 #folder_list = glob.glob(os.path.join(path,'*'))
92 97 folder_list = [p for p in folder_list \
93 98 if os.path.exists(os.path.join(path, p,'__init__.py'))\
94 99 or p[-3:] in ('.py','.so')\
95 or p[-4:] in ('.pyc','.pyo')]
100 or p[-4:] in ('.pyc','.pyo','.pyd')]
96 101
97 102 folder_list = [os.path.basename(p).split('.')[0] for p in folder_list]
98 103 return folder_list
99 104
100 105 def moduleCompletion(line):
101 106 """
102 107 Returns a list containing the completion possibilities for an import line.
103 108 The line looks like this :
104 109 'import xml.d'
105 110 'from xml.dom import'
106 111 """
107 112 def tryImport(mod, only_modules=False):
108 113 def isImportable(module, attr):
109 114 if only_modules:
110 115 return inspect.ismodule(getattr(module, attr))
111 116 else:
112 117 return not(attr[:2] == '__' and attr[-2:] == '__')
113 118 try:
114 119 m = __import__(mod)
115 120 except:
116 121 return []
117 122 mods = mod.split('.')
118 123 for module in mods[1:]:
119 124 m = getattr(m,module)
120 125 if (not hasattr(m, '__file__')) or (not only_modules) or\
121 126 (hasattr(m, '__file__') and '__init__' in m.__file__):
122 127 completion_list = [attr for attr in dir(m) if isImportable(m, attr)]
123 128 completion_list.extend(getattr(m,'__all__',[]))
124 129 if hasattr(m, '__file__') and '__init__' in m.__file__:
125 130 completion_list.extend(moduleList(os.path.dirname(m.__file__)))
126 131 completion_list = list(set(completion_list))
127 132 if '__init__' in completion_list:
128 133 completion_list.remove('__init__')
129 134 return completion_list
130 135
131 136 words = line.split(' ')
132 137 if len(words) == 3 and words[0] == 'from':
133 138 return ['import ']
134 139 if len(words) < 3 and (words[0] in ['import','from']) :
135 140 if len(words) == 1:
136 141 return getRootModules()
137 142 mod = words[1].split('.')
138 143 if len(mod) < 2:
139 144 return getRootModules()
140 145 completion_list = tryImport('.'.join(mod[:-1]), True)
141 146 completion_list = ['.'.join(mod[:-1] + [el]) for el in completion_list]
142 147 return completion_list
143 148 if len(words) >= 3 and words[0] == 'from':
144 149 mod = words[1]
145 150 return tryImport(mod)
146 151
147 152 def vcs_completer(commands, event):
148 153 """ utility to make writing typical version control app completers easier
149 154
150 155 VCS command line apps typically have the format:
151 156
152 157 [sudo ]PROGNAME [help] [command] file file...
153 158
154 159 """
155 160
156 161
157 162 cmd_param = event.line.split()
158 163 if event.line.endswith(' '):
159 164 cmd_param.append('')
160 165
161 166 if cmd_param[0] == 'sudo':
162 167 cmd_param = cmd_param[1:]
163 168
164 169 if len(cmd_param) == 2 or 'help' in cmd_param:
165 170 return commands.split()
166 171
167 172 return ip.IP.Completer.file_matches(event.symbol)
168 173
169 174
170 175 pkg_cache = None
171 176
172 177 def module_completer(self,event):
173 178 """ Give completions after user has typed 'import ...' or 'from ...'"""
174 179
175 180 # This works in all versions of python. While 2.5 has
176 181 # pkgutil.walk_packages(), that particular routine is fairly dangerous,
177 182 # since it imports *EVERYTHING* on sys.path. That is: a) very slow b) full
178 183 # of possibly problematic side effects.
179 184 # This search the folders in the sys.path for available modules.
180 185
181 186 return moduleCompletion(event.line)
182 187
183 188
184 189 svn_commands = """\
185 190 add blame praise annotate ann cat checkout co cleanup commit ci copy
186 191 cp delete del remove rm diff di export help ? h import info list ls
187 192 lock log merge mkdir move mv rename ren propdel pdel pd propedit pedit
188 193 pe propget pget pg proplist plist pl propset pset ps resolved revert
189 194 status stat st switch sw unlock update
190 195 """
191 196
192 197 def svn_completer(self,event):
193 198 return vcs_completer(svn_commands, event)
194 199
195 200
196 201 hg_commands = """
197 202 add addremove annotate archive backout branch branches bundle cat
198 203 clone commit copy diff export grep heads help identify import incoming
199 204 init locate log manifest merge outgoing parents paths pull push
200 205 qapplied qclone qcommit qdelete qdiff qfold qguard qheader qimport
201 206 qinit qnew qnext qpop qprev qpush qrefresh qrename qrestore qsave
202 207 qselect qseries qtop qunapplied recover remove rename revert rollback
203 208 root serve showconfig status strip tag tags tip unbundle update verify
204 209 version
205 210 """
206 211
207 212 def hg_completer(self,event):
208 213 """ Completer for mercurial commands """
209 214
210 215 return vcs_completer(hg_commands, event)
211 216
212 217
213 218
214 bzr_commands = """
215 add annotate bind branch break-lock bundle-revisions cat check
216 checkout commit conflicts deleted diff export gannotate gbranch
217 gcommit gdiff help ignore ignored info init init-repository inventory
218 log merge missing mkdir mv nick pull push reconcile register-branch
219 remerge remove renames resolve revert revno root serve sign-my-commits
220 status testament unbind uncommit unknowns update upgrade version
221 version-info visualise whoami
222 """
219 __bzr_commands = None
220
221 def bzr_commands():
222 global __bzr_commands
223 if __bzr_commands is not None:
224 return __bzr_commands
225 out = os.popen('bzr help commands')
226 __bzr_commands = [l.split()[0] for l in out]
227 return __bzr_commands
223 228
224 229 def bzr_completer(self,event):
225 230 """ Completer for bazaar commands """
226 231 cmd_param = event.line.split()
227 232 if event.line.endswith(' '):
228 233 cmd_param.append('')
229 234
230 235 if len(cmd_param) > 2:
231 236 cmd = cmd_param[1]
232 237 param = cmd_param[-1]
233 238 output_file = (param == '--output=')
234 239 if cmd == 'help':
235 return bzr_commands.split()
240 return bzr_commands()
236 241 elif cmd in ['bundle-revisions','conflicts',
237 242 'deleted','nick','register-branch',
238 243 'serve','unbind','upgrade','version',
239 244 'whoami'] and not output_file:
240 245 return []
241 246 else:
242 247 # the rest are probably file names
243 248 return ip.IP.Completer.file_matches(event.symbol)
244 249
245 return bzr_commands.split()
250 return bzr_commands()
246 251
247 252
248 253 def shlex_split(x):
249 254 """Helper function to split lines into segments."""
250 255 #shlex.split raise exception if syntax error in sh syntax
251 256 #for example if no closing " is found. This function keeps dropping
252 257 #the last character of the line until shlex.split does not raise
253 258 #exception. Adds end of the line to the result of shlex.split
254 259 #example: %run "c:/python -> ['%run','"c:/python']
255 260 endofline=[]
256 261 while x!="":
257 262 try:
258 263 comps=shlex.split(x)
259 264 if len(endofline)>=1:
260 265 comps.append("".join(endofline))
261 266 return comps
262 267 except ValueError:
263 268 endofline=[x[-1:]]+endofline
264 269 x=x[:-1]
265 270 return ["".join(endofline)]
266 271
267 272 def runlistpy(self, event):
268 273 comps = shlex_split(event.line)
269 274 relpath = (len(comps) > 1 and comps[-1] or '').strip("'\"")
270 275
271 276 #print "\nev=",event # dbg
272 277 #print "rp=",relpath # dbg
273 278 #print 'comps=',comps # dbg
274 279
275 280 lglob = glob.glob
276 281 isdir = os.path.isdir
277 282 if relpath.startswith('~'):
278 283 relpath = os.path.expanduser(relpath)
279 284 dirs = [f.replace('\\','/') + "/" for f in lglob(relpath+'*')
280 285 if isdir(f)]
281 286
282 287 # Find if the user has already typed the first filename, after which we
283 288 # should complete on all files, since after the first one other files may
284 289 # be arguments to the input script.
285 290 #filter(
286 291 if filter(lambda f: f.endswith('.py') or f.endswith('.ipy') or
287 292 f.endswith('.pyw'),comps):
288 293 pys = [f.replace('\\','/') for f in lglob('*')]
289 294 else:
290 295 pys = [f.replace('\\','/')
291 296 for f in lglob(relpath+'*.py') + lglob(relpath+'*.ipy') +
292 297 lglob(relpath + '*.pyw')]
293 298 return dirs + pys
294 299
295 300
296 301 def cd_completer(self, event):
297 302 relpath = event.symbol
298 303 #print event # dbg
299 304 if '-b' in event.line:
300 305 # return only bookmark completions
301 306 bkms = self.db.get('bookmarks',{})
302 307 return bkms.keys()
303 308
304 309
305 310 if event.symbol == '-':
306 311 width_dh = str(len(str(len(ip.user_ns['_dh']) + 1)))
307 312 # jump in directory history by number
308 313 fmt = '-%0' + width_dh +'d [%s]'
309 314 ents = [ fmt % (i,s) for i,s in enumerate(ip.user_ns['_dh'])]
310 315 if len(ents) > 1:
311 316 return ents
312 317 return []
313 318
314 319 if relpath.startswith('~'):
315 320 relpath = os.path.expanduser(relpath).replace('\\','/')
316 321 found = []
317 322 for d in [f.replace('\\','/') + '/' for f in glob.glob(relpath+'*')
318 323 if os.path.isdir(f)]:
319 324 if ' ' in d:
320 325 # we don't want to deal with any of that, complex code
321 326 # for this is elsewhere
322 327 raise IPython.ipapi.TryNext
323 328 found.append( d )
324 329
325 330 if not found:
326 331 if os.path.isdir(relpath):
327 332 return [relpath]
328 333 raise IPython.ipapi.TryNext
329 return found
334
335
336 def single_dir_expand(matches):
337 "Recursively expand match lists containing a single dir."
338
339 if len(matches) == 1 and os.path.isdir(matches[0]):
340 # Takes care of links to directories also. Use '/'
341 # explicitly, even under Windows, so that name completions
342 # don't end up escaped.
343 d = matches[0]
344 if d[-1] in ['/','\\']:
345 d = d[:-1]
346
347 subdirs = [p for p in os.listdir(d) if os.path.isdir( d + '/' + p)]
348 if subdirs:
349 matches = [ (d + '/' + p) for p in subdirs ]
350 return single_dir_expand(matches)
351 else:
352 return matches
353 else:
354 return matches
355
356 return single_dir_expand(found)
330 357
331 358 def apt_get_packages(prefix):
332 359 out = os.popen('apt-cache pkgnames')
333 360 for p in out:
334 361 if p.startswith(prefix):
335 362 yield p.rstrip()
336 363
337 364
338 365 apt_commands = """\
339 366 update upgrade install remove purge source build-dep dist-upgrade
340 367 dselect-upgrade clean autoclean check"""
341 368
342 369 def apt_completer(self, event):
343 370 """ Completer for apt-get (uses apt-cache internally)
344 371
345 372 """
346 373
347 374
348 375 cmd_param = event.line.split()
349 376 if event.line.endswith(' '):
350 377 cmd_param.append('')
351 378
352 379 if cmd_param[0] == 'sudo':
353 380 cmd_param = cmd_param[1:]
354 381
355 382 if len(cmd_param) == 2 or 'help' in cmd_param:
356 383 return apt_commands.split()
357 384
358 385 return list(apt_get_packages(event.symbol))
359 386
This diff has been collapsed as it changes many lines, (840 lines changed) Show them Hide them
@@ -1,248 +1,592 b''
1 """ Leo plugin for IPython
2
3 Example use:
4
5 nodes.foo = "hello world"
6
7 -> create '@ipy foo' node with text "hello world"
8
9 Access works also, and so does tab completion.
10
11 """
12 import IPython.ipapi
13 import IPython.genutils
14 import IPython.generics
15 import re
16
17
18
19 ip = IPython.ipapi.get()
20 leo = ip.user_ns['leox']
21 c,g = leo.c, leo.g
22
23 # will probably be overwritten by user, but handy for experimentation early on
24 ip.user_ns['c'] = c
25 ip.user_ns['g'] = g
26
27
28 from IPython.external.simplegeneric import generic
29 import pprint
30
31 @generic
32 def format_for_leo(obj):
33 """ Convert obj to string representiation (for editing in Leo)"""
34 return pprint.pformat(obj)
35
36 @format_for_leo.when_type(list)
37 def format_list(obj):
38 return "\n".join(str(s) for s in obj)
39
40 nodename_re = r'(@ipy?[\w-]+)?\s?(\w+)'
41
42 def all_cells():
43 d = {}
44 for p in c.allNodes_iter():
45 h = p.headString()
46 if h.startswith('@') and len(h.split()) == 1:
47 continue
48 mo = re.match(nodename_re, h)
49 if not mo:
50 continue
51 d[mo.group(2)] = p.copy()
52 return d
53
54
55 class TrivialLeoWorkbook:
56 """ class to find cells with simple syntax
57
58 """
59 def __getattr__(self, key):
60 cells = all_cells()
61 p = cells[key]
62 body = p.bodyString()
63 return eval_body(body)
64 def __setattr__(self,key,val):
65 cells = all_cells()
66 p = cells.get(key,None)
67 if p is None:
68 add_var(key,val)
69 else:
70 c.setBodyString(p,format_for_leo(val))
71 def __str__(self):
72 return "<TrivialLeoWorkbook>"
73 __repr__ = __str__
74
75 ip.user_ns['nodes'] = TrivialLeoWorkbook()
76
77
78 class LeoNode(object):
79 def __init__(self,p):
80 self.p = p.copy()
81
82 def get_h(self): return self.p.headString()
83 def set_h(self,val):
84 print "set head",val
85 c.beginUpdate()
86 try:
87 c.setHeadString(self.p,val)
88 finally:
89 c.endUpdate()
90
91 h = property( get_h, set_h)
92
93 def get_b(self): return self.p.bodyString()
94 def set_b(self,val):
95 print "set body",val
96 c.beginUpdate()
97 try:
98 c.setBodyString(self.p, val)
99 finally:
100 c.endUpdate()
101
102 b = property(get_b, set_b)
103
104 def set_val(self, val):
105 self.b = pprint.pformat(val)
106
107 v = property(lambda self: ip.ev(self.b.strip()), set_val)
108
109 def set_l(self,val):
110 self.b = '\n'.join(val )
111 l = property(lambda self : IPython.genutils.SList(self.b.splitlines()),
112 set_l)
113
114 def __iter__(self):
115 return (LeoNode(p) for p in self.p.children_iter())
116
117
118 class LeoWorkbook:
119 """ class for 'advanced' node access """
120 def __getattr__(self, key):
121 if key.startswith('_') or key == 'trait_names':
122 raise AttributeError
123 cells = all_cells()
124 p = cells.get(key, None)
125 if p is None:
126 p = add_var(key,None)
127
128 return LeoNode(p)
129
130 def __str__(self):
131 return "<LeoWorkbook>"
132 __repr__ = __str__
133 ip.user_ns['wb'] = LeoWorkbook()
134
135
136 _dummyval = object()
137 @IPython.generics.complete_object.when_type(LeoWorkbook)
138 def workbook_complete(obj, prev):
139 return all_cells().keys()
140
141
142 def add_var(varname, value = _dummyval):
143 c.beginUpdate()
144 try:
145
146 nodename = '@ipy-var ' + varname
147 p2 = g.findNodeAnywhere(c,nodename)
148 if not c.positionExists(p2):
149 p2 = c.currentPosition().insertAfter()
150 c.setHeadString(p2,'@ipy ' + varname)
151
152 c.setCurrentPosition(p2)
153 if value is _dummyval:
154 val = ip.user_ns[varname]
155 else:
156 val = value
157 if val is not None:
158 formatted = format_for_leo(val)
159 c.setBodyString(p2,formatted)
160 return p2
161 finally:
162 c.endUpdate()
163
164 def add_file(self,fname):
165 p2 = c.currentPosition().insertAfter()
166
167 def push_script(p):
168 c.beginUpdate()
169 try:
170 ohist = ip.IP.output_hist
171 hstart = len(ip.IP.input_hist)
172 script = g.getScript(c,p,useSelectedText=False,forcePythonSentinels=False,useSentinels=False)
173
174 script = g.splitLines(script + '\n')
175 script = ''.join(z for z in script if z.strip())
176
177 ip.runlines(script)
178
179 has_output = False
180 for idx in range(hstart,len(ip.IP.input_hist)):
181 val = ohist.get(idx,None)
182 if val is None:
183 continue
184 has_output = True
185 inp = ip.IP.input_hist[idx]
186 if inp.strip():
187 g.es('In: %s' % (inp[:40], ), tabName = 'IPython')
188
189 g.es('<%d> %s' % (idx, pprint.pformat(ohist[idx],width = 40)), tabName = 'IPython')
190
191 if not has_output:
192 g.es('ipy run: %s' %( p.headString(),), tabName = 'IPython')
193 finally:
194 c.endUpdate()
195
196
197 def eval_body(body):
198 try:
199 val = ip.ev(body)
200 except:
201 # just use stringlist if it's not completely legal python expression
202 val = IPython.genutils.SList(body.splitlines())
203 return val
204
205 def push_variable(p,varname):
206 body = p.bodyString()
207 val = eval_body(body.strip())
208 ip.user_ns[varname] = val
209 g.es('ipy var: %s' % (varname,), tabName = "IPython")
210
211 def push_from_leo(p):
212 tup = p.headString().split(None,1)
213 # @ipy foo is variable foo
214 if len(tup) == 2 and tup[0] == '@ipy':
215 varname = tup[1]
216 push_variable(p,varname)
217 return
218
219 push_script(p)
220 return
221
222
223 ip.user_ns['leox'].push = push_from_leo
224
225 def leo_f(self,s):
226 """ open file(s) in Leo
227
228 Takes an mglob pattern, e.g. '%leo *.cpp' or %leo 'rec:*.cpp'
229 """
230 import os
231 from IPython.external import mglob
232
233 files = mglob.expand(s)
234 c.beginUpdate()
235 try:
236 for fname in files:
237 p = g.findNodeAnywhere(c,'@auto ' + fname)
238 if not p:
239 p = c.currentPosition().insertAfter()
240
241 p.setHeadString('@auto ' + fname)
242 if os.path.isfile(fname):
243 c.setBodyString(p,open(fname).read())
244 c.selectPosition(p)
245 finally:
246 c.endUpdate()
247
248 ip.expose_magic('leo',leo_f)
1 """ ILeo - Leo plugin for IPython
2
3
4 """
5 import IPython.ipapi
6 import IPython.genutils
7 import IPython.generics
8 from IPython.hooks import CommandChainDispatcher
9 import re
10 import UserDict
11 from IPython.ipapi import TryNext
12 import IPython.macro
13 import IPython.Shell
14
15 def init_ipython(ipy):
16 """ This will be run by _ip.load('ipy_leo')
17
18 Leo still needs to run update_commander() after this.
19
20 """
21 global ip
22 ip = ipy
23 IPython.Shell.hijack_tk()
24 ip.set_hook('complete_command', mb_completer, str_key = '%mb')
25 ip.expose_magic('mb',mb_f)
26 ip.expose_magic('lee',lee_f)
27 ip.expose_magic('leoref',leoref_f)
28 expose_ileo_push(push_cl_node,100)
29 # this should be the LAST one that will be executed, and it will never raise TryNext
30 expose_ileo_push(push_ipython_script, 1000)
31 expose_ileo_push(push_plain_python, 100)
32 expose_ileo_push(push_ev_node, 100)
33 global wb
34 wb = LeoWorkbook()
35 ip.user_ns['wb'] = wb
36
37 show_welcome()
38
39
40 def update_commander(new_leox):
41 """ Set the Leo commander to use
42
43 This will be run every time Leo does ipython-launch; basically,
44 when the user switches the document he is focusing on, he should do
45 ipython-launch to tell ILeo what document the commands apply to.
46
47 """
48
49 global c,g
50 c,g = new_leox.c, new_leox.g
51 print "Set Leo Commander:",c.frame.getTitle()
52
53 # will probably be overwritten by user, but handy for experimentation early on
54 ip.user_ns['c'] = c
55 ip.user_ns['g'] = g
56 ip.user_ns['_leo'] = new_leox
57
58 new_leox.push = push_position_from_leo
59 run_leo_startup_node()
60
61 from IPython.external.simplegeneric import generic
62 import pprint
63
64 def es(s):
65 g.es(s, tabName = 'IPython')
66 pass
67
68 @generic
69 def format_for_leo(obj):
70 """ Convert obj to string representiation (for editing in Leo)"""
71 return pprint.pformat(obj)
72
73 @format_for_leo.when_type(list)
74 def format_list(obj):
75 return "\n".join(str(s) for s in obj)
76
77
78 attribute_re = re.compile('^[a-zA-Z_][a-zA-Z0-9_]*$')
79 def valid_attribute(s):
80 return attribute_re.match(s)
81
82 _rootnode = None
83 def rootnode():
84 """ Get ileo root node (@ipy-root)
85
86 if node has become invalid or has not been set, return None
87
88 Note that the root is the *first* @ipy-root item found
89 """
90 global _rootnode
91 if _rootnode is None:
92 return None
93 if c.positionExists(_rootnode.p):
94 return _rootnode
95 _rootnode = None
96 return None
97
98 def all_cells():
99 global _rootnode
100 d = {}
101 r = rootnode()
102 if r is not None:
103 nodes = r.p.children_iter()
104 else:
105 nodes = c.allNodes_iter()
106
107 for p in nodes:
108 h = p.headString()
109 if h.strip() == '@ipy-root':
110 # update root node (found it for the first time)
111 _rootnode = LeoNode(p)
112 # the next recursive call will use the children of new root
113 return all_cells()
114
115 if h.startswith('@a '):
116 d[h.lstrip('@a ').strip()] = p.parent().copy()
117 elif not valid_attribute(h):
118 continue
119 d[h] = p.copy()
120 return d
121
122 def eval_node(n):
123 body = n.b
124 if not body.startswith('@cl'):
125 # plain python repr node, just eval it
126 return ip.ev(n.b)
127 # @cl nodes deserve special treatment - first eval the first line (minus cl), then use it to call the rest of body
128 first, rest = body.split('\n',1)
129 tup = first.split(None, 1)
130 # @cl alone SPECIAL USE-> dump var to user_ns
131 if len(tup) == 1:
132 val = ip.ev(rest)
133 ip.user_ns[n.h] = val
134 es("%s = %s" % (n.h, repr(val)[:20] ))
135 return val
136
137 cl, hd = tup
138
139 xformer = ip.ev(hd.strip())
140 es('Transform w/ %s' % repr(xformer))
141 return xformer(rest, n)
142
143 class LeoNode(object, UserDict.DictMixin):
144 """ Node in Leo outline
145
146 Most important attributes (getters/setters available:
147 .v - evaluate node, can also be alligned
148 .b, .h - body string, headline string
149 .l - value as string list
150
151 Also supports iteration,
152
153 setitem / getitem (indexing):
154 wb.foo['key'] = 12
155 assert wb.foo['key'].v == 12
156
157 Note the asymmetry on setitem and getitem! Also other
158 dict methods are available.
159
160 .ipush() - run push-to-ipython
161
162 Minibuffer command access (tab completion works):
163
164 mb save-to-file
165
166 """
167 def __init__(self,p):
168 self.p = p.copy()
169
170 def __str__(self):
171 return "<LeoNode %s>" % str(self.p)
172
173 __repr__ = __str__
174
175 def __get_h(self): return self.p.headString()
176 def __set_h(self,val):
177 print "set head",val
178 c.beginUpdate()
179 try:
180 c.setHeadString(self.p,val)
181 finally:
182 c.endUpdate()
183
184 h = property( __get_h, __set_h, doc = "Node headline string")
185
186 def __get_b(self): return self.p.bodyString()
187 def __set_b(self,val):
188 print "set body",val
189 c.beginUpdate()
190 try:
191 c.setBodyString(self.p, val)
192 finally:
193 c.endUpdate()
194
195 b = property(__get_b, __set_b, doc = "Nody body string")
196
197 def __set_val(self, val):
198 self.b = format_for_leo(val)
199
200 v = property(lambda self: eval_node(self), __set_val, doc = "Node evaluated value")
201
202 def __set_l(self,val):
203 self.b = '\n'.join(val )
204 l = property(lambda self : IPython.genutils.SList(self.b.splitlines()),
205 __set_l, doc = "Node value as string list")
206
207 def __iter__(self):
208 """ Iterate through nodes direct children """
209
210 return (LeoNode(p) for p in self.p.children_iter())
211
212 def __children(self):
213 d = {}
214 for child in self:
215 head = child.h
216 tup = head.split(None,1)
217 if len(tup) > 1 and tup[0] == '@k':
218 d[tup[1]] = child
219 continue
220
221 if not valid_attribute(head):
222 d[head] = child
223 continue
224 return d
225 def keys(self):
226 d = self.__children()
227 return d.keys()
228 def __getitem__(self, key):
229 """ wb.foo['Some stuff'] Return a child node with headline 'Some stuff'
230
231 If key is a valid python name (e.g. 'foo'), look for headline '@k foo' as well
232 """
233 key = str(key)
234 d = self.__children()
235 return d[key]
236 def __setitem__(self, key, val):
237 """ You can do wb.foo['My Stuff'] = 12 to create children
238
239 This will create 'My Stuff' as a child of foo (if it does not exist), and
240 do .v = 12 assignment.
241
242 Exception:
243
244 wb.foo['bar'] = 12
245
246 will create a child with headline '@k bar', because bar is a valid python name
247 and we don't want to crowd the WorkBook namespace with (possibly numerous) entries
248 """
249 key = str(key)
250 d = self.__children()
251 if key in d:
252 d[key].v = val
253 return
254
255 if not valid_attribute(key):
256 head = key
257 else:
258 head = '@k ' + key
259 p = c.createLastChildNode(self.p, head, '')
260 LeoNode(p).v = val
261
262 def ipush(self):
263 """ Does push-to-ipython on the node """
264 push_from_leo(self)
265
266 def go(self):
267 """ Set node as current node (to quickly see it in Outline) """
268 c.beginUpdate()
269 try:
270 c.setCurrentPosition(self.p)
271 finally:
272 c.endUpdate()
273
274 def script(self):
275 """ Method to get the 'tangled' contents of the node
276
277 (parse @others, << section >> references etc.)
278 """
279 return g.getScript(c,self.p,useSelectedText=False,useSentinels=False)
280
281 def __get_uA(self):
282 p = self.p
283 # Create the uA if necessary.
284 if not hasattr(p.v.t,'unknownAttributes'):
285 p.v.t.unknownAttributes = {}
286
287 d = p.v.t.unknownAttributes.setdefault('ipython', {})
288 return d
289
290 uA = property(__get_uA, doc = "Access persistent unknownAttributes of node")
291
292
293 class LeoWorkbook:
294 """ class for 'advanced' node access
295
296 Has attributes for all "discoverable" nodes. Node is discoverable if it
297 either
298
299 - has a valid python name (Foo, bar_12)
300 - is a parent of an anchor node (if it has a child '@a foo', it is visible as foo)
301
302 """
303 def __getattr__(self, key):
304 if key.startswith('_') or key == 'trait_names' or not valid_attribute(key):
305 raise AttributeError
306 cells = all_cells()
307 p = cells.get(key, None)
308 if p is None:
309 return add_var(key)
310
311 return LeoNode(p)
312
313 def __str__(self):
314 return "<LeoWorkbook>"
315 def __setattr__(self,key, val):
316 raise AttributeError("Direct assignment to workbook denied, try wb.%s.v = %s" % (key,val))
317
318 __repr__ = __str__
319
320 def __iter__(self):
321 """ Iterate all (even non-exposed) nodes """
322 cells = all_cells()
323 return (LeoNode(p) for p in c.allNodes_iter())
324
325 current = property(lambda self: LeoNode(c.currentPosition()), doc = "Currently selected node")
326
327 def match_h(self, regex):
328 cmp = re.compile(regex)
329 for node in self:
330 if re.match(cmp, node.h, re.IGNORECASE):
331 yield node
332 return
333
334 @IPython.generics.complete_object.when_type(LeoWorkbook)
335 def workbook_complete(obj, prev):
336 return all_cells().keys() + [s for s in prev if not s.startswith('_')]
337
338
339 def add_var(varname):
340 c.beginUpdate()
341 r = rootnode()
342 try:
343 if r is None:
344 p2 = g.findNodeAnywhere(c,varname)
345 else:
346 p2 = g.findNodeInChildren(c, r.p, varname)
347 if p2:
348 return LeoNode(p2)
349
350 if r is not None:
351 p2 = r.p.insertAsLastChild()
352
353 else:
354 p2 = c.currentPosition().insertAfter()
355
356 c.setHeadString(p2,varname)
357 return LeoNode(p2)
358 finally:
359 c.endUpdate()
360
361 def add_file(self,fname):
362 p2 = c.currentPosition().insertAfter()
363
364 push_from_leo = CommandChainDispatcher()
365
366 def expose_ileo_push(f, prio = 0):
367 push_from_leo.add(f, prio)
368
369 def push_ipython_script(node):
370 """ Execute the node body in IPython, as if it was entered in interactive prompt """
371 c.beginUpdate()
372 try:
373 ohist = ip.IP.output_hist
374 hstart = len(ip.IP.input_hist)
375 script = node.script()
376
377 ip.user_ns['_p'] = node
378 ip.runlines(script)
379 ip.user_ns.pop('_p',None)
380
381 has_output = False
382 for idx in range(hstart,len(ip.IP.input_hist)):
383 val = ohist.get(idx,None)
384 if val is None:
385 continue
386 has_output = True
387 inp = ip.IP.input_hist[idx]
388 if inp.strip():
389 es('In: %s' % (inp[:40], ))
390
391 es('<%d> %s' % (idx, pprint.pformat(ohist[idx],width = 40)))
392
393 if not has_output:
394 es('ipy run: %s (%d LL)' %( node.h,len(script)))
395 finally:
396 c.endUpdate()
397
398
399 def eval_body(body):
400 try:
401 val = ip.ev(body)
402 except:
403 # just use stringlist if it's not completely legal python expression
404 val = IPython.genutils.SList(body.splitlines())
405 return val
406
407 def push_plain_python(node):
408 if not node.h.endswith('P'):
409 raise TryNext
410 script = node.script()
411 lines = script.count('\n')
412 try:
413 exec script in ip.user_ns
414 except:
415 print " -- Exception in script:\n"+script + "\n --"
416 raise
417 es('ipy plain: %s (%d LL)' % (node.h,lines))
418
419
420 def push_cl_node(node):
421 """ If node starts with @cl, eval it
422
423 The result is put as last child of @ipy-results node, if it exists
424 """
425 if not node.b.startswith('@cl'):
426 raise TryNext
427
428 p2 = g.findNodeAnywhere(c,'@ipy-results')
429 val = node.v
430 if p2:
431 es("=> @ipy-results")
432 LeoNode(p2).v = val
433 es(val)
434
435 def push_ev_node(node):
436 """ If headline starts with @ev, eval it and put result in body """
437 if not node.h.startswith('@ev '):
438 raise TryNext
439 expr = node.h.lstrip('@ev ')
440 es('ipy eval ' + expr)
441 res = ip.ev(expr)
442 node.v = res
443
444
445 def push_position_from_leo(p):
446 try:
447 push_from_leo(LeoNode(p))
448 except AttributeError,e:
449 if e.args == ("Commands instance has no attribute 'frame'",):
450 es("Error: ILeo not associated with .leo document")
451 es("Press alt+shift+I to fix!")
452 else:
453 raise
454
455 @generic
456 def edit_object_in_leo(obj, varname):
457 """ Make it @cl node so it can be pushed back directly by alt+I """
458 node = add_var(varname)
459 formatted = format_for_leo(obj)
460 if not formatted.startswith('@cl'):
461 formatted = '@cl\n' + formatted
462 node.b = formatted
463 node.go()
464
465 @edit_object_in_leo.when_type(IPython.macro.Macro)
466 def edit_macro(obj,varname):
467 bod = '_ip.defmacro("""\\\n' + obj.value + '""")'
468 node = add_var('Macro_' + varname)
469 node.b = bod
470 node.go()
471
472 def get_history(hstart = 0):
473 res = []
474 ohist = ip.IP.output_hist
475
476 for idx in range(hstart, len(ip.IP.input_hist)):
477 val = ohist.get(idx,None)
478 has_output = True
479 inp = ip.IP.input_hist_raw[idx]
480 if inp.strip():
481 res.append('In [%d]: %s' % (idx, inp))
482 if val:
483 res.append(pprint.pformat(val))
484 res.append('\n')
485 return ''.join(res)
486
487
488 def lee_f(self,s):
489 """ Open file(s)/objects in Leo
490
491 - %lee hist -> open full session history in leo
492 - Takes an object. l = [1,2,"hello"]; %lee l. Alt+I in leo pushes the object back
493 - Takes an mglob pattern, e.g. '%lee *.cpp' or %lee 'rec:*.cpp'
494 - Takes input history indices: %lee 4 6-8 10 12-47
495 """
496 import os
497
498 c.beginUpdate()
499 try:
500 if s == 'hist':
501 wb.ipython_history.b = get_history()
502 wb.ipython_history.go()
503 return
504
505
506 if s and s[0].isdigit():
507 # numbers; push input slices to leo
508 lines = self.extract_input_slices(s.strip().split(), True)
509 v = add_var('stored_ipython_input')
510 v.b = '\n'.join(lines)
511 return
512
513
514 # try editing the object directly
515 obj = ip.user_ns.get(s, None)
516 if obj is not None:
517 edit_object_in_leo(obj,s)
518 return
519
520
521 # if it's not object, it's a file name / mglob pattern
522 from IPython.external import mglob
523
524 files = (os.path.abspath(f) for f in mglob.expand(s))
525 for fname in files:
526 p = g.findNodeAnywhere(c,'@auto ' + fname)
527 if not p:
528 p = c.currentPosition().insertAfter()
529
530 p.setHeadString('@auto ' + fname)
531 if os.path.isfile(fname):
532 c.setBodyString(p,open(fname).read())
533 c.selectPosition(p)
534 print "Editing file(s), press ctrl+shift+w in Leo to write @auto nodes"
535 finally:
536 c.endUpdate()
537
538
539
540 def leoref_f(self,s):
541 """ Quick reference for ILeo """
542 import textwrap
543 print textwrap.dedent("""\
544 %leoe file/object - open file / object in leo
545 wb.foo.v - eval node foo (i.e. headstring is 'foo' or '@ipy foo')
546 wb.foo.v = 12 - assign to body of node foo
547 wb.foo.b - read or write the body of node foo
548 wb.foo.l - body of node foo as string list
549
550 for el in wb.foo:
551 print el.v
552
553 """
554 )
555
556
557
558 def mb_f(self, arg):
559 """ Execute leo minibuffer commands
560
561 Example:
562 mb save-to-file
563 """
564 c.executeMinibufferCommand(arg)
565
566 def mb_completer(self,event):
567 """ Custom completer for minibuffer """
568 cmd_param = event.line.split()
569 if event.line.endswith(' '):
570 cmd_param.append('')
571 if len(cmd_param) > 2:
572 return ip.IP.Completer.file_matches(event.symbol)
573 cmds = c.commandsDict.keys()
574 cmds.sort()
575 return cmds
576
577 def show_welcome():
578 print "------------------"
579 print "Welcome to Leo-enabled IPython session!"
580 print "Try %leoref for quick reference."
581 import IPython.platutils
582 IPython.platutils.set_term_title('ILeo')
583 IPython.platutils.freeze_term_title()
584
585 def run_leo_startup_node():
586 p = g.findNodeAnywhere(c,'@ipy-startup')
587 if p:
588 print "Running @ipy-startup nodes"
589 for n in LeoNode(p):
590 push_from_leo(n)
591
592
@@ -1,226 +1,251 b''
1 1 """Shell mode for IPython.
2 2
3 3 Start ipython in shell mode by invoking "ipython -p sh"
4 4
5 5 (the old version, "ipython -p pysh" still works but this is the more "modern"
6 6 shell mode and is recommended for users who don't care about pysh-mode
7 7 compatibility)
8 8 """
9 9
10 10 from IPython import ipapi
11 11 import os,textwrap
12 12
13 13 # The import below effectively obsoletes your old-style ipythonrc[.ini],
14 14 # so consider yourself warned!
15 15
16 16 import ipy_defaults
17 17
18 18 def main():
19 19 ip = ipapi.get()
20 20 o = ip.options
21 21 # autocall to "full" mode (smart mode is default, I like full mode)
22 22
23 23 o.autocall = 2
24 24
25 25 # Jason Orendorff's path class is handy to have in user namespace
26 26 # if you are doing shell-like stuff
27 27 try:
28 28 ip.ex("from IPython.external.path import path" )
29 29 except ImportError:
30 30 pass
31 31
32 32 # beefed up %env is handy in shell mode
33 33 import envpersist
34 34
35 35 # To see where mycmd resides (in path/aliases), do %which mycmd
36 36 import ipy_which
37 37
38 38 # tab completers for hg, svn, ...
39 39 import ipy_app_completers
40 40
41 41 # To make executables foo and bar in mybin usable without PATH change, do:
42 42 # %rehashdir c:/mybin
43 43 # %store foo
44 44 # %store bar
45 45 import ipy_rehashdir
46 import ipy_signals
46
47 # does not work without subprocess module!
48 #import ipy_signals
47 49
48 50 ip.ex('import os')
49 51 ip.ex("def up(): os.chdir('..')")
50
52 ip.user_ns['LA'] = LastArgFinder()
51 53 # Nice prompt
52 54
53 55 o.prompt_in1= r'\C_LightBlue[\C_LightCyan\Y2\C_LightBlue]\C_Green|\#> '
54 56 o.prompt_in2= r'\C_Green|\C_LightGreen\D\C_Green> '
55 57 o.prompt_out= '<\#> '
56 58
57 59 from IPython import Release
58 60
59 61 import sys
60 62 # Non-chatty banner
61 63 o.banner = "IPython %s [on Py %s]\n" % (Release.version,sys.version.split(None,1)[0])
62 64
63 65
64 66 ip.IP.default_option('cd','-q')
65 67 ip.IP.default_option('macro', '-r')
66 68 # If you only rarely want to execute the things you %edit...
67 69 #ip.IP.default_option('edit','-x')
68 70
69 71
70 72 o.prompts_pad_left="1"
71 73 # Remove all blank lines in between prompts, like a normal shell.
72 74 o.separate_in="0"
73 75 o.separate_out="0"
74 76 o.separate_out2="0"
75 77
76 78 # now alias all syscommands
77 79
78 80 db = ip.db
79 81
80 82 syscmds = db.get("syscmdlist",[] )
81 83 if not syscmds:
82 84 print textwrap.dedent("""
83 85 System command list not initialized, probably the first run...
84 86 running %rehashx to refresh the command list. Run %rehashx
85 87 again to refresh command list (after installing new software etc.)
86 88 """)
87 89 ip.magic('rehashx')
88 90 syscmds = db.get("syscmdlist")
89 91
90 92 # lowcase aliases on win32 only
91 93 if os.name == 'posix':
92 94 mapper = lambda s:s
93 95 else:
94 96 def mapper(s): return s.lower()
95 97
96 98 for cmd in syscmds:
97 99 # print "sys",cmd #dbg
98 100 noext, ext = os.path.splitext(cmd)
99 101 key = mapper(noext)
100 102 if key not in ip.IP.alias_table:
101 103 ip.defalias(key, cmd)
102 104
103 105 # mglob combines 'find', recursion, exclusion... '%mglob?' to learn more
104 106 ip.load("IPython.external.mglob")
105 107
106 108 # win32 is crippled w/o cygwin, try to help it a little bit
107 109 if sys.platform == 'win32':
108 110 if 'cygwin' in os.environ['PATH'].lower():
109 111 # use the colors of cygwin ls (recommended)
110 112 ip.defalias('d', 'ls -F --color=auto')
111 113 else:
112 114 # get icp, imv, imkdir, igrep, irm,...
113 115 ip.load('ipy_fsops')
114 116
115 117 # and the next best thing to real 'ls -F'
116 118 ip.defalias('d','dir /w /og /on')
117 119
118 120 extend_shell_behavior(ip)
119 121
122 class LastArgFinder:
123 """ Allow $LA to work as "last argument of previous command", like $! in bash
124
125 To call this in normal IPython code, do LA()
126 """
127 def __call__(self, hist_idx = None):
128 ip = ipapi.get()
129 if hist_idx is None:
130 return str(self)
131 return ip.IP.input_hist_raw[hist_idx].strip().split()[-1]
132 def __str__(self):
133 ip = ipapi.get()
134 for cmd in reversed(ip.IP.input_hist_raw):
135 parts = cmd.strip().split()
136 if len(parts) < 2 or parts[-1] in ['$LA', 'LA()']:
137 continue
138 return parts[-1]
139 return ""
140
141
142
143
144
120 145 # XXX You do not need to understand the next function!
121 146 # This should probably be moved out of profile
122 147
123 148 def extend_shell_behavior(ip):
124 149
125 150 # Instead of making signature a global variable tie it to IPSHELL.
126 151 # In future if it is required to distinguish between different
127 152 # shells we can assign a signature per shell basis
128 153 ip.IP.__sig__ = 0xa005
129 154 # mark the IPSHELL with this signature
130 155 ip.IP.user_ns['__builtins__'].__dict__['__sig__'] = ip.IP.__sig__
131 156
132 157 from IPython.Itpl import ItplNS
133 158 from IPython.genutils import shell
134 159 # utility to expand user variables via Itpl
135 160 # xxx do something sensible with depth?
136 161 ip.IP.var_expand = lambda cmd, lvars=None, depth=2: \
137 162 str(ItplNS(cmd, ip.IP.user_ns, get_locals()))
138 163
139 164 def get_locals():
140 165 """ Substituting a variable through Itpl deep inside the IPSHELL stack
141 166 requires the knowledge of all the variables in scope upto the last
142 167 IPSHELL frame. This routine simply merges all the local variables
143 168 on the IPSHELL stack without worrying about their scope rules
144 169 """
145 170 import sys
146 171 # note lambda expression constitues a function call
147 172 # hence fno should be incremented by one
148 173 getsig = lambda fno: sys._getframe(fno+1).f_globals \
149 174 ['__builtins__'].__dict__['__sig__']
150 175 getlvars = lambda fno: sys._getframe(fno+1).f_locals
151 176 # trackback until we enter the IPSHELL
152 177 frame_no = 1
153 178 sig = ip.IP.__sig__
154 179 fsig = ~sig
155 180 while fsig != sig :
156 181 try:
157 182 fsig = getsig(frame_no)
158 183 except (AttributeError, KeyError):
159 184 frame_no += 1
160 185 except ValueError:
161 186 # stack is depleted
162 187 # call did not originate from IPSHELL
163 188 return {}
164 189 first_frame = frame_no
165 190 # walk further back until we exit from IPSHELL or deplete stack
166 191 try:
167 192 while(sig == getsig(frame_no+1)):
168 193 frame_no += 1
169 194 except (AttributeError, KeyError, ValueError):
170 195 pass
171 196 # merge the locals from top down hence overriding
172 197 # any re-definitions of variables, functions etc.
173 198 lvars = {}
174 199 for fno in range(frame_no, first_frame-1, -1):
175 200 lvars.update(getlvars(fno))
176 201 #print '\n'*5, first_frame, frame_no, '\n', lvars, '\n'*5 #dbg
177 202 return lvars
178 203
179 204 def _runlines(lines):
180 205 """Run a string of one or more lines of source.
181 206
182 207 This method is capable of running a string containing multiple source
183 208 lines, as if they had been entered at the IPython prompt. Since it
184 209 exposes IPython's processing machinery, the given strings can contain
185 210 magic calls (%magic), special shell access (!cmd), etc."""
186 211
187 212 # We must start with a clean buffer, in case this is run from an
188 213 # interactive IPython session (via a magic, for example).
189 214 ip.IP.resetbuffer()
190 215 lines = lines.split('\n')
191 216 more = 0
192 217 command = ''
193 218 for line in lines:
194 219 # skip blank lines so we don't mess up the prompt counter, but do
195 220 # NOT skip even a blank line if we are in a code block (more is
196 221 # true)
197 222 # if command is not empty trim the line
198 223 if command != '' :
199 224 line = line.strip()
200 225 # add the broken line to the command
201 226 if line and line[-1] == '\\' :
202 227 command += line[0:-1] + ' '
203 228 more = True
204 229 continue
205 230 else :
206 231 # add the last (current) line to the command
207 232 command += line
208 233 if command or more:
209 234 # push to raw history, so hist line numbers stay in sync
210 235 ip.IP.input_hist_raw.append("# " + command + "\n")
211 236
212 237 more = ip.IP.push(ip.IP.prefilter(command,more))
213 238 command = ''
214 239 # IPython's runsource returns None if there was an error
215 240 # compiling the code. This allows us to stop processing right
216 241 # away, so the user gets the error message at the right place.
217 242 if more is None:
218 243 break
219 244 # final newline in case the input didn't have it, so that the code
220 245 # actually does get executed
221 246 if more:
222 247 ip.IP.push('\n')
223 248
224 249 ip.IP.runlines = _runlines
225 250
226 251 main()
@@ -1,162 +1,240 b''
1 1 """ Preliminary "job control" extensions for IPython
2 2
3 3 requires python 2.4 (or separate 'subprocess' module
4 4
5 5 This provides 2 features, launching background jobs and killing foreground jobs from another IPython instance.
6 6
7 7 Launching background jobs:
8 8
9 9 Usage:
10 10
11 11 [ipython]|2> import jobctrl
12 12 [ipython]|3> &ls
13 13 <3> <jobctrl.IpyPopen object at 0x00D87FD0>
14 14 [ipython]|4> _3.go
15 15 -----------> _3.go()
16 16 ChangeLog
17 17 IPython
18 18 MANIFEST.in
19 19 README
20 20 README_Windows.txt
21 21
22 22 ...
23 23
24 24 Killing foreground tasks:
25 25
26 26 Launch IPython instance, run a blocking command:
27 27
28 28 [Q:/ipython]|1> import jobctrl
29 29 [Q:/ipython]|2> cat
30 30
31 31 Now launch a new IPython prompt and kill the process:
32 32
33 33 IPython 0.8.3.svn.r2919 [on Py 2.5]
34 34 [Q:/ipython]|1> import jobctrl
35 35 [Q:/ipython]|2> %tasks
36 36 6020: 'cat ' (Q:\ipython)
37 37 [Q:/ipython]|3> %kill
38 38 SUCCESS: The process with PID 6020 has been terminated.
39 39 [Q:/ipython]|4>
40 40
41 41 (you don't need to specify PID for %kill if only one task is running)
42 42 """
43 43
44 from subprocess import Popen,PIPE
44 from subprocess import *
45 45 import os,shlex,sys,time
46 import threading,Queue
46 47
47 48 from IPython import genutils
48 49
49 50 import IPython.ipapi
50 51
51 52 if os.name == 'nt':
52 53 def kill_process(pid):
53 54 os.system('taskkill /F /PID %d' % pid)
54 55 else:
55 56 def kill_process(pid):
56 57 os.system('kill -9 %d' % pid)
57 58
58 59
59 60
60 61 class IpyPopen(Popen):
61 62 def go(self):
62 63 print self.communicate()[0]
63 64 def __repr__(self):
64 65 return '<IPython job "%s" PID=%d>' % (self.line, self.pid)
65 66
66 67 def kill(self):
67 68 kill_process(self.pid)
68 69
69 70 def startjob(job):
70 71 p = IpyPopen(shlex.split(job), stdout=PIPE, shell = False)
71 72 p.line = job
72 73 return p
73 74
75 class AsyncJobQ(threading.Thread):
76 def __init__(self):
77 threading.Thread.__init__(self)
78 self.q = Queue.Queue()
79 self.output = []
80 self.stop = False
81 def run(self):
82 while 1:
83 cmd,cwd = self.q.get()
84 if self.stop:
85 self.output.append("** Discarding: '%s' - %s" % (cmd,cwd))
86 continue
87 self.output.append("** Task started: '%s' - %s" % (cmd,cwd))
88
89 p = Popen(cmd, shell=True, stdout=PIPE, stderr=STDOUT, cwd = cwd)
90 out = p.stdout.read()
91 self.output.append("** Task complete: '%s'\n" % cmd)
92 self.output.append(out)
93
94 def add(self,cmd):
95 self.q.put_nowait((cmd, os.getcwd()))
96
97 def dumpoutput(self):
98 while self.output:
99 item = self.output.pop(0)
100 print item
101
102 _jobq = None
103
104 def jobqueue_f(self, line):
105
106 global _jobq
107 if not _jobq:
108 print "Starting jobqueue - do '&some_long_lasting_system_command' to enqueue"
109 _jobq = AsyncJobQ()
110 _jobq.setDaemon(True)
111 _jobq.start()
112 ip.jobq = _jobq.add
113 return
114 if line.strip() == 'stop':
115 print "Stopping and clearing jobqueue, %jobqueue start to start again"
116 _jobq.stop = True
117 return
118 if line.strip() == 'start':
119 _jobq.stop = False
120 return
121
74 122 def jobctrl_prefilter_f(self,line):
75 123 if line.startswith('&'):
76 124 pre,fn,rest = self.split_user_input(line[1:])
77 125
78 126 line = ip.IP.expand_aliases(fn,rest)
79 return '_ip.startjob(%s)' % genutils.make_quoted_expr(line)
127 if not _jobq:
128 return '_ip.startjob(%s)' % genutils.make_quoted_expr(line)
129 return '_ip.jobq(%s)' % genutils.make_quoted_expr(line)
80 130
81 131 raise IPython.ipapi.TryNext
82 132
133 def jobq_output_hook(self):
134 if not _jobq:
135 return
136 _jobq.dumpoutput()
137
138
83 139
84 140 def job_list(ip):
85 141 keys = ip.db.keys('tasks/*')
86 142 ents = [ip.db[k] for k in keys]
87 143 return ents
88 144
89 145 def magic_tasks(self,line):
90 146 """ Show a list of tasks.
91 147
92 148 A 'task' is a process that has been started in IPython when 'jobctrl' extension is enabled.
93 149 Tasks can be killed with %kill.
150
151 '%tasks clear' clears the task list (from stale tasks)
94 152 """
95 153 ip = self.getapi()
154 if line.strip() == 'clear':
155 for k in ip.db.keys('tasks/*'):
156 print "Clearing",ip.db[k]
157 del ip.db[k]
158 return
159
96 160 ents = job_list(ip)
97 161 if not ents:
98 162 print "No tasks running"
99 163 for pid,cmd,cwd,t in ents:
100 164 dur = int(time.time()-t)
101 165 print "%d: '%s' (%s) %d:%02d" % (pid,cmd,cwd, dur / 60,dur%60)
102 166
103 167 def magic_kill(self,line):
104 168 """ Kill a task
105 169
106 170 Without args, either kill one task (if only one running) or show list (if many)
107 171 With arg, assume it's the process id.
108 172
109 173 %kill is typically (much) more powerful than trying to terminate a process with ctrl+C.
110 174 """
111 175 ip = self.getapi()
112 176 jobs = job_list(ip)
113 177
114 178 if not line.strip():
115 179 if len(jobs) == 1:
116 180 kill_process(jobs[0][0])
117 181 else:
118 182 magic_tasks(self,line)
119 183 return
120 184
121 185 try:
122 186 pid = int(line)
123 187 kill_process(pid)
124 188 except ValueError:
125 189 magic_tasks(self,line)
126 190
127 191 if sys.platform == 'win32':
128 shell_internal_commands = 'break chcp cls copy ctty date del erase dir md mkdir path prompt rd rmdir time type ver vol'.split()
192 shell_internal_commands = 'break chcp cls copy ctty date del erase dir md mkdir path prompt rd rmdir start time type ver vol'.split()
129 193 else:
130 194 # todo linux commands
131 195 shell_internal_commands = []
132 196
133 197
134 198 def jobctrl_shellcmd(ip,cmd):
135 199 """ os.system replacement that stores process info to db['tasks/t1234'] """
200 cmd = cmd.strip()
136 201 cmdname = cmd.split(None,1)[0]
137 if cmdname in shell_internal_commands:
202 if cmdname in shell_internal_commands or '|' in cmd or '>' in cmd or '<' in cmd:
138 203 use_shell = True
139 204 else:
140 205 use_shell = False
141 206
142 p = Popen(cmd,shell = use_shell)
143 jobentry = 'tasks/t' + str(p.pid)
144
207 jobentry = None
145 208 try:
209 try:
210 p = Popen(cmd,shell = use_shell)
211 except WindowsError:
212 if use_shell:
213 # try with os.system
214 os.system(cmd)
215 return
216 else:
217 # have to go via shell, sucks
218 p = Popen(cmd,shell = True)
219
220 jobentry = 'tasks/t' + str(p.pid)
146 221 ip.db[jobentry] = (p.pid,cmd,os.getcwd(),time.time())
147 p.communicate()
222 p.communicate()
223
148 224 finally:
149 del ip.db[jobentry]
225 if jobentry:
226 del ip.db[jobentry]
150 227
151 228
152 229 def install():
153 230 global ip
154 231 ip = IPython.ipapi.get()
155 232 # needed to make startjob visible as _ip.startjob('blah')
156 233 ip.startjob = startjob
157 234 ip.set_hook('input_prefilter', jobctrl_prefilter_f)
158 235 ip.set_hook('shell_hook', jobctrl_shellcmd)
159 236 ip.expose_magic('kill',magic_kill)
160 237 ip.expose_magic('tasks',magic_tasks)
161
238 ip.expose_magic('jobqueue',jobqueue_f)
239 ip.set_hook('pre_prompt_hook', jobq_output_hook)
162 240 install()
@@ -1,284 +1,292 b''
1 1 # -*- coding: utf-8 -*-
2 2 """String interpolation for Python (by Ka-Ping Yee, 14 Feb 2000).
3 3
4 4 This module lets you quickly and conveniently interpolate values into
5 5 strings (in the flavour of Perl or Tcl, but with less extraneous
6 6 punctuation). You get a bit more power than in the other languages,
7 7 because this module allows subscripting, slicing, function calls,
8 8 attribute lookup, or arbitrary expressions. Variables and expressions
9 9 are evaluated in the namespace of the caller.
10 10
11 11 The itpl() function returns the result of interpolating a string, and
12 12 printpl() prints out an interpolated string. Here are some examples:
13 13
14 14 from Itpl import printpl
15 15 printpl("Here is a $string.")
16 16 printpl("Here is a $module.member.")
17 17 printpl("Here is an $object.member.")
18 18 printpl("Here is a $functioncall(with, arguments).")
19 19 printpl("Here is an ${arbitrary + expression}.")
20 20 printpl("Here is an $array[3] member.")
21 21 printpl("Here is a $dictionary['member'].")
22 22
23 23 The filter() function filters a file object so that output through it
24 24 is interpolated. This lets you produce the illusion that Python knows
25 25 how to do interpolation:
26 26
27 27 import Itpl
28 28 sys.stdout = Itpl.filter()
29 29 f = "fancy"
30 30 print "Isn't this $f?"
31 31 print "Standard output has been replaced with a $sys.stdout object."
32 32 sys.stdout = Itpl.unfilter()
33 33 print "Okay, back $to $normal."
34 34
35 35 Under the hood, the Itpl class represents a string that knows how to
36 36 interpolate values. An instance of the class parses the string once
37 37 upon initialization; the evaluation and substitution can then be done
38 38 each time the instance is evaluated with str(instance). For example:
39 39
40 40 from Itpl import Itpl
41 41 s = Itpl("Here is $foo.")
42 42 foo = 5
43 43 print str(s)
44 44 foo = "bar"
45 45 print str(s)
46 46
47 47 $Id: Itpl.py 2918 2007-12-31 14:34:47Z vivainio $
48 48 """ # ' -> close an open quote for stupid emacs
49 49
50 50 #*****************************************************************************
51 51 #
52 52 # Copyright (c) 2001 Ka-Ping Yee <ping@lfw.org>
53 53 #
54 54 #
55 55 # Published under the terms of the MIT license, hereby reproduced:
56 56 #
57 57 # Permission is hereby granted, free of charge, to any person obtaining a copy
58 58 # of this software and associated documentation files (the "Software"), to
59 59 # deal in the Software without restriction, including without limitation the
60 60 # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
61 61 # sell copies of the Software, and to permit persons to whom the Software is
62 62 # furnished to do so, subject to the following conditions:
63 63 #
64 64 # The above copyright notice and this permission notice shall be included in
65 65 # all copies or substantial portions of the Software.
66 66 #
67 67 # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
68 68 # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
69 69 # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
70 70 # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
71 71 # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
72 72 # FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
73 73 # IN THE SOFTWARE.
74 74 #
75 75 #*****************************************************************************
76 76
77 77 __author__ = 'Ka-Ping Yee <ping@lfw.org>'
78 78 __license__ = 'MIT'
79 79
80 80 import string
81 81 import sys
82 82 from tokenize import tokenprog
83 83 from types import StringType
84 84
85 85 class ItplError(ValueError):
86 86 def __init__(self, text, pos):
87 87 self.text = text
88 88 self.pos = pos
89 89 def __str__(self):
90 90 return "unfinished expression in %s at char %d" % (
91 91 repr(self.text), self.pos)
92 92
93 93 def matchorfail(text, pos):
94 94 match = tokenprog.match(text, pos)
95 95 if match is None:
96 96 raise ItplError(text, pos)
97
97 98 return match, match.end()
98 99
100 try:
101 itpl_encoding = sys.stdin.encoding or 'ascii'
102 except AttributeError:
103 itpl_encoding = 'ascii'
104
105
106
99 107 class Itpl:
100 108 """Class representing a string with interpolation abilities.
101 109
102 110 Upon creation, an instance works out what parts of the format
103 111 string are literal and what parts need to be evaluated. The
104 112 evaluation and substitution happens in the namespace of the
105 113 caller when str(instance) is called."""
106 114
107 def __init__(self, format,codec=sys.stdin.encoding,encoding_errors='backslashreplace'):
115 def __init__(self, format,codec=itpl_encoding,encoding_errors='backslashreplace'):
108 116 """The single mandatory argument to this constructor is a format
109 117 string.
110 118
111 119 The format string is parsed according to the following rules:
112 120
113 121 1. A dollar sign and a name, possibly followed by any of:
114 122 - an open-paren, and anything up to the matching paren
115 123 - an open-bracket, and anything up to the matching bracket
116 124 - a period and a name
117 125 any number of times, is evaluated as a Python expression.
118 126
119 127 2. A dollar sign immediately followed by an open-brace, and
120 128 anything up to the matching close-brace, is evaluated as
121 129 a Python expression.
122 130
123 131 3. Outside of the expressions described in the above two rules,
124 132 two dollar signs in a row give you one literal dollar sign.
125 133
126 134 Optional arguments:
127 135
128 136 - codec('utf_8'): a string containing the name of a valid Python
129 137 codec.
130 138
131 139 - encoding_errors('backslashreplace'): a string with a valid error handling
132 140 policy. See the codecs module documentation for details.
133 141
134 142 These are used to encode the format string if a call to str() fails on
135 143 the expanded result."""
136 144
137 145 if not isinstance(format,basestring):
138 146 raise TypeError, "needs string initializer"
139 147 self.format = format
140 148 self.codec = codec
141 149 self.encoding_errors = encoding_errors
142 150
143 151 namechars = "abcdefghijklmnopqrstuvwxyz" \
144 152 "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_";
145 153 chunks = []
146 154 pos = 0
147 155
148 156 while 1:
149 157 dollar = string.find(format, "$", pos)
150 158 if dollar < 0: break
151 159 nextchar = format[dollar+1]
152 160
153 161 if nextchar == "{":
154 162 chunks.append((0, format[pos:dollar]))
155 163 pos, level = dollar+2, 1
156 164 while level:
157 165 match, pos = matchorfail(format, pos)
158 166 tstart, tend = match.regs[3]
159 167 token = format[tstart:tend]
160 168 if token == "{": level = level+1
161 169 elif token == "}": level = level-1
162 170 chunks.append((1, format[dollar+2:pos-1]))
163 171
164 172 elif nextchar in namechars:
165 173 chunks.append((0, format[pos:dollar]))
166 174 match, pos = matchorfail(format, dollar+1)
167 175 while pos < len(format):
168 176 if format[pos] == "." and \
169 177 pos+1 < len(format) and format[pos+1] in namechars:
170 178 match, pos = matchorfail(format, pos+1)
171 179 elif format[pos] in "([":
172 180 pos, level = pos+1, 1
173 181 while level:
174 182 match, pos = matchorfail(format, pos)
175 183 tstart, tend = match.regs[3]
176 184 token = format[tstart:tend]
177 185 if token[0] in "([": level = level+1
178 186 elif token[0] in ")]": level = level-1
179 187 else: break
180 188 chunks.append((1, format[dollar+1:pos]))
181 189
182 190 else:
183 191 chunks.append((0, format[pos:dollar+1]))
184 192 pos = dollar + 1 + (nextchar == "$")
185 193
186 194 if pos < len(format): chunks.append((0, format[pos:]))
187 195 self.chunks = chunks
188 196
189 197 def __repr__(self):
190 198 return "<Itpl %s >" % repr(self.format)
191 199
192 200 def _str(self,glob,loc):
193 201 """Evaluate to a string in the given globals/locals.
194 202
195 203 The final output is built by calling str(), but if this fails, the
196 204 result is encoded with the instance's codec and error handling policy,
197 205 via a call to out.encode(self.codec,self.encoding_errors)"""
198 206 result = []
199 207 app = result.append
200 208 for live, chunk in self.chunks:
201 209 if live:
202 210 val = eval(chunk,glob,loc)
203 211 try:
204 212 app(str(val))
205 213 except UnicodeEncodeError:
206 214 app(unicode(val))
207 215
208 216 else: app(chunk)
209 217 out = ''.join(result)
210 218 try:
211 219 return str(out)
212 220 except UnicodeError:
213 221 return out.encode(self.codec,self.encoding_errors)
214 222
215 223 def __str__(self):
216 224 """Evaluate and substitute the appropriate parts of the string."""
217 225
218 226 # We need to skip enough frames to get to the actual caller outside of
219 227 # Itpl.
220 228 frame = sys._getframe(1)
221 229 while frame.f_globals["__name__"] == __name__: frame = frame.f_back
222 230 loc, glob = frame.f_locals, frame.f_globals
223 231
224 232 return self._str(glob,loc)
225 233
226 234 class ItplNS(Itpl):
227 235 """Class representing a string with interpolation abilities.
228 236
229 237 This inherits from Itpl, but at creation time a namespace is provided
230 238 where the evaluation will occur. The interpolation becomes a bit more
231 239 efficient, as no traceback needs to be extracte. It also allows the
232 240 caller to supply a different namespace for the interpolation to occur than
233 241 its own."""
234 242
235 243 def __init__(self, format,globals,locals=None,
236 244 codec='utf_8',encoding_errors='backslashreplace'):
237 245 """ItplNS(format,globals[,locals]) -> interpolating string instance.
238 246
239 247 This constructor, besides a format string, takes a globals dictionary
240 248 and optionally a locals (which defaults to globals if not provided).
241 249
242 250 For further details, see the Itpl constructor."""
243 251
244 252 if locals is None:
245 253 locals = globals
246 254 self.globals = globals
247 255 self.locals = locals
248 256 Itpl.__init__(self,format,codec,encoding_errors)
249 257
250 258 def __str__(self):
251 259 """Evaluate and substitute the appropriate parts of the string."""
252 260 return self._str(self.globals,self.locals)
253 261
254 262 def __repr__(self):
255 263 return "<ItplNS %s >" % repr(self.format)
256 264
257 265 # utilities for fast printing
258 266 def itpl(text): return str(Itpl(text))
259 267 def printpl(text): print itpl(text)
260 268 # versions with namespace
261 269 def itplns(text,globals,locals=None): return str(ItplNS(text,globals,locals))
262 270 def printplns(text,globals,locals=None): print itplns(text,globals,locals)
263 271
264 272 class ItplFile:
265 273 """A file object that filters each write() through an interpolator."""
266 274 def __init__(self, file): self.file = file
267 275 def __repr__(self): return "<interpolated " + repr(self.file) + ">"
268 276 def __getattr__(self, attr): return getattr(self.file, attr)
269 277 def write(self, text): self.file.write(str(Itpl(text)))
270 278
271 279 def filter(file=sys.stdout):
272 280 """Return an ItplFile that filters writes to the given file object.
273 281
274 282 'file = filter(file)' replaces 'file' with a filtered object that
275 283 has a write() method. When called with no argument, this creates
276 284 a filter to sys.stdout."""
277 285 return ItplFile(file)
278 286
279 287 def unfilter(ifile=None):
280 288 """Return the original file that corresponds to the given ItplFile.
281 289
282 290 'file = unfilter(file)' undoes the effect of 'file = filter(file)'.
283 291 'sys.stdout = unfilter()' undoes the effect of 'sys.stdout = filter()'."""
284 292 return ifile and ifile.file or sys.stdout.file
@@ -1,3283 +1,3319 b''
1 1 # -*- coding: utf-8 -*-
2 2 """Magic functions for InteractiveShell.
3 3
4 4 $Id: Magic.py 2996 2008-01-30 06:31:39Z fperez $"""
5 5
6 6 #*****************************************************************************
7 7 # Copyright (C) 2001 Janko Hauser <jhauser@zscout.de> and
8 8 # Copyright (C) 2001-2006 Fernando Perez <fperez@colorado.edu>
9 9 #
10 10 # Distributed under the terms of the BSD License. The full license is in
11 11 # the file COPYING, distributed as part of this software.
12 12 #*****************************************************************************
13 13
14 14 #****************************************************************************
15 15 # Modules and globals
16 16
17 17 from IPython import Release
18 18 __author__ = '%s <%s>\n%s <%s>' % \
19 19 ( Release.authors['Janko'] + Release.authors['Fernando'] )
20 20 __license__ = Release.license
21 21
22 22 # Python standard modules
23 23 import __builtin__
24 24 import bdb
25 25 import inspect
26 26 import os
27 27 import pdb
28 28 import pydoc
29 29 import sys
30 30 import re
31 31 import tempfile
32 32 import time
33 33 import cPickle as pickle
34 34 import textwrap
35 35 from cStringIO import StringIO
36 36 from getopt import getopt,GetoptError
37 37 from pprint import pprint, pformat
38 38 from sets import Set
39 39
40 40 # cProfile was added in Python2.5
41 41 try:
42 42 import cProfile as profile
43 43 import pstats
44 44 except ImportError:
45 45 # profile isn't bundled by default in Debian for license reasons
46 46 try:
47 47 import profile,pstats
48 48 except ImportError:
49 49 profile = pstats = None
50 50
51 51 # Homebrewed
52 52 import IPython
53 53 from IPython import Debugger, OInspect, wildcard
54 54 from IPython.FakeModule import FakeModule
55 55 from IPython.Itpl import Itpl, itpl, printpl,itplns
56 56 from IPython.PyColorize import Parser
57 57 from IPython.ipstruct import Struct
58 58 from IPython.macro import Macro
59 59 from IPython.genutils import *
60 60 from IPython import platutils
61 61 import IPython.generics
62 62 import IPython.ipapi
63 63 from IPython.ipapi import UsageError
64 64 #***************************************************************************
65 65 # Utility functions
66 66 def on_off(tag):
67 67 """Return an ON/OFF string for a 1/0 input. Simple utility function."""
68 68 return ['OFF','ON'][tag]
69 69
70 70 class Bunch: pass
71 71
72 72 def compress_dhist(dh):
73 73 head, tail = dh[:-10], dh[-10:]
74 74
75 75 newhead = []
76 76 done = Set()
77 77 for h in head:
78 78 if h in done:
79 79 continue
80 80 newhead.append(h)
81 81 done.add(h)
82 82
83 83 return newhead + tail
84 84
85 85
86 86 #***************************************************************************
87 87 # Main class implementing Magic functionality
88 88 class Magic:
89 89 """Magic functions for InteractiveShell.
90 90
91 91 Shell functions which can be reached as %function_name. All magic
92 92 functions should accept a string, which they can parse for their own
93 93 needs. This can make some functions easier to type, eg `%cd ../`
94 94 vs. `%cd("../")`
95 95
96 96 ALL definitions MUST begin with the prefix magic_. The user won't need it
97 97 at the command line, but it is is needed in the definition. """
98 98
99 99 # class globals
100 100 auto_status = ['Automagic is OFF, % prefix IS needed for magic functions.',
101 101 'Automagic is ON, % prefix NOT needed for magic functions.']
102 102
103 103 #......................................................................
104 104 # some utility functions
105 105
106 106 def __init__(self,shell):
107 107
108 108 self.options_table = {}
109 109 if profile is None:
110 110 self.magic_prun = self.profile_missing_notice
111 111 self.shell = shell
112 112
113 113 # namespace for holding state we may need
114 114 self._magic_state = Bunch()
115 115
116 116 def profile_missing_notice(self, *args, **kwargs):
117 117 error("""\
118 The profile module could not be found. If you are a Debian user,
119 it has been removed from the standard Debian package because of its non-free
120 license. To use profiling, please install"python2.3-profiler" from non-free.""")
118 The profile module could not be found. It has been removed from the standard
119 python packages because of its non-free license. To use profiling, install the
120 python-profiler package from non-free.""")
121 121
122 122 def default_option(self,fn,optstr):
123 123 """Make an entry in the options_table for fn, with value optstr"""
124 124
125 125 if fn not in self.lsmagic():
126 126 error("%s is not a magic function" % fn)
127 127 self.options_table[fn] = optstr
128 128
129 129 def lsmagic(self):
130 130 """Return a list of currently available magic functions.
131 131
132 132 Gives a list of the bare names after mangling (['ls','cd', ...], not
133 133 ['magic_ls','magic_cd',...]"""
134 134
135 135 # FIXME. This needs a cleanup, in the way the magics list is built.
136 136
137 137 # magics in class definition
138 138 class_magic = lambda fn: fn.startswith('magic_') and \
139 139 callable(Magic.__dict__[fn])
140 140 # in instance namespace (run-time user additions)
141 141 inst_magic = lambda fn: fn.startswith('magic_') and \
142 142 callable(self.__dict__[fn])
143 143 # and bound magics by user (so they can access self):
144 144 inst_bound_magic = lambda fn: fn.startswith('magic_') and \
145 145 callable(self.__class__.__dict__[fn])
146 146 magics = filter(class_magic,Magic.__dict__.keys()) + \
147 147 filter(inst_magic,self.__dict__.keys()) + \
148 148 filter(inst_bound_magic,self.__class__.__dict__.keys())
149 149 out = []
150 for fn in magics:
150 for fn in Set(magics):
151 151 out.append(fn.replace('magic_','',1))
152 152 out.sort()
153 153 return out
154 154
155 155 def extract_input_slices(self,slices,raw=False):
156 156 """Return as a string a set of input history slices.
157 157
158 158 Inputs:
159 159
160 160 - slices: the set of slices is given as a list of strings (like
161 161 ['1','4:8','9'], since this function is for use by magic functions
162 162 which get their arguments as strings.
163 163
164 164 Optional inputs:
165 165
166 166 - raw(False): by default, the processed input is used. If this is
167 167 true, the raw input history is used instead.
168 168
169 169 Note that slices can be called with two notations:
170 170
171 171 N:M -> standard python form, means including items N...(M-1).
172 172
173 173 N-M -> include items N..M (closed endpoint)."""
174 174
175 175 if raw:
176 176 hist = self.shell.input_hist_raw
177 177 else:
178 178 hist = self.shell.input_hist
179 179
180 180 cmds = []
181 181 for chunk in slices:
182 182 if ':' in chunk:
183 183 ini,fin = map(int,chunk.split(':'))
184 184 elif '-' in chunk:
185 185 ini,fin = map(int,chunk.split('-'))
186 186 fin += 1
187 187 else:
188 188 ini = int(chunk)
189 189 fin = ini+1
190 190 cmds.append(hist[ini:fin])
191 191 return cmds
192 192
193 193 def _ofind(self, oname, namespaces=None):
194 194 """Find an object in the available namespaces.
195 195
196 196 self._ofind(oname) -> dict with keys: found,obj,ospace,ismagic
197 197
198 198 Has special code to detect magic functions.
199 199 """
200 200
201 201 oname = oname.strip()
202 202
203 203 alias_ns = None
204 204 if namespaces is None:
205 205 # Namespaces to search in:
206 206 # Put them in a list. The order is important so that we
207 207 # find things in the same order that Python finds them.
208 208 namespaces = [ ('Interactive', self.shell.user_ns),
209 209 ('IPython internal', self.shell.internal_ns),
210 210 ('Python builtin', __builtin__.__dict__),
211 211 ('Alias', self.shell.alias_table),
212 212 ]
213 213 alias_ns = self.shell.alias_table
214 214
215 215 # initialize results to 'null'
216 216 found = 0; obj = None; ospace = None; ds = None;
217 217 ismagic = 0; isalias = 0; parent = None
218 218
219 219 # Look for the given name by splitting it in parts. If the head is
220 220 # found, then we look for all the remaining parts as members, and only
221 221 # declare success if we can find them all.
222 222 oname_parts = oname.split('.')
223 223 oname_head, oname_rest = oname_parts[0],oname_parts[1:]
224 224 for nsname,ns in namespaces:
225 225 try:
226 226 obj = ns[oname_head]
227 227 except KeyError:
228 228 continue
229 229 else:
230 230 #print 'oname_rest:', oname_rest # dbg
231 231 for part in oname_rest:
232 232 try:
233 233 parent = obj
234 234 obj = getattr(obj,part)
235 235 except:
236 236 # Blanket except b/c some badly implemented objects
237 237 # allow __getattr__ to raise exceptions other than
238 238 # AttributeError, which then crashes IPython.
239 239 break
240 240 else:
241 241 # If we finish the for loop (no break), we got all members
242 242 found = 1
243 243 ospace = nsname
244 244 if ns == alias_ns:
245 245 isalias = 1
246 246 break # namespace loop
247 247
248 248 # Try to see if it's magic
249 249 if not found:
250 250 if oname.startswith(self.shell.ESC_MAGIC):
251 251 oname = oname[1:]
252 252 obj = getattr(self,'magic_'+oname,None)
253 253 if obj is not None:
254 254 found = 1
255 255 ospace = 'IPython internal'
256 256 ismagic = 1
257 257
258 258 # Last try: special-case some literals like '', [], {}, etc:
259 259 if not found and oname_head in ["''",'""','[]','{}','()']:
260 260 obj = eval(oname_head)
261 261 found = 1
262 262 ospace = 'Interactive'
263 263
264 264 return {'found':found, 'obj':obj, 'namespace':ospace,
265 265 'ismagic':ismagic, 'isalias':isalias, 'parent':parent}
266 266
267 267 def arg_err(self,func):
268 268 """Print docstring if incorrect arguments were passed"""
269 269 print 'Error in arguments:'
270 270 print OInspect.getdoc(func)
271 271
272 272 def format_latex(self,strng):
273 273 """Format a string for latex inclusion."""
274 274
275 275 # Characters that need to be escaped for latex:
276 276 escape_re = re.compile(r'(%|_|\$|#|&)',re.MULTILINE)
277 277 # Magic command names as headers:
278 278 cmd_name_re = re.compile(r'^(%s.*?):' % self.shell.ESC_MAGIC,
279 279 re.MULTILINE)
280 280 # Magic commands
281 281 cmd_re = re.compile(r'(?P<cmd>%s.+?\b)(?!\}\}:)' % self.shell.ESC_MAGIC,
282 282 re.MULTILINE)
283 283 # Paragraph continue
284 284 par_re = re.compile(r'\\$',re.MULTILINE)
285 285
286 286 # The "\n" symbol
287 287 newline_re = re.compile(r'\\n')
288 288
289 289 # Now build the string for output:
290 290 #strng = cmd_name_re.sub(r'\n\\texttt{\\textsl{\\large \1}}:',strng)
291 291 strng = cmd_name_re.sub(r'\n\\bigskip\n\\texttt{\\textbf{ \1}}:',
292 292 strng)
293 293 strng = cmd_re.sub(r'\\texttt{\g<cmd>}',strng)
294 294 strng = par_re.sub(r'\\\\',strng)
295 295 strng = escape_re.sub(r'\\\1',strng)
296 296 strng = newline_re.sub(r'\\textbackslash{}n',strng)
297 297 return strng
298 298
299 299 def format_screen(self,strng):
300 300 """Format a string for screen printing.
301 301
302 302 This removes some latex-type format codes."""
303 303 # Paragraph continue
304 304 par_re = re.compile(r'\\$',re.MULTILINE)
305 305 strng = par_re.sub('',strng)
306 306 return strng
307 307
308 308 def parse_options(self,arg_str,opt_str,*long_opts,**kw):
309 309 """Parse options passed to an argument string.
310 310
311 311 The interface is similar to that of getopt(), but it returns back a
312 312 Struct with the options as keys and the stripped argument string still
313 313 as a string.
314 314
315 315 arg_str is quoted as a true sys.argv vector by using shlex.split.
316 316 This allows us to easily expand variables, glob files, quote
317 317 arguments, etc.
318 318
319 319 Options:
320 320 -mode: default 'string'. If given as 'list', the argument string is
321 321 returned as a list (split on whitespace) instead of a string.
322 322
323 323 -list_all: put all option values in lists. Normally only options
324 324 appearing more than once are put in a list.
325 325
326 326 -posix (True): whether to split the input line in POSIX mode or not,
327 327 as per the conventions outlined in the shlex module from the
328 328 standard library."""
329 329
330 330 # inject default options at the beginning of the input line
331 331 caller = sys._getframe(1).f_code.co_name.replace('magic_','')
332 332 arg_str = '%s %s' % (self.options_table.get(caller,''),arg_str)
333 333
334 334 mode = kw.get('mode','string')
335 335 if mode not in ['string','list']:
336 336 raise ValueError,'incorrect mode given: %s' % mode
337 337 # Get options
338 338 list_all = kw.get('list_all',0)
339 339 posix = kw.get('posix',True)
340 340
341 341 # Check if we have more than one argument to warrant extra processing:
342 342 odict = {} # Dictionary with options
343 343 args = arg_str.split()
344 344 if len(args) >= 1:
345 345 # If the list of inputs only has 0 or 1 thing in it, there's no
346 346 # need to look for options
347 347 argv = arg_split(arg_str,posix)
348 348 # Do regular option processing
349 349 try:
350 350 opts,args = getopt(argv,opt_str,*long_opts)
351 351 except GetoptError,e:
352 352 raise UsageError('%s ( allowed: "%s" %s)' % (e.msg,opt_str,
353 353 " ".join(long_opts)))
354 354 for o,a in opts:
355 355 if o.startswith('--'):
356 356 o = o[2:]
357 357 else:
358 358 o = o[1:]
359 359 try:
360 360 odict[o].append(a)
361 361 except AttributeError:
362 362 odict[o] = [odict[o],a]
363 363 except KeyError:
364 364 if list_all:
365 365 odict[o] = [a]
366 366 else:
367 367 odict[o] = a
368 368
369 369 # Prepare opts,args for return
370 370 opts = Struct(odict)
371 371 if mode == 'string':
372 372 args = ' '.join(args)
373 373
374 374 return opts,args
375 375
376 376 #......................................................................
377 377 # And now the actual magic functions
378 378
379 379 # Functions for IPython shell work (vars,funcs, config, etc)
380 380 def magic_lsmagic(self, parameter_s = ''):
381 381 """List currently available magic functions."""
382 382 mesc = self.shell.ESC_MAGIC
383 383 print 'Available magic functions:\n'+mesc+\
384 384 (' '+mesc).join(self.lsmagic())
385 385 print '\n' + Magic.auto_status[self.shell.rc.automagic]
386 386 return None
387 387
388 388 def magic_magic(self, parameter_s = ''):
389 """Print information about the magic function system."""
389 """Print information about the magic function system.
390
391 Supported formats: -latex, -brief, -rest
392 """
390 393
391 394 mode = ''
392 395 try:
393 396 if parameter_s.split()[0] == '-latex':
394 397 mode = 'latex'
395 398 if parameter_s.split()[0] == '-brief':
396 399 mode = 'brief'
400 if parameter_s.split()[0] == '-rest':
401 mode = 'rest'
402 rest_docs = []
397 403 except:
398 404 pass
399 405
400 406 magic_docs = []
401 407 for fname in self.lsmagic():
402 408 mname = 'magic_' + fname
403 409 for space in (Magic,self,self.__class__):
404 410 try:
405 411 fn = space.__dict__[mname]
406 412 except KeyError:
407 413 pass
408 414 else:
409 415 break
410 416 if mode == 'brief':
411 417 # only first line
412 fndoc = fn.__doc__.split('\n',1)[0]
418 if fn.__doc__:
419 fndoc = fn.__doc__.split('\n',1)[0]
420 else:
421 fndoc = 'No documentation'
422 else:
423 fndoc = fn.__doc__.rstrip()
424
425 if mode == 'rest':
426 rest_docs.append('**%s%s**::\n\n\t%s\n\n' %(self.shell.ESC_MAGIC,
427 fname,fndoc))
428
413 429 else:
414 fndoc = fn.__doc__
430 magic_docs.append('%s%s:\n\t%s\n' %(self.shell.ESC_MAGIC,
431 fname,fndoc))
415 432
416 magic_docs.append('%s%s:\n\t%s\n' %(self.shell.ESC_MAGIC,
417 fname,fndoc))
418 433 magic_docs = ''.join(magic_docs)
419 434
435 if mode == 'rest':
436 return "".join(rest_docs)
437
420 438 if mode == 'latex':
421 439 print self.format_latex(magic_docs)
422 440 return
423 441 else:
424 442 magic_docs = self.format_screen(magic_docs)
425 443 if mode == 'brief':
426 444 return magic_docs
427 445
428 446 outmsg = """
429 447 IPython's 'magic' functions
430 448 ===========================
431 449
432 450 The magic function system provides a series of functions which allow you to
433 451 control the behavior of IPython itself, plus a lot of system-type
434 452 features. All these functions are prefixed with a % character, but parameters
435 453 are given without parentheses or quotes.
436 454
437 455 NOTE: If you have 'automagic' enabled (via the command line option or with the
438 456 %automagic function), you don't need to type in the % explicitly. By default,
439 457 IPython ships with automagic on, so you should only rarely need the % escape.
440 458
441 459 Example: typing '%cd mydir' (without the quotes) changes you working directory
442 460 to 'mydir', if it exists.
443 461
444 462 You can define your own magic functions to extend the system. See the supplied
445 463 ipythonrc and example-magic.py files for details (in your ipython
446 464 configuration directory, typically $HOME/.ipython/).
447 465
448 466 You can also define your own aliased names for magic functions. In your
449 467 ipythonrc file, placing a line like:
450 468
451 469 execute __IPYTHON__.magic_pf = __IPYTHON__.magic_profile
452 470
453 471 will define %pf as a new name for %profile.
454 472
455 473 You can also call magics in code using the ipmagic() function, which IPython
456 474 automatically adds to the builtin namespace. Type 'ipmagic?' for details.
457 475
458 476 For a list of the available magic functions, use %lsmagic. For a description
459 477 of any of them, type %magic_name?, e.g. '%cd?'.
460 478
461 479 Currently the magic system has the following functions:\n"""
462 480
463 481 mesc = self.shell.ESC_MAGIC
464 482 outmsg = ("%s\n%s\n\nSummary of magic functions (from %slsmagic):"
465 483 "\n\n%s%s\n\n%s" % (outmsg,
466 484 magic_docs,mesc,mesc,
467 485 (' '+mesc).join(self.lsmagic()),
468 486 Magic.auto_status[self.shell.rc.automagic] ) )
469 487
470 488 page(outmsg,screen_lines=self.shell.rc.screen_length)
471 489
472 490
473 491 def magic_autoindent(self, parameter_s = ''):
474 492 """Toggle autoindent on/off (if available)."""
475 493
476 494 self.shell.set_autoindent()
477 495 print "Automatic indentation is:",['OFF','ON'][self.shell.autoindent]
478 496
479 497
480 498 def magic_automagic(self, parameter_s = ''):
481 499 """Make magic functions callable without having to type the initial %.
482 500
483 501 Without argumentsl toggles on/off (when off, you must call it as
484 502 %automagic, of course). With arguments it sets the value, and you can
485 503 use any of (case insensitive):
486 504
487 505 - on,1,True: to activate
488 506
489 507 - off,0,False: to deactivate.
490 508
491 509 Note that magic functions have lowest priority, so if there's a
492 510 variable whose name collides with that of a magic fn, automagic won't
493 511 work for that function (you get the variable instead). However, if you
494 512 delete the variable (del var), the previously shadowed magic function
495 513 becomes visible to automagic again."""
496 514
497 515 rc = self.shell.rc
498 516 arg = parameter_s.lower()
499 517 if parameter_s in ('on','1','true'):
500 518 rc.automagic = True
501 519 elif parameter_s in ('off','0','false'):
502 520 rc.automagic = False
503 521 else:
504 522 rc.automagic = not rc.automagic
505 523 print '\n' + Magic.auto_status[rc.automagic]
506 524
507 525
508 526 def magic_autocall(self, parameter_s = ''):
509 527 """Make functions callable without having to type parentheses.
510 528
511 529 Usage:
512 530
513 531 %autocall [mode]
514 532
515 533 The mode can be one of: 0->Off, 1->Smart, 2->Full. If not given, the
516 534 value is toggled on and off (remembering the previous state).
517 535
518 536 In more detail, these values mean:
519 537
520 538 0 -> fully disabled
521 539
522 540 1 -> active, but do not apply if there are no arguments on the line.
523 541
524 542 In this mode, you get:
525 543
526 544 In [1]: callable
527 545 Out[1]: <built-in function callable>
528 546
529 547 In [2]: callable 'hello'
530 548 ------> callable('hello')
531 549 Out[2]: False
532 550
533 551 2 -> Active always. Even if no arguments are present, the callable
534 552 object is called:
535 553
536 554 In [4]: callable
537 555 ------> callable()
538 556
539 557 Note that even with autocall off, you can still use '/' at the start of
540 558 a line to treat the first argument on the command line as a function
541 559 and add parentheses to it:
542 560
543 561 In [8]: /str 43
544 562 ------> str(43)
545 563 Out[8]: '43'
546 564 """
547 565
548 566 rc = self.shell.rc
549 567
550 568 if parameter_s:
551 569 arg = int(parameter_s)
552 570 else:
553 571 arg = 'toggle'
554 572
555 573 if not arg in (0,1,2,'toggle'):
556 574 error('Valid modes: (0->Off, 1->Smart, 2->Full')
557 575 return
558 576
559 577 if arg in (0,1,2):
560 578 rc.autocall = arg
561 579 else: # toggle
562 580 if rc.autocall:
563 581 self._magic_state.autocall_save = rc.autocall
564 582 rc.autocall = 0
565 583 else:
566 584 try:
567 585 rc.autocall = self._magic_state.autocall_save
568 586 except AttributeError:
569 587 rc.autocall = self._magic_state.autocall_save = 1
570 588
571 589 print "Automatic calling is:",['OFF','Smart','Full'][rc.autocall]
572 590
573 591 def magic_system_verbose(self, parameter_s = ''):
574 592 """Set verbose printing of system calls.
575 593
576 594 If called without an argument, act as a toggle"""
577 595
578 596 if parameter_s:
579 597 val = bool(eval(parameter_s))
580 598 else:
581 599 val = None
582 600
583 601 self.shell.rc_set_toggle('system_verbose',val)
584 602 print "System verbose printing is:",\
585 603 ['OFF','ON'][self.shell.rc.system_verbose]
586 604
587 605
588 606 def magic_page(self, parameter_s=''):
589 607 """Pretty print the object and display it through a pager.
590 608
591 609 %page [options] OBJECT
592 610
593 611 If no object is given, use _ (last output).
594 612
595 613 Options:
596 614
597 615 -r: page str(object), don't pretty-print it."""
598 616
599 617 # After a function contributed by Olivier Aubert, slightly modified.
600 618
601 619 # Process options/args
602 620 opts,args = self.parse_options(parameter_s,'r')
603 621 raw = 'r' in opts
604 622
605 623 oname = args and args or '_'
606 624 info = self._ofind(oname)
607 625 if info['found']:
608 626 txt = (raw and str or pformat)( info['obj'] )
609 627 page(txt)
610 628 else:
611 629 print 'Object `%s` not found' % oname
612 630
613 631 def magic_profile(self, parameter_s=''):
614 632 """Print your currently active IPyhton profile."""
615 633 if self.shell.rc.profile:
616 634 printpl('Current IPython profile: $self.shell.rc.profile.')
617 635 else:
618 636 print 'No profile active.'
619 637
620 638 def magic_pinfo(self, parameter_s='', namespaces=None):
621 639 """Provide detailed information about an object.
622 640
623 641 '%pinfo object' is just a synonym for object? or ?object."""
624 642
625 643 #print 'pinfo par: <%s>' % parameter_s # dbg
626 644
627 645
628 646 # detail_level: 0 -> obj? , 1 -> obj??
629 647 detail_level = 0
630 648 # We need to detect if we got called as 'pinfo pinfo foo', which can
631 649 # happen if the user types 'pinfo foo?' at the cmd line.
632 650 pinfo,qmark1,oname,qmark2 = \
633 651 re.match('(pinfo )?(\?*)(.*?)(\??$)',parameter_s).groups()
634 652 if pinfo or qmark1 or qmark2:
635 653 detail_level = 1
636 654 if "*" in oname:
637 655 self.magic_psearch(oname)
638 656 else:
639 657 self._inspect('pinfo', oname, detail_level=detail_level,
640 658 namespaces=namespaces)
641 659
642 660 def magic_pdef(self, parameter_s='', namespaces=None):
643 661 """Print the definition header for any callable object.
644 662
645 663 If the object is a class, print the constructor information."""
646 664 self._inspect('pdef',parameter_s, namespaces)
647 665
648 666 def magic_pdoc(self, parameter_s='', namespaces=None):
649 667 """Print the docstring for an object.
650 668
651 669 If the given object is a class, it will print both the class and the
652 670 constructor docstrings."""
653 671 self._inspect('pdoc',parameter_s, namespaces)
654 672
655 673 def magic_psource(self, parameter_s='', namespaces=None):
656 674 """Print (or run through pager) the source code for an object."""
657 675 self._inspect('psource',parameter_s, namespaces)
658 676
659 677 def magic_pfile(self, parameter_s=''):
660 678 """Print (or run through pager) the file where an object is defined.
661 679
662 680 The file opens at the line where the object definition begins. IPython
663 681 will honor the environment variable PAGER if set, and otherwise will
664 682 do its best to print the file in a convenient form.
665 683
666 684 If the given argument is not an object currently defined, IPython will
667 685 try to interpret it as a filename (automatically adding a .py extension
668 686 if needed). You can thus use %pfile as a syntax highlighting code
669 687 viewer."""
670 688
671 689 # first interpret argument as an object name
672 690 out = self._inspect('pfile',parameter_s)
673 691 # if not, try the input as a filename
674 692 if out == 'not found':
675 693 try:
676 694 filename = get_py_filename(parameter_s)
677 695 except IOError,msg:
678 696 print msg
679 697 return
680 698 page(self.shell.inspector.format(file(filename).read()))
681 699
682 700 def _inspect(self,meth,oname,namespaces=None,**kw):
683 701 """Generic interface to the inspector system.
684 702
685 703 This function is meant to be called by pdef, pdoc & friends."""
686 704
687 705 #oname = oname.strip()
688 706 #print '1- oname: <%r>' % oname # dbg
689 707 try:
690 708 oname = oname.strip().encode('ascii')
691 709 #print '2- oname: <%r>' % oname # dbg
692 710 except UnicodeEncodeError:
693 711 print 'Python identifiers can only contain ascii characters.'
694 712 return 'not found'
695 713
696 714 info = Struct(self._ofind(oname, namespaces))
697 715
698 716 if info.found:
699 717 try:
700 718 IPython.generics.inspect_object(info.obj)
701 719 return
702 720 except IPython.ipapi.TryNext:
703 721 pass
704 722 # Get the docstring of the class property if it exists.
705 723 path = oname.split('.')
706 724 root = '.'.join(path[:-1])
707 725 if info.parent is not None:
708 726 try:
709 727 target = getattr(info.parent, '__class__')
710 728 # The object belongs to a class instance.
711 729 try:
712 730 target = getattr(target, path[-1])
713 731 # The class defines the object.
714 732 if isinstance(target, property):
715 733 oname = root + '.__class__.' + path[-1]
716 734 info = Struct(self._ofind(oname))
717 735 except AttributeError: pass
718 736 except AttributeError: pass
719 737
720 738 pmethod = getattr(self.shell.inspector,meth)
721 739 formatter = info.ismagic and self.format_screen or None
722 740 if meth == 'pdoc':
723 741 pmethod(info.obj,oname,formatter)
724 742 elif meth == 'pinfo':
725 743 pmethod(info.obj,oname,formatter,info,**kw)
726 744 else:
727 745 pmethod(info.obj,oname)
728 746 else:
729 747 print 'Object `%s` not found.' % oname
730 748 return 'not found' # so callers can take other action
731 749
732 750 def magic_psearch(self, parameter_s=''):
733 751 """Search for object in namespaces by wildcard.
734 752
735 753 %psearch [options] PATTERN [OBJECT TYPE]
736 754
737 755 Note: ? can be used as a synonym for %psearch, at the beginning or at
738 756 the end: both a*? and ?a* are equivalent to '%psearch a*'. Still, the
739 757 rest of the command line must be unchanged (options come first), so
740 758 for example the following forms are equivalent
741 759
742 760 %psearch -i a* function
743 761 -i a* function?
744 762 ?-i a* function
745 763
746 764 Arguments:
747 765
748 766 PATTERN
749 767
750 768 where PATTERN is a string containing * as a wildcard similar to its
751 769 use in a shell. The pattern is matched in all namespaces on the
752 770 search path. By default objects starting with a single _ are not
753 771 matched, many IPython generated objects have a single
754 772 underscore. The default is case insensitive matching. Matching is
755 773 also done on the attributes of objects and not only on the objects
756 774 in a module.
757 775
758 776 [OBJECT TYPE]
759 777
760 778 Is the name of a python type from the types module. The name is
761 779 given in lowercase without the ending type, ex. StringType is
762 780 written string. By adding a type here only objects matching the
763 781 given type are matched. Using all here makes the pattern match all
764 782 types (this is the default).
765 783
766 784 Options:
767 785
768 786 -a: makes the pattern match even objects whose names start with a
769 787 single underscore. These names are normally ommitted from the
770 788 search.
771 789
772 790 -i/-c: make the pattern case insensitive/sensitive. If neither of
773 791 these options is given, the default is read from your ipythonrc
774 792 file. The option name which sets this value is
775 793 'wildcards_case_sensitive'. If this option is not specified in your
776 794 ipythonrc file, IPython's internal default is to do a case sensitive
777 795 search.
778 796
779 797 -e/-s NAMESPACE: exclude/search a given namespace. The pattern you
780 798 specifiy can be searched in any of the following namespaces:
781 799 'builtin', 'user', 'user_global','internal', 'alias', where
782 800 'builtin' and 'user' are the search defaults. Note that you should
783 801 not use quotes when specifying namespaces.
784 802
785 803 'Builtin' contains the python module builtin, 'user' contains all
786 804 user data, 'alias' only contain the shell aliases and no python
787 805 objects, 'internal' contains objects used by IPython. The
788 806 'user_global' namespace is only used by embedded IPython instances,
789 807 and it contains module-level globals. You can add namespaces to the
790 808 search with -s or exclude them with -e (these options can be given
791 809 more than once).
792 810
793 811 Examples:
794 812
795 813 %psearch a* -> objects beginning with an a
796 814 %psearch -e builtin a* -> objects NOT in the builtin space starting in a
797 815 %psearch a* function -> all functions beginning with an a
798 816 %psearch re.e* -> objects beginning with an e in module re
799 817 %psearch r*.e* -> objects that start with e in modules starting in r
800 818 %psearch r*.* string -> all strings in modules beginning with r
801 819
802 820 Case sensitve search:
803 821
804 822 %psearch -c a* list all object beginning with lower case a
805 823
806 824 Show objects beginning with a single _:
807 825
808 826 %psearch -a _* list objects beginning with a single underscore"""
809 827 try:
810 828 parameter_s = parameter_s.encode('ascii')
811 829 except UnicodeEncodeError:
812 830 print 'Python identifiers can only contain ascii characters.'
813 831 return
814 832
815 833 # default namespaces to be searched
816 834 def_search = ['user','builtin']
817 835
818 836 # Process options/args
819 837 opts,args = self.parse_options(parameter_s,'cias:e:',list_all=True)
820 838 opt = opts.get
821 839 shell = self.shell
822 840 psearch = shell.inspector.psearch
823 841
824 842 # select case options
825 843 if opts.has_key('i'):
826 844 ignore_case = True
827 845 elif opts.has_key('c'):
828 846 ignore_case = False
829 847 else:
830 848 ignore_case = not shell.rc.wildcards_case_sensitive
831 849
832 850 # Build list of namespaces to search from user options
833 851 def_search.extend(opt('s',[]))
834 852 ns_exclude = ns_exclude=opt('e',[])
835 853 ns_search = [nm for nm in def_search if nm not in ns_exclude]
836 854
837 855 # Call the actual search
838 856 try:
839 857 psearch(args,shell.ns_table,ns_search,
840 858 show_all=opt('a'),ignore_case=ignore_case)
841 859 except:
842 860 shell.showtraceback()
843 861
844 862 def magic_who_ls(self, parameter_s=''):
845 863 """Return a sorted list of all interactive variables.
846 864
847 865 If arguments are given, only variables of types matching these
848 866 arguments are returned."""
849 867
850 868 user_ns = self.shell.user_ns
851 869 internal_ns = self.shell.internal_ns
852 870 user_config_ns = self.shell.user_config_ns
853 871 out = []
854 872 typelist = parameter_s.split()
855 873
856 874 for i in user_ns:
857 875 if not (i.startswith('_') or i.startswith('_i')) \
858 876 and not (i in internal_ns or i in user_config_ns):
859 877 if typelist:
860 878 if type(user_ns[i]).__name__ in typelist:
861 879 out.append(i)
862 880 else:
863 881 out.append(i)
864 882 out.sort()
865 883 return out
866 884
867 885 def magic_who(self, parameter_s=''):
868 886 """Print all interactive variables, with some minimal formatting.
869 887
870 888 If any arguments are given, only variables whose type matches one of
871 889 these are printed. For example:
872 890
873 891 %who function str
874 892
875 893 will only list functions and strings, excluding all other types of
876 894 variables. To find the proper type names, simply use type(var) at a
877 895 command line to see how python prints type names. For example:
878 896
879 897 In [1]: type('hello')\\
880 898 Out[1]: <type 'str'>
881 899
882 900 indicates that the type name for strings is 'str'.
883 901
884 902 %who always excludes executed names loaded through your configuration
885 903 file and things which are internal to IPython.
886 904
887 905 This is deliberate, as typically you may load many modules and the
888 906 purpose of %who is to show you only what you've manually defined."""
889 907
890 908 varlist = self.magic_who_ls(parameter_s)
891 909 if not varlist:
892 910 if parameter_s:
893 911 print 'No variables match your requested type.'
894 912 else:
895 913 print 'Interactive namespace is empty.'
896 914 return
897 915
898 916 # if we have variables, move on...
899 917 count = 0
900 918 for i in varlist:
901 919 print i+'\t',
902 920 count += 1
903 921 if count > 8:
904 922 count = 0
905 923 print
906 924 print
907 925
908 926 def magic_whos(self, parameter_s=''):
909 927 """Like %who, but gives some extra information about each variable.
910 928
911 929 The same type filtering of %who can be applied here.
912 930
913 931 For all variables, the type is printed. Additionally it prints:
914 932
915 933 - For {},[],(): their length.
916 934
917 935 - For numpy and Numeric arrays, a summary with shape, number of
918 936 elements, typecode and size in memory.
919 937
920 938 - Everything else: a string representation, snipping their middle if
921 939 too long."""
922 940
923 941 varnames = self.magic_who_ls(parameter_s)
924 942 if not varnames:
925 943 if parameter_s:
926 944 print 'No variables match your requested type.'
927 945 else:
928 946 print 'Interactive namespace is empty.'
929 947 return
930 948
931 949 # if we have variables, move on...
932 950
933 951 # for these types, show len() instead of data:
934 952 seq_types = [types.DictType,types.ListType,types.TupleType]
935 953
936 954 # for numpy/Numeric arrays, display summary info
937 955 try:
938 956 import numpy
939 957 except ImportError:
940 958 ndarray_type = None
941 959 else:
942 960 ndarray_type = numpy.ndarray.__name__
943 961 try:
944 962 import Numeric
945 963 except ImportError:
946 964 array_type = None
947 965 else:
948 966 array_type = Numeric.ArrayType.__name__
949 967
950 968 # Find all variable names and types so we can figure out column sizes
951 969 def get_vars(i):
952 970 return self.shell.user_ns[i]
953 971
954 972 # some types are well known and can be shorter
955 973 abbrevs = {'IPython.macro.Macro' : 'Macro'}
956 974 def type_name(v):
957 975 tn = type(v).__name__
958 976 return abbrevs.get(tn,tn)
959 977
960 978 varlist = map(get_vars,varnames)
961 979
962 980 typelist = []
963 981 for vv in varlist:
964 982 tt = type_name(vv)
965 983
966 984 if tt=='instance':
967 985 typelist.append( abbrevs.get(str(vv.__class__),
968 986 str(vv.__class__)))
969 987 else:
970 988 typelist.append(tt)
971 989
972 990 # column labels and # of spaces as separator
973 991 varlabel = 'Variable'
974 992 typelabel = 'Type'
975 993 datalabel = 'Data/Info'
976 994 colsep = 3
977 995 # variable format strings
978 996 vformat = "$vname.ljust(varwidth)$vtype.ljust(typewidth)"
979 997 vfmt_short = '$vstr[:25]<...>$vstr[-25:]'
980 998 aformat = "%s: %s elems, type `%s`, %s bytes"
981 999 # find the size of the columns to format the output nicely
982 1000 varwidth = max(max(map(len,varnames)), len(varlabel)) + colsep
983 1001 typewidth = max(max(map(len,typelist)), len(typelabel)) + colsep
984 1002 # table header
985 1003 print varlabel.ljust(varwidth) + typelabel.ljust(typewidth) + \
986 1004 ' '+datalabel+'\n' + '-'*(varwidth+typewidth+len(datalabel)+1)
987 1005 # and the table itself
988 1006 kb = 1024
989 1007 Mb = 1048576 # kb**2
990 1008 for vname,var,vtype in zip(varnames,varlist,typelist):
991 1009 print itpl(vformat),
992 1010 if vtype in seq_types:
993 1011 print len(var)
994 1012 elif vtype in [array_type,ndarray_type]:
995 1013 vshape = str(var.shape).replace(',','').replace(' ','x')[1:-1]
996 1014 if vtype==ndarray_type:
997 1015 # numpy
998 1016 vsize = var.size
999 1017 vbytes = vsize*var.itemsize
1000 1018 vdtype = var.dtype
1001 1019 else:
1002 1020 # Numeric
1003 1021 vsize = Numeric.size(var)
1004 1022 vbytes = vsize*var.itemsize()
1005 1023 vdtype = var.typecode()
1006 1024
1007 1025 if vbytes < 100000:
1008 1026 print aformat % (vshape,vsize,vdtype,vbytes)
1009 1027 else:
1010 1028 print aformat % (vshape,vsize,vdtype,vbytes),
1011 1029 if vbytes < Mb:
1012 1030 print '(%s kb)' % (vbytes/kb,)
1013 1031 else:
1014 1032 print '(%s Mb)' % (vbytes/Mb,)
1015 1033 else:
1016 1034 try:
1017 1035 vstr = str(var)
1018 1036 except UnicodeEncodeError:
1019 1037 vstr = unicode(var).encode(sys.getdefaultencoding(),
1020 1038 'backslashreplace')
1021 1039 vstr = vstr.replace('\n','\\n')
1022 1040 if len(vstr) < 50:
1023 1041 print vstr
1024 1042 else:
1025 1043 printpl(vfmt_short)
1026 1044
1027 1045 def magic_reset(self, parameter_s=''):
1028 1046 """Resets the namespace by removing all names defined by the user.
1029 1047
1030 1048 Input/Output history are left around in case you need them."""
1031 1049
1032 1050 ans = self.shell.ask_yes_no(
1033 1051 "Once deleted, variables cannot be recovered. Proceed (y/[n])? ")
1034 1052 if not ans:
1035 1053 print 'Nothing done.'
1036 1054 return
1037 1055 user_ns = self.shell.user_ns
1038 1056 for i in self.magic_who_ls():
1039 1057 del(user_ns[i])
1040 1058
1041 1059 # Also flush the private list of module references kept for script
1042 1060 # execution protection
1043 1061 self.shell._user_main_modules[:] = []
1044 1062
1045 1063 def magic_logstart(self,parameter_s=''):
1046 1064 """Start logging anywhere in a session.
1047 1065
1048 1066 %logstart [-o|-r|-t] [log_name [log_mode]]
1049 1067
1050 1068 If no name is given, it defaults to a file named 'ipython_log.py' in your
1051 1069 current directory, in 'rotate' mode (see below).
1052 1070
1053 1071 '%logstart name' saves to file 'name' in 'backup' mode. It saves your
1054 1072 history up to that point and then continues logging.
1055 1073
1056 1074 %logstart takes a second optional parameter: logging mode. This can be one
1057 1075 of (note that the modes are given unquoted):\\
1058 1076 append: well, that says it.\\
1059 1077 backup: rename (if exists) to name~ and start name.\\
1060 1078 global: single logfile in your home dir, appended to.\\
1061 1079 over : overwrite existing log.\\
1062 1080 rotate: create rotating logs name.1~, name.2~, etc.
1063 1081
1064 1082 Options:
1065 1083
1066 1084 -o: log also IPython's output. In this mode, all commands which
1067 1085 generate an Out[NN] prompt are recorded to the logfile, right after
1068 1086 their corresponding input line. The output lines are always
1069 1087 prepended with a '#[Out]# ' marker, so that the log remains valid
1070 1088 Python code.
1071 1089
1072 1090 Since this marker is always the same, filtering only the output from
1073 1091 a log is very easy, using for example a simple awk call:
1074 1092
1075 1093 awk -F'#\\[Out\\]# ' '{if($2) {print $2}}' ipython_log.py
1076 1094
1077 1095 -r: log 'raw' input. Normally, IPython's logs contain the processed
1078 1096 input, so that user lines are logged in their final form, converted
1079 1097 into valid Python. For example, %Exit is logged as
1080 1098 '_ip.magic("Exit"). If the -r flag is given, all input is logged
1081 1099 exactly as typed, with no transformations applied.
1082 1100
1083 1101 -t: put timestamps before each input line logged (these are put in
1084 1102 comments)."""
1085 1103
1086 1104 opts,par = self.parse_options(parameter_s,'ort')
1087 1105 log_output = 'o' in opts
1088 1106 log_raw_input = 'r' in opts
1089 1107 timestamp = 't' in opts
1090 1108
1091 1109 rc = self.shell.rc
1092 1110 logger = self.shell.logger
1093 1111
1094 1112 # if no args are given, the defaults set in the logger constructor by
1095 1113 # ipytohn remain valid
1096 1114 if par:
1097 1115 try:
1098 1116 logfname,logmode = par.split()
1099 1117 except:
1100 1118 logfname = par
1101 1119 logmode = 'backup'
1102 1120 else:
1103 1121 logfname = logger.logfname
1104 1122 logmode = logger.logmode
1105 1123 # put logfname into rc struct as if it had been called on the command
1106 1124 # line, so it ends up saved in the log header Save it in case we need
1107 1125 # to restore it...
1108 1126 old_logfile = rc.opts.get('logfile','')
1109 1127 if logfname:
1110 1128 logfname = os.path.expanduser(logfname)
1111 1129 rc.opts.logfile = logfname
1112 1130 loghead = self.shell.loghead_tpl % (rc.opts,rc.args)
1113 1131 try:
1114 1132 started = logger.logstart(logfname,loghead,logmode,
1115 1133 log_output,timestamp,log_raw_input)
1116 1134 except:
1117 1135 rc.opts.logfile = old_logfile
1118 1136 warn("Couldn't start log: %s" % sys.exc_info()[1])
1119 1137 else:
1120 1138 # log input history up to this point, optionally interleaving
1121 1139 # output if requested
1122 1140
1123 1141 if timestamp:
1124 1142 # disable timestamping for the previous history, since we've
1125 1143 # lost those already (no time machine here).
1126 1144 logger.timestamp = False
1127 1145
1128 1146 if log_raw_input:
1129 1147 input_hist = self.shell.input_hist_raw
1130 1148 else:
1131 1149 input_hist = self.shell.input_hist
1132 1150
1133 1151 if log_output:
1134 1152 log_write = logger.log_write
1135 1153 output_hist = self.shell.output_hist
1136 1154 for n in range(1,len(input_hist)-1):
1137 1155 log_write(input_hist[n].rstrip())
1138 1156 if n in output_hist:
1139 1157 log_write(repr(output_hist[n]),'output')
1140 1158 else:
1141 1159 logger.log_write(input_hist[1:])
1142 1160 if timestamp:
1143 1161 # re-enable timestamping
1144 1162 logger.timestamp = True
1145 1163
1146 1164 print ('Activating auto-logging. '
1147 1165 'Current session state plus future input saved.')
1148 1166 logger.logstate()
1149 1167
1150 1168 def magic_logstop(self,parameter_s=''):
1151 1169 """Fully stop logging and close log file.
1152 1170
1153 1171 In order to start logging again, a new %logstart call needs to be made,
1154 1172 possibly (though not necessarily) with a new filename, mode and other
1155 1173 options."""
1156 1174 self.logger.logstop()
1157 1175
1158 1176 def magic_logoff(self,parameter_s=''):
1159 1177 """Temporarily stop logging.
1160 1178
1161 1179 You must have previously started logging."""
1162 1180 self.shell.logger.switch_log(0)
1163 1181
1164 1182 def magic_logon(self,parameter_s=''):
1165 1183 """Restart logging.
1166 1184
1167 1185 This function is for restarting logging which you've temporarily
1168 1186 stopped with %logoff. For starting logging for the first time, you
1169 1187 must use the %logstart function, which allows you to specify an
1170 1188 optional log filename."""
1171 1189
1172 1190 self.shell.logger.switch_log(1)
1173 1191
1174 1192 def magic_logstate(self,parameter_s=''):
1175 1193 """Print the status of the logging system."""
1176 1194
1177 1195 self.shell.logger.logstate()
1178 1196
1179 1197 def magic_pdb(self, parameter_s=''):
1180 1198 """Control the automatic calling of the pdb interactive debugger.
1181 1199
1182 1200 Call as '%pdb on', '%pdb 1', '%pdb off' or '%pdb 0'. If called without
1183 1201 argument it works as a toggle.
1184 1202
1185 1203 When an exception is triggered, IPython can optionally call the
1186 1204 interactive pdb debugger after the traceback printout. %pdb toggles
1187 1205 this feature on and off.
1188 1206
1189 1207 The initial state of this feature is set in your ipythonrc
1190 1208 configuration file (the variable is called 'pdb').
1191 1209
1192 1210 If you want to just activate the debugger AFTER an exception has fired,
1193 1211 without having to type '%pdb on' and rerunning your code, you can use
1194 1212 the %debug magic."""
1195 1213
1196 1214 par = parameter_s.strip().lower()
1197 1215
1198 1216 if par:
1199 1217 try:
1200 1218 new_pdb = {'off':0,'0':0,'on':1,'1':1}[par]
1201 1219 except KeyError:
1202 1220 print ('Incorrect argument. Use on/1, off/0, '
1203 1221 'or nothing for a toggle.')
1204 1222 return
1205 1223 else:
1206 1224 # toggle
1207 1225 new_pdb = not self.shell.call_pdb
1208 1226
1209 1227 # set on the shell
1210 1228 self.shell.call_pdb = new_pdb
1211 1229 print 'Automatic pdb calling has been turned',on_off(new_pdb)
1212 1230
1213 1231 def magic_debug(self, parameter_s=''):
1214 1232 """Activate the interactive debugger in post-mortem mode.
1215 1233
1216 1234 If an exception has just occurred, this lets you inspect its stack
1217 1235 frames interactively. Note that this will always work only on the last
1218 1236 traceback that occurred, so you must call this quickly after an
1219 1237 exception that you wish to inspect has fired, because if another one
1220 1238 occurs, it clobbers the previous one.
1221 1239
1222 1240 If you want IPython to automatically do this on every exception, see
1223 1241 the %pdb magic for more details.
1224 1242 """
1225 1243
1226 1244 self.shell.debugger(force=True)
1227 1245
1228 1246 def magic_prun(self, parameter_s ='',user_mode=1,
1229 1247 opts=None,arg_lst=None,prog_ns=None):
1230 1248
1231 1249 """Run a statement through the python code profiler.
1232 1250
1233 1251 Usage:\\
1234 1252 %prun [options] statement
1235 1253
1236 1254 The given statement (which doesn't require quote marks) is run via the
1237 1255 python profiler in a manner similar to the profile.run() function.
1238 1256 Namespaces are internally managed to work correctly; profile.run
1239 1257 cannot be used in IPython because it makes certain assumptions about
1240 1258 namespaces which do not hold under IPython.
1241 1259
1242 1260 Options:
1243 1261
1244 1262 -l <limit>: you can place restrictions on what or how much of the
1245 1263 profile gets printed. The limit value can be:
1246 1264
1247 1265 * A string: only information for function names containing this string
1248 1266 is printed.
1249 1267
1250 1268 * An integer: only these many lines are printed.
1251 1269
1252 1270 * A float (between 0 and 1): this fraction of the report is printed
1253 1271 (for example, use a limit of 0.4 to see the topmost 40% only).
1254 1272
1255 1273 You can combine several limits with repeated use of the option. For
1256 1274 example, '-l __init__ -l 5' will print only the topmost 5 lines of
1257 1275 information about class constructors.
1258 1276
1259 1277 -r: return the pstats.Stats object generated by the profiling. This
1260 1278 object has all the information about the profile in it, and you can
1261 1279 later use it for further analysis or in other functions.
1262 1280
1263 1281 -s <key>: sort profile by given key. You can provide more than one key
1264 1282 by using the option several times: '-s key1 -s key2 -s key3...'. The
1265 1283 default sorting key is 'time'.
1266 1284
1267 1285 The following is copied verbatim from the profile documentation
1268 1286 referenced below:
1269 1287
1270 1288 When more than one key is provided, additional keys are used as
1271 1289 secondary criteria when the there is equality in all keys selected
1272 1290 before them.
1273 1291
1274 1292 Abbreviations can be used for any key names, as long as the
1275 1293 abbreviation is unambiguous. The following are the keys currently
1276 1294 defined:
1277 1295
1278 1296 Valid Arg Meaning\\
1279 1297 "calls" call count\\
1280 1298 "cumulative" cumulative time\\
1281 1299 "file" file name\\
1282 1300 "module" file name\\
1283 1301 "pcalls" primitive call count\\
1284 1302 "line" line number\\
1285 1303 "name" function name\\
1286 1304 "nfl" name/file/line\\
1287 1305 "stdname" standard name\\
1288 1306 "time" internal time
1289 1307
1290 1308 Note that all sorts on statistics are in descending order (placing
1291 1309 most time consuming items first), where as name, file, and line number
1292 1310 searches are in ascending order (i.e., alphabetical). The subtle
1293 1311 distinction between "nfl" and "stdname" is that the standard name is a
1294 1312 sort of the name as printed, which means that the embedded line
1295 1313 numbers get compared in an odd way. For example, lines 3, 20, and 40
1296 1314 would (if the file names were the same) appear in the string order
1297 1315 "20" "3" and "40". In contrast, "nfl" does a numeric compare of the
1298 1316 line numbers. In fact, sort_stats("nfl") is the same as
1299 1317 sort_stats("name", "file", "line").
1300 1318
1301 1319 -T <filename>: save profile results as shown on screen to a text
1302 1320 file. The profile is still shown on screen.
1303 1321
1304 1322 -D <filename>: save (via dump_stats) profile statistics to given
1305 1323 filename. This data is in a format understod by the pstats module, and
1306 1324 is generated by a call to the dump_stats() method of profile
1307 1325 objects. The profile is still shown on screen.
1308 1326
1309 1327 If you want to run complete programs under the profiler's control, use
1310 1328 '%run -p [prof_opts] filename.py [args to program]' where prof_opts
1311 1329 contains profiler specific options as described here.
1312 1330
1313 1331 You can read the complete documentation for the profile module with:\\
1314 1332 In [1]: import profile; profile.help() """
1315 1333
1316 1334 opts_def = Struct(D=[''],l=[],s=['time'],T=[''])
1317 1335 # protect user quote marks
1318 1336 parameter_s = parameter_s.replace('"',r'\"').replace("'",r"\'")
1319 1337
1320 1338 if user_mode: # regular user call
1321 1339 opts,arg_str = self.parse_options(parameter_s,'D:l:rs:T:',
1322 1340 list_all=1)
1323 1341 namespace = self.shell.user_ns
1324 1342 else: # called to run a program by %run -p
1325 1343 try:
1326 1344 filename = get_py_filename(arg_lst[0])
1327 1345 except IOError,msg:
1328 1346 error(msg)
1329 1347 return
1330 1348
1331 1349 arg_str = 'execfile(filename,prog_ns)'
1332 1350 namespace = locals()
1333 1351
1334 1352 opts.merge(opts_def)
1335 1353
1336 1354 prof = profile.Profile()
1337 1355 try:
1338 1356 prof = prof.runctx(arg_str,namespace,namespace)
1339 1357 sys_exit = ''
1340 1358 except SystemExit:
1341 1359 sys_exit = """*** SystemExit exception caught in code being profiled."""
1342 1360
1343 1361 stats = pstats.Stats(prof).strip_dirs().sort_stats(*opts.s)
1344 1362
1345 1363 lims = opts.l
1346 1364 if lims:
1347 1365 lims = [] # rebuild lims with ints/floats/strings
1348 1366 for lim in opts.l:
1349 1367 try:
1350 1368 lims.append(int(lim))
1351 1369 except ValueError:
1352 1370 try:
1353 1371 lims.append(float(lim))
1354 1372 except ValueError:
1355 1373 lims.append(lim)
1356 1374
1357 1375 # Trap output.
1358 1376 stdout_trap = StringIO()
1359 1377
1360 1378 if hasattr(stats,'stream'):
1361 1379 # In newer versions of python, the stats object has a 'stream'
1362 1380 # attribute to write into.
1363 1381 stats.stream = stdout_trap
1364 1382 stats.print_stats(*lims)
1365 1383 else:
1366 1384 # For older versions, we manually redirect stdout during printing
1367 1385 sys_stdout = sys.stdout
1368 1386 try:
1369 1387 sys.stdout = stdout_trap
1370 1388 stats.print_stats(*lims)
1371 1389 finally:
1372 1390 sys.stdout = sys_stdout
1373 1391
1374 1392 output = stdout_trap.getvalue()
1375 1393 output = output.rstrip()
1376 1394
1377 1395 page(output,screen_lines=self.shell.rc.screen_length)
1378 1396 print sys_exit,
1379 1397
1380 1398 dump_file = opts.D[0]
1381 1399 text_file = opts.T[0]
1382 1400 if dump_file:
1383 1401 prof.dump_stats(dump_file)
1384 1402 print '\n*** Profile stats marshalled to file',\
1385 1403 `dump_file`+'.',sys_exit
1386 1404 if text_file:
1387 1405 pfile = file(text_file,'w')
1388 1406 pfile.write(output)
1389 1407 pfile.close()
1390 1408 print '\n*** Profile printout saved to text file',\
1391 1409 `text_file`+'.',sys_exit
1392 1410
1393 1411 if opts.has_key('r'):
1394 1412 return stats
1395 1413 else:
1396 1414 return None
1397 1415
1398 1416 def magic_run(self, parameter_s ='',runner=None):
1399 1417 """Run the named file inside IPython as a program.
1400 1418
1401 1419 Usage:\\
1402 1420 %run [-n -i -t [-N<N>] -d [-b<N>] -p [profile options]] file [args]
1403 1421
1404 1422 Parameters after the filename are passed as command-line arguments to
1405 1423 the program (put in sys.argv). Then, control returns to IPython's
1406 1424 prompt.
1407 1425
1408 1426 This is similar to running at a system prompt:\\
1409 1427 $ python file args\\
1410 1428 but with the advantage of giving you IPython's tracebacks, and of
1411 1429 loading all variables into your interactive namespace for further use
1412 1430 (unless -p is used, see below).
1413 1431
1414 1432 The file is executed in a namespace initially consisting only of
1415 1433 __name__=='__main__' and sys.argv constructed as indicated. It thus
1416 1434 sees its environment as if it were being run as a stand-alone program
1417 1435 (except for sharing global objects such as previously imported
1418 1436 modules). But after execution, the IPython interactive namespace gets
1419 1437 updated with all variables defined in the program (except for __name__
1420 1438 and sys.argv). This allows for very convenient loading of code for
1421 1439 interactive work, while giving each program a 'clean sheet' to run in.
1422 1440
1423 1441 Options:
1424 1442
1425 1443 -n: __name__ is NOT set to '__main__', but to the running file's name
1426 1444 without extension (as python does under import). This allows running
1427 1445 scripts and reloading the definitions in them without calling code
1428 1446 protected by an ' if __name__ == "__main__" ' clause.
1429 1447
1430 1448 -i: run the file in IPython's namespace instead of an empty one. This
1431 1449 is useful if you are experimenting with code written in a text editor
1432 1450 which depends on variables defined interactively.
1433 1451
1434 1452 -e: ignore sys.exit() calls or SystemExit exceptions in the script
1435 1453 being run. This is particularly useful if IPython is being used to
1436 1454 run unittests, which always exit with a sys.exit() call. In such
1437 1455 cases you are interested in the output of the test results, not in
1438 1456 seeing a traceback of the unittest module.
1439 1457
1440 1458 -t: print timing information at the end of the run. IPython will give
1441 1459 you an estimated CPU time consumption for your script, which under
1442 1460 Unix uses the resource module to avoid the wraparound problems of
1443 1461 time.clock(). Under Unix, an estimate of time spent on system tasks
1444 1462 is also given (for Windows platforms this is reported as 0.0).
1445 1463
1446 1464 If -t is given, an additional -N<N> option can be given, where <N>
1447 1465 must be an integer indicating how many times you want the script to
1448 1466 run. The final timing report will include total and per run results.
1449 1467
1450 1468 For example (testing the script uniq_stable.py):
1451 1469
1452 1470 In [1]: run -t uniq_stable
1453 1471
1454 1472 IPython CPU timings (estimated):\\
1455 1473 User : 0.19597 s.\\
1456 1474 System: 0.0 s.\\
1457 1475
1458 1476 In [2]: run -t -N5 uniq_stable
1459 1477
1460 1478 IPython CPU timings (estimated):\\
1461 1479 Total runs performed: 5\\
1462 1480 Times : Total Per run\\
1463 1481 User : 0.910862 s, 0.1821724 s.\\
1464 1482 System: 0.0 s, 0.0 s.
1465 1483
1466 1484 -d: run your program under the control of pdb, the Python debugger.
1467 1485 This allows you to execute your program step by step, watch variables,
1468 1486 etc. Internally, what IPython does is similar to calling:
1469 1487
1470 1488 pdb.run('execfile("YOURFILENAME")')
1471 1489
1472 1490 with a breakpoint set on line 1 of your file. You can change the line
1473 1491 number for this automatic breakpoint to be <N> by using the -bN option
1474 1492 (where N must be an integer). For example:
1475 1493
1476 1494 %run -d -b40 myscript
1477 1495
1478 1496 will set the first breakpoint at line 40 in myscript.py. Note that
1479 1497 the first breakpoint must be set on a line which actually does
1480 1498 something (not a comment or docstring) for it to stop execution.
1481 1499
1482 1500 When the pdb debugger starts, you will see a (Pdb) prompt. You must
1483 1501 first enter 'c' (without qoutes) to start execution up to the first
1484 1502 breakpoint.
1485 1503
1486 1504 Entering 'help' gives information about the use of the debugger. You
1487 1505 can easily see pdb's full documentation with "import pdb;pdb.help()"
1488 1506 at a prompt.
1489 1507
1490 1508 -p: run program under the control of the Python profiler module (which
1491 1509 prints a detailed report of execution times, function calls, etc).
1492 1510
1493 1511 You can pass other options after -p which affect the behavior of the
1494 1512 profiler itself. See the docs for %prun for details.
1495 1513
1496 1514 In this mode, the program's variables do NOT propagate back to the
1497 1515 IPython interactive namespace (because they remain in the namespace
1498 1516 where the profiler executes them).
1499 1517
1500 1518 Internally this triggers a call to %prun, see its documentation for
1501 1519 details on the options available specifically for profiling.
1502 1520
1503 1521 There is one special usage for which the text above doesn't apply:
1504 1522 if the filename ends with .ipy, the file is run as ipython script,
1505 1523 just as if the commands were written on IPython prompt.
1506 1524 """
1507 1525
1508 1526 # get arguments and set sys.argv for program to be run.
1509 1527 opts,arg_lst = self.parse_options(parameter_s,'nidtN:b:pD:l:rs:T:e',
1510 1528 mode='list',list_all=1)
1511 1529
1512 1530 try:
1513 1531 filename = get_py_filename(arg_lst[0])
1514 1532 except IndexError:
1515 1533 warn('you must provide at least a filename.')
1516 1534 print '\n%run:\n',OInspect.getdoc(self.magic_run)
1517 1535 return
1518 1536 except IOError,msg:
1519 1537 error(msg)
1520 1538 return
1521 1539
1522 1540 if filename.lower().endswith('.ipy'):
1523 1541 self.api.runlines(open(filename).read())
1524 1542 return
1525 1543
1526 1544 # Control the response to exit() calls made by the script being run
1527 1545 exit_ignore = opts.has_key('e')
1528 1546
1529 1547 # Make sure that the running script gets a proper sys.argv as if it
1530 1548 # were run from a system shell.
1531 1549 save_argv = sys.argv # save it for later restoring
1532 1550 sys.argv = [filename]+ arg_lst[1:] # put in the proper filename
1533 1551
1534 1552 if opts.has_key('i'):
1535 1553 # Run in user's interactive namespace
1536 1554 prog_ns = self.shell.user_ns
1537 1555 __name__save = self.shell.user_ns['__name__']
1538 1556 prog_ns['__name__'] = '__main__'
1539 1557 main_mod = FakeModule(prog_ns)
1540 1558 else:
1541 1559 # Run in a fresh, empty namespace
1542 1560 if opts.has_key('n'):
1543 1561 name = os.path.splitext(os.path.basename(filename))[0]
1544 1562 else:
1545 1563 name = '__main__'
1546 1564 main_mod = FakeModule()
1547 1565 prog_ns = main_mod.__dict__
1548 1566 prog_ns['__name__'] = name
1549 1567 # The shell MUST hold a reference to main_mod so after %run exits,
1550 1568 # the python deletion mechanism doesn't zero it out (leaving
1551 1569 # dangling references)
1552 1570 self.shell._user_main_modules.append(main_mod)
1553 1571
1554 1572 # Since '%run foo' emulates 'python foo.py' at the cmd line, we must
1555 1573 # set the __file__ global in the script's namespace
1556 1574 prog_ns['__file__'] = filename
1557 1575
1558 1576 # pickle fix. See iplib for an explanation. But we need to make sure
1559 1577 # that, if we overwrite __main__, we replace it at the end
1560 1578 if prog_ns['__name__'] == '__main__':
1561 1579 restore_main = sys.modules['__main__']
1562 1580 else:
1563 1581 restore_main = False
1564 1582
1565 1583 sys.modules[prog_ns['__name__']] = main_mod
1566 1584
1567 1585 stats = None
1568 1586 try:
1569 1587 self.shell.savehist()
1570 1588
1571 1589 if opts.has_key('p'):
1572 1590 stats = self.magic_prun('',0,opts,arg_lst,prog_ns)
1573 1591 else:
1574 1592 if opts.has_key('d'):
1575 1593 deb = Debugger.Pdb(self.shell.rc.colors)
1576 1594 # reset Breakpoint state, which is moronically kept
1577 1595 # in a class
1578 1596 bdb.Breakpoint.next = 1
1579 1597 bdb.Breakpoint.bplist = {}
1580 1598 bdb.Breakpoint.bpbynumber = [None]
1581 1599 # Set an initial breakpoint to stop execution
1582 1600 maxtries = 10
1583 1601 bp = int(opts.get('b',[1])[0])
1584 1602 checkline = deb.checkline(filename,bp)
1585 1603 if not checkline:
1586 1604 for bp in range(bp+1,bp+maxtries+1):
1587 1605 if deb.checkline(filename,bp):
1588 1606 break
1589 1607 else:
1590 1608 msg = ("\nI failed to find a valid line to set "
1591 1609 "a breakpoint\n"
1592 1610 "after trying up to line: %s.\n"
1593 1611 "Please set a valid breakpoint manually "
1594 1612 "with the -b option." % bp)
1595 1613 error(msg)
1596 1614 return
1597 1615 # if we find a good linenumber, set the breakpoint
1598 1616 deb.do_break('%s:%s' % (filename,bp))
1599 1617 # Start file run
1600 1618 print "NOTE: Enter 'c' at the",
1601 1619 print "%s prompt to start your script." % deb.prompt
1602 1620 try:
1603 1621 deb.run('execfile("%s")' % filename,prog_ns)
1604 1622
1605 1623 except:
1606 1624 etype, value, tb = sys.exc_info()
1607 1625 # Skip three frames in the traceback: the %run one,
1608 1626 # one inside bdb.py, and the command-line typed by the
1609 1627 # user (run by exec in pdb itself).
1610 1628 self.shell.InteractiveTB(etype,value,tb,tb_offset=3)
1611 1629 else:
1612 1630 if runner is None:
1613 1631 runner = self.shell.safe_execfile
1614 1632 if opts.has_key('t'):
1615 1633 # timed execution
1616 1634 try:
1617 1635 nruns = int(opts['N'][0])
1618 1636 if nruns < 1:
1619 1637 error('Number of runs must be >=1')
1620 1638 return
1621 1639 except (KeyError):
1622 1640 nruns = 1
1623 1641 if nruns == 1:
1624 1642 t0 = clock2()
1625 1643 runner(filename,prog_ns,prog_ns,
1626 1644 exit_ignore=exit_ignore)
1627 1645 t1 = clock2()
1628 1646 t_usr = t1[0]-t0[0]
1629 1647 t_sys = t1[1]-t1[1]
1630 1648 print "\nIPython CPU timings (estimated):"
1631 1649 print " User : %10s s." % t_usr
1632 1650 print " System: %10s s." % t_sys
1633 1651 else:
1634 1652 runs = range(nruns)
1635 1653 t0 = clock2()
1636 1654 for nr in runs:
1637 1655 runner(filename,prog_ns,prog_ns,
1638 1656 exit_ignore=exit_ignore)
1639 1657 t1 = clock2()
1640 1658 t_usr = t1[0]-t0[0]
1641 1659 t_sys = t1[1]-t1[1]
1642 1660 print "\nIPython CPU timings (estimated):"
1643 1661 print "Total runs performed:",nruns
1644 1662 print " Times : %10s %10s" % ('Total','Per run')
1645 1663 print " User : %10s s, %10s s." % (t_usr,t_usr/nruns)
1646 1664 print " System: %10s s, %10s s." % (t_sys,t_sys/nruns)
1647 1665
1648 1666 else:
1649 1667 # regular execution
1650 1668 runner(filename,prog_ns,prog_ns,exit_ignore=exit_ignore)
1651 1669 if opts.has_key('i'):
1652 1670 self.shell.user_ns['__name__'] = __name__save
1653 1671 else:
1654 1672 # update IPython interactive namespace
1655 1673 del prog_ns['__name__']
1656 1674 self.shell.user_ns.update(prog_ns)
1657 1675 finally:
1658 1676 sys.argv = save_argv
1659 1677 if restore_main:
1660 1678 sys.modules['__main__'] = restore_main
1661 1679 self.shell.reloadhist()
1662 1680
1663 1681 return stats
1664 1682
1665 1683 def magic_runlog(self, parameter_s =''):
1666 1684 """Run files as logs.
1667 1685
1668 1686 Usage:\\
1669 1687 %runlog file1 file2 ...
1670 1688
1671 1689 Run the named files (treating them as log files) in sequence inside
1672 1690 the interpreter, and return to the prompt. This is much slower than
1673 1691 %run because each line is executed in a try/except block, but it
1674 1692 allows running files with syntax errors in them.
1675 1693
1676 1694 Normally IPython will guess when a file is one of its own logfiles, so
1677 1695 you can typically use %run even for logs. This shorthand allows you to
1678 1696 force any file to be treated as a log file."""
1679 1697
1680 1698 for f in parameter_s.split():
1681 1699 self.shell.safe_execfile(f,self.shell.user_ns,
1682 1700 self.shell.user_ns,islog=1)
1683 1701
1684 1702 def magic_timeit(self, parameter_s =''):
1685 1703 """Time execution of a Python statement or expression
1686 1704
1687 1705 Usage:\\
1688 1706 %timeit [-n<N> -r<R> [-t|-c]] statement
1689 1707
1690 1708 Time execution of a Python statement or expression using the timeit
1691 1709 module.
1692 1710
1693 1711 Options:
1694 1712 -n<N>: execute the given statement <N> times in a loop. If this value
1695 1713 is not given, a fitting value is chosen.
1696 1714
1697 1715 -r<R>: repeat the loop iteration <R> times and take the best result.
1698 1716 Default: 3
1699 1717
1700 1718 -t: use time.time to measure the time, which is the default on Unix.
1701 1719 This function measures wall time.
1702 1720
1703 1721 -c: use time.clock to measure the time, which is the default on
1704 1722 Windows and measures wall time. On Unix, resource.getrusage is used
1705 1723 instead and returns the CPU user time.
1706 1724
1707 1725 -p<P>: use a precision of <P> digits to display the timing result.
1708 1726 Default: 3
1709 1727
1710 1728
1711 1729 Examples:\\
1712 1730 In [1]: %timeit pass
1713 1731 10000000 loops, best of 3: 53.3 ns per loop
1714 1732
1715 1733 In [2]: u = None
1716 1734
1717 1735 In [3]: %timeit u is None
1718 1736 10000000 loops, best of 3: 184 ns per loop
1719 1737
1720 1738 In [4]: %timeit -r 4 u == None
1721 1739 1000000 loops, best of 4: 242 ns per loop
1722 1740
1723 1741 In [5]: import time
1724 1742
1725 1743 In [6]: %timeit -n1 time.sleep(2)
1726 1744 1 loops, best of 3: 2 s per loop
1727 1745
1728 1746
1729 1747 The times reported by %timeit will be slightly higher than those
1730 1748 reported by the timeit.py script when variables are accessed. This is
1731 1749 due to the fact that %timeit executes the statement in the namespace
1732 1750 of the shell, compared with timeit.py, which uses a single setup
1733 1751 statement to import function or create variables. Generally, the bias
1734 1752 does not matter as long as results from timeit.py are not mixed with
1735 1753 those from %timeit."""
1736 1754
1737 1755 import timeit
1738 1756 import math
1739 1757
1740 1758 units = ["s", "ms", "\xc2\xb5s", "ns"]
1741 1759 scaling = [1, 1e3, 1e6, 1e9]
1742 1760
1743 1761 opts, stmt = self.parse_options(parameter_s,'n:r:tcp:',
1744 1762 posix=False)
1745 1763 if stmt == "":
1746 1764 return
1747 1765 timefunc = timeit.default_timer
1748 1766 number = int(getattr(opts, "n", 0))
1749 1767 repeat = int(getattr(opts, "r", timeit.default_repeat))
1750 1768 precision = int(getattr(opts, "p", 3))
1751 1769 if hasattr(opts, "t"):
1752 1770 timefunc = time.time
1753 1771 if hasattr(opts, "c"):
1754 1772 timefunc = clock
1755 1773
1756 1774 timer = timeit.Timer(timer=timefunc)
1757 1775 # this code has tight coupling to the inner workings of timeit.Timer,
1758 1776 # but is there a better way to achieve that the code stmt has access
1759 1777 # to the shell namespace?
1760 1778
1761 1779 src = timeit.template % {'stmt': timeit.reindent(stmt, 8),
1762 1780 'setup': "pass"}
1763 1781 # Track compilation time so it can be reported if too long
1764 1782 # Minimum time above which compilation time will be reported
1765 1783 tc_min = 0.1
1766 1784
1767 1785 t0 = clock()
1768 1786 code = compile(src, "<magic-timeit>", "exec")
1769 1787 tc = clock()-t0
1770 1788
1771 1789 ns = {}
1772 1790 exec code in self.shell.user_ns, ns
1773 1791 timer.inner = ns["inner"]
1774 1792
1775 1793 if number == 0:
1776 1794 # determine number so that 0.2 <= total time < 2.0
1777 1795 number = 1
1778 1796 for i in range(1, 10):
1779 1797 number *= 10
1780 1798 if timer.timeit(number) >= 0.2:
1781 1799 break
1782 1800
1783 1801 best = min(timer.repeat(repeat, number)) / number
1784 1802
1785 1803 if best > 0.0:
1786 1804 order = min(-int(math.floor(math.log10(best)) // 3), 3)
1787 1805 else:
1788 1806 order = 3
1789 1807 print "%d loops, best of %d: %.*g %s per loop" % (number, repeat,
1790 1808 precision,
1791 1809 best * scaling[order],
1792 1810 units[order])
1793 1811 if tc > tc_min:
1794 1812 print "Compiler time: %.2f s" % tc
1795 1813
1796 1814 def magic_time(self,parameter_s = ''):
1797 1815 """Time execution of a Python statement or expression.
1798 1816
1799 1817 The CPU and wall clock times are printed, and the value of the
1800 1818 expression (if any) is returned. Note that under Win32, system time
1801 1819 is always reported as 0, since it can not be measured.
1802 1820
1803 1821 This function provides very basic timing functionality. In Python
1804 1822 2.3, the timeit module offers more control and sophistication, so this
1805 1823 could be rewritten to use it (patches welcome).
1806 1824
1807 1825 Some examples:
1808 1826
1809 1827 In [1]: time 2**128
1810 1828 CPU times: user 0.00 s, sys: 0.00 s, total: 0.00 s
1811 1829 Wall time: 0.00
1812 1830 Out[1]: 340282366920938463463374607431768211456L
1813 1831
1814 1832 In [2]: n = 1000000
1815 1833
1816 1834 In [3]: time sum(range(n))
1817 1835 CPU times: user 1.20 s, sys: 0.05 s, total: 1.25 s
1818 1836 Wall time: 1.37
1819 1837 Out[3]: 499999500000L
1820 1838
1821 1839 In [4]: time print 'hello world'
1822 1840 hello world
1823 1841 CPU times: user 0.00 s, sys: 0.00 s, total: 0.00 s
1824 1842 Wall time: 0.00
1825 1843
1826 1844 Note that the time needed by Python to compile the given expression
1827 1845 will be reported if it is more than 0.1s. In this example, the
1828 1846 actual exponentiation is done by Python at compilation time, so while
1829 1847 the expression can take a noticeable amount of time to compute, that
1830 1848 time is purely due to the compilation:
1831 1849
1832 1850 In [5]: time 3**9999;
1833 1851 CPU times: user 0.00 s, sys: 0.00 s, total: 0.00 s
1834 1852 Wall time: 0.00 s
1835 1853
1836 1854 In [6]: time 3**999999;
1837 1855 CPU times: user 0.00 s, sys: 0.00 s, total: 0.00 s
1838 1856 Wall time: 0.00 s
1839 1857 Compiler : 0.78 s
1840 1858 """
1841 1859
1842 1860 # fail immediately if the given expression can't be compiled
1843 1861
1844 1862 expr = self.shell.prefilter(parameter_s,False)
1845 1863
1846 1864 # Minimum time above which compilation time will be reported
1847 1865 tc_min = 0.1
1848 1866
1849 1867 try:
1850 1868 mode = 'eval'
1851 1869 t0 = clock()
1852 1870 code = compile(expr,'<timed eval>',mode)
1853 1871 tc = clock()-t0
1854 1872 except SyntaxError:
1855 1873 mode = 'exec'
1856 1874 t0 = clock()
1857 1875 code = compile(expr,'<timed exec>',mode)
1858 1876 tc = clock()-t0
1859 1877 # skew measurement as little as possible
1860 1878 glob = self.shell.user_ns
1861 1879 clk = clock2
1862 1880 wtime = time.time
1863 1881 # time execution
1864 1882 wall_st = wtime()
1865 1883 if mode=='eval':
1866 1884 st = clk()
1867 1885 out = eval(code,glob)
1868 1886 end = clk()
1869 1887 else:
1870 1888 st = clk()
1871 1889 exec code in glob
1872 1890 end = clk()
1873 1891 out = None
1874 1892 wall_end = wtime()
1875 1893 # Compute actual times and report
1876 1894 wall_time = wall_end-wall_st
1877 1895 cpu_user = end[0]-st[0]
1878 1896 cpu_sys = end[1]-st[1]
1879 1897 cpu_tot = cpu_user+cpu_sys
1880 1898 print "CPU times: user %.2f s, sys: %.2f s, total: %.2f s" % \
1881 1899 (cpu_user,cpu_sys,cpu_tot)
1882 1900 print "Wall time: %.2f s" % wall_time
1883 1901 if tc > tc_min:
1884 1902 print "Compiler : %.2f s" % tc
1885 1903 return out
1886 1904
1887 1905 def magic_macro(self,parameter_s = ''):
1888 1906 """Define a set of input lines as a macro for future re-execution.
1889 1907
1890 1908 Usage:\\
1891 1909 %macro [options] name n1-n2 n3-n4 ... n5 .. n6 ...
1892 1910
1893 1911 Options:
1894 1912
1895 1913 -r: use 'raw' input. By default, the 'processed' history is used,
1896 1914 so that magics are loaded in their transformed version to valid
1897 1915 Python. If this option is given, the raw input as typed as the
1898 1916 command line is used instead.
1899 1917
1900 1918 This will define a global variable called `name` which is a string
1901 1919 made of joining the slices and lines you specify (n1,n2,... numbers
1902 1920 above) from your input history into a single string. This variable
1903 1921 acts like an automatic function which re-executes those lines as if
1904 1922 you had typed them. You just type 'name' at the prompt and the code
1905 1923 executes.
1906 1924
1907 1925 The notation for indicating number ranges is: n1-n2 means 'use line
1908 1926 numbers n1,...n2' (the endpoint is included). That is, '5-7' means
1909 1927 using the lines numbered 5,6 and 7.
1910 1928
1911 1929 Note: as a 'hidden' feature, you can also use traditional python slice
1912 1930 notation, where N:M means numbers N through M-1.
1913 1931
1914 1932 For example, if your history contains (%hist prints it):
1915 1933
1916 1934 44: x=1\\
1917 1935 45: y=3\\
1918 1936 46: z=x+y\\
1919 1937 47: print x\\
1920 1938 48: a=5\\
1921 1939 49: print 'x',x,'y',y\\
1922 1940
1923 1941 you can create a macro with lines 44 through 47 (included) and line 49
1924 1942 called my_macro with:
1925 1943
1926 1944 In [51]: %macro my_macro 44-47 49
1927 1945
1928 1946 Now, typing `my_macro` (without quotes) will re-execute all this code
1929 1947 in one pass.
1930 1948
1931 1949 You don't need to give the line-numbers in order, and any given line
1932 1950 number can appear multiple times. You can assemble macros with any
1933 1951 lines from your input history in any order.
1934 1952
1935 1953 The macro is a simple object which holds its value in an attribute,
1936 1954 but IPython's display system checks for macros and executes them as
1937 1955 code instead of printing them when you type their name.
1938 1956
1939 1957 You can view a macro's contents by explicitly printing it with:
1940 1958
1941 1959 'print macro_name'.
1942 1960
1943 1961 For one-off cases which DON'T contain magic function calls in them you
1944 1962 can obtain similar results by explicitly executing slices from your
1945 1963 input history with:
1946 1964
1947 1965 In [60]: exec In[44:48]+In[49]"""
1948 1966
1949 1967 opts,args = self.parse_options(parameter_s,'r',mode='list')
1950 1968 if not args:
1951 1969 macs = [k for k,v in self.shell.user_ns.items() if isinstance(v, Macro)]
1952 1970 macs.sort()
1953 1971 return macs
1954 1972 if len(args) == 1:
1955 1973 raise UsageError(
1956 1974 "%macro insufficient args; usage '%macro name n1-n2 n3-4...")
1957 1975 name,ranges = args[0], args[1:]
1958 1976
1959 1977 #print 'rng',ranges # dbg
1960 1978 lines = self.extract_input_slices(ranges,opts.has_key('r'))
1961 1979 macro = Macro(lines)
1962 1980 self.shell.user_ns.update({name:macro})
1963 1981 print 'Macro `%s` created. To execute, type its name (without quotes).' % name
1964 1982 print 'Macro contents:'
1965 1983 print macro,
1966 1984
1967 1985 def magic_save(self,parameter_s = ''):
1968 1986 """Save a set of lines to a given filename.
1969 1987
1970 1988 Usage:\\
1971 1989 %save [options] filename n1-n2 n3-n4 ... n5 .. n6 ...
1972 1990
1973 1991 Options:
1974 1992
1975 1993 -r: use 'raw' input. By default, the 'processed' history is used,
1976 1994 so that magics are loaded in their transformed version to valid
1977 1995 Python. If this option is given, the raw input as typed as the
1978 1996 command line is used instead.
1979 1997
1980 1998 This function uses the same syntax as %macro for line extraction, but
1981 1999 instead of creating a macro it saves the resulting string to the
1982 2000 filename you specify.
1983 2001
1984 2002 It adds a '.py' extension to the file if you don't do so yourself, and
1985 2003 it asks for confirmation before overwriting existing files."""
1986 2004
1987 2005 opts,args = self.parse_options(parameter_s,'r',mode='list')
1988 2006 fname,ranges = args[0], args[1:]
1989 2007 if not fname.endswith('.py'):
1990 2008 fname += '.py'
1991 2009 if os.path.isfile(fname):
1992 2010 ans = raw_input('File `%s` exists. Overwrite (y/[N])? ' % fname)
1993 2011 if ans.lower() not in ['y','yes']:
1994 2012 print 'Operation cancelled.'
1995 2013 return
1996 2014 cmds = ''.join(self.extract_input_slices(ranges,opts.has_key('r')))
1997 2015 f = file(fname,'w')
1998 2016 f.write(cmds)
1999 2017 f.close()
2000 2018 print 'The following commands were written to file `%s`:' % fname
2001 2019 print cmds
2002 2020
2003 2021 def _edit_macro(self,mname,macro):
2004 2022 """open an editor with the macro data in a file"""
2005 2023 filename = self.shell.mktempfile(macro.value)
2006 2024 self.shell.hooks.editor(filename)
2007 2025
2008 2026 # and make a new macro object, to replace the old one
2009 2027 mfile = open(filename)
2010 2028 mvalue = mfile.read()
2011 2029 mfile.close()
2012 2030 self.shell.user_ns[mname] = Macro(mvalue)
2013 2031
2014 2032 def magic_ed(self,parameter_s=''):
2015 2033 """Alias to %edit."""
2016 2034 return self.magic_edit(parameter_s)
2017 2035
2018 2036 def magic_edit(self,parameter_s='',last_call=['','']):
2019 2037 """Bring up an editor and execute the resulting code.
2020 2038
2021 2039 Usage:
2022 2040 %edit [options] [args]
2023 2041
2024 2042 %edit runs IPython's editor hook. The default version of this hook is
2025 2043 set to call the __IPYTHON__.rc.editor command. This is read from your
2026 2044 environment variable $EDITOR. If this isn't found, it will default to
2027 2045 vi under Linux/Unix and to notepad under Windows. See the end of this
2028 2046 docstring for how to change the editor hook.
2029 2047
2030 2048 You can also set the value of this editor via the command line option
2031 2049 '-editor' or in your ipythonrc file. This is useful if you wish to use
2032 2050 specifically for IPython an editor different from your typical default
2033 2051 (and for Windows users who typically don't set environment variables).
2034 2052
2035 2053 This command allows you to conveniently edit multi-line code right in
2036 2054 your IPython session.
2037 2055
2038 2056 If called without arguments, %edit opens up an empty editor with a
2039 2057 temporary file and will execute the contents of this file when you
2040 2058 close it (don't forget to save it!).
2041 2059
2042 2060
2043 2061 Options:
2044 2062
2045 2063 -n <number>: open the editor at a specified line number. By default,
2046 2064 the IPython editor hook uses the unix syntax 'editor +N filename', but
2047 2065 you can configure this by providing your own modified hook if your
2048 2066 favorite editor supports line-number specifications with a different
2049 2067 syntax.
2050 2068
2051 2069 -p: this will call the editor with the same data as the previous time
2052 2070 it was used, regardless of how long ago (in your current session) it
2053 2071 was.
2054 2072
2055 2073 -r: use 'raw' input. This option only applies to input taken from the
2056 2074 user's history. By default, the 'processed' history is used, so that
2057 2075 magics are loaded in their transformed version to valid Python. If
2058 2076 this option is given, the raw input as typed as the command line is
2059 2077 used instead. When you exit the editor, it will be executed by
2060 2078 IPython's own processor.
2061 2079
2062 2080 -x: do not execute the edited code immediately upon exit. This is
2063 2081 mainly useful if you are editing programs which need to be called with
2064 2082 command line arguments, which you can then do using %run.
2065 2083
2066 2084
2067 2085 Arguments:
2068 2086
2069 2087 If arguments are given, the following possibilites exist:
2070 2088
2071 2089 - The arguments are numbers or pairs of colon-separated numbers (like
2072 2090 1 4:8 9). These are interpreted as lines of previous input to be
2073 2091 loaded into the editor. The syntax is the same of the %macro command.
2074 2092
2075 2093 - If the argument doesn't start with a number, it is evaluated as a
2076 2094 variable and its contents loaded into the editor. You can thus edit
2077 2095 any string which contains python code (including the result of
2078 2096 previous edits).
2079 2097
2080 2098 - If the argument is the name of an object (other than a string),
2081 2099 IPython will try to locate the file where it was defined and open the
2082 2100 editor at the point where it is defined. You can use `%edit function`
2083 2101 to load an editor exactly at the point where 'function' is defined,
2084 2102 edit it and have the file be executed automatically.
2085 2103
2086 2104 If the object is a macro (see %macro for details), this opens up your
2087 2105 specified editor with a temporary file containing the macro's data.
2088 2106 Upon exit, the macro is reloaded with the contents of the file.
2089 2107
2090 2108 Note: opening at an exact line is only supported under Unix, and some
2091 2109 editors (like kedit and gedit up to Gnome 2.8) do not understand the
2092 2110 '+NUMBER' parameter necessary for this feature. Good editors like
2093 2111 (X)Emacs, vi, jed, pico and joe all do.
2094 2112
2095 2113 - If the argument is not found as a variable, IPython will look for a
2096 2114 file with that name (adding .py if necessary) and load it into the
2097 2115 editor. It will execute its contents with execfile() when you exit,
2098 2116 loading any code in the file into your interactive namespace.
2099 2117
2100 2118 After executing your code, %edit will return as output the code you
2101 2119 typed in the editor (except when it was an existing file). This way
2102 2120 you can reload the code in further invocations of %edit as a variable,
2103 2121 via _<NUMBER> or Out[<NUMBER>], where <NUMBER> is the prompt number of
2104 2122 the output.
2105 2123
2106 2124 Note that %edit is also available through the alias %ed.
2107 2125
2108 2126 This is an example of creating a simple function inside the editor and
2109 2127 then modifying it. First, start up the editor:
2110 2128
2111 2129 In [1]: ed\\
2112 2130 Editing... done. Executing edited code...\\
2113 2131 Out[1]: 'def foo():\\n print "foo() was defined in an editing session"\\n'
2114 2132
2115 2133 We can then call the function foo():
2116 2134
2117 2135 In [2]: foo()\\
2118 2136 foo() was defined in an editing session
2119 2137
2120 2138 Now we edit foo. IPython automatically loads the editor with the
2121 2139 (temporary) file where foo() was previously defined:
2122 2140
2123 2141 In [3]: ed foo\\
2124 2142 Editing... done. Executing edited code...
2125 2143
2126 2144 And if we call foo() again we get the modified version:
2127 2145
2128 2146 In [4]: foo()\\
2129 2147 foo() has now been changed!
2130 2148
2131 2149 Here is an example of how to edit a code snippet successive
2132 2150 times. First we call the editor:
2133 2151
2134 2152 In [8]: ed\\
2135 2153 Editing... done. Executing edited code...\\
2136 2154 hello\\
2137 2155 Out[8]: "print 'hello'\\n"
2138 2156
2139 2157 Now we call it again with the previous output (stored in _):
2140 2158
2141 2159 In [9]: ed _\\
2142 2160 Editing... done. Executing edited code...\\
2143 2161 hello world\\
2144 2162 Out[9]: "print 'hello world'\\n"
2145 2163
2146 2164 Now we call it with the output #8 (stored in _8, also as Out[8]):
2147 2165
2148 2166 In [10]: ed _8\\
2149 2167 Editing... done. Executing edited code...\\
2150 2168 hello again\\
2151 2169 Out[10]: "print 'hello again'\\n"
2152 2170
2153 2171
2154 2172 Changing the default editor hook:
2155 2173
2156 2174 If you wish to write your own editor hook, you can put it in a
2157 2175 configuration file which you load at startup time. The default hook
2158 2176 is defined in the IPython.hooks module, and you can use that as a
2159 2177 starting example for further modifications. That file also has
2160 2178 general instructions on how to set a new hook for use once you've
2161 2179 defined it."""
2162 2180
2163 2181 # FIXME: This function has become a convoluted mess. It needs a
2164 2182 # ground-up rewrite with clean, simple logic.
2165 2183
2166 2184 def make_filename(arg):
2167 2185 "Make a filename from the given args"
2168 2186 try:
2169 2187 filename = get_py_filename(arg)
2170 2188 except IOError:
2171 2189 if args.endswith('.py'):
2172 2190 filename = arg
2173 2191 else:
2174 2192 filename = None
2175 2193 return filename
2176 2194
2177 2195 # custom exceptions
2178 2196 class DataIsObject(Exception): pass
2179 2197
2180 2198 opts,args = self.parse_options(parameter_s,'prxn:')
2181 2199 # Set a few locals from the options for convenience:
2182 2200 opts_p = opts.has_key('p')
2183 2201 opts_r = opts.has_key('r')
2184 2202
2185 2203 # Default line number value
2186 2204 lineno = opts.get('n',None)
2187 2205
2188 2206 if opts_p:
2189 2207 args = '_%s' % last_call[0]
2190 2208 if not self.shell.user_ns.has_key(args):
2191 2209 args = last_call[1]
2192 2210
2193 2211 # use last_call to remember the state of the previous call, but don't
2194 2212 # let it be clobbered by successive '-p' calls.
2195 2213 try:
2196 2214 last_call[0] = self.shell.outputcache.prompt_count
2197 2215 if not opts_p:
2198 2216 last_call[1] = parameter_s
2199 2217 except:
2200 2218 pass
2201 2219
2202 2220 # by default this is done with temp files, except when the given
2203 2221 # arg is a filename
2204 2222 use_temp = 1
2205 2223
2206 2224 if re.match(r'\d',args):
2207 2225 # Mode where user specifies ranges of lines, like in %macro.
2208 2226 # This means that you can't edit files whose names begin with
2209 2227 # numbers this way. Tough.
2210 2228 ranges = args.split()
2211 2229 data = ''.join(self.extract_input_slices(ranges,opts_r))
2212 2230 elif args.endswith('.py'):
2213 2231 filename = make_filename(args)
2214 2232 data = ''
2215 2233 use_temp = 0
2216 2234 elif args:
2217 2235 try:
2218 2236 # Load the parameter given as a variable. If not a string,
2219 2237 # process it as an object instead (below)
2220 2238
2221 2239 #print '*** args',args,'type',type(args) # dbg
2222 2240 data = eval(args,self.shell.user_ns)
2223 2241 if not type(data) in StringTypes:
2224 2242 raise DataIsObject
2225 2243
2226 2244 except (NameError,SyntaxError):
2227 2245 # given argument is not a variable, try as a filename
2228 2246 filename = make_filename(args)
2229 2247 if filename is None:
2230 2248 warn("Argument given (%s) can't be found as a variable "
2231 2249 "or as a filename." % args)
2232 2250 return
2233 2251
2234 2252 data = ''
2235 2253 use_temp = 0
2236 2254 except DataIsObject:
2237 2255
2238 2256 # macros have a special edit function
2239 2257 if isinstance(data,Macro):
2240 2258 self._edit_macro(args,data)
2241 2259 return
2242 2260
2243 2261 # For objects, try to edit the file where they are defined
2244 2262 try:
2245 2263 filename = inspect.getabsfile(data)
2246 2264 if 'fakemodule' in filename.lower() and inspect.isclass(data):
2247 2265 # class created by %edit? Try to find source
2248 2266 # by looking for method definitions instead, the
2249 2267 # __module__ in those classes is FakeModule.
2250 2268 attrs = [getattr(data, aname) for aname in dir(data)]
2251 2269 for attr in attrs:
2252 2270 if not inspect.ismethod(attr):
2253 2271 continue
2254 2272 filename = inspect.getabsfile(attr)
2255 2273 if filename and 'fakemodule' not in filename.lower():
2256 2274 # change the attribute to be the edit target instead
2257 2275 data = attr
2258 2276 break
2259 2277
2260 2278 datafile = 1
2261 2279 except TypeError:
2262 2280 filename = make_filename(args)
2263 2281 datafile = 1
2264 2282 warn('Could not find file where `%s` is defined.\n'
2265 2283 'Opening a file named `%s`' % (args,filename))
2266 2284 # Now, make sure we can actually read the source (if it was in
2267 2285 # a temp file it's gone by now).
2268 2286 if datafile:
2269 2287 try:
2270 2288 if lineno is None:
2271 2289 lineno = inspect.getsourcelines(data)[1]
2272 2290 except IOError:
2273 2291 filename = make_filename(args)
2274 2292 if filename is None:
2275 2293 warn('The file `%s` where `%s` was defined cannot '
2276 2294 'be read.' % (filename,data))
2277 2295 return
2278 2296 use_temp = 0
2279 2297 else:
2280 2298 data = ''
2281 2299
2282 2300 if use_temp:
2283 2301 filename = self.shell.mktempfile(data)
2284 2302 print 'IPython will make a temporary file named:',filename
2285 2303
2286 2304 # do actual editing here
2287 2305 print 'Editing...',
2288 2306 sys.stdout.flush()
2289 2307 self.shell.hooks.editor(filename,lineno)
2290 2308 if opts.has_key('x'): # -x prevents actual execution
2291 2309 print
2292 2310 else:
2293 2311 print 'done. Executing edited code...'
2294 2312 if opts_r:
2295 2313 self.shell.runlines(file_read(filename))
2296 2314 else:
2297 2315 self.shell.safe_execfile(filename,self.shell.user_ns,
2298 2316 self.shell.user_ns)
2299 2317 if use_temp:
2300 2318 try:
2301 2319 return open(filename).read()
2302 2320 except IOError,msg:
2303 2321 if msg.filename == filename:
2304 2322 warn('File not found. Did you forget to save?')
2305 2323 return
2306 2324 else:
2307 2325 self.shell.showtraceback()
2308 2326
2309 2327 def magic_xmode(self,parameter_s = ''):
2310 2328 """Switch modes for the exception handlers.
2311 2329
2312 2330 Valid modes: Plain, Context and Verbose.
2313 2331
2314 2332 If called without arguments, acts as a toggle."""
2315 2333
2316 2334 def xmode_switch_err(name):
2317 2335 warn('Error changing %s exception modes.\n%s' %
2318 2336 (name,sys.exc_info()[1]))
2319 2337
2320 2338 shell = self.shell
2321 2339 new_mode = parameter_s.strip().capitalize()
2322 2340 try:
2323 2341 shell.InteractiveTB.set_mode(mode=new_mode)
2324 2342 print 'Exception reporting mode:',shell.InteractiveTB.mode
2325 2343 except:
2326 2344 xmode_switch_err('user')
2327 2345
2328 2346 # threaded shells use a special handler in sys.excepthook
2329 2347 if shell.isthreaded:
2330 2348 try:
2331 2349 shell.sys_excepthook.set_mode(mode=new_mode)
2332 2350 except:
2333 2351 xmode_switch_err('threaded')
2334 2352
2335 2353 def magic_colors(self,parameter_s = ''):
2336 2354 """Switch color scheme for prompts, info system and exception handlers.
2337 2355
2338 2356 Currently implemented schemes: NoColor, Linux, LightBG.
2339 2357
2340 2358 Color scheme names are not case-sensitive."""
2341 2359
2342 2360 def color_switch_err(name):
2343 2361 warn('Error changing %s color schemes.\n%s' %
2344 2362 (name,sys.exc_info()[1]))
2345 2363
2346 2364
2347 2365 new_scheme = parameter_s.strip()
2348 2366 if not new_scheme:
2349 2367 raise UsageError(
2350 2368 "%colors: you must specify a color scheme. See '%colors?'")
2351 2369 return
2352 2370 # local shortcut
2353 2371 shell = self.shell
2354 2372
2355 2373 import IPython.rlineimpl as readline
2356 2374
2357 2375 if not readline.have_readline and sys.platform == "win32":
2358 2376 msg = """\
2359 2377 Proper color support under MS Windows requires the pyreadline library.
2360 2378 You can find it at:
2361 2379 http://ipython.scipy.org/moin/PyReadline/Intro
2362 2380 Gary's readline needs the ctypes module, from:
2363 2381 http://starship.python.net/crew/theller/ctypes
2364 2382 (Note that ctypes is already part of Python versions 2.5 and newer).
2365 2383
2366 2384 Defaulting color scheme to 'NoColor'"""
2367 2385 new_scheme = 'NoColor'
2368 2386 warn(msg)
2369 2387
2370 2388 # readline option is 0
2371 2389 if not shell.has_readline:
2372 2390 new_scheme = 'NoColor'
2373 2391
2374 2392 # Set prompt colors
2375 2393 try:
2376 2394 shell.outputcache.set_colors(new_scheme)
2377 2395 except:
2378 2396 color_switch_err('prompt')
2379 2397 else:
2380 2398 shell.rc.colors = \
2381 2399 shell.outputcache.color_table.active_scheme_name
2382 2400 # Set exception colors
2383 2401 try:
2384 2402 shell.InteractiveTB.set_colors(scheme = new_scheme)
2385 2403 shell.SyntaxTB.set_colors(scheme = new_scheme)
2386 2404 except:
2387 2405 color_switch_err('exception')
2388 2406
2389 2407 # threaded shells use a verbose traceback in sys.excepthook
2390 2408 if shell.isthreaded:
2391 2409 try:
2392 2410 shell.sys_excepthook.set_colors(scheme=new_scheme)
2393 2411 except:
2394 2412 color_switch_err('system exception handler')
2395 2413
2396 2414 # Set info (for 'object?') colors
2397 2415 if shell.rc.color_info:
2398 2416 try:
2399 2417 shell.inspector.set_active_scheme(new_scheme)
2400 2418 except:
2401 2419 color_switch_err('object inspector')
2402 2420 else:
2403 2421 shell.inspector.set_active_scheme('NoColor')
2404 2422
2405 2423 def magic_color_info(self,parameter_s = ''):
2406 2424 """Toggle color_info.
2407 2425
2408 2426 The color_info configuration parameter controls whether colors are
2409 2427 used for displaying object details (by things like %psource, %pfile or
2410 2428 the '?' system). This function toggles this value with each call.
2411 2429
2412 2430 Note that unless you have a fairly recent pager (less works better
2413 2431 than more) in your system, using colored object information displays
2414 2432 will not work properly. Test it and see."""
2415 2433
2416 2434 self.shell.rc.color_info = 1 - self.shell.rc.color_info
2417 2435 self.magic_colors(self.shell.rc.colors)
2418 2436 print 'Object introspection functions have now coloring:',
2419 2437 print ['OFF','ON'][self.shell.rc.color_info]
2420 2438
2421 2439 def magic_Pprint(self, parameter_s=''):
2422 2440 """Toggle pretty printing on/off."""
2423 2441
2424 2442 self.shell.rc.pprint = 1 - self.shell.rc.pprint
2425 2443 print 'Pretty printing has been turned', \
2426 2444 ['OFF','ON'][self.shell.rc.pprint]
2427 2445
2428 2446 def magic_exit(self, parameter_s=''):
2429 2447 """Exit IPython, confirming if configured to do so.
2430 2448
2431 2449 You can configure whether IPython asks for confirmation upon exit by
2432 2450 setting the confirm_exit flag in the ipythonrc file."""
2433 2451
2434 2452 self.shell.exit()
2435 2453
2436 2454 def magic_quit(self, parameter_s=''):
2437 2455 """Exit IPython, confirming if configured to do so (like %exit)"""
2438 2456
2439 2457 self.shell.exit()
2440 2458
2441 2459 def magic_Exit(self, parameter_s=''):
2442 2460 """Exit IPython without confirmation."""
2443 2461
2444 2462 self.shell.exit_now = True
2445 2463
2446 2464 #......................................................................
2447 2465 # Functions to implement unix shell-type things
2448 2466
2449 2467 def magic_alias(self, parameter_s = ''):
2450 2468 """Define an alias for a system command.
2451 2469
2452 2470 '%alias alias_name cmd' defines 'alias_name' as an alias for 'cmd'
2453 2471
2454 2472 Then, typing 'alias_name params' will execute the system command 'cmd
2455 2473 params' (from your underlying operating system).
2456 2474
2457 2475 Aliases have lower precedence than magic functions and Python normal
2458 2476 variables, so if 'foo' is both a Python variable and an alias, the
2459 2477 alias can not be executed until 'del foo' removes the Python variable.
2460 2478
2461 2479 You can use the %l specifier in an alias definition to represent the
2462 2480 whole line when the alias is called. For example:
2463 2481
2464 2482 In [2]: alias all echo "Input in brackets: <%l>"\\
2465 2483 In [3]: all hello world\\
2466 2484 Input in brackets: <hello world>
2467 2485
2468 2486 You can also define aliases with parameters using %s specifiers (one
2469 2487 per parameter):
2470 2488
2471 2489 In [1]: alias parts echo first %s second %s\\
2472 2490 In [2]: %parts A B\\
2473 2491 first A second B\\
2474 2492 In [3]: %parts A\\
2475 2493 Incorrect number of arguments: 2 expected.\\
2476 2494 parts is an alias to: 'echo first %s second %s'
2477 2495
2478 2496 Note that %l and %s are mutually exclusive. You can only use one or
2479 2497 the other in your aliases.
2480 2498
2481 2499 Aliases expand Python variables just like system calls using ! or !!
2482 2500 do: all expressions prefixed with '$' get expanded. For details of
2483 2501 the semantic rules, see PEP-215:
2484 2502 http://www.python.org/peps/pep-0215.html. This is the library used by
2485 2503 IPython for variable expansion. If you want to access a true shell
2486 2504 variable, an extra $ is necessary to prevent its expansion by IPython:
2487 2505
2488 2506 In [6]: alias show echo\\
2489 2507 In [7]: PATH='A Python string'\\
2490 2508 In [8]: show $PATH\\
2491 2509 A Python string\\
2492 2510 In [9]: show $$PATH\\
2493 2511 /usr/local/lf9560/bin:/usr/local/intel/compiler70/ia32/bin:...
2494 2512
2495 2513 You can use the alias facility to acess all of $PATH. See the %rehash
2496 2514 and %rehashx functions, which automatically create aliases for the
2497 2515 contents of your $PATH.
2498 2516
2499 2517 If called with no parameters, %alias prints the current alias table."""
2500 2518
2501 2519 par = parameter_s.strip()
2502 2520 if not par:
2503 2521 stored = self.db.get('stored_aliases', {} )
2504 2522 atab = self.shell.alias_table
2505 2523 aliases = atab.keys()
2506 2524 aliases.sort()
2507 2525 res = []
2508 2526 showlast = []
2509 2527 for alias in aliases:
2510 2528 special = False
2511 2529 try:
2512 2530 tgt = atab[alias][1]
2513 2531 except (TypeError, AttributeError):
2514 2532 # unsubscriptable? probably a callable
2515 2533 tgt = atab[alias]
2516 2534 special = True
2517 2535 # 'interesting' aliases
2518 2536 if (alias in stored or
2519 2537 special or
2520 2538 alias.lower() != os.path.splitext(tgt)[0].lower() or
2521 2539 ' ' in tgt):
2522 2540 showlast.append((alias, tgt))
2523 2541 else:
2524 2542 res.append((alias, tgt ))
2525 2543
2526 2544 # show most interesting aliases last
2527 2545 res.extend(showlast)
2528 2546 print "Total number of aliases:",len(aliases)
2529 2547 return res
2530 2548 try:
2531 2549 alias,cmd = par.split(None,1)
2532 2550 except:
2533 2551 print OInspect.getdoc(self.magic_alias)
2534 2552 else:
2535 2553 nargs = cmd.count('%s')
2536 2554 if nargs>0 and cmd.find('%l')>=0:
2537 2555 error('The %s and %l specifiers are mutually exclusive '
2538 2556 'in alias definitions.')
2539 2557 else: # all looks OK
2540 2558 self.shell.alias_table[alias] = (nargs,cmd)
2541 2559 self.shell.alias_table_validate(verbose=0)
2542 2560 # end magic_alias
2543 2561
2544 2562 def magic_unalias(self, parameter_s = ''):
2545 2563 """Remove an alias"""
2546 2564
2547 2565 aname = parameter_s.strip()
2548 2566 if aname in self.shell.alias_table:
2549 2567 del self.shell.alias_table[aname]
2550 2568 stored = self.db.get('stored_aliases', {} )
2551 2569 if aname in stored:
2552 2570 print "Removing %stored alias",aname
2553 2571 del stored[aname]
2554 2572 self.db['stored_aliases'] = stored
2555 2573
2556 2574
2557 2575 def magic_rehashx(self, parameter_s = ''):
2558 2576 """Update the alias table with all executable files in $PATH.
2559 2577
2560 2578 This version explicitly checks that every entry in $PATH is a file
2561 2579 with execute access (os.X_OK), so it is much slower than %rehash.
2562 2580
2563 2581 Under Windows, it checks executability as a match agains a
2564 2582 '|'-separated string of extensions, stored in the IPython config
2565 2583 variable win_exec_ext. This defaults to 'exe|com|bat'.
2566 2584
2567 2585 This function also resets the root module cache of module completer,
2568 2586 used on slow filesystems.
2569 2587 """
2570 2588
2571 2589
2572 2590 ip = self.api
2573 2591
2574 2592 # for the benefit of module completer in ipy_completers.py
2575 2593 del ip.db['rootmodules']
2576 2594
2577 2595 path = [os.path.abspath(os.path.expanduser(p)) for p in
2578 2596 os.environ.get('PATH','').split(os.pathsep)]
2579 2597 path = filter(os.path.isdir,path)
2580 2598
2581 2599 alias_table = self.shell.alias_table
2582 2600 syscmdlist = []
2583 2601 if os.name == 'posix':
2584 2602 isexec = lambda fname:os.path.isfile(fname) and \
2585 2603 os.access(fname,os.X_OK)
2586 2604 else:
2587 2605
2588 2606 try:
2589 2607 winext = os.environ['pathext'].replace(';','|').replace('.','')
2590 2608 except KeyError:
2591 2609 winext = 'exe|com|bat|py'
2592 2610 if 'py' not in winext:
2593 2611 winext += '|py'
2594 2612 execre = re.compile(r'(.*)\.(%s)$' % winext,re.IGNORECASE)
2595 2613 isexec = lambda fname:os.path.isfile(fname) and execre.match(fname)
2596 2614 savedir = os.getcwd()
2597 2615 try:
2598 2616 # write the whole loop for posix/Windows so we don't have an if in
2599 2617 # the innermost part
2600 2618 if os.name == 'posix':
2601 2619 for pdir in path:
2602 2620 os.chdir(pdir)
2603 2621 for ff in os.listdir(pdir):
2604 2622 if isexec(ff) and ff not in self.shell.no_alias:
2605 2623 # each entry in the alias table must be (N,name),
2606 2624 # where N is the number of positional arguments of the
2607 2625 # alias.
2608 2626 alias_table[ff] = (0,ff)
2609 2627 syscmdlist.append(ff)
2610 2628 else:
2611 2629 for pdir in path:
2612 2630 os.chdir(pdir)
2613 2631 for ff in os.listdir(pdir):
2614 2632 base, ext = os.path.splitext(ff)
2615 if isexec(ff) and base not in self.shell.no_alias:
2633 if isexec(ff) and base.lower() not in self.shell.no_alias:
2616 2634 if ext.lower() == '.exe':
2617 2635 ff = base
2618 2636 alias_table[base.lower()] = (0,ff)
2619 2637 syscmdlist.append(ff)
2620 2638 # Make sure the alias table doesn't contain keywords or builtins
2621 2639 self.shell.alias_table_validate()
2622 2640 # Call again init_auto_alias() so we get 'rm -i' and other
2623 2641 # modified aliases since %rehashx will probably clobber them
2624 2642
2625 2643 # no, we don't want them. if %rehashx clobbers them, good,
2626 2644 # we'll probably get better versions
2627 2645 # self.shell.init_auto_alias()
2628 2646 db = ip.db
2629 2647 db['syscmdlist'] = syscmdlist
2630 2648 finally:
2631 2649 os.chdir(savedir)
2632 2650
2633 2651 def magic_pwd(self, parameter_s = ''):
2634 2652 """Return the current working directory path."""
2635 2653 return os.getcwd()
2636 2654
2637 2655 def magic_cd(self, parameter_s=''):
2638 2656 """Change the current working directory.
2639 2657
2640 2658 This command automatically maintains an internal list of directories
2641 2659 you visit during your IPython session, in the variable _dh. The
2642 2660 command %dhist shows this history nicely formatted. You can also
2643 2661 do 'cd -<tab>' to see directory history conveniently.
2644 2662
2645 2663 Usage:
2646 2664
2647 2665 cd 'dir': changes to directory 'dir'.
2648 2666
2649 2667 cd -: changes to the last visited directory.
2650 2668
2651 2669 cd -<n>: changes to the n-th directory in the directory history.
2652 2670
2653 2671 cd -b <bookmark_name>: jump to a bookmark set by %bookmark
2654 2672 (note: cd <bookmark_name> is enough if there is no
2655 2673 directory <bookmark_name>, but a bookmark with the name exists.)
2656 2674 'cd -b <tab>' allows you to tab-complete bookmark names.
2657 2675
2658 2676 Options:
2659 2677
2660 2678 -q: quiet. Do not print the working directory after the cd command is
2661 2679 executed. By default IPython's cd command does print this directory,
2662 2680 since the default prompts do not display path information.
2663 2681
2664 2682 Note that !cd doesn't work for this purpose because the shell where
2665 2683 !command runs is immediately discarded after executing 'command'."""
2666 2684
2667 2685 parameter_s = parameter_s.strip()
2668 2686 #bkms = self.shell.persist.get("bookmarks",{})
2669 2687
2688 oldcwd = os.getcwd()
2670 2689 numcd = re.match(r'(-)(\d+)$',parameter_s)
2671 2690 # jump in directory history by number
2672 2691 if numcd:
2673 2692 nn = int(numcd.group(2))
2674 2693 try:
2675 2694 ps = self.shell.user_ns['_dh'][nn]
2676 2695 except IndexError:
2677 2696 print 'The requested directory does not exist in history.'
2678 2697 return
2679 2698 else:
2680 2699 opts = {}
2681 2700 else:
2682 2701 #turn all non-space-escaping backslashes to slashes,
2683 2702 # for c:\windows\directory\names\
2684 2703 parameter_s = re.sub(r'\\(?! )','/', parameter_s)
2685 2704 opts,ps = self.parse_options(parameter_s,'qb',mode='string')
2686 2705 # jump to previous
2687 2706 if ps == '-':
2688 2707 try:
2689 2708 ps = self.shell.user_ns['_dh'][-2]
2690 2709 except IndexError:
2691 2710 raise UsageError('%cd -: No previous directory to change to.')
2692 2711 # jump to bookmark if needed
2693 2712 else:
2694 2713 if not os.path.isdir(ps) or opts.has_key('b'):
2695 2714 bkms = self.db.get('bookmarks', {})
2696 2715
2697 2716 if bkms.has_key(ps):
2698 2717 target = bkms[ps]
2699 2718 print '(bookmark:%s) -> %s' % (ps,target)
2700 2719 ps = target
2701 2720 else:
2702 2721 if opts.has_key('b'):
2703 2722 raise UsageError("Bookmark '%s' not found. "
2704 2723 "Use '%%bookmark -l' to see your bookmarks." % ps)
2705 2724
2706 2725 # at this point ps should point to the target dir
2707 2726 if ps:
2708 try:
2727 try:
2709 2728 os.chdir(os.path.expanduser(ps))
2710 2729 if self.shell.rc.term_title:
2711 2730 #print 'set term title:',self.shell.rc.term_title # dbg
2712 2731 ttitle = 'IPy ' + abbrev_cwd()
2713 2732 platutils.set_term_title(ttitle)
2714 2733 except OSError:
2715 2734 print sys.exc_info()[1]
2716 2735 else:
2717 2736 cwd = os.getcwd()
2718 2737 dhist = self.shell.user_ns['_dh']
2719 dhist.append(cwd)
2720 self.db['dhist'] = compress_dhist(dhist)[-100:]
2738 if oldcwd != cwd:
2739 dhist.append(cwd)
2740 self.db['dhist'] = compress_dhist(dhist)[-100:]
2721 2741
2722 2742 else:
2723 2743 os.chdir(self.shell.home_dir)
2724 2744 if self.shell.rc.term_title:
2725 2745 platutils.set_term_title("IPy ~")
2726 2746 cwd = os.getcwd()
2727 2747 dhist = self.shell.user_ns['_dh']
2728 dhist.append(cwd)
2729 self.db['dhist'] = compress_dhist(dhist)[-100:]
2748
2749 if oldcwd != cwd:
2750 dhist.append(cwd)
2751 self.db['dhist'] = compress_dhist(dhist)[-100:]
2730 2752 if not 'q' in opts and self.shell.user_ns['_dh']:
2731 2753 print self.shell.user_ns['_dh'][-1]
2732 2754
2733 2755
2734 2756 def magic_env(self, parameter_s=''):
2735 2757 """List environment variables."""
2736 2758
2737 2759 return os.environ.data
2738 2760
2739 2761 def magic_pushd(self, parameter_s=''):
2740 2762 """Place the current dir on stack and change directory.
2741 2763
2742 2764 Usage:\\
2743 2765 %pushd ['dirname']
2744 2766 """
2745 2767
2746 2768 dir_s = self.shell.dir_stack
2747 2769 tgt = os.path.expanduser(parameter_s)
2748 2770 cwd = os.getcwd().replace(self.home_dir,'~')
2749 2771 if tgt:
2750 2772 self.magic_cd(parameter_s)
2751 2773 dir_s.insert(0,cwd)
2752 2774 return self.magic_dirs()
2753 2775
2754 2776 def magic_popd(self, parameter_s=''):
2755 2777 """Change to directory popped off the top of the stack.
2756 2778 """
2757 2779 if not self.shell.dir_stack:
2758 2780 raise UsageError("%popd on empty stack")
2759 2781 top = self.shell.dir_stack.pop(0)
2760 2782 self.magic_cd(top)
2761 2783 print "popd ->",top
2762 2784
2763 2785 def magic_dirs(self, parameter_s=''):
2764 2786 """Return the current directory stack."""
2765 2787
2766 2788 return self.shell.dir_stack
2767 2789
2768 2790 def magic_dhist(self, parameter_s=''):
2769 2791 """Print your history of visited directories.
2770 2792
2771 2793 %dhist -> print full history\\
2772 2794 %dhist n -> print last n entries only\\
2773 2795 %dhist n1 n2 -> print entries between n1 and n2 (n1 not included)\\
2774 2796
2775 2797 This history is automatically maintained by the %cd command, and
2776 2798 always available as the global list variable _dh. You can use %cd -<n>
2777 2799 to go to directory number <n>.
2778 2800
2779 2801 Note that most of time, you should view directory history by entering
2780 2802 cd -<TAB>.
2781 2803
2782 2804 """
2783 2805
2784 2806 dh = self.shell.user_ns['_dh']
2785 2807 if parameter_s:
2786 2808 try:
2787 2809 args = map(int,parameter_s.split())
2788 2810 except:
2789 2811 self.arg_err(Magic.magic_dhist)
2790 2812 return
2791 2813 if len(args) == 1:
2792 2814 ini,fin = max(len(dh)-(args[0]),0),len(dh)
2793 2815 elif len(args) == 2:
2794 2816 ini,fin = args
2795 2817 else:
2796 2818 self.arg_err(Magic.magic_dhist)
2797 2819 return
2798 2820 else:
2799 2821 ini,fin = 0,len(dh)
2800 2822 nlprint(dh,
2801 2823 header = 'Directory history (kept in _dh)',
2802 2824 start=ini,stop=fin)
2803 2825
2804 2826
2805 2827 def magic_sc(self, parameter_s=''):
2806 2828 """Shell capture - execute a shell command and capture its output.
2807 2829
2808 2830 DEPRECATED. Suboptimal, retained for backwards compatibility.
2809 2831
2810 2832 You should use the form 'var = !command' instead. Example:
2811 2833
2812 2834 "%sc -l myfiles = ls ~" should now be written as
2813 2835
2814 2836 "myfiles = !ls ~"
2815 2837
2816 2838 myfiles.s, myfiles.l and myfiles.n still apply as documented
2817 2839 below.
2818 2840
2819 2841 --
2820 2842 %sc [options] varname=command
2821 2843
2822 2844 IPython will run the given command using commands.getoutput(), and
2823 2845 will then update the user's interactive namespace with a variable
2824 2846 called varname, containing the value of the call. Your command can
2825 2847 contain shell wildcards, pipes, etc.
2826 2848
2827 2849 The '=' sign in the syntax is mandatory, and the variable name you
2828 2850 supply must follow Python's standard conventions for valid names.
2829 2851
2830 2852 (A special format without variable name exists for internal use)
2831 2853
2832 2854 Options:
2833 2855
2834 2856 -l: list output. Split the output on newlines into a list before
2835 2857 assigning it to the given variable. By default the output is stored
2836 2858 as a single string.
2837 2859
2838 2860 -v: verbose. Print the contents of the variable.
2839 2861
2840 2862 In most cases you should not need to split as a list, because the
2841 2863 returned value is a special type of string which can automatically
2842 2864 provide its contents either as a list (split on newlines) or as a
2843 2865 space-separated string. These are convenient, respectively, either
2844 2866 for sequential processing or to be passed to a shell command.
2845 2867
2846 2868 For example:
2847 2869
2848 2870 # Capture into variable a
2849 2871 In [9]: sc a=ls *py
2850 2872
2851 2873 # a is a string with embedded newlines
2852 2874 In [10]: a
2853 2875 Out[10]: 'setup.py\nwin32_manual_post_install.py'
2854 2876
2855 2877 # which can be seen as a list:
2856 2878 In [11]: a.l
2857 2879 Out[11]: ['setup.py', 'win32_manual_post_install.py']
2858 2880
2859 2881 # or as a whitespace-separated string:
2860 2882 In [12]: a.s
2861 2883 Out[12]: 'setup.py win32_manual_post_install.py'
2862 2884
2863 2885 # a.s is useful to pass as a single command line:
2864 2886 In [13]: !wc -l $a.s
2865 2887 146 setup.py
2866 2888 130 win32_manual_post_install.py
2867 2889 276 total
2868 2890
2869 2891 # while the list form is useful to loop over:
2870 2892 In [14]: for f in a.l:
2871 2893 ....: !wc -l $f
2872 2894 ....:
2873 2895 146 setup.py
2874 2896 130 win32_manual_post_install.py
2875 2897
2876 2898 Similiarly, the lists returned by the -l option are also special, in
2877 2899 the sense that you can equally invoke the .s attribute on them to
2878 2900 automatically get a whitespace-separated string from their contents:
2879 2901
2880 2902 In [1]: sc -l b=ls *py
2881 2903
2882 2904 In [2]: b
2883 2905 Out[2]: ['setup.py', 'win32_manual_post_install.py']
2884 2906
2885 2907 In [3]: b.s
2886 2908 Out[3]: 'setup.py win32_manual_post_install.py'
2887 2909
2888 2910 In summary, both the lists and strings used for ouptut capture have
2889 2911 the following special attributes:
2890 2912
2891 2913 .l (or .list) : value as list.
2892 2914 .n (or .nlstr): value as newline-separated string.
2893 2915 .s (or .spstr): value as space-separated string.
2894 2916 """
2895 2917
2896 2918 opts,args = self.parse_options(parameter_s,'lv')
2897 2919 # Try to get a variable name and command to run
2898 2920 try:
2899 2921 # the variable name must be obtained from the parse_options
2900 2922 # output, which uses shlex.split to strip options out.
2901 2923 var,_ = args.split('=',1)
2902 2924 var = var.strip()
2903 2925 # But the the command has to be extracted from the original input
2904 2926 # parameter_s, not on what parse_options returns, to avoid the
2905 2927 # quote stripping which shlex.split performs on it.
2906 2928 _,cmd = parameter_s.split('=',1)
2907 2929 except ValueError:
2908 2930 var,cmd = '',''
2909 2931 # If all looks ok, proceed
2910 2932 out,err = self.shell.getoutputerror(cmd)
2911 2933 if err:
2912 2934 print >> Term.cerr,err
2913 2935 if opts.has_key('l'):
2914 2936 out = SList(out.split('\n'))
2915 2937 else:
2916 2938 out = LSString(out)
2917 2939 if opts.has_key('v'):
2918 2940 print '%s ==\n%s' % (var,pformat(out))
2919 2941 if var:
2920 2942 self.shell.user_ns.update({var:out})
2921 2943 else:
2922 2944 return out
2923 2945
2924 2946 def magic_sx(self, parameter_s=''):
2925 2947 """Shell execute - run a shell command and capture its output.
2926 2948
2927 2949 %sx command
2928 2950
2929 2951 IPython will run the given command using commands.getoutput(), and
2930 2952 return the result formatted as a list (split on '\\n'). Since the
2931 2953 output is _returned_, it will be stored in ipython's regular output
2932 2954 cache Out[N] and in the '_N' automatic variables.
2933 2955
2934 2956 Notes:
2935 2957
2936 2958 1) If an input line begins with '!!', then %sx is automatically
2937 2959 invoked. That is, while:
2938 2960 !ls
2939 2961 causes ipython to simply issue system('ls'), typing
2940 2962 !!ls
2941 2963 is a shorthand equivalent to:
2942 2964 %sx ls
2943 2965
2944 2966 2) %sx differs from %sc in that %sx automatically splits into a list,
2945 2967 like '%sc -l'. The reason for this is to make it as easy as possible
2946 2968 to process line-oriented shell output via further python commands.
2947 2969 %sc is meant to provide much finer control, but requires more
2948 2970 typing.
2949 2971
2950 2972 3) Just like %sc -l, this is a list with special attributes:
2951 2973
2952 2974 .l (or .list) : value as list.
2953 2975 .n (or .nlstr): value as newline-separated string.
2954 2976 .s (or .spstr): value as whitespace-separated string.
2955 2977
2956 2978 This is very useful when trying to use such lists as arguments to
2957 2979 system commands."""
2958 2980
2959 2981 if parameter_s:
2960 2982 out,err = self.shell.getoutputerror(parameter_s)
2961 2983 if err:
2962 2984 print >> Term.cerr,err
2963 2985 return SList(out.split('\n'))
2964 2986
2965 2987 def magic_bg(self, parameter_s=''):
2966 2988 """Run a job in the background, in a separate thread.
2967 2989
2968 2990 For example,
2969 2991
2970 2992 %bg myfunc(x,y,z=1)
2971 2993
2972 2994 will execute 'myfunc(x,y,z=1)' in a background thread. As soon as the
2973 2995 execution starts, a message will be printed indicating the job
2974 2996 number. If your job number is 5, you can use
2975 2997
2976 2998 myvar = jobs.result(5) or myvar = jobs[5].result
2977 2999
2978 3000 to assign this result to variable 'myvar'.
2979 3001
2980 3002 IPython has a job manager, accessible via the 'jobs' object. You can
2981 3003 type jobs? to get more information about it, and use jobs.<TAB> to see
2982 3004 its attributes. All attributes not starting with an underscore are
2983 3005 meant for public use.
2984 3006
2985 3007 In particular, look at the jobs.new() method, which is used to create
2986 3008 new jobs. This magic %bg function is just a convenience wrapper
2987 3009 around jobs.new(), for expression-based jobs. If you want to create a
2988 3010 new job with an explicit function object and arguments, you must call
2989 3011 jobs.new() directly.
2990 3012
2991 3013 The jobs.new docstring also describes in detail several important
2992 3014 caveats associated with a thread-based model for background job
2993 3015 execution. Type jobs.new? for details.
2994 3016
2995 3017 You can check the status of all jobs with jobs.status().
2996 3018
2997 3019 The jobs variable is set by IPython into the Python builtin namespace.
2998 3020 If you ever declare a variable named 'jobs', you will shadow this
2999 3021 name. You can either delete your global jobs variable to regain
3000 3022 access to the job manager, or make a new name and assign it manually
3001 3023 to the manager (stored in IPython's namespace). For example, to
3002 3024 assign the job manager to the Jobs name, use:
3003 3025
3004 3026 Jobs = __builtins__.jobs"""
3005 3027
3006 3028 self.shell.jobs.new(parameter_s,self.shell.user_ns)
3007 3029
3008 3030 def magic_r(self, parameter_s=''):
3009 3031 """Repeat previous input.
3010 3032
3011 3033 Note: Consider using the more powerfull %rep instead!
3012 3034
3013 3035 If given an argument, repeats the previous command which starts with
3014 3036 the same string, otherwise it just repeats the previous input.
3015 3037
3016 3038 Shell escaped commands (with ! as first character) are not recognized
3017 3039 by this system, only pure python code and magic commands.
3018 3040 """
3019 3041
3020 3042 start = parameter_s.strip()
3021 3043 esc_magic = self.shell.ESC_MAGIC
3022 3044 # Identify magic commands even if automagic is on (which means
3023 3045 # the in-memory version is different from that typed by the user).
3024 3046 if self.shell.rc.automagic:
3025 3047 start_magic = esc_magic+start
3026 3048 else:
3027 3049 start_magic = start
3028 3050 # Look through the input history in reverse
3029 3051 for n in range(len(self.shell.input_hist)-2,0,-1):
3030 3052 input = self.shell.input_hist[n]
3031 3053 # skip plain 'r' lines so we don't recurse to infinity
3032 3054 if input != '_ip.magic("r")\n' and \
3033 3055 (input.startswith(start) or input.startswith(start_magic)):
3034 3056 #print 'match',`input` # dbg
3035 3057 print 'Executing:',input,
3036 3058 self.shell.runlines(input)
3037 3059 return
3038 3060 print 'No previous input matching `%s` found.' % start
3039 3061
3040 3062
3041 3063 def magic_bookmark(self, parameter_s=''):
3042 3064 """Manage IPython's bookmark system.
3043 3065
3044 3066 %bookmark <name> - set bookmark to current dir
3045 3067 %bookmark <name> <dir> - set bookmark to <dir>
3046 3068 %bookmark -l - list all bookmarks
3047 3069 %bookmark -d <name> - remove bookmark
3048 3070 %bookmark -r - remove all bookmarks
3049 3071
3050 3072 You can later on access a bookmarked folder with:
3051 3073 %cd -b <name>
3052 3074 or simply '%cd <name>' if there is no directory called <name> AND
3053 3075 there is such a bookmark defined.
3054 3076
3055 3077 Your bookmarks persist through IPython sessions, but they are
3056 3078 associated with each profile."""
3057 3079
3058 3080 opts,args = self.parse_options(parameter_s,'drl',mode='list')
3059 3081 if len(args) > 2:
3060 3082 raise UsageError("%bookmark: too many arguments")
3061 3083
3062 3084 bkms = self.db.get('bookmarks',{})
3063 3085
3064 3086 if opts.has_key('d'):
3065 3087 try:
3066 3088 todel = args[0]
3067 3089 except IndexError:
3068 3090 raise UsageError(
3069 3091 "%bookmark -d: must provide a bookmark to delete")
3070 3092 else:
3071 3093 try:
3072 3094 del bkms[todel]
3073 3095 except KeyError:
3074 3096 raise UsageError(
3075 3097 "%%bookmark -d: Can't delete bookmark '%s'" % todel)
3076 3098
3077 3099 elif opts.has_key('r'):
3078 3100 bkms = {}
3079 3101 elif opts.has_key('l'):
3080 3102 bks = bkms.keys()
3081 3103 bks.sort()
3082 3104 if bks:
3083 3105 size = max(map(len,bks))
3084 3106 else:
3085 3107 size = 0
3086 3108 fmt = '%-'+str(size)+'s -> %s'
3087 3109 print 'Current bookmarks:'
3088 3110 for bk in bks:
3089 3111 print fmt % (bk,bkms[bk])
3090 3112 else:
3091 3113 if not args:
3092 3114 raise UsageError("%bookmark: You must specify the bookmark name")
3093 3115 elif len(args)==1:
3094 3116 bkms[args[0]] = os.getcwd()
3095 3117 elif len(args)==2:
3096 3118 bkms[args[0]] = args[1]
3097 3119 self.db['bookmarks'] = bkms
3098 3120
3099 3121 def magic_pycat(self, parameter_s=''):
3100 3122 """Show a syntax-highlighted file through a pager.
3101 3123
3102 3124 This magic is similar to the cat utility, but it will assume the file
3103 3125 to be Python source and will show it with syntax highlighting. """
3104 3126
3105 3127 try:
3106 3128 filename = get_py_filename(parameter_s)
3107 3129 cont = file_read(filename)
3108 3130 except IOError:
3109 3131 try:
3110 3132 cont = eval(parameter_s,self.user_ns)
3111 3133 except NameError:
3112 3134 cont = None
3113 3135 if cont is None:
3114 3136 print "Error: no such file or variable"
3115 3137 return
3116 3138
3117 3139 page(self.shell.pycolorize(cont),
3118 3140 screen_lines=self.shell.rc.screen_length)
3119 3141
3120 3142 def magic_cpaste(self, parameter_s=''):
3121 """Allows you to paste & execute a pre-formatted code block from clipboard
3143 """Allows you to paste & execute a pre-formatted code block from clipboard.
3122 3144
3123 3145 You must terminate the block with '--' (two minus-signs) alone on the
3124 3146 line. You can also provide your own sentinel with '%paste -s %%' ('%%'
3125 3147 is the new sentinel for this operation)
3126 3148
3127 3149 The block is dedented prior to execution to enable execution of method
3128 3150 definitions. '>' and '+' characters at the beginning of a line are
3129 ignored, to allow pasting directly from e-mails or diff files. The
3151 ignored, to allow pasting directly from e-mails, diff files and
3152 doctests (the '...' continuation prompt is also stripped). The
3130 3153 executed block is also assigned to variable named 'pasted_block' for
3131 3154 later editing with '%edit pasted_block'.
3132 3155
3133 3156 You can also pass a variable name as an argument, e.g. '%cpaste foo'.
3134 3157 This assigns the pasted block to variable 'foo' as string, without
3135 dedenting or executing it.
3158 dedenting or executing it (preceding >>> and + is still stripped)
3136 3159
3137 3160 Do not be alarmed by garbled output on Windows (it's a readline bug).
3138 3161 Just press enter and type -- (and press enter again) and the block
3139 3162 will be what was just pasted.
3140 3163
3141 3164 IPython statements (magics, shell escapes) are not supported (yet).
3142 3165 """
3143 3166 opts,args = self.parse_options(parameter_s,'s:',mode='string')
3144 3167 par = args.strip()
3145 3168 sentinel = opts.get('s','--')
3169
3170 # Regular expressions that declare text we strip from the input:
3171 strip_re = [r'^\s*In \[\d+\]:', # IPython input prompt
3172 r'^\s*(\s?>)+', # Python input prompt
3173 r'^\s*\.{3,}', # Continuation prompts
3174 r'^\++',
3175 ]
3176
3177 strip_from_start = map(re.compile,strip_re)
3146 3178
3147 3179 from IPython import iplib
3148 3180 lines = []
3149 3181 print "Pasting code; enter '%s' alone on the line to stop." % sentinel
3150 3182 while 1:
3151 3183 l = iplib.raw_input_original(':')
3152 3184 if l ==sentinel:
3153 3185 break
3154 lines.append(l.lstrip('>').lstrip('+'))
3186
3187 for pat in strip_from_start:
3188 l = pat.sub('',l)
3189 lines.append(l)
3190
3155 3191 block = "\n".join(lines) + '\n'
3156 3192 #print "block:\n",block
3157 3193 if not par:
3158 3194 b = textwrap.dedent(block)
3159 3195 exec b in self.user_ns
3160 3196 self.user_ns['pasted_block'] = b
3161 3197 else:
3162 3198 self.user_ns[par] = block
3163 3199 print "Block assigned to '%s'" % par
3164 3200
3165 3201 def magic_quickref(self,arg):
3166 3202 """ Show a quick reference sheet """
3167 3203 import IPython.usage
3168 3204 qr = IPython.usage.quick_reference + self.magic_magic('-brief')
3169 3205
3170 3206 page(qr)
3171 3207
3172 3208 def magic_upgrade(self,arg):
3173 3209 """ Upgrade your IPython installation
3174 3210
3175 3211 This will copy the config files that don't yet exist in your
3176 3212 ipython dir from the system config dir. Use this after upgrading
3177 3213 IPython if you don't wish to delete your .ipython dir.
3178 3214
3179 3215 Call with -nolegacy to get rid of ipythonrc* files (recommended for
3180 3216 new users)
3181 3217
3182 3218 """
3183 3219 ip = self.getapi()
3184 3220 ipinstallation = path(IPython.__file__).dirname()
3185 3221 upgrade_script = '%s "%s"' % (sys.executable,ipinstallation / 'upgrade_dir.py')
3186 3222 src_config = ipinstallation / 'UserConfig'
3187 3223 userdir = path(ip.options.ipythondir)
3188 3224 cmd = '%s "%s" "%s"' % (upgrade_script, src_config, userdir)
3189 3225 print ">",cmd
3190 3226 shell(cmd)
3191 3227 if arg == '-nolegacy':
3192 3228 legacy = userdir.files('ipythonrc*')
3193 3229 print "Nuking legacy files:",legacy
3194 3230
3195 3231 [p.remove() for p in legacy]
3196 3232 suffix = (sys.platform == 'win32' and '.ini' or '')
3197 3233 (userdir / ('ipythonrc' + suffix)).write_text('# Empty, see ipy_user_conf.py\n')
3198 3234
3199 3235
3200 3236 def magic_doctest_mode(self,parameter_s=''):
3201 3237 """Toggle doctest mode on and off.
3202 3238
3203 3239 This mode allows you to toggle the prompt behavior between normal
3204 3240 IPython prompts and ones that are as similar to the default IPython
3205 3241 interpreter as possible.
3206 3242
3207 3243 It also supports the pasting of code snippets that have leading '>>>'
3208 3244 and '...' prompts in them. This means that you can paste doctests from
3209 3245 files or docstrings (even if they have leading whitespace), and the
3210 3246 code will execute correctly. You can then use '%history -tn' to see
3211 3247 the translated history without line numbers; this will give you the
3212 3248 input after removal of all the leading prompts and whitespace, which
3213 3249 can be pasted back into an editor.
3214 3250
3215 3251 With these features, you can switch into this mode easily whenever you
3216 3252 need to do testing and changes to doctests, without having to leave
3217 3253 your existing IPython session.
3218 3254 """
3219 3255
3220 3256 # XXX - Fix this to have cleaner activate/deactivate calls.
3221 3257 from IPython.Extensions import InterpreterPasteInput as ipaste
3222 3258 from IPython.ipstruct import Struct
3223 3259
3224 3260 # Shorthands
3225 3261 shell = self.shell
3226 3262 oc = shell.outputcache
3227 3263 rc = shell.rc
3228 3264 meta = shell.meta
3229 3265 # dstore is a data store kept in the instance metadata bag to track any
3230 3266 # changes we make, so we can undo them later.
3231 3267 dstore = meta.setdefault('doctest_mode',Struct())
3232 3268 save_dstore = dstore.setdefault
3233 3269
3234 3270 # save a few values we'll need to recover later
3235 3271 mode = save_dstore('mode',False)
3236 3272 save_dstore('rc_pprint',rc.pprint)
3237 3273 save_dstore('xmode',shell.InteractiveTB.mode)
3238 3274 save_dstore('rc_separate_out',rc.separate_out)
3239 3275 save_dstore('rc_separate_out2',rc.separate_out2)
3240 3276 save_dstore('rc_prompts_pad_left',rc.prompts_pad_left)
3241 3277
3242 3278 if mode == False:
3243 3279 # turn on
3244 3280 ipaste.activate_prefilter()
3245 3281
3246 3282 oc.prompt1.p_template = '>>> '
3247 3283 oc.prompt2.p_template = '... '
3248 3284 oc.prompt_out.p_template = ''
3249 3285
3250 3286 oc.output_sep = ''
3251 3287 oc.output_sep2 = ''
3252 3288
3253 3289 oc.prompt1.pad_left = oc.prompt2.pad_left = \
3254 3290 oc.prompt_out.pad_left = False
3255 3291
3256 3292 rc.pprint = False
3257 3293
3258 3294 shell.magic_xmode('Plain')
3259 3295
3260 3296 else:
3261 3297 # turn off
3262 3298 ipaste.deactivate_prefilter()
3263 3299
3264 3300 oc.prompt1.p_template = rc.prompt_in1
3265 3301 oc.prompt2.p_template = rc.prompt_in2
3266 3302 oc.prompt_out.p_template = rc.prompt_out
3267 3303
3268 3304 oc.output_sep = dstore.rc_separate_out
3269 3305 oc.output_sep2 = dstore.rc_separate_out2
3270 3306
3271 3307 oc.prompt1.pad_left = oc.prompt2.pad_left = \
3272 3308 oc.prompt_out.pad_left = dstore.rc_prompts_pad_left
3273 3309
3274 3310 rc.pprint = dstore.rc_pprint
3275 3311
3276 3312 shell.magic_xmode(dstore.xmode)
3277 3313
3278 3314 # Store new mode and inform
3279 3315 dstore.mode = bool(1-int(mode))
3280 3316 print 'Doctest mode is:',
3281 3317 print ['OFF','ON'][dstore.mode]
3282 3318
3283 3319 # end Magic
@@ -1,582 +1,593 b''
1 1 # -*- coding: utf-8 -*-
2 2 """Tools for inspecting Python objects.
3 3
4 4 Uses syntax highlighting for presenting the various information elements.
5 5
6 6 Similar in spirit to the inspect module, but all calls take a name argument to
7 7 reference the name under which an object is being read.
8 8
9 9 $Id: OInspect.py 2843 2007-10-15 21:22:32Z fperez $
10 10 """
11 11
12 12 #*****************************************************************************
13 13 # Copyright (C) 2001-2004 Fernando Perez <fperez@colorado.edu>
14 14 #
15 15 # Distributed under the terms of the BSD License. The full license is in
16 16 # the file COPYING, distributed as part of this software.
17 17 #*****************************************************************************
18 18
19 19 from IPython import Release
20 20 __author__ = '%s <%s>' % Release.authors['Fernando']
21 21 __license__ = Release.license
22 22
23 23 __all__ = ['Inspector','InspectColors']
24 24
25 25 # stdlib modules
26 26 import __builtin__
27 27 import inspect
28 28 import linecache
29 29 import string
30 30 import StringIO
31 31 import types
32 32 import os
33 33 import sys
34 34 # IPython's own
35 35 from IPython import PyColorize
36 36 from IPython.genutils import page,indent,Term,mkdict
37 37 from IPython.Itpl import itpl
38 38 from IPython.wildcard import list_namespace
39 39 from IPython.ColorANSI import *
40 40
41 41 #****************************************************************************
42 42 # HACK!!! This is a crude fix for bugs in python 2.3's inspect module. We
43 43 # simply monkeypatch inspect with code copied from python 2.4.
44 44 if sys.version_info[:2] == (2,3):
45 45 from inspect import ismodule, getabsfile, modulesbyfile
46 46 def getmodule(object):
47 47 """Return the module an object was defined in, or None if not found."""
48 48 if ismodule(object):
49 49 return object
50 50 if hasattr(object, '__module__'):
51 51 return sys.modules.get(object.__module__)
52 52 try:
53 53 file = getabsfile(object)
54 54 except TypeError:
55 55 return None
56 56 if file in modulesbyfile:
57 57 return sys.modules.get(modulesbyfile[file])
58 58 for module in sys.modules.values():
59 59 if hasattr(module, '__file__'):
60 60 modulesbyfile[
61 61 os.path.realpath(
62 62 getabsfile(module))] = module.__name__
63 63 if file in modulesbyfile:
64 64 return sys.modules.get(modulesbyfile[file])
65 65 main = sys.modules['__main__']
66 66 if not hasattr(object, '__name__'):
67 67 return None
68 68 if hasattr(main, object.__name__):
69 69 mainobject = getattr(main, object.__name__)
70 70 if mainobject is object:
71 71 return main
72 72 builtin = sys.modules['__builtin__']
73 73 if hasattr(builtin, object.__name__):
74 74 builtinobject = getattr(builtin, object.__name__)
75 75 if builtinobject is object:
76 76 return builtin
77 77
78 78 inspect.getmodule = getmodule
79 79
80 80 #****************************************************************************
81 81 # Builtin color schemes
82 82
83 83 Colors = TermColors # just a shorthand
84 84
85 85 # Build a few color schemes
86 86 NoColor = ColorScheme(
87 87 'NoColor',{
88 88 'header' : Colors.NoColor,
89 89 'normal' : Colors.NoColor # color off (usu. Colors.Normal)
90 90 } )
91 91
92 92 LinuxColors = ColorScheme(
93 93 'Linux',{
94 94 'header' : Colors.LightRed,
95 95 'normal' : Colors.Normal # color off (usu. Colors.Normal)
96 96 } )
97 97
98 98 LightBGColors = ColorScheme(
99 99 'LightBG',{
100 100 'header' : Colors.Red,
101 101 'normal' : Colors.Normal # color off (usu. Colors.Normal)
102 102 } )
103 103
104 104 # Build table of color schemes (needed by the parser)
105 105 InspectColors = ColorSchemeTable([NoColor,LinuxColors,LightBGColors],
106 106 'Linux')
107 107
108 108 #****************************************************************************
109 109 # Auxiliary functions
110 110 def getdoc(obj):
111 111 """Stable wrapper around inspect.getdoc.
112 112
113 113 This can't crash because of attribute problems.
114 114
115 115 It also attempts to call a getdoc() method on the given object. This
116 116 allows objects which provide their docstrings via non-standard mechanisms
117 117 (like Pyro proxies) to still be inspected by ipython's ? system."""
118 118
119 119 ds = None # default return value
120 120 try:
121 121 ds = inspect.getdoc(obj)
122 122 except:
123 123 # Harden against an inspect failure, which can occur with
124 124 # SWIG-wrapped extensions.
125 125 pass
126 126 # Allow objects to offer customized documentation via a getdoc method:
127 127 try:
128 128 ds2 = obj.getdoc()
129 129 except:
130 130 pass
131 131 else:
132 132 # if we get extra info, we add it to the normal docstring.
133 133 if ds is None:
134 134 ds = ds2
135 135 else:
136 136 ds = '%s\n%s' % (ds,ds2)
137 137 return ds
138 138
139 139 def getsource(obj,is_binary=False):
140 140 """Wrapper around inspect.getsource.
141 141
142 142 This can be modified by other projects to provide customized source
143 143 extraction.
144 144
145 145 Inputs:
146 146
147 147 - obj: an object whose source code we will attempt to extract.
148 148
149 149 Optional inputs:
150 150
151 151 - is_binary: whether the object is known to come from a binary source.
152 152 This implementation will skip returning any output for binary objects, but
153 153 custom extractors may know how to meaningfully process them."""
154 154
155 155 if is_binary:
156 156 return None
157 157 else:
158 158 return inspect.getsource(obj)
159 159
160 160 #****************************************************************************
161 161 # Class definitions
162 162
163 163 class myStringIO(StringIO.StringIO):
164 164 """Adds a writeln method to normal StringIO."""
165 165 def writeln(self,*arg,**kw):
166 166 """Does a write() and then a write('\n')"""
167 167 self.write(*arg,**kw)
168 168 self.write('\n')
169 169
170 170 class Inspector:
171 171 def __init__(self,color_table,code_color_table,scheme,
172 172 str_detail_level=0):
173 173 self.color_table = color_table
174 174 self.parser = PyColorize.Parser(code_color_table,out='str')
175 175 self.format = self.parser.format
176 176 self.str_detail_level = str_detail_level
177 177 self.set_active_scheme(scheme)
178 178
179 179 def __getargspec(self,obj):
180 180 """Get the names and default values of a function's arguments.
181 181
182 182 A tuple of four things is returned: (args, varargs, varkw, defaults).
183 183 'args' is a list of the argument names (it may contain nested lists).
184 184 'varargs' and 'varkw' are the names of the * and ** arguments or None.
185 185 'defaults' is an n-tuple of the default values of the last n arguments.
186 186
187 187 Modified version of inspect.getargspec from the Python Standard
188 188 Library."""
189 189
190 190 if inspect.isfunction(obj):
191 191 func_obj = obj
192 192 elif inspect.ismethod(obj):
193 193 func_obj = obj.im_func
194 194 else:
195 195 raise TypeError, 'arg is not a Python function'
196 196 args, varargs, varkw = inspect.getargs(func_obj.func_code)
197 197 return args, varargs, varkw, func_obj.func_defaults
198 198
199 199 def __getdef(self,obj,oname=''):
200 200 """Return the definition header for any callable object.
201 201
202 202 If any exception is generated, None is returned instead and the
203 203 exception is suppressed."""
204 204
205 205 try:
206 206 return oname + inspect.formatargspec(*self.__getargspec(obj))
207 207 except:
208 208 return None
209 209
210 210 def __head(self,h):
211 211 """Return a header string with proper colors."""
212 212 return '%s%s%s' % (self.color_table.active_colors.header,h,
213 213 self.color_table.active_colors.normal)
214 214
215 215 def set_active_scheme(self,scheme):
216 216 self.color_table.set_active_scheme(scheme)
217 217 self.parser.color_table.set_active_scheme(scheme)
218 218
219 219 def noinfo(self,msg,oname):
220 220 """Generic message when no information is found."""
221 221 print 'No %s found' % msg,
222 222 if oname:
223 223 print 'for %s' % oname
224 224 else:
225 225 print
226 226
227 227 def pdef(self,obj,oname=''):
228 228 """Print the definition header for any callable object.
229 229
230 230 If the object is a class, print the constructor information."""
231 231
232 232 if not callable(obj):
233 233 print 'Object is not callable.'
234 234 return
235 235
236 236 header = ''
237 237
238 238 if inspect.isclass(obj):
239 239 header = self.__head('Class constructor information:\n')
240 240 obj = obj.__init__
241 241 elif type(obj) is types.InstanceType:
242 242 obj = obj.__call__
243 243
244 244 output = self.__getdef(obj,oname)
245 245 if output is None:
246 246 self.noinfo('definition header',oname)
247 247 else:
248 248 print >>Term.cout, header,self.format(output),
249 249
250 250 def pdoc(self,obj,oname='',formatter = None):
251 251 """Print the docstring for any object.
252 252
253 253 Optional:
254 254 -formatter: a function to run the docstring through for specially
255 255 formatted docstrings."""
256 256
257 257 head = self.__head # so that itpl can find it even if private
258 258 ds = getdoc(obj)
259 259 if formatter:
260 260 ds = formatter(ds)
261 261 if inspect.isclass(obj):
262 262 init_ds = getdoc(obj.__init__)
263 263 output = itpl('$head("Class Docstring:")\n'
264 264 '$indent(ds)\n'
265 265 '$head("Constructor Docstring"):\n'
266 266 '$indent(init_ds)')
267 267 elif (type(obj) is types.InstanceType or isinstance(obj,object)) \
268 268 and hasattr(obj,'__call__'):
269 269 call_ds = getdoc(obj.__call__)
270 270 if call_ds:
271 271 output = itpl('$head("Class Docstring:")\n$indent(ds)\n'
272 272 '$head("Calling Docstring:")\n$indent(call_ds)')
273 273 else:
274 274 output = ds
275 275 else:
276 276 output = ds
277 277 if output is None:
278 278 self.noinfo('documentation',oname)
279 279 return
280 280 page(output)
281 281
282 282 def psource(self,obj,oname=''):
283 283 """Print the source code for an object."""
284 284
285 285 # Flush the source cache because inspect can return out-of-date source
286 286 linecache.checkcache()
287 287 try:
288 288 src = getsource(obj)
289 289 except:
290 290 self.noinfo('source',oname)
291 291 else:
292 292 page(self.format(src))
293 293
294 294 def pfile(self,obj,oname=''):
295 295 """Show the whole file where an object was defined."""
296 296 try:
297 297 sourcelines,lineno = inspect.getsourcelines(obj)
298 298 except:
299 299 self.noinfo('file',oname)
300 300 else:
301 301 # run contents of file through pager starting at line
302 302 # where the object is defined
303 303 ofile = inspect.getabsfile(obj)
304 304
305 305 if (ofile.endswith('.so') or ofile.endswith('.dll')):
306 306 print 'File %r is binary, not printing.' % ofile
307 307 elif not os.path.isfile(ofile):
308 308 print 'File %r does not exist, not printing.' % ofile
309 309 else:
310 310 # Print only text files, not extension binaries.
311 311 page(self.format(open(ofile).read()),lineno)
312 312 #page(self.format(open(inspect.getabsfile(obj)).read()),lineno)
313 313
314 314 def pinfo(self,obj,oname='',formatter=None,info=None,detail_level=0):
315 315 """Show detailed information about an object.
316 316
317 317 Optional arguments:
318 318
319 319 - oname: name of the variable pointing to the object.
320 320
321 321 - formatter: special formatter for docstrings (see pdoc)
322 322
323 323 - info: a structure with some information fields which may have been
324 324 precomputed already.
325 325
326 326 - detail_level: if set to 1, more information is given.
327 327 """
328 328
329 329 obj_type = type(obj)
330 330
331 331 header = self.__head
332 332 if info is None:
333 333 ismagic = 0
334 334 isalias = 0
335 335 ospace = ''
336 336 else:
337 337 ismagic = info.ismagic
338 338 isalias = info.isalias
339 339 ospace = info.namespace
340 340 # Get docstring, special-casing aliases:
341 341 if isalias:
342 342 if not callable(obj):
343 343 try:
344 344 ds = "Alias to the system command:\n %s" % obj[1]
345 345 except:
346 346 ds = "Alias: " + str(obj)
347 347 else:
348 348 ds = "Alias to " + str(obj)
349 349 if obj.__doc__:
350 350 ds += "\nDocstring:\n" + obj.__doc__
351 351 else:
352 352 ds = getdoc(obj)
353 353 if ds is None:
354 354 ds = '<no docstring>'
355 355 if formatter is not None:
356 356 ds = formatter(ds)
357 357
358 358 # store output in a list which gets joined with \n at the end.
359 359 out = myStringIO()
360 360
361 361 string_max = 200 # max size of strings to show (snipped if longer)
362 362 shalf = int((string_max -5)/2)
363 363
364 364 if ismagic:
365 365 obj_type_name = 'Magic function'
366 366 elif isalias:
367 367 obj_type_name = 'System alias'
368 368 else:
369 369 obj_type_name = obj_type.__name__
370 370 out.writeln(header('Type:\t\t')+obj_type_name)
371 371
372 372 try:
373 373 bclass = obj.__class__
374 374 out.writeln(header('Base Class:\t')+str(bclass))
375 375 except: pass
376 376
377 377 # String form, but snip if too long in ? form (full in ??)
378 378 if detail_level >= self.str_detail_level:
379 379 try:
380 380 ostr = str(obj)
381 381 str_head = 'String Form:'
382 382 if not detail_level and len(ostr)>string_max:
383 383 ostr = ostr[:shalf] + ' <...> ' + ostr[-shalf:]
384 384 ostr = ("\n" + " " * len(str_head.expandtabs())).\
385 385 join(map(string.strip,ostr.split("\n")))
386 386 if ostr.find('\n') > -1:
387 387 # Print multi-line strings starting at the next line.
388 388 str_sep = '\n'
389 389 else:
390 390 str_sep = '\t'
391 391 out.writeln("%s%s%s" % (header(str_head),str_sep,ostr))
392 392 except:
393 393 pass
394 394
395 395 if ospace:
396 396 out.writeln(header('Namespace:\t')+ospace)
397 397
398 398 # Length (for strings and lists)
399 399 try:
400 400 length = str(len(obj))
401 401 out.writeln(header('Length:\t\t')+length)
402 402 except: pass
403 403
404 404 # Filename where object was defined
405 405 binary_file = False
406 406 try:
407 fname = inspect.getabsfile(obj)
407 try:
408 fname = inspect.getabsfile(obj)
409 except TypeError:
410 # For an instance, the file that matters is where its class was
411 # declared.
412 if hasattr(obj,'__class__'):
413 fname = inspect.getabsfile(obj.__class__)
408 414 if fname.endswith('<string>'):
409 415 fname = 'Dynamically generated function. No source code available.'
410 416 if (fname.endswith('.so') or fname.endswith('.dll')):
411 417 binary_file = True
412 418 out.writeln(header('File:\t\t')+fname)
413 419 except:
414 420 # if anything goes wrong, we don't want to show source, so it's as
415 421 # if the file was binary
416 422 binary_file = True
417 423
418 424 # reconstruct the function definition and print it:
419 425 defln = self.__getdef(obj,oname)
420 426 if defln:
421 427 out.write(header('Definition:\t')+self.format(defln))
422 428
423 429 # Docstrings only in detail 0 mode, since source contains them (we
424 430 # avoid repetitions). If source fails, we add them back, see below.
425 431 if ds and detail_level == 0:
426 432 out.writeln(header('Docstring:\n') + indent(ds))
427 433
428 434 # Original source code for any callable
429 435 if detail_level:
430 436 # Flush the source cache because inspect can return out-of-date
431 437 # source
432 438 linecache.checkcache()
433 439 source_success = False
434 440 try:
435 source = self.format(getsource(obj,binary_file))
436 if source:
441 try:
442 src = getsource(obj,binary_file)
443 except TypeError:
444 if hasattr(obj,'__class__'):
445 src = getsource(obj.__class__,binary_file)
446 if src is not None:
447 source = self.format(src)
437 448 out.write(header('Source:\n')+source.rstrip())
438 449 source_success = True
439 450 except Exception, msg:
440 451 pass
441 452
442 453 if ds and not source_success:
443 454 out.writeln(header('Docstring [source file open failed]:\n')
444 455 + indent(ds))
445 456
446 457 # Constructor docstring for classes
447 458 if inspect.isclass(obj):
448 459 # reconstruct the function definition and print it:
449 460 try:
450 461 obj_init = obj.__init__
451 462 except AttributeError:
452 463 init_def = init_ds = None
453 464 else:
454 465 init_def = self.__getdef(obj_init,oname)
455 466 init_ds = getdoc(obj_init)
456 467 # Skip Python's auto-generated docstrings
457 468 if init_ds and \
458 469 init_ds.startswith('x.__init__(...) initializes'):
459 470 init_ds = None
460 471
461 472 if init_def or init_ds:
462 473 out.writeln(header('\nConstructor information:'))
463 474 if init_def:
464 475 out.write(header('Definition:\t')+ self.format(init_def))
465 476 if init_ds:
466 477 out.writeln(header('Docstring:\n') + indent(init_ds))
467 478 # and class docstring for instances:
468 479 elif obj_type is types.InstanceType or \
469 480 isinstance(obj,object):
470 481
471 482 # First, check whether the instance docstring is identical to the
472 483 # class one, and print it separately if they don't coincide. In
473 484 # most cases they will, but it's nice to print all the info for
474 485 # objects which use instance-customized docstrings.
475 486 if ds:
476 487 try:
477 488 cls = getattr(obj,'__class__')
478 489 except:
479 490 class_ds = None
480 491 else:
481 492 class_ds = getdoc(cls)
482 493 # Skip Python's auto-generated docstrings
483 494 if class_ds and \
484 495 (class_ds.startswith('function(code, globals[,') or \
485 496 class_ds.startswith('instancemethod(function, instance,') or \
486 497 class_ds.startswith('module(name[,') ):
487 498 class_ds = None
488 499 if class_ds and ds != class_ds:
489 500 out.writeln(header('Class Docstring:\n') +
490 501 indent(class_ds))
491 502
492 503 # Next, try to show constructor docstrings
493 504 try:
494 505 init_ds = getdoc(obj.__init__)
495 506 # Skip Python's auto-generated docstrings
496 507 if init_ds and \
497 508 init_ds.startswith('x.__init__(...) initializes'):
498 509 init_ds = None
499 510 except AttributeError:
500 511 init_ds = None
501 512 if init_ds:
502 513 out.writeln(header('Constructor Docstring:\n') +
503 514 indent(init_ds))
504 515
505 516 # Call form docstring for callable instances
506 517 if hasattr(obj,'__call__'):
507 518 #out.writeln(header('Callable:\t')+'Yes')
508 519 call_def = self.__getdef(obj.__call__,oname)
509 520 #if call_def is None:
510 521 # out.writeln(header('Call def:\t')+
511 522 # 'Calling definition not available.')
512 523 if call_def is not None:
513 524 out.writeln(header('Call def:\t')+self.format(call_def))
514 525 call_ds = getdoc(obj.__call__)
515 526 # Skip Python's auto-generated docstrings
516 527 if call_ds and call_ds.startswith('x.__call__(...) <==> x(...)'):
517 528 call_ds = None
518 529 if call_ds:
519 530 out.writeln(header('Call docstring:\n') + indent(call_ds))
520 531
521 532 # Finally send to printer/pager
522 533 output = out.getvalue()
523 534 if output:
524 535 page(output)
525 536 # end pinfo
526 537
527 538 def psearch(self,pattern,ns_table,ns_search=[],
528 539 ignore_case=False,show_all=False):
529 540 """Search namespaces with wildcards for objects.
530 541
531 542 Arguments:
532 543
533 544 - pattern: string containing shell-like wildcards to use in namespace
534 545 searches and optionally a type specification to narrow the search to
535 546 objects of that type.
536 547
537 548 - ns_table: dict of name->namespaces for search.
538 549
539 550 Optional arguments:
540 551
541 552 - ns_search: list of namespace names to include in search.
542 553
543 554 - ignore_case(False): make the search case-insensitive.
544 555
545 556 - show_all(False): show all names, including those starting with
546 557 underscores.
547 558 """
548 559 #print 'ps pattern:<%r>' % pattern # dbg
549 560
550 561 # defaults
551 562 type_pattern = 'all'
552 563 filter = ''
553 564
554 565 cmds = pattern.split()
555 566 len_cmds = len(cmds)
556 567 if len_cmds == 1:
557 568 # Only filter pattern given
558 569 filter = cmds[0]
559 570 elif len_cmds == 2:
560 571 # Both filter and type specified
561 572 filter,type_pattern = cmds
562 573 else:
563 574 raise ValueError('invalid argument string for psearch: <%s>' %
564 575 pattern)
565 576
566 577 # filter search namespaces
567 578 for name in ns_search:
568 579 if name not in ns_table:
569 580 raise ValueError('invalid namespace <%s>. Valid names: %s' %
570 581 (name,ns_table.keys()))
571 582
572 583 #print 'type_pattern:',type_pattern # dbg
573 584 search_result = []
574 585 for ns_name in ns_search:
575 586 ns = ns_table[ns_name]
576 587 tmp_res = list(list_namespace(ns,type_pattern,filter,
577 588 ignore_case=ignore_case,
578 589 show_all=show_all))
579 590 search_result.extend(tmp_res)
580 591 search_result.sort()
581 592
582 593 page('\n'.join(search_result))
@@ -1,83 +1,89 b''
1 1 # -*- coding: utf-8 -*-
2 2 """Release data for the IPython project.
3 3
4 4 $Id: Release.py 3002 2008-02-01 07:17:00Z fperez $"""
5 5
6 6 #*****************************************************************************
7 7 # Copyright (C) 2001-2006 Fernando Perez <fperez@colorado.edu>
8 8 #
9 9 # Copyright (c) 2001 Janko Hauser <jhauser@zscout.de> and Nathaniel Gray
10 10 # <n8gray@caltech.edu>
11 11 #
12 12 # Distributed under the terms of the BSD License. The full license is in
13 13 # the file COPYING, distributed as part of this software.
14 14 #*****************************************************************************
15 15
16 16 # Name of the package for release purposes. This is the name which labels
17 17 # the tarballs and RPMs made by distutils, so it's best to lowercase it.
18 18 name = 'ipython'
19 19
20 20 # For versions with substrings (like 0.6.16.svn), use an extra . to separate
21 21 # the new substring. We have to avoid using either dashes or underscores,
22 22 # because bdist_rpm does not accept dashes (an RPM) convention, and
23 23 # bdist_deb does not accept underscores (a Debian convention).
24 24
25 revision = '3001'
25 revision = '128'
26 branch = 'ipython'
26 27
27 version = '0.8.3.svn.r' + revision.rstrip('M')
28 if branch == 'ipython':
29 version = '0.8.4.bzr.r' + revision
30 else:
31 version = '0.8.4.bzr.r%s.%s' % (revision,branch)
32
33 version = '0.8.4'
28 34
29 35 description = "An enhanced interactive Python shell."
30 36
31 37 long_description = \
32 38 """
33 39 IPython provides a replacement for the interactive Python interpreter with
34 40 extra functionality.
35 41
36 42 Main features:
37 43
38 44 * Comprehensive object introspection.
39 45
40 46 * Input history, persistent across sessions.
41 47
42 48 * Caching of output results during a session with automatically generated
43 49 references.
44 50
45 51 * Readline based name completion.
46 52
47 53 * Extensible system of 'magic' commands for controlling the environment and
48 54 performing many tasks related either to IPython or the operating system.
49 55
50 56 * Configuration system with easy switching between different setups (simpler
51 57 than changing $PYTHONSTARTUP environment variables every time).
52 58
53 59 * Session logging and reloading.
54 60
55 61 * Extensible syntax processing for special purpose situations.
56 62
57 63 * Access to the system shell with user-extensible alias system.
58 64
59 65 * Easily embeddable in other Python programs.
60 66
61 67 * Integrated access to the pdb debugger and the Python profiler.
62 68
63 69 The latest development version is always available at the IPython subversion
64 70 repository_.
65 71
66 72 .. _repository: http://ipython.scipy.org/svn/ipython/ipython/trunk#egg=ipython-dev
67 73 """
68 74
69 75 license = 'BSD'
70 76
71 77 authors = {'Fernando' : ('Fernando Perez','fperez@colorado.edu'),
72 78 'Janko' : ('Janko Hauser','jhauser@zscout.de'),
73 79 'Nathan' : ('Nathaniel Gray','n8gray@caltech.edu'),
74 80 'Ville' : ('Ville Vainio','vivainio@gmail.com')
75 81 }
76 82
77 83 url = 'http://ipython.scipy.org'
78 84
79 85 download_url = 'http://ipython.scipy.org/dist'
80 86
81 87 platforms = ['Linux','Mac OSX','Windows XP/2000/NT','Windows 95/98/ME']
82 88
83 89 keywords = ['Interactive','Interpreter','Shell']
@@ -1,1205 +1,1225 b''
1 1 # -*- coding: utf-8 -*-
2 2 """IPython Shell classes.
3 3
4 4 All the matplotlib support code was co-developed with John Hunter,
5 5 matplotlib's author.
6 6
7 7 $Id: Shell.py 3024 2008-02-07 15:34:42Z darren.dale $"""
8 8
9 9 #*****************************************************************************
10 10 # Copyright (C) 2001-2006 Fernando Perez <fperez@colorado.edu>
11 11 #
12 12 # Distributed under the terms of the BSD License. The full license is in
13 13 # the file COPYING, distributed as part of this software.
14 14 #*****************************************************************************
15 15
16 16 from IPython import Release
17 17 __author__ = '%s <%s>' % Release.authors['Fernando']
18 18 __license__ = Release.license
19 19
20 20 # Code begins
21 21 # Stdlib imports
22 22 import __builtin__
23 23 import __main__
24 24 import Queue
25 25 import inspect
26 26 import os
27 27 import sys
28 28 import thread
29 29 import threading
30 30 import time
31 31
32 32 from signal import signal, SIGINT
33 33
34 34 try:
35 35 import ctypes
36 36 HAS_CTYPES = True
37 37 except ImportError:
38 38 HAS_CTYPES = False
39 39
40 40 # IPython imports
41 41 import IPython
42 42 from IPython import ultraTB, ipapi
43 43 from IPython.genutils import Term,warn,error,flag_calls, ask_yes_no
44 44 from IPython.iplib import InteractiveShell
45 45 from IPython.ipmaker import make_IPython
46 46 from IPython.Magic import Magic
47 47 from IPython.ipstruct import Struct
48 48
49 try: # Python 2.3 compatibility
50 set
51 except NameError:
52 import sets
53 set = sets.Set
54
55
49 56 # Globals
50 57 # global flag to pass around information about Ctrl-C without exceptions
51 58 KBINT = False
52 59
53 60 # global flag to turn on/off Tk support.
54 61 USE_TK = False
55 62
56 63 # ID for the main thread, used for cross-thread exceptions
57 64 MAIN_THREAD_ID = thread.get_ident()
58 65
59 66 # Tag when runcode() is active, for exception handling
60 67 CODE_RUN = None
61 68
62 69 #-----------------------------------------------------------------------------
63 70 # This class is trivial now, but I want to have it in to publish a clean
64 71 # interface. Later when the internals are reorganized, code that uses this
65 72 # shouldn't have to change.
66 73
67 74 class IPShell:
68 75 """Create an IPython instance."""
69 76
70 77 def __init__(self,argv=None,user_ns=None,user_global_ns=None,
71 78 debug=1,shell_class=InteractiveShell):
72 79 self.IP = make_IPython(argv,user_ns=user_ns,
73 80 user_global_ns=user_global_ns,
74 81 debug=debug,shell_class=shell_class)
75 82
76 83 def mainloop(self,sys_exit=0,banner=None):
77 84 self.IP.mainloop(banner)
78 85 if sys_exit:
79 86 sys.exit()
80 87
81 88 #-----------------------------------------------------------------------------
82 89 def kill_embedded(self,parameter_s=''):
83 90 """%kill_embedded : deactivate for good the current embedded IPython.
84 91
85 92 This function (after asking for confirmation) sets an internal flag so that
86 93 an embedded IPython will never activate again. This is useful to
87 94 permanently disable a shell that is being called inside a loop: once you've
88 95 figured out what you needed from it, you may then kill it and the program
89 96 will then continue to run without the interactive shell interfering again.
90 97 """
91 98
92 99 kill = ask_yes_no("Are you sure you want to kill this embedded instance "
93 100 "(y/n)? [y/N] ",'n')
94 101 if kill:
95 102 self.shell.embedded_active = False
96 103 print "This embedded IPython will not reactivate anymore once you exit."
97 104
98 105 class IPShellEmbed:
99 106 """Allow embedding an IPython shell into a running program.
100 107
101 108 Instances of this class are callable, with the __call__ method being an
102 109 alias to the embed() method of an InteractiveShell instance.
103 110
104 111 Usage (see also the example-embed.py file for a running example):
105 112
106 113 ipshell = IPShellEmbed([argv,banner,exit_msg,rc_override])
107 114
108 115 - argv: list containing valid command-line options for IPython, as they
109 116 would appear in sys.argv[1:].
110 117
111 118 For example, the following command-line options:
112 119
113 120 $ ipython -prompt_in1 'Input <\\#>' -colors LightBG
114 121
115 122 would be passed in the argv list as:
116 123
117 124 ['-prompt_in1','Input <\\#>','-colors','LightBG']
118 125
119 126 - banner: string which gets printed every time the interpreter starts.
120 127
121 128 - exit_msg: string which gets printed every time the interpreter exits.
122 129
123 130 - rc_override: a dict or Struct of configuration options such as those
124 131 used by IPython. These options are read from your ~/.ipython/ipythonrc
125 132 file when the Shell object is created. Passing an explicit rc_override
126 133 dict with any options you want allows you to override those values at
127 134 creation time without having to modify the file. This way you can create
128 135 embeddable instances configured in any way you want without editing any
129 136 global files (thus keeping your interactive IPython configuration
130 137 unchanged).
131 138
132 139 Then the ipshell instance can be called anywhere inside your code:
133 140
134 141 ipshell(header='') -> Opens up an IPython shell.
135 142
136 143 - header: string printed by the IPython shell upon startup. This can let
137 144 you know where in your code you are when dropping into the shell. Note
138 145 that 'banner' gets prepended to all calls, so header is used for
139 146 location-specific information.
140 147
141 148 For more details, see the __call__ method below.
142 149
143 150 When the IPython shell is exited with Ctrl-D, normal program execution
144 151 resumes.
145 152
146 153 This functionality was inspired by a posting on comp.lang.python by cmkl
147 154 <cmkleffner@gmx.de> on Dec. 06/01 concerning similar uses of pyrepl, and
148 155 by the IDL stop/continue commands."""
149 156
150 157 def __init__(self,argv=None,banner='',exit_msg=None,rc_override=None,
151 158 user_ns=None):
152 159 """Note that argv here is a string, NOT a list."""
153 160 self.set_banner(banner)
154 161 self.set_exit_msg(exit_msg)
155 162 self.set_dummy_mode(0)
156 163
157 164 # sys.displayhook is a global, we need to save the user's original
158 165 # Don't rely on __displayhook__, as the user may have changed that.
159 166 self.sys_displayhook_ori = sys.displayhook
160 167
161 168 # save readline completer status
162 169 try:
163 170 #print 'Save completer',sys.ipcompleter # dbg
164 171 self.sys_ipcompleter_ori = sys.ipcompleter
165 172 except:
166 173 pass # not nested with IPython
167 174
168 175 self.IP = make_IPython(argv,rc_override=rc_override,
169 176 embedded=True,
170 177 user_ns=user_ns)
171 178
172 179 ip = ipapi.IPApi(self.IP)
173 180 ip.expose_magic("kill_embedded",kill_embedded)
174 181
175 182 # copy our own displayhook also
176 183 self.sys_displayhook_embed = sys.displayhook
177 184 # and leave the system's display hook clean
178 185 sys.displayhook = self.sys_displayhook_ori
179 186 # don't use the ipython crash handler so that user exceptions aren't
180 187 # trapped
181 188 sys.excepthook = ultraTB.FormattedTB(color_scheme = self.IP.rc.colors,
182 189 mode = self.IP.rc.xmode,
183 190 call_pdb = self.IP.rc.pdb)
184 191 self.restore_system_completer()
185 192
186 193 def restore_system_completer(self):
187 194 """Restores the readline completer which was in place.
188 195
189 196 This allows embedded IPython within IPython not to disrupt the
190 197 parent's completion.
191 198 """
192 199
193 200 try:
194 201 self.IP.readline.set_completer(self.sys_ipcompleter_ori)
195 202 sys.ipcompleter = self.sys_ipcompleter_ori
196 203 except:
197 204 pass
198 205
199 206 def __call__(self,header='',local_ns=None,global_ns=None,dummy=None):
200 207 """Activate the interactive interpreter.
201 208
202 209 __call__(self,header='',local_ns=None,global_ns,dummy=None) -> Start
203 210 the interpreter shell with the given local and global namespaces, and
204 211 optionally print a header string at startup.
205 212
206 213 The shell can be globally activated/deactivated using the
207 214 set/get_dummy_mode methods. This allows you to turn off a shell used
208 215 for debugging globally.
209 216
210 217 However, *each* time you call the shell you can override the current
211 218 state of dummy_mode with the optional keyword parameter 'dummy'. For
212 219 example, if you set dummy mode on with IPShell.set_dummy_mode(1), you
213 220 can still have a specific call work by making it as IPShell(dummy=0).
214 221
215 222 The optional keyword parameter dummy controls whether the call
216 223 actually does anything. """
217 224
218 225 # If the user has turned it off, go away
219 226 if not self.IP.embedded_active:
220 227 return
221 228
222 229 # Normal exits from interactive mode set this flag, so the shell can't
223 230 # re-enter (it checks this variable at the start of interactive mode).
224 231 self.IP.exit_now = False
225 232
226 233 # Allow the dummy parameter to override the global __dummy_mode
227 234 if dummy or (dummy != 0 and self.__dummy_mode):
228 235 return
229 236
230 237 # Set global subsystems (display,completions) to our values
231 238 sys.displayhook = self.sys_displayhook_embed
232 239 if self.IP.has_readline:
233 240 self.IP.set_completer()
234 241
235 242 if self.banner and header:
236 243 format = '%s\n%s\n'
237 244 else:
238 245 format = '%s%s\n'
239 246 banner = format % (self.banner,header)
240 247
241 248 # Call the embedding code with a stack depth of 1 so it can skip over
242 249 # our call and get the original caller's namespaces.
243 250 self.IP.embed_mainloop(banner,local_ns,global_ns,stack_depth=1)
244 251
245 252 if self.exit_msg:
246 253 print self.exit_msg
247 254
248 255 # Restore global systems (display, completion)
249 256 sys.displayhook = self.sys_displayhook_ori
250 257 self.restore_system_completer()
251 258
252 259 def set_dummy_mode(self,dummy):
253 260 """Sets the embeddable shell's dummy mode parameter.
254 261
255 262 set_dummy_mode(dummy): dummy = 0 or 1.
256 263
257 264 This parameter is persistent and makes calls to the embeddable shell
258 265 silently return without performing any action. This allows you to
259 266 globally activate or deactivate a shell you're using with a single call.
260 267
261 268 If you need to manually"""
262 269
263 270 if dummy not in [0,1,False,True]:
264 271 raise ValueError,'dummy parameter must be boolean'
265 272 self.__dummy_mode = dummy
266 273
267 274 def get_dummy_mode(self):
268 275 """Return the current value of the dummy mode parameter.
269 276 """
270 277 return self.__dummy_mode
271 278
272 279 def set_banner(self,banner):
273 280 """Sets the global banner.
274 281
275 282 This banner gets prepended to every header printed when the shell
276 283 instance is called."""
277 284
278 285 self.banner = banner
279 286
280 287 def set_exit_msg(self,exit_msg):
281 288 """Sets the global exit_msg.
282 289
283 290 This exit message gets printed upon exiting every time the embedded
284 291 shell is called. It is None by default. """
285 292
286 293 self.exit_msg = exit_msg
287 294
288 295 #-----------------------------------------------------------------------------
289 296 if HAS_CTYPES:
290 297 # Add async exception support. Trick taken from:
291 298 # http://sebulba.wikispaces.com/recipe+thread2
292 299 def _async_raise(tid, exctype):
293 300 """raises the exception, performs cleanup if needed"""
294 301 if not inspect.isclass(exctype):
295 302 raise TypeError("Only types can be raised (not instances)")
296 303 res = ctypes.pythonapi.PyThreadState_SetAsyncExc(tid,
297 304 ctypes.py_object(exctype))
298 305 if res == 0:
299 306 raise ValueError("invalid thread id")
300 307 elif res != 1:
301 308 # """if it returns a number greater than one, you're in trouble,
302 309 # and you should call it again with exc=NULL to revert the effect"""
303 310 ctypes.pythonapi.PyThreadState_SetAsyncExc(tid, 0)
304 311 raise SystemError("PyThreadState_SetAsyncExc failed")
305 312
306 313 def sigint_handler (signum,stack_frame):
307 314 """Sigint handler for threaded apps.
308 315
309 316 This is a horrible hack to pass information about SIGINT _without_
310 317 using exceptions, since I haven't been able to properly manage
311 318 cross-thread exceptions in GTK/WX. In fact, I don't think it can be
312 319 done (or at least that's my understanding from a c.l.py thread where
313 320 this was discussed)."""
314 321
315 322 global KBINT
316 323
317 324 if CODE_RUN:
318 325 _async_raise(MAIN_THREAD_ID,KeyboardInterrupt)
319 326 else:
320 327 KBINT = True
321 328 print '\nKeyboardInterrupt - Press <Enter> to continue.',
322 329 Term.cout.flush()
323 330
324 331 else:
325 332 def sigint_handler (signum,stack_frame):
326 333 """Sigint handler for threaded apps.
327 334
328 335 This is a horrible hack to pass information about SIGINT _without_
329 336 using exceptions, since I haven't been able to properly manage
330 337 cross-thread exceptions in GTK/WX. In fact, I don't think it can be
331 338 done (or at least that's my understanding from a c.l.py thread where
332 339 this was discussed)."""
333 340
334 341 global KBINT
335 342
336 343 print '\nKeyboardInterrupt - Press <Enter> to continue.',
337 344 Term.cout.flush()
338 345 # Set global flag so that runsource can know that Ctrl-C was hit
339 346 KBINT = True
340 347
341 348
342 349 class MTInteractiveShell(InteractiveShell):
343 350 """Simple multi-threaded shell."""
344 351
345 352 # Threading strategy taken from:
346 353 # http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/65109, by Brian
347 354 # McErlean and John Finlay. Modified with corrections by Antoon Pardon,
348 355 # from the pygtk mailing list, to avoid lockups with system calls.
349 356
350 357 # class attribute to indicate whether the class supports threads or not.
351 358 # Subclasses with thread support should override this as needed.
352 359 isthreaded = True
353 360
354 361 def __init__(self,name,usage=None,rc=Struct(opts=None,args=None),
355 362 user_ns=None,user_global_ns=None,banner2='',**kw):
356 363 """Similar to the normal InteractiveShell, but with threading control"""
357 364
358 365 InteractiveShell.__init__(self,name,usage,rc,user_ns,
359 366 user_global_ns,banner2)
360 367
361 # Locking control variable.
362 self.thread_ready = threading.Condition(threading.RLock())
363 368
364 # A queue to hold the code to be executed. A scalar variable is NOT
365 # enough, because uses like macros cause reentrancy.
369 # A queue to hold the code to be executed.
366 370 self.code_queue = Queue.Queue()
367 371
368 372 # Stuff to do at closing time
369 self._kill = False
370 on_kill = kw.get('on_kill')
371 if on_kill is None:
372 on_kill = []
373 self._kill = None
374 on_kill = kw.get('on_kill', [])
373 375 # Check that all things to kill are callable:
374 376 for t in on_kill:
375 377 if not callable(t):
376 378 raise TypeError,'on_kill must be a list of callables'
377 379 self.on_kill = on_kill
378
380 # thread identity of the "worker thread" (that may execute code directly)
381 self.worker_ident = None
382
379 383 def runsource(self, source, filename="<input>", symbol="single"):
380 384 """Compile and run some source in the interpreter.
381 385
382 386 Modified version of code.py's runsource(), to handle threading issues.
383 387 See the original for full docstring details."""
384
388
385 389 global KBINT
386 390
387 391 # If Ctrl-C was typed, we reset the flag and return right away
388 392 if KBINT:
389 393 KBINT = False
390 394 return False
395
396 if self._kill:
397 # can't queue new code if we are being killed
398 return True
391 399
392 400 try:
393 401 code = self.compile(source, filename, symbol)
394 402 except (OverflowError, SyntaxError, ValueError):
395 403 # Case 1
396 404 self.showsyntaxerror(filename)
397 405 return False
398 406
399 407 if code is None:
400 408 # Case 2
401 409 return True
402 410
411 # shortcut - if we are in worker thread, or the worker thread is not running,
412 # execute directly (to allow recursion and prevent deadlock if code is run early
413 # in IPython construction)
414
415 if (self.worker_ident is None or self.worker_ident == thread.get_ident()):
416 InteractiveShell.runcode(self,code)
417 return
418
403 419 # Case 3
404 420 # Store code in queue, so the execution thread can handle it.
405 421
406 # Note that with macros and other applications, we MAY re-enter this
407 # section, so we have to acquire the lock with non-blocking semantics,
408 # else we deadlock.
409 got_lock = self.thread_ready.acquire()
410 self.code_queue.put(code)
411 if got_lock:
412 self.thread_ready.wait() # Wait until processed in timeout interval
413 self.thread_ready.release()
414
422 completed_ev, received_ev = threading.Event(), threading.Event()
423
424 self.code_queue.put((code,completed_ev, received_ev))
425 # first make sure the message was received, with timeout
426 received_ev.wait(5)
427 if not received_ev.isSet():
428 # the mainloop is dead, start executing code directly
429 print "Warning: Timeout for mainloop thread exceeded"
430 print "switching to nonthreaded mode (until mainloop wakes up again)"
431 self.worker_ident = None
432 else:
433 completed_ev.wait()
415 434 return False
416 435
417 436 def runcode(self):
418 437 """Execute a code object.
419 438
420 439 Multithreaded wrapper around IPython's runcode()."""
421
440
422 441 global CODE_RUN
423
424 # lock thread-protected stuff
425 got_lock = self.thread_ready.acquire()
442
443 # we are in worker thread, stash out the id for runsource()
444 self.worker_ident = thread.get_ident()
426 445
427 446 if self._kill:
428 447 print >>Term.cout, 'Closing threads...',
429 448 Term.cout.flush()
430 449 for tokill in self.on_kill:
431 450 tokill()
432 451 print >>Term.cout, 'Done.'
452 # allow kill() to return
453 self._kill.set()
454 return True
433 455
434 456 # Install sigint handler. We do it every time to ensure that if user
435 457 # code modifies it, we restore our own handling.
436 458 try:
437 459 signal(SIGINT,sigint_handler)
438 460 except SystemError:
439 461 # This happens under Windows, which seems to have all sorts
440 462 # of problems with signal handling. Oh well...
441 463 pass
442 464
443 465 # Flush queue of pending code by calling the run methood of the parent
444 466 # class with all items which may be in the queue.
445 467 code_to_run = None
446 468 while 1:
447 469 try:
448 code_to_run = self.code_queue.get_nowait()
470 code_to_run, completed_ev, received_ev = self.code_queue.get_nowait()
449 471 except Queue.Empty:
450 472 break
451
473 received_ev.set()
474
452 475 # Exceptions need to be raised differently depending on which
453 476 # thread is active. This convoluted try/except is only there to
454 477 # protect against asynchronous exceptions, to ensure that a KBINT
455 478 # at the wrong time doesn't deadlock everything. The global
456 479 # CODE_TO_RUN is set to true/false as close as possible to the
457 480 # runcode() call, so that the KBINT handler is correctly informed.
458 481 try:
459 482 try:
460 483 CODE_RUN = True
461 484 InteractiveShell.runcode(self,code_to_run)
462 485 except KeyboardInterrupt:
463 486 print "Keyboard interrupted in mainloop"
464 487 while not self.code_queue.empty():
465 self.code_queue.get_nowait()
488 code, ev1,ev2 = self.code_queue.get_nowait()
489 ev1.set()
490 ev2.set()
466 491 break
467 492 finally:
468 if got_lock:
469 CODE_RUN = False
470
471 # We're done with thread-protected variables
472 if code_to_run is not None:
473 self.thread_ready.notify()
474 self.thread_ready.release()
475
476 # We're done...
477 CODE_RUN = False
493 CODE_RUN = False
494 # allow runsource() return from wait
495 completed_ev.set()
496
497
478 498 # This MUST return true for gtk threading to work
479 499 return True
480 500
481 501 def kill(self):
482 502 """Kill the thread, returning when it has been shut down."""
483 got_lock = self.thread_ready.acquire(False)
484 self._kill = True
485 if got_lock:
486 self.thread_ready.release()
503 self._kill = threading.Event()
504 self._kill.wait()
487 505
488 506 class MatplotlibShellBase:
489 507 """Mixin class to provide the necessary modifications to regular IPython
490 508 shell classes for matplotlib support.
491 509
492 510 Given Python's MRO, this should be used as the FIRST class in the
493 511 inheritance hierarchy, so that it overrides the relevant methods."""
494 512
495 513 def _matplotlib_config(self,name,user_ns):
496 514 """Return items needed to setup the user's shell with matplotlib"""
497 515
498 516 # Initialize matplotlib to interactive mode always
499 517 import matplotlib
500 518 from matplotlib import backends
501 519 matplotlib.interactive(True)
502 520
503 521 def use(arg):
504 522 """IPython wrapper for matplotlib's backend switcher.
505 523
506 524 In interactive use, we can not allow switching to a different
507 525 interactive backend, since thread conflicts will most likely crash
508 526 the python interpreter. This routine does a safety check first,
509 527 and refuses to perform a dangerous switch. It still allows
510 528 switching to non-interactive backends."""
511 529
512 530 if arg in backends.interactive_bk and arg != self.mpl_backend:
513 531 m=('invalid matplotlib backend switch.\n'
514 532 'This script attempted to switch to the interactive '
515 533 'backend: `%s`\n'
516 534 'Your current choice of interactive backend is: `%s`\n\n'
517 535 'Switching interactive matplotlib backends at runtime\n'
518 536 'would crash the python interpreter, '
519 537 'and IPython has blocked it.\n\n'
520 538 'You need to either change your choice of matplotlib backend\n'
521 539 'by editing your .matplotlibrc file, or run this script as a \n'
522 540 'standalone file from the command line, not using IPython.\n' %
523 541 (arg,self.mpl_backend) )
524 542 raise RuntimeError, m
525 543 else:
526 544 self.mpl_use(arg)
527 545 self.mpl_use._called = True
528 546
529 547 self.matplotlib = matplotlib
530 548 self.mpl_backend = matplotlib.rcParams['backend']
531 549
532 550 # we also need to block switching of interactive backends by use()
533 551 self.mpl_use = matplotlib.use
534 552 self.mpl_use._called = False
535 553 # overwrite the original matplotlib.use with our wrapper
536 554 matplotlib.use = use
537 555
538 556 # This must be imported last in the matplotlib series, after
539 557 # backend/interactivity choices have been made
540 558 import matplotlib.pylab as pylab
541 559 self.pylab = pylab
542 560
543 561 self.pylab.show._needmain = False
544 562 # We need to detect at runtime whether show() is called by the user.
545 563 # For this, we wrap it into a decorator which adds a 'called' flag.
546 564 self.pylab.draw_if_interactive = flag_calls(self.pylab.draw_if_interactive)
547 565
548 566 # Build a user namespace initialized with matplotlib/matlab features.
549 567 user_ns = IPython.ipapi.make_user_ns(user_ns)
550 568
551 569 exec ("import matplotlib\n"
552 570 "import matplotlib.pylab as pylab\n") in user_ns
553 571
554 572 # Build matplotlib info banner
555 573 b="""
556 574 Welcome to pylab, a matplotlib-based Python environment.
557 575 For more information, type 'help(pylab)'.
558 576 """
559 577 return user_ns,b
560 578
561 579 def mplot_exec(self,fname,*where,**kw):
562 580 """Execute a matplotlib script.
563 581
564 582 This is a call to execfile(), but wrapped in safeties to properly
565 583 handle interactive rendering and backend switching."""
566 584
567 585 #print '*** Matplotlib runner ***' # dbg
568 586 # turn off rendering until end of script
569 587 isInteractive = self.matplotlib.rcParams['interactive']
570 588 self.matplotlib.interactive(False)
571 589 self.safe_execfile(fname,*where,**kw)
572 590 self.matplotlib.interactive(isInteractive)
573 591 # make rendering call now, if the user tried to do it
574 592 if self.pylab.draw_if_interactive.called:
575 593 self.pylab.draw()
576 594 self.pylab.draw_if_interactive.called = False
577 595
578 596 # if a backend switch was performed, reverse it now
579 597 if self.mpl_use._called:
580 598 self.matplotlib.rcParams['backend'] = self.mpl_backend
581 599
582 600 def magic_run(self,parameter_s=''):
583 601 Magic.magic_run(self,parameter_s,runner=self.mplot_exec)
584 602
585 603 # Fix the docstring so users see the original as well
586 604 magic_run.__doc__ = "%s\n%s" % (Magic.magic_run.__doc__,
587 605 "\n *** Modified %run for Matplotlib,"
588 606 " with proper interactive handling ***")
589 607
590 608 # Now we provide 2 versions of a matplotlib-aware IPython base shells, single
591 609 # and multithreaded. Note that these are meant for internal use, the IPShell*
592 610 # classes below are the ones meant for public consumption.
593 611
594 612 class MatplotlibShell(MatplotlibShellBase,InteractiveShell):
595 613 """Single-threaded shell with matplotlib support."""
596 614
597 615 def __init__(self,name,usage=None,rc=Struct(opts=None,args=None),
598 616 user_ns=None,user_global_ns=None,**kw):
599 617 user_ns,b2 = self._matplotlib_config(name,user_ns)
600 618 InteractiveShell.__init__(self,name,usage,rc,user_ns,user_global_ns,
601 619 banner2=b2,**kw)
602 620
603 621 class MatplotlibMTShell(MatplotlibShellBase,MTInteractiveShell):
604 622 """Multi-threaded shell with matplotlib support."""
605 623
606 624 def __init__(self,name,usage=None,rc=Struct(opts=None,args=None),
607 625 user_ns=None,user_global_ns=None, **kw):
608 626 user_ns,b2 = self._matplotlib_config(name,user_ns)
609 627 MTInteractiveShell.__init__(self,name,usage,rc,user_ns,user_global_ns,
610 628 banner2=b2,**kw)
611 629
612 630 #-----------------------------------------------------------------------------
613 631 # Utility functions for the different GUI enabled IPShell* classes.
614 632
615 633 def get_tk():
616 634 """Tries to import Tkinter and returns a withdrawn Tkinter root
617 635 window. If Tkinter is already imported or not available, this
618 636 returns None. This function calls `hijack_tk` underneath.
619 637 """
620 638 if not USE_TK or sys.modules.has_key('Tkinter'):
621 639 return None
622 640 else:
623 641 try:
624 642 import Tkinter
625 643 except ImportError:
626 644 return None
627 645 else:
628 646 hijack_tk()
629 647 r = Tkinter.Tk()
630 648 r.withdraw()
631 649 return r
632 650
633 651 def hijack_tk():
634 652 """Modifies Tkinter's mainloop with a dummy so when a module calls
635 653 mainloop, it does not block.
636 654
637 655 """
638 656 def misc_mainloop(self, n=0):
639 657 pass
640 658 def tkinter_mainloop(n=0):
641 659 pass
642 660
643 661 import Tkinter
644 662 Tkinter.Misc.mainloop = misc_mainloop
645 663 Tkinter.mainloop = tkinter_mainloop
646 664
647 665 def update_tk(tk):
648 666 """Updates the Tkinter event loop. This is typically called from
649 667 the respective WX or GTK mainloops.
650 668 """
651 669 if tk:
652 670 tk.update()
653 671
654 672 def hijack_wx():
655 673 """Modifies wxPython's MainLoop with a dummy so user code does not
656 674 block IPython. The hijacked mainloop function is returned.
657 675 """
658 676 def dummy_mainloop(*args, **kw):
659 677 pass
660 678
661 679 try:
662 680 import wx
663 681 except ImportError:
664 682 # For very old versions of WX
665 683 import wxPython as wx
666 684
667 685 ver = wx.__version__
668 686 orig_mainloop = None
669 687 if ver[:3] >= '2.5':
670 688 import wx
671 689 if hasattr(wx, '_core_'): core = getattr(wx, '_core_')
672 690 elif hasattr(wx, '_core'): core = getattr(wx, '_core')
673 691 else: raise AttributeError('Could not find wx core module')
674 692 orig_mainloop = core.PyApp_MainLoop
675 693 core.PyApp_MainLoop = dummy_mainloop
676 694 elif ver[:3] == '2.4':
677 695 orig_mainloop = wx.wxc.wxPyApp_MainLoop
678 696 wx.wxc.wxPyApp_MainLoop = dummy_mainloop
679 697 else:
680 698 warn("Unable to find either wxPython version 2.4 or >= 2.5.")
681 699 return orig_mainloop
682 700
683 701 def hijack_gtk():
684 702 """Modifies pyGTK's mainloop with a dummy so user code does not
685 703 block IPython. This function returns the original `gtk.mainloop`
686 704 function that has been hijacked.
687 705 """
688 706 def dummy_mainloop(*args, **kw):
689 707 pass
690 708 import gtk
691 709 if gtk.pygtk_version >= (2,4,0): orig_mainloop = gtk.main
692 710 else: orig_mainloop = gtk.mainloop
693 711 gtk.mainloop = dummy_mainloop
694 712 gtk.main = dummy_mainloop
695 713 return orig_mainloop
696 714
697 715 def hijack_qt():
698 716 """Modifies PyQt's mainloop with a dummy so user code does not
699 717 block IPython. This function returns the original
700 718 `qt.qApp.exec_loop` function that has been hijacked.
701 719 """
702 720 def dummy_mainloop(*args, **kw):
703 721 pass
704 722 import qt
705 723 orig_mainloop = qt.qApp.exec_loop
706 724 qt.qApp.exec_loop = dummy_mainloop
707 725 qt.QApplication.exec_loop = dummy_mainloop
708 726 return orig_mainloop
709 727
710 728 def hijack_qt4():
711 729 """Modifies PyQt4's mainloop with a dummy so user code does not
712 730 block IPython. This function returns the original
713 731 `QtGui.qApp.exec_` function that has been hijacked.
714 732 """
715 733 def dummy_mainloop(*args, **kw):
716 734 pass
717 735 from PyQt4 import QtGui, QtCore
718 736 orig_mainloop = QtGui.qApp.exec_
719 737 QtGui.qApp.exec_ = dummy_mainloop
720 738 QtGui.QApplication.exec_ = dummy_mainloop
721 739 QtCore.QCoreApplication.exec_ = dummy_mainloop
722 740 return orig_mainloop
723 741
724 742 #-----------------------------------------------------------------------------
725 743 # The IPShell* classes below are the ones meant to be run by external code as
726 744 # IPython instances. Note that unless a specific threading strategy is
727 745 # desired, the factory function start() below should be used instead (it
728 746 # selects the proper threaded class).
729 747
730 748 class IPThread(threading.Thread):
731 749 def run(self):
732 750 self.IP.mainloop(self._banner)
733 751 self.IP.kill()
734 752
735 753 class IPShellGTK(IPThread):
736 754 """Run a gtk mainloop() in a separate thread.
737 755
738 756 Python commands can be passed to the thread where they will be executed.
739 757 This is implemented by periodically checking for passed code using a
740 758 GTK timeout callback."""
741 759
742 760 TIMEOUT = 100 # Millisecond interval between timeouts.
743 761
744 762 def __init__(self,argv=None,user_ns=None,user_global_ns=None,
745 763 debug=1,shell_class=MTInteractiveShell):
746 764
747 765 import gtk
748 766
749 767 self.gtk = gtk
750 768 self.gtk_mainloop = hijack_gtk()
751 769
752 770 # Allows us to use both Tk and GTK.
753 771 self.tk = get_tk()
754 772
755 773 if gtk.pygtk_version >= (2,4,0): mainquit = self.gtk.main_quit
756 774 else: mainquit = self.gtk.mainquit
757 775
758 776 self.IP = make_IPython(argv,user_ns=user_ns,
759 777 user_global_ns=user_global_ns,
760 778 debug=debug,
761 779 shell_class=shell_class,
762 780 on_kill=[mainquit])
763 781
764 782 # HACK: slot for banner in self; it will be passed to the mainloop
765 783 # method only and .run() needs it. The actual value will be set by
766 784 # .mainloop().
767 785 self._banner = None
768 786
769 787 threading.Thread.__init__(self)
770 788
771 789 def mainloop(self,sys_exit=0,banner=None):
772 790
773 791 self._banner = banner
774 792
775 793 if self.gtk.pygtk_version >= (2,4,0):
776 794 import gobject
777 795 gobject.idle_add(self.on_timer)
778 796 else:
779 797 self.gtk.idle_add(self.on_timer)
780 798
781 799 if sys.platform != 'win32':
782 800 try:
783 801 if self.gtk.gtk_version[0] >= 2:
784 802 self.gtk.gdk.threads_init()
785 803 except AttributeError:
786 804 pass
787 805 except RuntimeError:
788 806 error('Your pyGTK likely has not been compiled with '
789 807 'threading support.\n'
790 808 'The exception printout is below.\n'
791 809 'You can either rebuild pyGTK with threads, or '
792 810 'try using \n'
793 811 'matplotlib with a different backend (like Tk or WX).\n'
794 812 'Note that matplotlib will most likely not work in its '
795 813 'current state!')
796 814 self.IP.InteractiveTB()
797 815
798 816 self.start()
799 817 self.gtk.gdk.threads_enter()
800 818 self.gtk_mainloop()
801 819 self.gtk.gdk.threads_leave()
802 820 self.join()
803 821
804 822 def on_timer(self):
805 823 """Called when GTK is idle.
806 824
807 825 Must return True always, otherwise GTK stops calling it"""
808 826
809 827 update_tk(self.tk)
810 828 self.IP.runcode()
811 829 time.sleep(0.01)
812 830 return True
813 831
814 832
815 833 class IPShellWX(IPThread):
816 834 """Run a wx mainloop() in a separate thread.
817 835
818 836 Python commands can be passed to the thread where they will be executed.
819 837 This is implemented by periodically checking for passed code using a
820 838 GTK timeout callback."""
821 839
822 840 TIMEOUT = 100 # Millisecond interval between timeouts.
823 841
824 842 def __init__(self,argv=None,user_ns=None,user_global_ns=None,
825 843 debug=1,shell_class=MTInteractiveShell):
826 844
827 845 self.IP = make_IPython(argv,user_ns=user_ns,
828 846 user_global_ns=user_global_ns,
829 847 debug=debug,
830 848 shell_class=shell_class,
831 849 on_kill=[self.wxexit])
832 850
833 851 wantedwxversion=self.IP.rc.wxversion
834 852 if wantedwxversion!="0":
835 853 try:
836 854 import wxversion
837 855 except ImportError:
838 856 error('The wxversion module is needed for WX version selection')
839 857 else:
840 858 try:
841 859 wxversion.select(wantedwxversion)
842 860 except:
843 861 self.IP.InteractiveTB()
844 862 error('Requested wxPython version %s could not be loaded' %
845 863 wantedwxversion)
846 864
847 865 import wx
848 866
849 867 threading.Thread.__init__(self)
850 868 self.wx = wx
851 869 self.wx_mainloop = hijack_wx()
852 870
853 871 # Allows us to use both Tk and GTK.
854 872 self.tk = get_tk()
855 873
856 874 # HACK: slot for banner in self; it will be passed to the mainloop
857 875 # method only and .run() needs it. The actual value will be set by
858 876 # .mainloop().
859 877 self._banner = None
860 878
861 879 self.app = None
862 880
863 881 def wxexit(self, *args):
864 882 if self.app is not None:
865 883 self.app.agent.timer.Stop()
866 884 self.app.ExitMainLoop()
867 885
868 886 def mainloop(self,sys_exit=0,banner=None):
869 887
870 888 self._banner = banner
871 889
872 890 self.start()
873 891
874 892 class TimerAgent(self.wx.MiniFrame):
875 893 wx = self.wx
876 894 IP = self.IP
877 895 tk = self.tk
878 896 def __init__(self, parent, interval):
879 897 style = self.wx.DEFAULT_FRAME_STYLE | self.wx.TINY_CAPTION_HORIZ
880 898 self.wx.MiniFrame.__init__(self, parent, -1, ' ', pos=(200, 200),
881 899 size=(100, 100),style=style)
882 900 self.Show(False)
883 901 self.interval = interval
884 902 self.timerId = self.wx.NewId()
885 903
886 904 def StartWork(self):
887 905 self.timer = self.wx.Timer(self, self.timerId)
888 906 self.wx.EVT_TIMER(self, self.timerId, self.OnTimer)
889 907 self.timer.Start(self.interval)
890 908
891 909 def OnTimer(self, event):
892 910 update_tk(self.tk)
893 911 self.IP.runcode()
894 912
895 913 class App(self.wx.App):
896 914 wx = self.wx
897 915 TIMEOUT = self.TIMEOUT
898 916 def OnInit(self):
899 917 'Create the main window and insert the custom frame'
900 918 self.agent = TimerAgent(None, self.TIMEOUT)
901 919 self.agent.Show(False)
902 920 self.agent.StartWork()
903 921 return True
904 922
905 923 self.app = App(redirect=False)
906 924 self.wx_mainloop(self.app)
907 925 self.join()
908 926
909 927
910 928 class IPShellQt(IPThread):
911 929 """Run a Qt event loop in a separate thread.
912 930
913 931 Python commands can be passed to the thread where they will be executed.
914 932 This is implemented by periodically checking for passed code using a
915 933 Qt timer / slot."""
916 934
917 935 TIMEOUT = 100 # Millisecond interval between timeouts.
918 936
919 937 def __init__(self, argv=None, user_ns=None, user_global_ns=None,
920 938 debug=0, shell_class=MTInteractiveShell):
921 939
922 940 import qt
923 941
924 942 self.exec_loop = hijack_qt()
925 943
926 944 # Allows us to use both Tk and QT.
927 945 self.tk = get_tk()
928 946
929 947 self.IP = make_IPython(argv,
930 948 user_ns=user_ns,
931 949 user_global_ns=user_global_ns,
932 950 debug=debug,
933 951 shell_class=shell_class,
934 952 on_kill=[qt.qApp.exit])
935 953
936 954 # HACK: slot for banner in self; it will be passed to the mainloop
937 955 # method only and .run() needs it. The actual value will be set by
938 956 # .mainloop().
939 957 self._banner = None
940 958
941 959 threading.Thread.__init__(self)
942 960
943 961 def mainloop(self, sys_exit=0, banner=None):
944 962
945 963 import qt
946 964
947 965 self._banner = banner
948 966
949 967 if qt.QApplication.startingUp():
950 968 a = qt.QApplication(sys.argv)
951 969
952 970 self.timer = qt.QTimer()
953 971 qt.QObject.connect(self.timer,
954 972 qt.SIGNAL('timeout()'),
955 973 self.on_timer)
956 974
957 975 self.start()
958 976 self.timer.start(self.TIMEOUT, True)
959 977 while True:
960 978 if self.IP._kill: break
961 979 self.exec_loop()
962 980 self.join()
963 981
964 982 def on_timer(self):
965 983 update_tk(self.tk)
966 984 result = self.IP.runcode()
967 985 self.timer.start(self.TIMEOUT, True)
968 986 return result
969 987
970 988
971 989 class IPShellQt4(IPThread):
972 990 """Run a Qt event loop in a separate thread.
973 991
974 992 Python commands can be passed to the thread where they will be executed.
975 993 This is implemented by periodically checking for passed code using a
976 994 Qt timer / slot."""
977 995
978 996 TIMEOUT = 100 # Millisecond interval between timeouts.
979 997
980 998 def __init__(self, argv=None, user_ns=None, user_global_ns=None,
981 999 debug=0, shell_class=MTInteractiveShell):
982 1000
983 1001 from PyQt4 import QtCore, QtGui
984 1002
985 1003 try:
986 1004 # present in PyQt4-4.2.1 or later
987 1005 QtCore.pyqtRemoveInputHook()
988 1006 except AttributeError:
989 1007 pass
990 1008
991 1009 if QtCore.PYQT_VERSION_STR == '4.3':
992 1010 warn('''PyQt4 version 4.3 detected.
993 1011 If you experience repeated threading warnings, please update PyQt4.
994 1012 ''')
995 1013
996 1014 self.exec_ = hijack_qt4()
997 1015
998 1016 # Allows us to use both Tk and QT.
999 1017 self.tk = get_tk()
1000 1018
1001 1019 self.IP = make_IPython(argv,
1002 1020 user_ns=user_ns,
1003 1021 user_global_ns=user_global_ns,
1004 1022 debug=debug,
1005 1023 shell_class=shell_class,
1006 1024 on_kill=[QtGui.qApp.exit])
1007 1025
1008 1026 # HACK: slot for banner in self; it will be passed to the mainloop
1009 1027 # method only and .run() needs it. The actual value will be set by
1010 1028 # .mainloop().
1011 1029 self._banner = None
1012 1030
1013 1031 threading.Thread.__init__(self)
1014 1032
1015 1033 def mainloop(self, sys_exit=0, banner=None):
1016 1034
1017 1035 from PyQt4 import QtCore, QtGui
1018 1036
1019 1037 self._banner = banner
1020 1038
1021 1039 if QtGui.QApplication.startingUp():
1022 1040 a = QtGui.QApplication(sys.argv)
1023 1041
1024 1042 self.timer = QtCore.QTimer()
1025 1043 QtCore.QObject.connect(self.timer,
1026 1044 QtCore.SIGNAL('timeout()'),
1027 1045 self.on_timer)
1028 1046
1029 1047 self.start()
1030 1048 self.timer.start(self.TIMEOUT)
1031 1049 while True:
1032 1050 if self.IP._kill: break
1033 1051 self.exec_()
1034 1052 self.join()
1035 1053
1036 1054 def on_timer(self):
1037 1055 update_tk(self.tk)
1038 1056 result = self.IP.runcode()
1039 1057 self.timer.start(self.TIMEOUT)
1040 1058 return result
1041 1059
1042 1060
1043 1061 # A set of matplotlib public IPython shell classes, for single-threaded (Tk*
1044 1062 # and FLTK*) and multithreaded (GTK*, WX* and Qt*) backends to use.
1045 1063 def _load_pylab(user_ns):
1046 1064 """Allow users to disable pulling all of pylab into the top-level
1047 1065 namespace.
1048 1066
1049 1067 This little utility must be called AFTER the actual ipython instance is
1050 1068 running, since only then will the options file have been fully parsed."""
1051 1069
1052 1070 ip = IPython.ipapi.get()
1053 1071 if ip.options.pylab_import_all:
1054 exec "from matplotlib.pylab import *" in user_ns
1072 ip.ex("from matplotlib.pylab import *")
1073 ip.IP.user_config_ns.update(ip.user_ns)
1074
1055 1075
1056 1076 class IPShellMatplotlib(IPShell):
1057 1077 """Subclass IPShell with MatplotlibShell as the internal shell.
1058 1078
1059 1079 Single-threaded class, meant for the Tk* and FLTK* backends.
1060 1080
1061 1081 Having this on a separate class simplifies the external driver code."""
1062 1082
1063 1083 def __init__(self,argv=None,user_ns=None,user_global_ns=None,debug=1):
1064 1084 IPShell.__init__(self,argv,user_ns,user_global_ns,debug,
1065 1085 shell_class=MatplotlibShell)
1066 1086 _load_pylab(self.IP.user_ns)
1067 1087
1068 1088 class IPShellMatplotlibGTK(IPShellGTK):
1069 1089 """Subclass IPShellGTK with MatplotlibMTShell as the internal shell.
1070 1090
1071 1091 Multi-threaded class, meant for the GTK* backends."""
1072 1092
1073 1093 def __init__(self,argv=None,user_ns=None,user_global_ns=None,debug=1):
1074 1094 IPShellGTK.__init__(self,argv,user_ns,user_global_ns,debug,
1075 1095 shell_class=MatplotlibMTShell)
1076 1096 _load_pylab(self.IP.user_ns)
1077 1097
1078 1098 class IPShellMatplotlibWX(IPShellWX):
1079 1099 """Subclass IPShellWX with MatplotlibMTShell as the internal shell.
1080 1100
1081 1101 Multi-threaded class, meant for the WX* backends."""
1082 1102
1083 1103 def __init__(self,argv=None,user_ns=None,user_global_ns=None,debug=1):
1084 1104 IPShellWX.__init__(self,argv,user_ns,user_global_ns,debug,
1085 1105 shell_class=MatplotlibMTShell)
1086 1106 _load_pylab(self.IP.user_ns)
1087 1107
1088 1108 class IPShellMatplotlibQt(IPShellQt):
1089 1109 """Subclass IPShellQt with MatplotlibMTShell as the internal shell.
1090 1110
1091 1111 Multi-threaded class, meant for the Qt* backends."""
1092 1112
1093 1113 def __init__(self,argv=None,user_ns=None,user_global_ns=None,debug=1):
1094 1114 IPShellQt.__init__(self,argv,user_ns,user_global_ns,debug,
1095 1115 shell_class=MatplotlibMTShell)
1096 1116 _load_pylab(self.IP.user_ns)
1097 1117
1098 1118 class IPShellMatplotlibQt4(IPShellQt4):
1099 1119 """Subclass IPShellQt4 with MatplotlibMTShell as the internal shell.
1100 1120
1101 1121 Multi-threaded class, meant for the Qt4* backends."""
1102 1122
1103 1123 def __init__(self,argv=None,user_ns=None,user_global_ns=None,debug=1):
1104 1124 IPShellQt4.__init__(self,argv,user_ns,user_global_ns,debug,
1105 1125 shell_class=MatplotlibMTShell)
1106 1126 _load_pylab(self.IP.user_ns)
1107 1127
1108 1128 #-----------------------------------------------------------------------------
1109 1129 # Factory functions to actually start the proper thread-aware shell
1110 1130
1111 1131 def _select_shell(argv):
1112 1132 """Select a shell from the given argv vector.
1113 1133
1114 1134 This function implements the threading selection policy, allowing runtime
1115 1135 control of the threading mode, both for general users and for matplotlib.
1116 1136
1117 1137 Return:
1118 1138 Shell class to be instantiated for runtime operation.
1119 1139 """
1120 1140
1121 1141 global USE_TK
1122 1142
1123 1143 mpl_shell = {'gthread' : IPShellMatplotlibGTK,
1124 1144 'wthread' : IPShellMatplotlibWX,
1125 1145 'qthread' : IPShellMatplotlibQt,
1126 1146 'q4thread' : IPShellMatplotlibQt4,
1127 1147 'tkthread' : IPShellMatplotlib, # Tk is built-in
1128 1148 }
1129 1149
1130 1150 th_shell = {'gthread' : IPShellGTK,
1131 1151 'wthread' : IPShellWX,
1132 1152 'qthread' : IPShellQt,
1133 1153 'q4thread' : IPShellQt4,
1134 1154 'tkthread' : IPShell, # Tk is built-in
1135 1155 }
1136 1156
1137 1157 backends = {'gthread' : 'GTKAgg',
1138 1158 'wthread' : 'WXAgg',
1139 1159 'qthread' : 'QtAgg',
1140 1160 'q4thread' :'Qt4Agg',
1141 1161 'tkthread' :'TkAgg',
1142 1162 }
1143 1163
1144 1164 all_opts = set(['tk','pylab','gthread','qthread','q4thread','wthread',
1145 1165 'tkthread'])
1146 1166 user_opts = set([s.replace('-','') for s in argv[:3]])
1147 special_opts = user_opts & all_opts
1167 special_opts = user_opts & all_opts
1148 1168
1149 1169 if 'tk' in special_opts:
1150 1170 USE_TK = True
1151 1171 special_opts.remove('tk')
1152 1172
1153 1173 if 'pylab' in special_opts:
1154 1174
1155 1175 try:
1156 1176 import matplotlib
1157 1177 except ImportError:
1158 1178 error('matplotlib could NOT be imported! Starting normal IPython.')
1159 1179 return IPShell
1160 1180
1161 1181 special_opts.remove('pylab')
1162 1182 # If there's any option left, it means the user wants to force the
1163 1183 # threading backend, else it's auto-selected from the rc file
1164 1184 if special_opts:
1165 1185 th_mode = special_opts.pop()
1166 1186 matplotlib.rcParams['backend'] = backends[th_mode]
1167 1187 else:
1168 1188 backend = matplotlib.rcParams['backend']
1169 1189 if backend.startswith('GTK'):
1170 1190 th_mode = 'gthread'
1171 1191 elif backend.startswith('WX'):
1172 1192 th_mode = 'wthread'
1173 1193 elif backend.startswith('Qt4'):
1174 1194 th_mode = 'q4thread'
1175 1195 elif backend.startswith('Qt'):
1176 1196 th_mode = 'qthread'
1177 1197 else:
1178 1198 # Any other backend, use plain Tk
1179 1199 th_mode = 'tkthread'
1180 1200
1181 1201 return mpl_shell[th_mode]
1182 1202 else:
1183 1203 # No pylab requested, just plain threads
1184 1204 try:
1185 1205 th_mode = special_opts.pop()
1186 1206 except KeyError:
1187 1207 th_mode = 'tkthread'
1188 1208 return th_shell[th_mode]
1189 1209
1190 1210
1191 1211 # This is the one which should be called by external code.
1192 1212 def start(user_ns = None):
1193 1213 """Return a running shell instance, dealing with threading options.
1194 1214
1195 1215 This is a factory function which will instantiate the proper IPython shell
1196 1216 based on the user's threading choice. Such a selector is needed because
1197 1217 different GUI toolkits require different thread handling details."""
1198 1218
1199 1219 shell = _select_shell(sys.argv)
1200 1220 return shell(user_ns = user_ns)
1201 1221
1202 1222 # Some aliases for backwards compatibility
1203 1223 IPythonShell = IPShell
1204 1224 IPythonShellEmbed = IPShellEmbed
1205 1225 #************************ End of file <Shell.py> ***************************
@@ -1,86 +1,107 b''
1 1 """ User configuration file for IPython
2 2
3 3 This is a more flexible and safe way to configure ipython than *rc files
4 4 (ipythonrc, ipythonrc-pysh etc.)
5 5
6 6 This file is always imported on ipython startup. You can import the
7 7 ipython extensions you need here (see IPython/Extensions directory).
8 8
9 9 Feel free to edit this file to customize your ipython experience.
10 10
11 11 Note that as such this file does nothing, for backwards compatibility.
12 12 Consult e.g. file 'ipy_profile_sh.py' for an example of the things
13 13 you can do here.
14 14
15 15 See http://ipython.scipy.org/moin/IpythonExtensionApi for detailed
16 16 description on what you could do here.
17 17 """
18 18
19 19 # Most of your config files and extensions will probably start with this import
20 20
21 21 import IPython.ipapi
22 22 ip = IPython.ipapi.get()
23 23
24 24 # You probably want to uncomment this if you did %upgrade -nolegacy
25 25 # import ipy_defaults
26 26
27 27 import os
28 28
29 29 def main():
30 30
31 31 # uncomment if you want to get ipython -p sh behaviour
32 32 # without having to use command line switches
33 33 # import ipy_profile_sh
34 34
35 35 # Configure your favourite editor?
36 36 # Good idea e.g. for %edit os.path.isfile
37 37
38 38 #import ipy_editors
39 39
40 40 # Choose one of these:
41 41
42 42 #ipy_editors.scite()
43 43 #ipy_editors.scite('c:/opt/scite/scite.exe')
44 44 #ipy_editors.komodo()
45 45 #ipy_editors.idle()
46 46 # ... or many others, try 'ipy_editors??' after import to see them
47 47
48 48 # Or roll your own:
49 49 #ipy_editors.install_editor("c:/opt/jed +$line $file")
50 50
51 51
52 52 o = ip.options
53 53 # An example on how to set options
54 54 #o.autocall = 1
55 55 o.system_verbose = 0
56 56
57 57 #import_all("os sys")
58 58 #execf('~/_ipython/ns.py')
59 59
60 60
61 61 # -- prompt
62 62 # A different, more compact set of prompts from the default ones, that
63 63 # always show your current location in the filesystem:
64 64
65 65 #o.prompt_in1 = r'\C_LightBlue[\C_LightCyan\Y2\C_LightBlue]\C_Normal\n\C_Green|\#>'
66 66 #o.prompt_in2 = r'.\D: '
67 67 #o.prompt_out = r'[\#] '
68 68
69 69 # Try one of these color settings if you can't read the text easily
70 70 # autoexec is a list of IPython commands to execute on startup
71 71 #o.autoexec.append('%colors LightBG')
72 72 #o.autoexec.append('%colors NoColor')
73 73 #o.autoexec.append('%colors Linux')
74 74
75 # for sane integer division that converts to float (1/2 == 0.5)
76 #o.autoexec.append('from __future__ import division')
77
78 # For %tasks and %kill
79 #import jobctrl
80
81 # For autoreloading of modules (%autoreload, %aimport)
82 #import ipy_autoreload
83
84 # For winpdb support (%wdb)
85 #import ipy_winpdb
86
87 # For bzr completer, requires bzrlib (the python installation of bzr)
88 #ip.load('ipy_bzr')
89
90 # Tab completer that is not quite so picky (i.e.
91 # "foo".<TAB> and str(2).<TAB> will work). Complete
92 # at your own risk!
93 #import ipy_greedycompleter
94
95
75 96
76 97 # some config helper functions you can use
77 98 def import_all(modules):
78 99 """ Usage: import_all("os sys") """
79 100 for m in modules.split():
80 101 ip.ex("from %s import *" % m)
81 102
82 103 def execf(fname):
83 104 """ Execute a file in user namespace """
84 105 ip.ex('execfile("%s")' % os.path.expanduser(fname))
85 106
86 107 main()
@@ -1,644 +1,644 b''
1 1 """Word completion for IPython.
2 2
3 3 This module is a fork of the rlcompleter module in the Python standard
4 4 library. The original enhancements made to rlcompleter have been sent
5 5 upstream and were accepted as of Python 2.3, but we need a lot more
6 6 functionality specific to IPython, so this module will continue to live as an
7 7 IPython-specific utility.
8 8
9 9 ---------------------------------------------------------------------------
10 10 Original rlcompleter documentation:
11 11
12 12 This requires the latest extension to the readline module (the
13 13 completes keywords, built-ins and globals in __main__; when completing
14 14 NAME.NAME..., it evaluates (!) the expression up to the last dot and
15 15 completes its attributes.
16 16
17 17 It's very cool to do "import string" type "string.", hit the
18 18 completion key (twice), and see the list of names defined by the
19 19 string module!
20 20
21 21 Tip: to use the tab key as the completion key, call
22 22
23 23 readline.parse_and_bind("tab: complete")
24 24
25 25 Notes:
26 26
27 27 - Exceptions raised by the completer function are *ignored* (and
28 28 generally cause the completion to fail). This is a feature -- since
29 29 readline sets the tty device in raw (or cbreak) mode, printing a
30 30 traceback wouldn't work well without some complicated hoopla to save,
31 31 reset and restore the tty state.
32 32
33 33 - The evaluation of the NAME.NAME... form may cause arbitrary
34 34 application defined code to be executed if an object with a
35 35 __getattr__ hook is found. Since it is the responsibility of the
36 36 application (or the user) to enable this feature, I consider this an
37 37 acceptable risk. More complicated expressions (e.g. function calls or
38 38 indexing operations) are *not* evaluated.
39 39
40 40 - GNU readline is also used by the built-in functions input() and
41 41 raw_input(), and thus these also benefit/suffer from the completer
42 42 features. Clearly an interactive application can benefit by
43 43 specifying its own completer function and using raw_input() for all
44 44 its input.
45 45
46 46 - When the original stdin is not a tty device, GNU readline is never
47 47 used, and this module (and the readline module) are silently inactive.
48 48
49 49 """
50 50
51 51 #*****************************************************************************
52 52 #
53 53 # Since this file is essentially a minimally modified copy of the rlcompleter
54 54 # module which is part of the standard Python distribution, I assume that the
55 55 # proper procedure is to maintain its copyright as belonging to the Python
56 56 # Software Foundation (in addition to my own, for all new code).
57 57 #
58 58 # Copyright (C) 2001 Python Software Foundation, www.python.org
59 59 # Copyright (C) 2001-2006 Fernando Perez. <fperez@colorado.edu>
60 60 #
61 61 # Distributed under the terms of the BSD License. The full license is in
62 62 # the file COPYING, distributed as part of this software.
63 63 #
64 64 #*****************************************************************************
65 65
66 66 import __builtin__
67 67 import __main__
68 68 import glob
69 69 import keyword
70 70 import os
71 71 import re
72 72 import shlex
73 73 import sys
74 74 import IPython.rlineimpl as readline
75 75 import itertools
76 76 from IPython.ipstruct import Struct
77 77 from IPython import ipapi
78 78 from IPython import generics
79 79 import types
80 80
81 81 # Python 2.4 offers sets as a builtin
82 82 try:
83 83 set()
84 84 except NameError:
85 85 from sets import Set as set
86 86
87 87 from IPython.genutils import debugx, dir2
88 88
89 89 __all__ = ['Completer','IPCompleter']
90 90
91 91 class Completer:
92 92 def __init__(self,namespace=None,global_namespace=None):
93 93 """Create a new completer for the command line.
94 94
95 95 Completer([namespace,global_namespace]) -> completer instance.
96 96
97 97 If unspecified, the default namespace where completions are performed
98 98 is __main__ (technically, __main__.__dict__). Namespaces should be
99 99 given as dictionaries.
100 100
101 101 An optional second namespace can be given. This allows the completer
102 102 to handle cases where both the local and global scopes need to be
103 103 distinguished.
104 104
105 105 Completer instances should be used as the completion mechanism of
106 106 readline via the set_completer() call:
107 107
108 108 readline.set_completer(Completer(my_namespace).complete)
109 109 """
110 110
111 111 # some minimal strict typechecks. For some core data structures, I
112 112 # want actual basic python types, not just anything that looks like
113 113 # one. This is especially true for namespaces.
114 114 for ns in (namespace,global_namespace):
115 115 if ns is not None and type(ns) != types.DictType:
116 116 raise TypeError,'namespace must be a dictionary'
117 117
118 118 # Don't bind to namespace quite yet, but flag whether the user wants a
119 119 # specific namespace or to use __main__.__dict__. This will allow us
120 120 # to bind to __main__.__dict__ at completion time, not now.
121 121 if namespace is None:
122 122 self.use_main_ns = 1
123 123 else:
124 124 self.use_main_ns = 0
125 125 self.namespace = namespace
126 126
127 127 # The global namespace, if given, can be bound directly
128 128 if global_namespace is None:
129 129 self.global_namespace = {}
130 130 else:
131 131 self.global_namespace = global_namespace
132 132
133 133 def complete(self, text, state):
134 134 """Return the next possible completion for 'text'.
135 135
136 136 This is called successively with state == 0, 1, 2, ... until it
137 137 returns None. The completion should begin with 'text'.
138 138
139 139 """
140 140 if self.use_main_ns:
141 141 self.namespace = __main__.__dict__
142 142
143 143 if state == 0:
144 144 if "." in text:
145 145 self.matches = self.attr_matches(text)
146 146 else:
147 147 self.matches = self.global_matches(text)
148 148 try:
149 149 return self.matches[state]
150 150 except IndexError:
151 151 return None
152 152
153 153 def global_matches(self, text):
154 154 """Compute matches when text is a simple name.
155 155
156 156 Return a list of all keywords, built-in functions and names currently
157 157 defined in self.namespace or self.global_namespace that match.
158 158
159 159 """
160 160 matches = []
161 161 match_append = matches.append
162 162 n = len(text)
163 163 for lst in [keyword.kwlist,
164 164 __builtin__.__dict__.keys(),
165 165 self.namespace.keys(),
166 166 self.global_namespace.keys()]:
167 167 for word in lst:
168 168 if word[:n] == text and word != "__builtins__":
169 169 match_append(word)
170 170 return matches
171 171
172 172 def attr_matches(self, text):
173 173 """Compute matches when text contains a dot.
174 174
175 175 Assuming the text is of the form NAME.NAME....[NAME], and is
176 176 evaluatable in self.namespace or self.global_namespace, it will be
177 177 evaluated and its attributes (as revealed by dir()) are used as
178 178 possible completions. (For class instances, class members are are
179 179 also considered.)
180 180
181 181 WARNING: this can still invoke arbitrary C code, if an object
182 182 with a __getattr__ hook is evaluated.
183 183
184 184 """
185 185 import re
186 186
187 187 # Another option, seems to work great. Catches things like ''.<tab>
188 188 m = re.match(r"(\S+(\.\w+)*)\.(\w*)$", text)
189 189
190 190 if not m:
191 191 return []
192 192
193 193 expr, attr = m.group(1, 3)
194 194 try:
195 195 obj = eval(expr, self.namespace)
196 196 except:
197 197 try:
198 198 obj = eval(expr, self.global_namespace)
199 199 except:
200 200 return []
201 201
202 202 words = dir2(obj)
203 203
204 204 try:
205 205 words = generics.complete_object(obj, words)
206 206 except ipapi.TryNext:
207 207 pass
208 208 # Build match list to return
209 209 n = len(attr)
210 210 res = ["%s.%s" % (expr, w) for w in words if w[:n] == attr ]
211 211 return res
212 212
213 213 class IPCompleter(Completer):
214 214 """Extension of the completer class with IPython-specific features"""
215 215
216 216 def __init__(self,shell,namespace=None,global_namespace=None,
217 217 omit__names=0,alias_table=None):
218 218 """IPCompleter() -> completer
219 219
220 220 Return a completer object suitable for use by the readline library
221 221 via readline.set_completer().
222 222
223 223 Inputs:
224 224
225 225 - shell: a pointer to the ipython shell itself. This is needed
226 226 because this completer knows about magic functions, and those can
227 227 only be accessed via the ipython instance.
228 228
229 229 - namespace: an optional dict where completions are performed.
230 230
231 231 - global_namespace: secondary optional dict for completions, to
232 232 handle cases (such as IPython embedded inside functions) where
233 233 both Python scopes are visible.
234 234
235 235 - The optional omit__names parameter sets the completer to omit the
236 236 'magic' names (__magicname__) for python objects unless the text
237 237 to be completed explicitly starts with one or more underscores.
238 238
239 239 - If alias_table is supplied, it should be a dictionary of aliases
240 240 to complete. """
241 241
242 242 Completer.__init__(self,namespace,global_namespace)
243 243 self.magic_prefix = shell.name+'.magic_'
244 244 self.magic_escape = shell.ESC_MAGIC
245 245 self.readline = readline
246 246 delims = self.readline.get_completer_delims()
247 247 delims = delims.replace(self.magic_escape,'')
248 248 self.readline.set_completer_delims(delims)
249 249 self.get_line_buffer = self.readline.get_line_buffer
250 250 self.get_endidx = self.readline.get_endidx
251 251 self.omit__names = omit__names
252 252 self.merge_completions = shell.rc.readline_merge_completions
253 253 if alias_table is None:
254 254 alias_table = {}
255 255 self.alias_table = alias_table
256 256 # Regexp to split filenames with spaces in them
257 257 self.space_name_re = re.compile(r'([^\\] )')
258 258 # Hold a local ref. to glob.glob for speed
259 259 self.glob = glob.glob
260 260
261 261 # Determine if we are running on 'dumb' terminals, like (X)Emacs
262 262 # buffers, to avoid completion problems.
263 263 term = os.environ.get('TERM','xterm')
264 264 self.dumb_terminal = term in ['dumb','emacs']
265 265
266 266 # Special handling of backslashes needed in win32 platforms
267 267 if sys.platform == "win32":
268 268 self.clean_glob = self._clean_glob_win32
269 269 else:
270 270 self.clean_glob = self._clean_glob
271 271 self.matchers = [self.python_matches,
272 272 self.file_matches,
273 273 self.alias_matches,
274 274 self.python_func_kw_matches]
275 275
276 276
277 277 # Code contributed by Alex Schmolck, for ipython/emacs integration
278 278 def all_completions(self, text):
279 279 """Return all possible completions for the benefit of emacs."""
280 280
281 281 completions = []
282 282 comp_append = completions.append
283 283 try:
284 284 for i in xrange(sys.maxint):
285 285 res = self.complete(text, i)
286 286
287 287 if not res: break
288 288
289 289 comp_append(res)
290 290 #XXX workaround for ``notDefined.<tab>``
291 291 except NameError:
292 292 pass
293 293 return completions
294 294 # /end Alex Schmolck code.
295 295
296 296 def _clean_glob(self,text):
297 297 return self.glob("%s*" % text)
298 298
299 299 def _clean_glob_win32(self,text):
300 300 return [f.replace("\\","/")
301 301 for f in self.glob("%s*" % text)]
302 302
303 303 def file_matches(self, text):
304 304 """Match filenames, expanding ~USER type strings.
305 305
306 306 Most of the seemingly convoluted logic in this completer is an
307 307 attempt to handle filenames with spaces in them. And yet it's not
308 308 quite perfect, because Python's readline doesn't expose all of the
309 309 GNU readline details needed for this to be done correctly.
310 310
311 311 For a filename with a space in it, the printed completions will be
312 312 only the parts after what's already been typed (instead of the
313 313 full completions, as is normally done). I don't think with the
314 314 current (as of Python 2.3) Python readline it's possible to do
315 315 better."""
316 316
317 317 #print 'Completer->file_matches: <%s>' % text # dbg
318 318
319 319 # chars that require escaping with backslash - i.e. chars
320 320 # that readline treats incorrectly as delimiters, but we
321 321 # don't want to treat as delimiters in filename matching
322 322 # when escaped with backslash
323 323
324 protectables = ' ()[]{}'
324 protectables = ' '
325 325
326 326 if text.startswith('!'):
327 327 text = text[1:]
328 328 text_prefix = '!'
329 329 else:
330 330 text_prefix = ''
331 331
332 332 def protect_filename(s):
333 333 return "".join([(ch in protectables and '\\' + ch or ch)
334 334 for ch in s])
335 335
336 336 def single_dir_expand(matches):
337 337 "Recursively expand match lists containing a single dir."
338 338
339 339 if len(matches) == 1 and os.path.isdir(matches[0]):
340 340 # Takes care of links to directories also. Use '/'
341 341 # explicitly, even under Windows, so that name completions
342 342 # don't end up escaped.
343 343 d = matches[0]
344 344 if d[-1] in ['/','\\']:
345 345 d = d[:-1]
346 346
347 347 subdirs = os.listdir(d)
348 348 if subdirs:
349 349 matches = [ (d + '/' + p) for p in subdirs]
350 350 return single_dir_expand(matches)
351 351 else:
352 352 return matches
353 353 else:
354 354 return matches
355 355
356 356 lbuf = self.lbuf
357 357 open_quotes = 0 # track strings with open quotes
358 358 try:
359 359 lsplit = shlex.split(lbuf)[-1]
360 360 except ValueError:
361 361 # typically an unmatched ", or backslash without escaped char.
362 362 if lbuf.count('"')==1:
363 363 open_quotes = 1
364 364 lsplit = lbuf.split('"')[-1]
365 365 elif lbuf.count("'")==1:
366 366 open_quotes = 1
367 367 lsplit = lbuf.split("'")[-1]
368 368 else:
369 369 return []
370 370 except IndexError:
371 371 # tab pressed on empty line
372 372 lsplit = ""
373 373
374 374 if lsplit != protect_filename(lsplit):
375 375 # if protectables are found, do matching on the whole escaped
376 376 # name
377 377 has_protectables = 1
378 378 text0,text = text,lsplit
379 379 else:
380 380 has_protectables = 0
381 381 text = os.path.expanduser(text)
382 382
383 383 if text == "":
384 384 return [text_prefix + protect_filename(f) for f in self.glob("*")]
385 385
386 386 m0 = self.clean_glob(text.replace('\\',''))
387 387 if has_protectables:
388 388 # If we had protectables, we need to revert our changes to the
389 389 # beginning of filename so that we don't double-write the part
390 390 # of the filename we have so far
391 391 len_lsplit = len(lsplit)
392 392 matches = [text_prefix + text0 +
393 393 protect_filename(f[len_lsplit:]) for f in m0]
394 394 else:
395 395 if open_quotes:
396 396 # if we have a string with an open quote, we don't need to
397 397 # protect the names at all (and we _shouldn't_, as it
398 398 # would cause bugs when the filesystem call is made).
399 399 matches = m0
400 400 else:
401 401 matches = [text_prefix +
402 402 protect_filename(f) for f in m0]
403 403
404 404 #print 'mm',matches # dbg
405 405 return single_dir_expand(matches)
406 406
407 407 def alias_matches(self, text):
408 408 """Match internal system aliases"""
409 409 #print 'Completer->alias_matches:',text,'lb',self.lbuf # dbg
410 410
411 411 # if we are not in the first 'item', alias matching
412 412 # doesn't make sense - unless we are starting with 'sudo' command.
413 413 if ' ' in self.lbuf.lstrip() and not self.lbuf.lstrip().startswith('sudo'):
414 414 return []
415 415 text = os.path.expanduser(text)
416 416 aliases = self.alias_table.keys()
417 417 if text == "":
418 418 return aliases
419 419 else:
420 420 return [alias for alias in aliases if alias.startswith(text)]
421 421
422 422 def python_matches(self,text):
423 423 """Match attributes or global python names"""
424 424
425 425 #print 'Completer->python_matches, txt=<%s>' % text # dbg
426 426 if "." in text:
427 427 try:
428 428 matches = self.attr_matches(text)
429 429 if text.endswith('.') and self.omit__names:
430 430 if self.omit__names == 1:
431 431 # true if txt is _not_ a __ name, false otherwise:
432 432 no__name = (lambda txt:
433 433 re.match(r'.*\.__.*?__',txt) is None)
434 434 else:
435 435 # true if txt is _not_ a _ name, false otherwise:
436 436 no__name = (lambda txt:
437 437 re.match(r'.*\._.*?',txt) is None)
438 438 matches = filter(no__name, matches)
439 439 except NameError:
440 440 # catches <undefined attributes>.<tab>
441 441 matches = []
442 442 else:
443 443 matches = self.global_matches(text)
444 444 # this is so completion finds magics when automagic is on:
445 445 if (matches == [] and
446 446 not text.startswith(os.sep) and
447 447 not ' ' in self.lbuf):
448 448 matches = self.attr_matches(self.magic_prefix+text)
449 449 return matches
450 450
451 451 def _default_arguments(self, obj):
452 452 """Return the list of default arguments of obj if it is callable,
453 453 or empty list otherwise."""
454 454
455 455 if not (inspect.isfunction(obj) or inspect.ismethod(obj)):
456 456 # for classes, check for __init__,__new__
457 457 if inspect.isclass(obj):
458 458 obj = (getattr(obj,'__init__',None) or
459 459 getattr(obj,'__new__',None))
460 460 # for all others, check if they are __call__able
461 461 elif hasattr(obj, '__call__'):
462 462 obj = obj.__call__
463 463 # XXX: is there a way to handle the builtins ?
464 464 try:
465 465 args,_,_1,defaults = inspect.getargspec(obj)
466 466 if defaults:
467 467 return args[-len(defaults):]
468 468 except TypeError: pass
469 469 return []
470 470
471 471 def python_func_kw_matches(self,text):
472 472 """Match named parameters (kwargs) of the last open function"""
473 473
474 474 if "." in text: # a parameter cannot be dotted
475 475 return []
476 476 try: regexp = self.__funcParamsRegex
477 477 except AttributeError:
478 478 regexp = self.__funcParamsRegex = re.compile(r'''
479 479 '.*?' | # single quoted strings or
480 480 ".*?" | # double quoted strings or
481 481 \w+ | # identifier
482 482 \S # other characters
483 483 ''', re.VERBOSE | re.DOTALL)
484 484 # 1. find the nearest identifier that comes before an unclosed
485 485 # parenthesis e.g. for "foo (1+bar(x), pa", the candidate is "foo"
486 486 tokens = regexp.findall(self.get_line_buffer())
487 487 tokens.reverse()
488 488 iterTokens = iter(tokens); openPar = 0
489 489 for token in iterTokens:
490 490 if token == ')':
491 491 openPar -= 1
492 492 elif token == '(':
493 493 openPar += 1
494 494 if openPar > 0:
495 495 # found the last unclosed parenthesis
496 496 break
497 497 else:
498 498 return []
499 499 # 2. Concatenate dotted names ("foo.bar" for "foo.bar(x, pa" )
500 500 ids = []
501 501 isId = re.compile(r'\w+$').match
502 502 while True:
503 503 try:
504 504 ids.append(iterTokens.next())
505 505 if not isId(ids[-1]):
506 506 ids.pop(); break
507 507 if not iterTokens.next() == '.':
508 508 break
509 509 except StopIteration:
510 510 break
511 511 # lookup the candidate callable matches either using global_matches
512 512 # or attr_matches for dotted names
513 513 if len(ids) == 1:
514 514 callableMatches = self.global_matches(ids[0])
515 515 else:
516 516 callableMatches = self.attr_matches('.'.join(ids[::-1]))
517 517 argMatches = []
518 518 for callableMatch in callableMatches:
519 519 try: namedArgs = self._default_arguments(eval(callableMatch,
520 520 self.namespace))
521 521 except: continue
522 522 for namedArg in namedArgs:
523 523 if namedArg.startswith(text):
524 524 argMatches.append("%s=" %namedArg)
525 525 return argMatches
526 526
527 527 def dispatch_custom_completer(self,text):
528 528 #print "Custom! '%s' %s" % (text, self.custom_completers) # dbg
529 529 line = self.full_lbuf
530 530 if not line.strip():
531 531 return None
532 532
533 533 event = Struct()
534 534 event.line = line
535 535 event.symbol = text
536 536 cmd = line.split(None,1)[0]
537 537 event.command = cmd
538 538 #print "\ncustom:{%s]\n" % event # dbg
539 539
540 540 # for foo etc, try also to find completer for %foo
541 541 if not cmd.startswith(self.magic_escape):
542 542 try_magic = self.custom_completers.s_matches(
543 543 self.magic_escape + cmd)
544 544 else:
545 545 try_magic = []
546 546
547 547
548 548 for c in itertools.chain(
549 549 self.custom_completers.s_matches(cmd),
550 550 try_magic,
551 551 self.custom_completers.flat_matches(self.lbuf)):
552 552 #print "try",c # dbg
553 553 try:
554 554 res = c(event)
555 555 # first, try case sensitive match
556 556 withcase = [r for r in res if r.startswith(text)]
557 557 if withcase:
558 558 return withcase
559 559 # if none, then case insensitive ones are ok too
560 560 return [r for r in res if r.lower().startswith(text.lower())]
561 561 except ipapi.TryNext:
562 562 pass
563 563
564 564 return None
565 565
566 566 def complete(self, text, state,line_buffer=None):
567 567 """Return the next possible completion for 'text'.
568 568
569 569 This is called successively with state == 0, 1, 2, ... until it
570 570 returns None. The completion should begin with 'text'.
571 571
572 572 :Keywords:
573 573 - line_buffer: string
574 574 If not given, the completer attempts to obtain the current line buffer
575 575 via readline. This keyword allows clients which are requesting for
576 576 text completions in non-readline contexts to inform the completer of
577 577 the entire text.
578 578 """
579 579
580 580 #print '\n*** COMPLETE: <%s> (%s)' % (text,state) # dbg
581 581
582 582 # if there is only a tab on a line with only whitespace, instead
583 583 # of the mostly useless 'do you want to see all million
584 584 # completions' message, just do the right thing and give the user
585 585 # his tab! Incidentally, this enables pasting of tabbed text from
586 586 # an editor (as long as autoindent is off).
587 587
588 588 # It should be noted that at least pyreadline still shows
589 589 # file completions - is there a way around it?
590 590
591 591 # don't apply this on 'dumb' terminals, such as emacs buffers, so we
592 592 # don't interfere with their own tab-completion mechanism.
593 593 if line_buffer is None:
594 594 self.full_lbuf = self.get_line_buffer()
595 595 else:
596 596 self.full_lbuf = line_buffer
597 597
598 598 if not (self.dumb_terminal or self.full_lbuf.strip()):
599 599 self.readline.insert_text('\t')
600 600 return None
601 601
602 602 magic_escape = self.magic_escape
603 603 magic_prefix = self.magic_prefix
604 604
605 605 self.lbuf = self.full_lbuf[:self.get_endidx()]
606 606
607 607 try:
608 608 if text.startswith(magic_escape):
609 609 text = text.replace(magic_escape,magic_prefix)
610 610 elif text.startswith('~'):
611 611 text = os.path.expanduser(text)
612 612 if state == 0:
613 613 custom_res = self.dispatch_custom_completer(text)
614 614 if custom_res is not None:
615 615 # did custom completers produce something?
616 616 self.matches = custom_res
617 617 else:
618 618 # Extend the list of completions with the results of each
619 619 # matcher, so we return results to the user from all
620 620 # namespaces.
621 621 if self.merge_completions:
622 622 self.matches = []
623 623 for matcher in self.matchers:
624 624 self.matches.extend(matcher(text))
625 625 else:
626 626 for matcher in self.matchers:
627 627 self.matches = matcher(text)
628 628 if self.matches:
629 629 break
630 630 def uniq(alist):
631 631 set = {}
632 632 return [set.setdefault(e,e) for e in alist if e not in set]
633 633 self.matches = uniq(self.matches)
634 634 try:
635 635 ret = self.matches[state].replace(magic_prefix,magic_escape)
636 636 return ret
637 637 except IndexError:
638 638 return None
639 639 except:
640 640 #from IPython.ultraTB import AutoFormattedTB; # dbg
641 641 #tb=AutoFormattedTB('Verbose');tb() #dbg
642 642
643 643 # If completion fails, don't annoy the user.
644 644 return None
@@ -1,186 +1,188 b''
1 1 # -*- coding: utf-8 -*-
2 2 """
3 3 A module to change reload() so that it acts recursively.
4 4 To enable it type:
5 5 >>> import __builtin__, deep_reload
6 6 >>> __builtin__.reload = deep_reload.reload
7 7 You can then disable it with:
8 8 >>> __builtin__.reload = deep_reload.original_reload
9 9
10 10 Alternatively, you can add a dreload builtin alongside normal reload with:
11 11 >>> __builtin__.dreload = deep_reload.reload
12 12
13 13 This code is almost entirely based on knee.py from the standard library.
14 14
15 15 $Id: deep_reload.py 958 2005-12-27 23:17:51Z fperez $"""
16 16
17 17 #*****************************************************************************
18 18 # Copyright (C) 2001 Nathaniel Gray <n8gray@caltech.edu>
19 19 #
20 20 # Distributed under the terms of the BSD License. The full license is in
21 21 # the file COPYING, distributed as part of this software.
22 22 #*****************************************************************************
23 23
24 24 from IPython import Release # do it explicitly so pydoc can see it - pydoc bug
25 25 __author__ = '%s <%s>' % Release.authors['Nathan']
26 26 __license__ = Release.license
27 27 __version__ = "0.5"
28 28 __date__ = "21 August 2001"
29 29
30 30 import __builtin__
31 31 import imp
32 32 import sys
33 33
34 34 # Replacement for __import__()
35 def deep_import_hook(name, globals=None, locals=None, fromlist=None):
35 def deep_import_hook(name, globals=None, locals=None, fromlist=None, level=-1):
36 # For now level is ignored, it's just there to prevent crash
37 # with from __future__ import absolute_import
36 38 parent = determine_parent(globals)
37 39 q, tail = find_head_package(parent, name)
38 40 m = load_tail(q, tail)
39 41 if not fromlist:
40 42 return q
41 43 if hasattr(m, "__path__"):
42 44 ensure_fromlist(m, fromlist)
43 45 return m
44 46
45 47 def determine_parent(globals):
46 48 if not globals or not globals.has_key("__name__"):
47 49 return None
48 50 pname = globals['__name__']
49 51 if globals.has_key("__path__"):
50 52 parent = sys.modules[pname]
51 53 assert globals is parent.__dict__
52 54 return parent
53 55 if '.' in pname:
54 56 i = pname.rfind('.')
55 57 pname = pname[:i]
56 58 parent = sys.modules[pname]
57 59 assert parent.__name__ == pname
58 60 return parent
59 61 return None
60 62
61 63 def find_head_package(parent, name):
62 64 # Import the first
63 65 if '.' in name:
64 66 # 'some.nested.package' -> head = 'some', tail = 'nested.package'
65 67 i = name.find('.')
66 68 head = name[:i]
67 69 tail = name[i+1:]
68 70 else:
69 71 # 'packagename' -> head = 'packagename', tail = ''
70 72 head = name
71 73 tail = ""
72 74 if parent:
73 75 # If this is a subpackage then qname = parent's name + head
74 76 qname = "%s.%s" % (parent.__name__, head)
75 77 else:
76 78 qname = head
77 79 q = import_module(head, qname, parent)
78 80 if q: return q, tail
79 81 if parent:
80 82 qname = head
81 83 parent = None
82 84 q = import_module(head, qname, parent)
83 85 if q: return q, tail
84 86 raise ImportError, "No module named " + qname
85 87
86 88 def load_tail(q, tail):
87 89 m = q
88 90 while tail:
89 91 i = tail.find('.')
90 92 if i < 0: i = len(tail)
91 93 head, tail = tail[:i], tail[i+1:]
92 94
93 95 # fperez: fix dotted.name reloading failures by changing:
94 96 #mname = "%s.%s" % (m.__name__, head)
95 97 # to:
96 98 mname = m.__name__
97 99 # This needs more testing!!! (I don't understand this module too well)
98 100
99 101 #print '** head,tail=|%s|->|%s|, mname=|%s|' % (head,tail,mname) # dbg
100 102 m = import_module(head, mname, m)
101 103 if not m:
102 104 raise ImportError, "No module named " + mname
103 105 return m
104 106
105 107 def ensure_fromlist(m, fromlist, recursive=0):
106 108 for sub in fromlist:
107 109 if sub == "*":
108 110 if not recursive:
109 111 try:
110 112 all = m.__all__
111 113 except AttributeError:
112 114 pass
113 115 else:
114 116 ensure_fromlist(m, all, 1)
115 117 continue
116 118 if sub != "*" and not hasattr(m, sub):
117 119 subname = "%s.%s" % (m.__name__, sub)
118 120 submod = import_module(sub, subname, m)
119 121 if not submod:
120 122 raise ImportError, "No module named " + subname
121 123
122 124 # Need to keep track of what we've already reloaded to prevent cyclic evil
123 125 found_now = {}
124 126
125 127 def import_module(partname, fqname, parent):
126 128 global found_now
127 129 if found_now.has_key(fqname):
128 130 try:
129 131 return sys.modules[fqname]
130 132 except KeyError:
131 133 pass
132 134
133 135 print 'Reloading', fqname #, sys.excepthook is sys.__excepthook__, \
134 136 #sys.displayhook is sys.__displayhook__
135 137
136 138 found_now[fqname] = 1
137 139 try:
138 140 fp, pathname, stuff = imp.find_module(partname,
139 141 parent and parent.__path__)
140 142 except ImportError:
141 143 return None
142 144
143 145 try:
144 146 m = imp.load_module(fqname, fp, pathname, stuff)
145 147 finally:
146 148 if fp: fp.close()
147 149
148 150 if parent:
149 151 setattr(parent, partname, m)
150 152
151 153 return m
152 154
153 155 def deep_reload_hook(module):
154 156 name = module.__name__
155 157 if '.' not in name:
156 158 return import_module(name, name, None)
157 159 i = name.rfind('.')
158 160 pname = name[:i]
159 161 parent = sys.modules[pname]
160 162 return import_module(name[i+1:], name, parent)
161 163
162 164 # Save the original hooks
163 165 original_reload = __builtin__.reload
164 166
165 167 # Replacement for reload()
166 168 def reload(module, exclude=['sys', '__builtin__', '__main__']):
167 169 """Recursively reload all modules used in the given module. Optionally
168 170 takes a list of modules to exclude from reloading. The default exclude
169 171 list contains sys, __main__, and __builtin__, to prevent, e.g., resetting
170 172 display, exception, and io hooks.
171 173 """
172 174 global found_now
173 175 for i in exclude:
174 176 found_now[i] = 1
175 177 original_import = __builtin__.__import__
176 178 __builtin__.__import__ = deep_import_hook
177 179 try:
178 180 ret = deep_reload_hook(module)
179 181 finally:
180 182 __builtin__.__import__ = original_import
181 183 found_now = {}
182 184 return ret
183 185
184 186 # Uncomment the following to automatically activate deep reloading whenever
185 187 # this module is imported
186 188 #__builtin__.reload = reload
@@ -1,203 +1,203 b''
1 1 #!/usr/bin/env python
2 2
3 3 r""" mglob - enhanced file list expansion module
4 4
5 5 Use as stand-alone utility (for xargs, `backticks` etc.),
6 6 or a globbing library for own python programs. Globbing the sys.argv is something
7 7 that almost every Windows script has to perform manually, and this module is here
8 8 to help with that task. Also Unix users will benefit from enhanced modes
9 9 such as recursion, exclusion, directory omission...
10 10
11 11 Unlike glob.glob, directories are not included in the glob unless specified
12 12 with 'dir:'
13 13
14 14 'expand' is the function to use in python programs. Typical use
15 15 to expand argv (esp. in windows)::
16 16
17 17 try:
18 18 import mglob
19 19 files = mglob.expand(sys.argv[1:])
20 20 except ImportError:
21 21 print "mglob not found; try 'easy_install mglob' for extra features"
22 22 files = sys.argv[1:]
23 23
24 24 Note that for unix, shell expands *normal* wildcards (*.cpp, etc.) in argv.
25 25 Therefore, you might want to use quotes with normal wildcards to prevent this
26 26 expansion, in order for mglob to see the wildcards and get the wanted behaviour.
27 27 Not quoting the wildcards is harmless and typically has equivalent results, though.
28 28
29 29 Author: Ville Vainio <vivainio@gmail.com>
30 30 License: MIT Open Source license
31 31
32 32 """
33 33
34 34 #Assigned in variable for "usage" printing convenience"
35 35
36 36 globsyntax = """\
37 This program allows specifying filenames with "mglob" mechanism.
38 Supported syntax in globs (wilcard matching patterns)::
39
40 *.cpp ?ellowo*
41 - obvious. Differs from normal glob in that dirs are not included.
42 Unix users might want to write this as: "*.cpp" "?ellowo*"
43 rec:/usr/share=*.txt,*.doc
44 - get all *.txt and *.doc under /usr/share,
45 recursively
46 rec:/usr/share
47 - All files under /usr/share, recursively
48 rec:*.py
49 - All .py files under current working dir, recursively
50 foo
51 - File or dir foo
52 !*.bak readme*
53 - readme*, exclude files ending with .bak
54 !.svn/ !.hg/ !*_Data/ rec:.
55 - Skip .svn, .hg, foo_Data dirs (and their subdirs) in recurse.
56 Trailing / is the key, \ does not work!
57 dir:foo
58 - the directory foo if it exists (not files in foo)
59 dir:*
60 - all directories in current folder
61 foo.py bar.* !h* rec:*.py
62 - Obvious. !h* exclusion only applies for rec:*.py.
63 foo.py is *not* included twice.
64 @filelist.txt
65 - All files listed in 'filelist.txt' file, on separate lines.
37 This program allows specifying filenames with "mglob" mechanism.
38 Supported syntax in globs (wilcard matching patterns)::
39
40 *.cpp ?ellowo*
41 - obvious. Differs from normal glob in that dirs are not included.
42 Unix users might want to write this as: "*.cpp" "?ellowo*"
43 rec:/usr/share=*.txt,*.doc
44 - get all *.txt and *.doc under /usr/share,
45 recursively
46 rec:/usr/share
47 - All files under /usr/share, recursively
48 rec:*.py
49 - All .py files under current working dir, recursively
50 foo
51 - File or dir foo
52 !*.bak readme*
53 - readme*, exclude files ending with .bak
54 !.svn/ !.hg/ !*_Data/ rec:.
55 - Skip .svn, .hg, foo_Data dirs (and their subdirs) in recurse.
56 Trailing / is the key, \ does not work!
57 dir:foo
58 - the directory foo if it exists (not files in foo)
59 dir:*
60 - all directories in current folder
61 foo.py bar.* !h* rec:*.py
62 - Obvious. !h* exclusion only applies for rec:*.py.
63 foo.py is *not* included twice.
64 @filelist.txt
65 - All files listed in 'filelist.txt' file, on separate lines.
66 66 """
67 67
68 68
69 69 __version__ = "0.2"
70 70
71 71
72 72 import os,glob,fnmatch,sys
73 73 from sets import Set as set
74 74
75 75
76 76 def expand(flist,exp_dirs = False):
77 77 """ Expand the glob(s) in flist.
78 78
79 79 flist may be either a whitespace-separated list of globs/files
80 80 or an array of globs/files.
81 81
82 82 if exp_dirs is true, directory names in glob are expanded to the files
83 83 contained in them - otherwise, directory names are returned as is.
84 84
85 85 """
86 86 if isinstance(flist, basestring):
87 87 flist = flist.split()
88 88 done_set = set()
89 89 denied_set = set()
90 90
91 91 def recfind(p, pats = ["*"]):
92 92 denied_dirs = ["*" + d+"*" for d in denied_set if d.endswith("/")]
93 93 #print "de", denied_dirs
94 94 for (dp,dnames,fnames) in os.walk(p):
95 95 # see if we should ignore the whole directory
96 96 dp_norm = dp.replace("\\","/") + "/"
97 97 deny = False
98 98 #print "dp",dp
99 99 for deny_pat in denied_dirs:
100 100 if fnmatch.fnmatch( dp_norm, deny_pat):
101 101 deny = True
102 102 break
103 103 if deny:
104 104 continue
105 105
106 106
107 107 for f in fnames:
108 108 matched = False
109 109 for p in pats:
110 110 if fnmatch.fnmatch(f,p):
111 111 matched = True
112 112 break
113 113 if matched:
114 114 yield os.path.join(dp,f)
115 115
116 116 def once_filter(seq):
117 117 for it in seq:
118 118 p = os.path.abspath(it)
119 119 if p in done_set:
120 120 continue
121 121 done_set.add(p)
122 122 deny = False
123 123 for deny_pat in denied_set:
124 124 if fnmatch.fnmatch(os.path.basename(p), deny_pat):
125 125 deny = True
126 126 break
127 127 if not deny:
128 128 yield it
129 129 return
130 130
131 131 res = []
132 132
133 133 for ent in flist:
134 134 ent = os.path.expanduser(os.path.expandvars(ent))
135 135 if ent.lower().startswith('rec:'):
136 136 fields = ent[4:].split('=')
137 137 if len(fields) == 2:
138 138 pth, patlist = fields
139 139 elif len(fields) == 1:
140 140 if os.path.isdir(fields[0]):
141 141 # single arg is dir
142 142 pth, patlist = fields[0], '*'
143 143 else:
144 144 # single arg is pattern
145 145 pth, patlist = '.', fields[0]
146 146
147 147 elif len(fields) == 0:
148 148 pth, pathlist = '.','*'
149 149
150 150 pats = patlist.split(',')
151 151 res.extend(once_filter(recfind(pth, pats)))
152 152 # filelist
153 153 elif ent.startswith('@') and os.path.isfile(ent[1:]):
154 154 res.extend(once_filter(open(ent[1:]).read().splitlines()))
155 155 # exclusion
156 156 elif ent.startswith('!'):
157 157 denied_set.add(ent[1:])
158 158 # glob only dirs
159 159 elif ent.lower().startswith('dir:'):
160 160 res.extend(once_filter(filter(os.path.isdir,glob.glob(ent[4:]))))
161 161
162 162 # get all files in the specified dir
163 163 elif os.path.isdir(ent) and exp_dirs:
164 164 res.extend(once_filter(filter(os.path.isfile,glob.glob(ent + os.sep+"*"))))
165 165
166 166 # glob only files
167 167
168 168 elif '*' in ent or '?' in ent:
169 169 res.extend(once_filter(filter(os.path.isfile,glob.glob(ent))))
170 170
171 171 else:
172 172 res.extend(once_filter([ent]))
173 173 return res
174 174
175 175
176 176 def test():
177 177 assert (
178 178 expand("*.py ~/.ipython/*.py rec:/usr/share/doc-base") ==
179 179 expand( ['*.py', '~/.ipython/*.py', 'rec:/usr/share/doc-base'] )
180 180 )
181 181
182 182 def main():
183 183 if len(sys.argv) < 2:
184 184 print globsyntax
185 185 return
186 186
187 187 print "\n".join(expand(sys.argv[1:])),
188 188
189 189 def mglob_f(self, arg):
190 190 from IPython.genutils import SList
191 191 if arg.strip():
192 192 return SList(expand(arg))
193 193 print "Please specify pattern!"
194 194 print globsyntax
195 195
196 196 def init_ipython(ip):
197 197 """ register %mglob for IPython """
198 198 mglob_f.__doc__ = globsyntax
199 199 ip.expose_magic("mglob",mglob_f)
200 200
201 201 # test()
202 202 if __name__ == "__main__":
203 203 main()
@@ -1,970 +1,973 b''
1 1 """ path.py - An object representing a path to a file or directory.
2 2
3 3 Example:
4 4
5 5 from IPython.external.path import path
6 6 d = path('/home/guido/bin')
7 7 for f in d.files('*.py'):
8 8 f.chmod(0755)
9 9
10 10 This module requires Python 2.2 or later.
11 11
12 12
13 13 URL: http://www.jorendorff.com/articles/python/path
14 14 Author: Jason Orendorff <jason.orendorff\x40gmail\x2ecom> (and others - see the url!)
15 15 Date: 9 Mar 2007
16 16 """
17 17
18 18
19 19 # TODO
20 20 # - Tree-walking functions don't avoid symlink loops. Matt Harrison
21 21 # sent me a patch for this.
22 22 # - Bug in write_text(). It doesn't support Universal newline mode.
23 23 # - Better error message in listdir() when self isn't a
24 24 # directory. (On Windows, the error message really sucks.)
25 25 # - Make sure everything has a good docstring.
26 26 # - Add methods for regex find and replace.
27 27 # - guess_content_type() method?
28 28 # - Perhaps support arguments to touch().
29 29
30 30 from __future__ import generators
31 31
32 import sys, warnings, os, fnmatch, glob, shutil, codecs, md5
32 import sys, warnings, os, fnmatch, glob, shutil, codecs
33 # deprecated in python 2.6
34 warnings.filterwarnings('ignore', r'.*md5.*')
35 import md5
33 36
34 37 __version__ = '2.2'
35 38 __all__ = ['path']
36 39
37 40 # Platform-specific support for path.owner
38 41 if os.name == 'nt':
39 42 try:
40 43 import win32security
41 44 except ImportError:
42 45 win32security = None
43 46 else:
44 47 try:
45 48 import pwd
46 49 except ImportError:
47 50 pwd = None
48 51
49 52 # Pre-2.3 support. Are unicode filenames supported?
50 53 _base = str
51 54 _getcwd = os.getcwd
52 55 try:
53 56 if os.path.supports_unicode_filenames:
54 57 _base = unicode
55 58 _getcwd = os.getcwdu
56 59 except AttributeError:
57 60 pass
58 61
59 62 # Pre-2.3 workaround for booleans
60 63 try:
61 64 True, False
62 65 except NameError:
63 66 True, False = 1, 0
64 67
65 68 # Pre-2.3 workaround for basestring.
66 69 try:
67 70 basestring
68 71 except NameError:
69 72 basestring = (str, unicode)
70 73
71 74 # Universal newline support
72 75 _textmode = 'r'
73 76 if hasattr(file, 'newlines'):
74 77 _textmode = 'U'
75 78
76 79
77 80 class TreeWalkWarning(Warning):
78 81 pass
79 82
80 83 class path(_base):
81 84 """ Represents a filesystem path.
82 85
83 86 For documentation on individual methods, consult their
84 87 counterparts in os.path.
85 88 """
86 89
87 90 # --- Special Python methods.
88 91
89 92 def __repr__(self):
90 93 return 'path(%s)' % _base.__repr__(self)
91 94
92 95 # Adding a path and a string yields a path.
93 96 def __add__(self, more):
94 97 try:
95 98 resultStr = _base.__add__(self, more)
96 99 except TypeError: #Python bug
97 100 resultStr = NotImplemented
98 101 if resultStr is NotImplemented:
99 102 return resultStr
100 103 return self.__class__(resultStr)
101 104
102 105 def __radd__(self, other):
103 106 if isinstance(other, basestring):
104 107 return self.__class__(other.__add__(self))
105 108 else:
106 109 return NotImplemented
107 110
108 111 # The / operator joins paths.
109 112 def __div__(self, rel):
110 113 """ fp.__div__(rel) == fp / rel == fp.joinpath(rel)
111 114
112 115 Join two path components, adding a separator character if
113 116 needed.
114 117 """
115 118 return self.__class__(os.path.join(self, rel))
116 119
117 120 # Make the / operator work even when true division is enabled.
118 121 __truediv__ = __div__
119 122
120 123 def getcwd(cls):
121 124 """ Return the current working directory as a path object. """
122 125 return cls(_getcwd())
123 126 getcwd = classmethod(getcwd)
124 127
125 128
126 129 # --- Operations on path strings.
127 130
128 131 isabs = os.path.isabs
129 132 def abspath(self): return self.__class__(os.path.abspath(self))
130 133 def normcase(self): return self.__class__(os.path.normcase(self))
131 134 def normpath(self): return self.__class__(os.path.normpath(self))
132 135 def realpath(self): return self.__class__(os.path.realpath(self))
133 136 def expanduser(self): return self.__class__(os.path.expanduser(self))
134 137 def expandvars(self): return self.__class__(os.path.expandvars(self))
135 138 def dirname(self): return self.__class__(os.path.dirname(self))
136 139 basename = os.path.basename
137 140
138 141 def expand(self):
139 142 """ Clean up a filename by calling expandvars(),
140 143 expanduser(), and normpath() on it.
141 144
142 145 This is commonly everything needed to clean up a filename
143 146 read from a configuration file, for example.
144 147 """
145 148 return self.expandvars().expanduser().normpath()
146 149
147 150 def _get_namebase(self):
148 151 base, ext = os.path.splitext(self.name)
149 152 return base
150 153
151 154 def _get_ext(self):
152 155 f, ext = os.path.splitext(_base(self))
153 156 return ext
154 157
155 158 def _get_drive(self):
156 159 drive, r = os.path.splitdrive(self)
157 160 return self.__class__(drive)
158 161
159 162 parent = property(
160 163 dirname, None, None,
161 164 """ This path's parent directory, as a new path object.
162 165
163 166 For example, path('/usr/local/lib/libpython.so').parent == path('/usr/local/lib')
164 167 """)
165 168
166 169 name = property(
167 170 basename, None, None,
168 171 """ The name of this file or directory without the full path.
169 172
170 173 For example, path('/usr/local/lib/libpython.so').name == 'libpython.so'
171 174 """)
172 175
173 176 namebase = property(
174 177 _get_namebase, None, None,
175 178 """ The same as path.name, but with one file extension stripped off.
176 179
177 180 For example, path('/home/guido/python.tar.gz').name == 'python.tar.gz',
178 181 but path('/home/guido/python.tar.gz').namebase == 'python.tar'
179 182 """)
180 183
181 184 ext = property(
182 185 _get_ext, None, None,
183 186 """ The file extension, for example '.py'. """)
184 187
185 188 drive = property(
186 189 _get_drive, None, None,
187 190 """ The drive specifier, for example 'C:'.
188 191 This is always empty on systems that don't use drive specifiers.
189 192 """)
190 193
191 194 def splitpath(self):
192 195 """ p.splitpath() -> Return (p.parent, p.name). """
193 196 parent, child = os.path.split(self)
194 197 return self.__class__(parent), child
195 198
196 199 def splitdrive(self):
197 200 """ p.splitdrive() -> Return (p.drive, <the rest of p>).
198 201
199 202 Split the drive specifier from this path. If there is
200 203 no drive specifier, p.drive is empty, so the return value
201 204 is simply (path(''), p). This is always the case on Unix.
202 205 """
203 206 drive, rel = os.path.splitdrive(self)
204 207 return self.__class__(drive), rel
205 208
206 209 def splitext(self):
207 210 """ p.splitext() -> Return (p.stripext(), p.ext).
208 211
209 212 Split the filename extension from this path and return
210 213 the two parts. Either part may be empty.
211 214
212 215 The extension is everything from '.' to the end of the
213 216 last path segment. This has the property that if
214 217 (a, b) == p.splitext(), then a + b == p.
215 218 """
216 219 filename, ext = os.path.splitext(self)
217 220 return self.__class__(filename), ext
218 221
219 222 def stripext(self):
220 223 """ p.stripext() -> Remove one file extension from the path.
221 224
222 225 For example, path('/home/guido/python.tar.gz').stripext()
223 226 returns path('/home/guido/python.tar').
224 227 """
225 228 return self.splitext()[0]
226 229
227 230 if hasattr(os.path, 'splitunc'):
228 231 def splitunc(self):
229 232 unc, rest = os.path.splitunc(self)
230 233 return self.__class__(unc), rest
231 234
232 235 def _get_uncshare(self):
233 236 unc, r = os.path.splitunc(self)
234 237 return self.__class__(unc)
235 238
236 239 uncshare = property(
237 240 _get_uncshare, None, None,
238 241 """ The UNC mount point for this path.
239 242 This is empty for paths on local drives. """)
240 243
241 244 def joinpath(self, *args):
242 245 """ Join two or more path components, adding a separator
243 246 character (os.sep) if needed. Returns a new path
244 247 object.
245 248 """
246 249 return self.__class__(os.path.join(self, *args))
247 250
248 251 def splitall(self):
249 252 r""" Return a list of the path components in this path.
250 253
251 254 The first item in the list will be a path. Its value will be
252 255 either os.curdir, os.pardir, empty, or the root directory of
253 256 this path (for example, '/' or 'C:\\'). The other items in
254 257 the list will be strings.
255 258
256 259 path.path.joinpath(*result) will yield the original path.
257 260 """
258 261 parts = []
259 262 loc = self
260 263 while loc != os.curdir and loc != os.pardir:
261 264 prev = loc
262 265 loc, child = prev.splitpath()
263 266 if loc == prev:
264 267 break
265 268 parts.append(child)
266 269 parts.append(loc)
267 270 parts.reverse()
268 271 return parts
269 272
270 273 def relpath(self):
271 274 """ Return this path as a relative path,
272 275 based from the current working directory.
273 276 """
274 277 cwd = self.__class__(os.getcwd())
275 278 return cwd.relpathto(self)
276 279
277 280 def relpathto(self, dest):
278 281 """ Return a relative path from self to dest.
279 282
280 283 If there is no relative path from self to dest, for example if
281 284 they reside on different drives in Windows, then this returns
282 285 dest.abspath().
283 286 """
284 287 origin = self.abspath()
285 288 dest = self.__class__(dest).abspath()
286 289
287 290 orig_list = origin.normcase().splitall()
288 291 # Don't normcase dest! We want to preserve the case.
289 292 dest_list = dest.splitall()
290 293
291 294 if orig_list[0] != os.path.normcase(dest_list[0]):
292 295 # Can't get here from there.
293 296 return dest
294 297
295 298 # Find the location where the two paths start to differ.
296 299 i = 0
297 300 for start_seg, dest_seg in zip(orig_list, dest_list):
298 301 if start_seg != os.path.normcase(dest_seg):
299 302 break
300 303 i += 1
301 304
302 305 # Now i is the point where the two paths diverge.
303 306 # Need a certain number of "os.pardir"s to work up
304 307 # from the origin to the point of divergence.
305 308 segments = [os.pardir] * (len(orig_list) - i)
306 309 # Need to add the diverging part of dest_list.
307 310 segments += dest_list[i:]
308 311 if len(segments) == 0:
309 312 # If they happen to be identical, use os.curdir.
310 313 relpath = os.curdir
311 314 else:
312 315 relpath = os.path.join(*segments)
313 316 return self.__class__(relpath)
314 317
315 318 # --- Listing, searching, walking, and matching
316 319
317 320 def listdir(self, pattern=None):
318 321 """ D.listdir() -> List of items in this directory.
319 322
320 323 Use D.files() or D.dirs() instead if you want a listing
321 324 of just files or just subdirectories.
322 325
323 326 The elements of the list are path objects.
324 327
325 328 With the optional 'pattern' argument, this only lists
326 329 items whose names match the given pattern.
327 330 """
328 331 names = os.listdir(self)
329 332 if pattern is not None:
330 333 names = fnmatch.filter(names, pattern)
331 334 return [self / child for child in names]
332 335
333 336 def dirs(self, pattern=None):
334 337 """ D.dirs() -> List of this directory's subdirectories.
335 338
336 339 The elements of the list are path objects.
337 340 This does not walk recursively into subdirectories
338 341 (but see path.walkdirs).
339 342
340 343 With the optional 'pattern' argument, this only lists
341 344 directories whose names match the given pattern. For
342 345 example, d.dirs('build-*').
343 346 """
344 347 return [p for p in self.listdir(pattern) if p.isdir()]
345 348
346 349 def files(self, pattern=None):
347 350 """ D.files() -> List of the files in this directory.
348 351
349 352 The elements of the list are path objects.
350 353 This does not walk into subdirectories (see path.walkfiles).
351 354
352 355 With the optional 'pattern' argument, this only lists files
353 356 whose names match the given pattern. For example,
354 357 d.files('*.pyc').
355 358 """
356 359
357 360 return [p for p in self.listdir(pattern) if p.isfile()]
358 361
359 362 def walk(self, pattern=None, errors='strict'):
360 363 """ D.walk() -> iterator over files and subdirs, recursively.
361 364
362 365 The iterator yields path objects naming each child item of
363 366 this directory and its descendants. This requires that
364 367 D.isdir().
365 368
366 369 This performs a depth-first traversal of the directory tree.
367 370 Each directory is returned just before all its children.
368 371
369 372 The errors= keyword argument controls behavior when an
370 373 error occurs. The default is 'strict', which causes an
371 374 exception. The other allowed values are 'warn', which
372 375 reports the error via warnings.warn(), and 'ignore'.
373 376 """
374 377 if errors not in ('strict', 'warn', 'ignore'):
375 378 raise ValueError("invalid errors parameter")
376 379
377 380 try:
378 381 childList = self.listdir()
379 382 except Exception:
380 383 if errors == 'ignore':
381 384 return
382 385 elif errors == 'warn':
383 386 warnings.warn(
384 387 "Unable to list directory '%s': %s"
385 388 % (self, sys.exc_info()[1]),
386 389 TreeWalkWarning)
387 390 return
388 391 else:
389 392 raise
390 393
391 394 for child in childList:
392 395 if pattern is None or child.fnmatch(pattern):
393 396 yield child
394 397 try:
395 398 isdir = child.isdir()
396 399 except Exception:
397 400 if errors == 'ignore':
398 401 isdir = False
399 402 elif errors == 'warn':
400 403 warnings.warn(
401 404 "Unable to access '%s': %s"
402 405 % (child, sys.exc_info()[1]),
403 406 TreeWalkWarning)
404 407 isdir = False
405 408 else:
406 409 raise
407 410
408 411 if isdir:
409 412 for item in child.walk(pattern, errors):
410 413 yield item
411 414
412 415 def walkdirs(self, pattern=None, errors='strict'):
413 416 """ D.walkdirs() -> iterator over subdirs, recursively.
414 417
415 418 With the optional 'pattern' argument, this yields only
416 419 directories whose names match the given pattern. For
417 420 example, mydir.walkdirs('*test') yields only directories
418 421 with names ending in 'test'.
419 422
420 423 The errors= keyword argument controls behavior when an
421 424 error occurs. The default is 'strict', which causes an
422 425 exception. The other allowed values are 'warn', which
423 426 reports the error via warnings.warn(), and 'ignore'.
424 427 """
425 428 if errors not in ('strict', 'warn', 'ignore'):
426 429 raise ValueError("invalid errors parameter")
427 430
428 431 try:
429 432 dirs = self.dirs()
430 433 except Exception:
431 434 if errors == 'ignore':
432 435 return
433 436 elif errors == 'warn':
434 437 warnings.warn(
435 438 "Unable to list directory '%s': %s"
436 439 % (self, sys.exc_info()[1]),
437 440 TreeWalkWarning)
438 441 return
439 442 else:
440 443 raise
441 444
442 445 for child in dirs:
443 446 if pattern is None or child.fnmatch(pattern):
444 447 yield child
445 448 for subsubdir in child.walkdirs(pattern, errors):
446 449 yield subsubdir
447 450
448 451 def walkfiles(self, pattern=None, errors='strict'):
449 452 """ D.walkfiles() -> iterator over files in D, recursively.
450 453
451 454 The optional argument, pattern, limits the results to files
452 455 with names that match the pattern. For example,
453 456 mydir.walkfiles('*.tmp') yields only files with the .tmp
454 457 extension.
455 458 """
456 459 if errors not in ('strict', 'warn', 'ignore'):
457 460 raise ValueError("invalid errors parameter")
458 461
459 462 try:
460 463 childList = self.listdir()
461 464 except Exception:
462 465 if errors == 'ignore':
463 466 return
464 467 elif errors == 'warn':
465 468 warnings.warn(
466 469 "Unable to list directory '%s': %s"
467 470 % (self, sys.exc_info()[1]),
468 471 TreeWalkWarning)
469 472 return
470 473 else:
471 474 raise
472 475
473 476 for child in childList:
474 477 try:
475 478 isfile = child.isfile()
476 479 isdir = not isfile and child.isdir()
477 480 except:
478 481 if errors == 'ignore':
479 482 continue
480 483 elif errors == 'warn':
481 484 warnings.warn(
482 485 "Unable to access '%s': %s"
483 486 % (self, sys.exc_info()[1]),
484 487 TreeWalkWarning)
485 488 continue
486 489 else:
487 490 raise
488 491
489 492 if isfile:
490 493 if pattern is None or child.fnmatch(pattern):
491 494 yield child
492 495 elif isdir:
493 496 for f in child.walkfiles(pattern, errors):
494 497 yield f
495 498
496 499 def fnmatch(self, pattern):
497 500 """ Return True if self.name matches the given pattern.
498 501
499 502 pattern - A filename pattern with wildcards,
500 503 for example '*.py'.
501 504 """
502 505 return fnmatch.fnmatch(self.name, pattern)
503 506
504 507 def glob(self, pattern):
505 508 """ Return a list of path objects that match the pattern.
506 509
507 510 pattern - a path relative to this directory, with wildcards.
508 511
509 512 For example, path('/users').glob('*/bin/*') returns a list
510 513 of all the files users have in their bin directories.
511 514 """
512 515 cls = self.__class__
513 516 return [cls(s) for s in glob.glob(_base(self / pattern))]
514 517
515 518
516 519 # --- Reading or writing an entire file at once.
517 520
518 521 def open(self, mode='r'):
519 522 """ Open this file. Return a file object. """
520 523 return file(self, mode)
521 524
522 525 def bytes(self):
523 526 """ Open this file, read all bytes, return them as a string. """
524 527 f = self.open('rb')
525 528 try:
526 529 return f.read()
527 530 finally:
528 531 f.close()
529 532
530 533 def write_bytes(self, bytes, append=False):
531 534 """ Open this file and write the given bytes to it.
532 535
533 536 Default behavior is to overwrite any existing file.
534 537 Call p.write_bytes(bytes, append=True) to append instead.
535 538 """
536 539 if append:
537 540 mode = 'ab'
538 541 else:
539 542 mode = 'wb'
540 543 f = self.open(mode)
541 544 try:
542 545 f.write(bytes)
543 546 finally:
544 547 f.close()
545 548
546 549 def text(self, encoding=None, errors='strict'):
547 550 r""" Open this file, read it in, return the content as a string.
548 551
549 552 This uses 'U' mode in Python 2.3 and later, so '\r\n' and '\r'
550 553 are automatically translated to '\n'.
551 554
552 555 Optional arguments:
553 556
554 557 encoding - The Unicode encoding (or character set) of
555 558 the file. If present, the content of the file is
556 559 decoded and returned as a unicode object; otherwise
557 560 it is returned as an 8-bit str.
558 561 errors - How to handle Unicode errors; see help(str.decode)
559 562 for the options. Default is 'strict'.
560 563 """
561 564 if encoding is None:
562 565 # 8-bit
563 566 f = self.open(_textmode)
564 567 try:
565 568 return f.read()
566 569 finally:
567 570 f.close()
568 571 else:
569 572 # Unicode
570 573 f = codecs.open(self, 'r', encoding, errors)
571 574 # (Note - Can't use 'U' mode here, since codecs.open
572 575 # doesn't support 'U' mode, even in Python 2.3.)
573 576 try:
574 577 t = f.read()
575 578 finally:
576 579 f.close()
577 580 return (t.replace(u'\r\n', u'\n')
578 581 .replace(u'\r\x85', u'\n')
579 582 .replace(u'\r', u'\n')
580 583 .replace(u'\x85', u'\n')
581 584 .replace(u'\u2028', u'\n'))
582 585
583 586 def write_text(self, text, encoding=None, errors='strict', linesep=os.linesep, append=False):
584 587 r""" Write the given text to this file.
585 588
586 589 The default behavior is to overwrite any existing file;
587 590 to append instead, use the 'append=True' keyword argument.
588 591
589 592 There are two differences between path.write_text() and
590 593 path.write_bytes(): newline handling and Unicode handling.
591 594 See below.
592 595
593 596 Parameters:
594 597
595 598 - text - str/unicode - The text to be written.
596 599
597 600 - encoding - str - The Unicode encoding that will be used.
598 601 This is ignored if 'text' isn't a Unicode string.
599 602
600 603 - errors - str - How to handle Unicode encoding errors.
601 604 Default is 'strict'. See help(unicode.encode) for the
602 605 options. This is ignored if 'text' isn't a Unicode
603 606 string.
604 607
605 608 - linesep - keyword argument - str/unicode - The sequence of
606 609 characters to be used to mark end-of-line. The default is
607 610 os.linesep. You can also specify None; this means to
608 611 leave all newlines as they are in 'text'.
609 612
610 613 - append - keyword argument - bool - Specifies what to do if
611 614 the file already exists (True: append to the end of it;
612 615 False: overwrite it.) The default is False.
613 616
614 617
615 618 --- Newline handling.
616 619
617 620 write_text() converts all standard end-of-line sequences
618 621 ('\n', '\r', and '\r\n') to your platform's default end-of-line
619 622 sequence (see os.linesep; on Windows, for example, the
620 623 end-of-line marker is '\r\n').
621 624
622 625 If you don't like your platform's default, you can override it
623 626 using the 'linesep=' keyword argument. If you specifically want
624 627 write_text() to preserve the newlines as-is, use 'linesep=None'.
625 628
626 629 This applies to Unicode text the same as to 8-bit text, except
627 630 there are three additional standard Unicode end-of-line sequences:
628 631 u'\x85', u'\r\x85', and u'\u2028'.
629 632
630 633 (This is slightly different from when you open a file for
631 634 writing with fopen(filename, "w") in C or file(filename, 'w')
632 635 in Python.)
633 636
634 637
635 638 --- Unicode
636 639
637 640 If 'text' isn't Unicode, then apart from newline handling, the
638 641 bytes are written verbatim to the file. The 'encoding' and
639 642 'errors' arguments are not used and must be omitted.
640 643
641 644 If 'text' is Unicode, it is first converted to bytes using the
642 645 specified 'encoding' (or the default encoding if 'encoding'
643 646 isn't specified). The 'errors' argument applies only to this
644 647 conversion.
645 648
646 649 """
647 650 if isinstance(text, unicode):
648 651 if linesep is not None:
649 652 # Convert all standard end-of-line sequences to
650 653 # ordinary newline characters.
651 654 text = (text.replace(u'\r\n', u'\n')
652 655 .replace(u'\r\x85', u'\n')
653 656 .replace(u'\r', u'\n')
654 657 .replace(u'\x85', u'\n')
655 658 .replace(u'\u2028', u'\n'))
656 659 text = text.replace(u'\n', linesep)
657 660 if encoding is None:
658 661 encoding = sys.getdefaultencoding()
659 662 bytes = text.encode(encoding, errors)
660 663 else:
661 664 # It is an error to specify an encoding if 'text' is
662 665 # an 8-bit string.
663 666 assert encoding is None
664 667
665 668 if linesep is not None:
666 669 text = (text.replace('\r\n', '\n')
667 670 .replace('\r', '\n'))
668 671 bytes = text.replace('\n', linesep)
669 672
670 673 self.write_bytes(bytes, append)
671 674
672 675 def lines(self, encoding=None, errors='strict', retain=True):
673 676 r""" Open this file, read all lines, return them in a list.
674 677
675 678 Optional arguments:
676 679 encoding - The Unicode encoding (or character set) of
677 680 the file. The default is None, meaning the content
678 681 of the file is read as 8-bit characters and returned
679 682 as a list of (non-Unicode) str objects.
680 683 errors - How to handle Unicode errors; see help(str.decode)
681 684 for the options. Default is 'strict'
682 685 retain - If true, retain newline characters; but all newline
683 686 character combinations ('\r', '\n', '\r\n') are
684 687 translated to '\n'. If false, newline characters are
685 688 stripped off. Default is True.
686 689
687 690 This uses 'U' mode in Python 2.3 and later.
688 691 """
689 692 if encoding is None and retain:
690 693 f = self.open(_textmode)
691 694 try:
692 695 return f.readlines()
693 696 finally:
694 697 f.close()
695 698 else:
696 699 return self.text(encoding, errors).splitlines(retain)
697 700
698 701 def write_lines(self, lines, encoding=None, errors='strict',
699 702 linesep=os.linesep, append=False):
700 703 r""" Write the given lines of text to this file.
701 704
702 705 By default this overwrites any existing file at this path.
703 706
704 707 This puts a platform-specific newline sequence on every line.
705 708 See 'linesep' below.
706 709
707 710 lines - A list of strings.
708 711
709 712 encoding - A Unicode encoding to use. This applies only if
710 713 'lines' contains any Unicode strings.
711 714
712 715 errors - How to handle errors in Unicode encoding. This
713 716 also applies only to Unicode strings.
714 717
715 718 linesep - The desired line-ending. This line-ending is
716 719 applied to every line. If a line already has any
717 720 standard line ending ('\r', '\n', '\r\n', u'\x85',
718 721 u'\r\x85', u'\u2028'), that will be stripped off and
719 722 this will be used instead. The default is os.linesep,
720 723 which is platform-dependent ('\r\n' on Windows, '\n' on
721 724 Unix, etc.) Specify None to write the lines as-is,
722 725 like file.writelines().
723 726
724 727 Use the keyword argument append=True to append lines to the
725 728 file. The default is to overwrite the file. Warning:
726 729 When you use this with Unicode data, if the encoding of the
727 730 existing data in the file is different from the encoding
728 731 you specify with the encoding= parameter, the result is
729 732 mixed-encoding data, which can really confuse someone trying
730 733 to read the file later.
731 734 """
732 735 if append:
733 736 mode = 'ab'
734 737 else:
735 738 mode = 'wb'
736 739 f = self.open(mode)
737 740 try:
738 741 for line in lines:
739 742 isUnicode = isinstance(line, unicode)
740 743 if linesep is not None:
741 744 # Strip off any existing line-end and add the
742 745 # specified linesep string.
743 746 if isUnicode:
744 747 if line[-2:] in (u'\r\n', u'\x0d\x85'):
745 748 line = line[:-2]
746 749 elif line[-1:] in (u'\r', u'\n',
747 750 u'\x85', u'\u2028'):
748 751 line = line[:-1]
749 752 else:
750 753 if line[-2:] == '\r\n':
751 754 line = line[:-2]
752 755 elif line[-1:] in ('\r', '\n'):
753 756 line = line[:-1]
754 757 line += linesep
755 758 if isUnicode:
756 759 if encoding is None:
757 760 encoding = sys.getdefaultencoding()
758 761 line = line.encode(encoding, errors)
759 762 f.write(line)
760 763 finally:
761 764 f.close()
762 765
763 766 def read_md5(self):
764 767 """ Calculate the md5 hash for this file.
765 768
766 769 This reads through the entire file.
767 770 """
768 771 f = self.open('rb')
769 772 try:
770 773 m = md5.new()
771 774 while True:
772 775 d = f.read(8192)
773 776 if not d:
774 777 break
775 778 m.update(d)
776 779 finally:
777 780 f.close()
778 781 return m.digest()
779 782
780 783 # --- Methods for querying the filesystem.
781 784
782 785 exists = os.path.exists
783 786 isdir = os.path.isdir
784 787 isfile = os.path.isfile
785 788 islink = os.path.islink
786 789 ismount = os.path.ismount
787 790
788 791 if hasattr(os.path, 'samefile'):
789 792 samefile = os.path.samefile
790 793
791 794 getatime = os.path.getatime
792 795 atime = property(
793 796 getatime, None, None,
794 797 """ Last access time of the file. """)
795 798
796 799 getmtime = os.path.getmtime
797 800 mtime = property(
798 801 getmtime, None, None,
799 802 """ Last-modified time of the file. """)
800 803
801 804 if hasattr(os.path, 'getctime'):
802 805 getctime = os.path.getctime
803 806 ctime = property(
804 807 getctime, None, None,
805 808 """ Creation time of the file. """)
806 809
807 810 getsize = os.path.getsize
808 811 size = property(
809 812 getsize, None, None,
810 813 """ Size of the file, in bytes. """)
811 814
812 815 if hasattr(os, 'access'):
813 816 def access(self, mode):
814 817 """ Return true if current user has access to this path.
815 818
816 819 mode - One of the constants os.F_OK, os.R_OK, os.W_OK, os.X_OK
817 820 """
818 821 return os.access(self, mode)
819 822
820 823 def stat(self):
821 824 """ Perform a stat() system call on this path. """
822 825 return os.stat(self)
823 826
824 827 def lstat(self):
825 828 """ Like path.stat(), but do not follow symbolic links. """
826 829 return os.lstat(self)
827 830
828 831 def get_owner(self):
829 832 r""" Return the name of the owner of this file or directory.
830 833
831 834 This follows symbolic links.
832 835
833 836 On Windows, this returns a name of the form ur'DOMAIN\User Name'.
834 837 On Windows, a group can own a file or directory.
835 838 """
836 839 if os.name == 'nt':
837 840 if win32security is None:
838 841 raise Exception("path.owner requires win32all to be installed")
839 842 desc = win32security.GetFileSecurity(
840 843 self, win32security.OWNER_SECURITY_INFORMATION)
841 844 sid = desc.GetSecurityDescriptorOwner()
842 845 account, domain, typecode = win32security.LookupAccountSid(None, sid)
843 846 return domain + u'\\' + account
844 847 else:
845 848 if pwd is None:
846 849 raise NotImplementedError("path.owner is not implemented on this platform.")
847 850 st = self.stat()
848 851 return pwd.getpwuid(st.st_uid).pw_name
849 852
850 853 owner = property(
851 854 get_owner, None, None,
852 855 """ Name of the owner of this file or directory. """)
853 856
854 857 if hasattr(os, 'statvfs'):
855 858 def statvfs(self):
856 859 """ Perform a statvfs() system call on this path. """
857 860 return os.statvfs(self)
858 861
859 862 if hasattr(os, 'pathconf'):
860 863 def pathconf(self, name):
861 864 return os.pathconf(self, name)
862 865
863 866
864 867 # --- Modifying operations on files and directories
865 868
866 869 def utime(self, times):
867 870 """ Set the access and modified times of this file. """
868 871 os.utime(self, times)
869 872
870 873 def chmod(self, mode):
871 874 os.chmod(self, mode)
872 875
873 876 if hasattr(os, 'chown'):
874 877 def chown(self, uid, gid):
875 878 os.chown(self, uid, gid)
876 879
877 880 def rename(self, new):
878 881 os.rename(self, new)
879 882
880 883 def renames(self, new):
881 884 os.renames(self, new)
882 885
883 886
884 887 # --- Create/delete operations on directories
885 888
886 889 def mkdir(self, mode=0777):
887 890 os.mkdir(self, mode)
888 891
889 892 def makedirs(self, mode=0777):
890 893 os.makedirs(self, mode)
891 894
892 895 def rmdir(self):
893 896 os.rmdir(self)
894 897
895 898 def removedirs(self):
896 899 os.removedirs(self)
897 900
898 901
899 902 # --- Modifying operations on files
900 903
901 904 def touch(self):
902 905 """ Set the access/modified times of this file to the current time.
903 906 Create the file if it does not exist.
904 907 """
905 908 fd = os.open(self, os.O_WRONLY | os.O_CREAT, 0666)
906 909 os.close(fd)
907 910 os.utime(self, None)
908 911
909 912 def remove(self):
910 913 os.remove(self)
911 914
912 915 def unlink(self):
913 916 os.unlink(self)
914 917
915 918
916 919 # --- Links
917 920
918 921 if hasattr(os, 'link'):
919 922 def link(self, newpath):
920 923 """ Create a hard link at 'newpath', pointing to this file. """
921 924 os.link(self, newpath)
922 925
923 926 if hasattr(os, 'symlink'):
924 927 def symlink(self, newlink):
925 928 """ Create a symbolic link at 'newlink', pointing here. """
926 929 os.symlink(self, newlink)
927 930
928 931 if hasattr(os, 'readlink'):
929 932 def readlink(self):
930 933 """ Return the path to which this symbolic link points.
931 934
932 935 The result may be an absolute or a relative path.
933 936 """
934 937 return self.__class__(os.readlink(self))
935 938
936 939 def readlinkabs(self):
937 940 """ Return the path to which this symbolic link points.
938 941
939 942 The result is always an absolute path.
940 943 """
941 944 p = self.readlink()
942 945 if p.isabs():
943 946 return p
944 947 else:
945 948 return (self.parent / p).abspath()
946 949
947 950
948 951 # --- High-level functions from shutil
949 952
950 953 copyfile = shutil.copyfile
951 954 copymode = shutil.copymode
952 955 copystat = shutil.copystat
953 956 copy = shutil.copy
954 957 copy2 = shutil.copy2
955 958 copytree = shutil.copytree
956 959 if hasattr(shutil, 'move'):
957 960 move = shutil.move
958 961 rmtree = shutil.rmtree
959 962
960 963
961 964 # --- Special stuff from os
962 965
963 966 if hasattr(os, 'chroot'):
964 967 def chroot(self):
965 968 os.chroot(self)
966 969
967 970 if hasattr(os, 'startfile'):
968 971 def startfile(self):
969 972 os.startfile(self)
970 973
@@ -1,2008 +1,2043 b''
1 1 # -*- coding: utf-8 -*-
2 2 """
3 3 General purpose utilities.
4 4
5 5 This is a grab-bag of stuff I find useful in most programs I write. Some of
6 6 these things are also convenient when working at the command line.
7 7
8 8 $Id: genutils.py 2998 2008-01-31 10:06:04Z vivainio $"""
9 9
10 10 #*****************************************************************************
11 11 # Copyright (C) 2001-2006 Fernando Perez. <fperez@colorado.edu>
12 12 #
13 13 # Distributed under the terms of the BSD License. The full license is in
14 14 # the file COPYING, distributed as part of this software.
15 15 #*****************************************************************************
16 16
17 17 from IPython import Release
18 18 __author__ = '%s <%s>' % Release.authors['Fernando']
19 19 __license__ = Release.license
20 20
21 21 #****************************************************************************
22 22 # required modules from the Python standard library
23 23 import __main__
24 24 import commands
25 import doctest
25 try:
26 import doctest
27 except ImportError:
28 pass
26 29 import os
27 30 import re
28 31 import shlex
29 32 import shutil
30 33 import sys
31 34 import tempfile
32 35 import time
33 36 import types
34 37 import warnings
35 38
39 # Curses and termios are Unix-only modules
40 try:
41 import curses
42 # We need termios as well, so if its import happens to raise, we bail on
43 # using curses altogether.
44 import termios
45 except ImportError:
46 USE_CURSES = False
47 else:
48 # Curses on Solaris may not be complete, so we can't use it there
49 USE_CURSES = hasattr(curses,'initscr')
50
36 51 # Other IPython utilities
37 52 import IPython
38 53 from IPython.Itpl import Itpl,itpl,printpl
39 54 from IPython import DPyGetOpt, platutils
40 55 from IPython.generics import result_display
41 56 import IPython.ipapi
42 57 from IPython.external.path import path
43 58 if os.name == "nt":
44 59 from IPython.winconsole import get_console_size
45 60
46 61 try:
47 62 set
48 63 except:
49 64 from sets import Set as set
50 65
51 66
52 67 #****************************************************************************
53 68 # Exceptions
54 69 class Error(Exception):
55 70 """Base class for exceptions in this module."""
56 71 pass
57 72
58 73 #----------------------------------------------------------------------------
59 74 class IOStream:
60 75 def __init__(self,stream,fallback):
61 76 if not hasattr(stream,'write') or not hasattr(stream,'flush'):
62 77 stream = fallback
63 78 self.stream = stream
64 79 self._swrite = stream.write
65 80 self.flush = stream.flush
66 81
67 82 def write(self,data):
68 83 try:
69 84 self._swrite(data)
70 85 except:
71 86 try:
72 87 # print handles some unicode issues which may trip a plain
73 88 # write() call. Attempt to emulate write() by using a
74 89 # trailing comma
75 90 print >> self.stream, data,
76 91 except:
77 92 # if we get here, something is seriously broken.
78 93 print >> sys.stderr, \
79 94 'ERROR - failed to write data to stream:', self.stream
80 95
81 96 def close(self):
82 97 pass
83 98
84 99
85 100 class IOTerm:
86 101 """ Term holds the file or file-like objects for handling I/O operations.
87 102
88 103 These are normally just sys.stdin, sys.stdout and sys.stderr but for
89 104 Windows they can can replaced to allow editing the strings before they are
90 105 displayed."""
91 106
92 107 # In the future, having IPython channel all its I/O operations through
93 108 # this class will make it easier to embed it into other environments which
94 109 # are not a normal terminal (such as a GUI-based shell)
95 110 def __init__(self,cin=None,cout=None,cerr=None):
96 111 self.cin = IOStream(cin,sys.stdin)
97 112 self.cout = IOStream(cout,sys.stdout)
98 113 self.cerr = IOStream(cerr,sys.stderr)
99 114
100 115 # Global variable to be used for all I/O
101 116 Term = IOTerm()
102 117
103 118 import IPython.rlineimpl as readline
104 119 # Remake Term to use the readline i/o facilities
105 120 if sys.platform == 'win32' and readline.have_readline:
106 121
107 122 Term = IOTerm(cout=readline._outputfile,cerr=readline._outputfile)
108 123
109 124
110 125 #****************************************************************************
111 126 # Generic warning/error printer, used by everything else
112 127 def warn(msg,level=2,exit_val=1):
113 128 """Standard warning printer. Gives formatting consistency.
114 129
115 130 Output is sent to Term.cerr (sys.stderr by default).
116 131
117 132 Options:
118 133
119 134 -level(2): allows finer control:
120 135 0 -> Do nothing, dummy function.
121 136 1 -> Print message.
122 137 2 -> Print 'WARNING:' + message. (Default level).
123 138 3 -> Print 'ERROR:' + message.
124 139 4 -> Print 'FATAL ERROR:' + message and trigger a sys.exit(exit_val).
125 140
126 141 -exit_val (1): exit value returned by sys.exit() for a level 4
127 142 warning. Ignored for all other levels."""
128 143
129 144 if level>0:
130 145 header = ['','','WARNING: ','ERROR: ','FATAL ERROR: ']
131 146 print >> Term.cerr, '%s%s' % (header[level],msg)
132 147 if level == 4:
133 148 print >> Term.cerr,'Exiting.\n'
134 149 sys.exit(exit_val)
135 150
136 151 def info(msg):
137 152 """Equivalent to warn(msg,level=1)."""
138 153
139 154 warn(msg,level=1)
140 155
141 156 def error(msg):
142 157 """Equivalent to warn(msg,level=3)."""
143 158
144 159 warn(msg,level=3)
145 160
146 161 def fatal(msg,exit_val=1):
147 162 """Equivalent to warn(msg,exit_val=exit_val,level=4)."""
148 163
149 164 warn(msg,exit_val=exit_val,level=4)
150 165
151 166 #---------------------------------------------------------------------------
152 167 # Debugging routines
153 168 #
154 169 def debugx(expr,pre_msg=''):
155 170 """Print the value of an expression from the caller's frame.
156 171
157 172 Takes an expression, evaluates it in the caller's frame and prints both
158 173 the given expression and the resulting value (as well as a debug mark
159 174 indicating the name of the calling function. The input must be of a form
160 175 suitable for eval().
161 176
162 177 An optional message can be passed, which will be prepended to the printed
163 178 expr->value pair."""
164 179
165 180 cf = sys._getframe(1)
166 181 print '[DBG:%s] %s%s -> %r' % (cf.f_code.co_name,pre_msg,expr,
167 182 eval(expr,cf.f_globals,cf.f_locals))
168 183
169 184 # deactivate it by uncommenting the following line, which makes it a no-op
170 185 #def debugx(expr,pre_msg=''): pass
171 186
172 187 #----------------------------------------------------------------------------
173 188 StringTypes = types.StringTypes
174 189
175 190 # Basic timing functionality
176 191
177 192 # If possible (Unix), use the resource module instead of time.clock()
178 193 try:
179 194 import resource
180 195 def clocku():
181 196 """clocku() -> floating point number
182 197
183 198 Return the *USER* CPU time in seconds since the start of the process.
184 199 This is done via a call to resource.getrusage, so it avoids the
185 200 wraparound problems in time.clock()."""
186 201
187 202 return resource.getrusage(resource.RUSAGE_SELF)[0]
188 203
189 204 def clocks():
190 205 """clocks() -> floating point number
191 206
192 207 Return the *SYSTEM* CPU time in seconds since the start of the process.
193 208 This is done via a call to resource.getrusage, so it avoids the
194 209 wraparound problems in time.clock()."""
195 210
196 211 return resource.getrusage(resource.RUSAGE_SELF)[1]
197 212
198 213 def clock():
199 214 """clock() -> floating point number
200 215
201 216 Return the *TOTAL USER+SYSTEM* CPU time in seconds since the start of
202 217 the process. This is done via a call to resource.getrusage, so it
203 218 avoids the wraparound problems in time.clock()."""
204 219
205 220 u,s = resource.getrusage(resource.RUSAGE_SELF)[:2]
206 221 return u+s
207 222
208 223 def clock2():
209 224 """clock2() -> (t_user,t_system)
210 225
211 226 Similar to clock(), but return a tuple of user/system times."""
212 227 return resource.getrusage(resource.RUSAGE_SELF)[:2]
213 228
214 229 except ImportError:
215 230 # There is no distinction of user/system time under windows, so we just use
216 231 # time.clock() for everything...
217 232 clocku = clocks = clock = time.clock
218 233 def clock2():
219 234 """Under windows, system CPU time can't be measured.
220 235
221 236 This just returns clock() and zero."""
222 237 return time.clock(),0.0
223 238
224 239 def timings_out(reps,func,*args,**kw):
225 240 """timings_out(reps,func,*args,**kw) -> (t_total,t_per_call,output)
226 241
227 242 Execute a function reps times, return a tuple with the elapsed total
228 243 CPU time in seconds, the time per call and the function's output.
229 244
230 245 Under Unix, the return value is the sum of user+system time consumed by
231 246 the process, computed via the resource module. This prevents problems
232 247 related to the wraparound effect which the time.clock() function has.
233 248
234 249 Under Windows the return value is in wall clock seconds. See the
235 250 documentation for the time module for more details."""
236 251
237 252 reps = int(reps)
238 253 assert reps >=1, 'reps must be >= 1'
239 254 if reps==1:
240 255 start = clock()
241 256 out = func(*args,**kw)
242 257 tot_time = clock()-start
243 258 else:
244 259 rng = xrange(reps-1) # the last time is executed separately to store output
245 260 start = clock()
246 261 for dummy in rng: func(*args,**kw)
247 262 out = func(*args,**kw) # one last time
248 263 tot_time = clock()-start
249 264 av_time = tot_time / reps
250 265 return tot_time,av_time,out
251 266
252 267 def timings(reps,func,*args,**kw):
253 268 """timings(reps,func,*args,**kw) -> (t_total,t_per_call)
254 269
255 270 Execute a function reps times, return a tuple with the elapsed total CPU
256 271 time in seconds and the time per call. These are just the first two values
257 272 in timings_out()."""
258 273
259 274 return timings_out(reps,func,*args,**kw)[0:2]
260 275
261 276 def timing(func,*args,**kw):
262 277 """timing(func,*args,**kw) -> t_total
263 278
264 279 Execute a function once, return the elapsed total CPU time in
265 280 seconds. This is just the first value in timings_out()."""
266 281
267 282 return timings_out(1,func,*args,**kw)[0]
268 283
269 284 #****************************************************************************
270 285 # file and system
271 286
272 287 def arg_split(s,posix=False):
273 288 """Split a command line's arguments in a shell-like manner.
274 289
275 290 This is a modified version of the standard library's shlex.split()
276 291 function, but with a default of posix=False for splitting, so that quotes
277 292 in inputs are respected."""
278 293
279 294 # XXX - there may be unicode-related problems here!!! I'm not sure that
280 295 # shlex is truly unicode-safe, so it might be necessary to do
281 296 #
282 297 # s = s.encode(sys.stdin.encoding)
283 298 #
284 299 # first, to ensure that shlex gets a normal string. Input from anyone who
285 300 # knows more about unicode and shlex than I would be good to have here...
286 301 lex = shlex.shlex(s, posix=posix)
287 302 lex.whitespace_split = True
288 303 return list(lex)
289 304
290 305 def system(cmd,verbose=0,debug=0,header=''):
291 306 """Execute a system command, return its exit status.
292 307
293 308 Options:
294 309
295 310 - verbose (0): print the command to be executed.
296 311
297 312 - debug (0): only print, do not actually execute.
298 313
299 314 - header (''): Header to print on screen prior to the executed command (it
300 315 is only prepended to the command, no newlines are added).
301 316
302 317 Note: a stateful version of this function is available through the
303 318 SystemExec class."""
304 319
305 320 stat = 0
306 321 if verbose or debug: print header+cmd
307 322 sys.stdout.flush()
308 323 if not debug: stat = os.system(cmd)
309 324 return stat
310 325
311 326 def abbrev_cwd():
312 327 """ Return abbreviated version of cwd, e.g. d:mydir """
313 328 cwd = os.getcwd().replace('\\','/')
314 329 drivepart = ''
315 330 tail = cwd
316 331 if sys.platform == 'win32':
317 332 if len(cwd) < 4:
318 333 return cwd
319 334 drivepart,tail = os.path.splitdrive(cwd)
320 335
321 336
322 337 parts = tail.split('/')
323 338 if len(parts) > 2:
324 339 tail = '/'.join(parts[-2:])
325 340
326 341 return (drivepart + (
327 342 cwd == '/' and '/' or tail))
328 343
329 344
330 345 # This function is used by ipython in a lot of places to make system calls.
331 346 # We need it to be slightly different under win32, due to the vagaries of
332 347 # 'network shares'. A win32 override is below.
333 348
334 349 def shell(cmd,verbose=0,debug=0,header=''):
335 350 """Execute a command in the system shell, always return None.
336 351
337 352 Options:
338 353
339 354 - verbose (0): print the command to be executed.
340 355
341 356 - debug (0): only print, do not actually execute.
342 357
343 358 - header (''): Header to print on screen prior to the executed command (it
344 359 is only prepended to the command, no newlines are added).
345 360
346 361 Note: this is similar to genutils.system(), but it returns None so it can
347 362 be conveniently used in interactive loops without getting the return value
348 363 (typically 0) printed many times."""
349 364
350 365 stat = 0
351 366 if verbose or debug: print header+cmd
352 367 # flush stdout so we don't mangle python's buffering
353 368 sys.stdout.flush()
354 369
355 370 if not debug:
356 371 platutils.set_term_title("IPy " + cmd)
357 372 os.system(cmd)
358 373 platutils.set_term_title("IPy " + abbrev_cwd())
359 374
360 375 # override shell() for win32 to deal with network shares
361 376 if os.name in ('nt','dos'):
362 377
363 378 shell_ori = shell
364 379
365 380 def shell(cmd,verbose=0,debug=0,header=''):
366 381 if os.getcwd().startswith(r"\\"):
367 382 path = os.getcwd()
368 383 # change to c drive (cannot be on UNC-share when issuing os.system,
369 384 # as cmd.exe cannot handle UNC addresses)
370 385 os.chdir("c:")
371 386 # issue pushd to the UNC-share and then run the command
372 387 try:
373 388 shell_ori('"pushd %s&&"'%path+cmd,verbose,debug,header)
374 389 finally:
375 390 os.chdir(path)
376 391 else:
377 392 shell_ori(cmd,verbose,debug,header)
378 393
379 394 shell.__doc__ = shell_ori.__doc__
380 395
381 396 def getoutput(cmd,verbose=0,debug=0,header='',split=0):
382 397 """Dummy substitute for perl's backquotes.
383 398
384 399 Executes a command and returns the output.
385 400
386 401 Accepts the same arguments as system(), plus:
387 402
388 403 - split(0): if true, the output is returned as a list split on newlines.
389 404
390 405 Note: a stateful version of this function is available through the
391 406 SystemExec class.
392 407
393 408 This is pretty much deprecated and rarely used,
394 409 genutils.getoutputerror may be what you need.
395 410
396 411 """
397 412
398 413 if verbose or debug: print header+cmd
399 414 if not debug:
400 415 output = os.popen(cmd).read()
401 416 # stipping last \n is here for backwards compat.
402 417 if output.endswith('\n'):
403 418 output = output[:-1]
404 419 if split:
405 420 return output.split('\n')
406 421 else:
407 422 return output
408 423
409 424 def getoutputerror(cmd,verbose=0,debug=0,header='',split=0):
410 425 """Return (standard output,standard error) of executing cmd in a shell.
411 426
412 427 Accepts the same arguments as system(), plus:
413 428
414 429 - split(0): if true, each of stdout/err is returned as a list split on
415 430 newlines.
416 431
417 432 Note: a stateful version of this function is available through the
418 433 SystemExec class."""
419 434
420 435 if verbose or debug: print header+cmd
421 436 if not cmd:
422 437 if split:
423 438 return [],[]
424 439 else:
425 440 return '',''
426 441 if not debug:
427 442 pin,pout,perr = os.popen3(cmd)
428 443 tout = pout.read().rstrip()
429 444 terr = perr.read().rstrip()
430 445 pin.close()
431 446 pout.close()
432 447 perr.close()
433 448 if split:
434 449 return tout.split('\n'),terr.split('\n')
435 450 else:
436 451 return tout,terr
437 452
438 453 # for compatibility with older naming conventions
439 454 xsys = system
440 455 bq = getoutput
441 456
442 457 class SystemExec:
443 458 """Access the system and getoutput functions through a stateful interface.
444 459
445 460 Note: here we refer to the system and getoutput functions from this
446 461 library, not the ones from the standard python library.
447 462
448 463 This class offers the system and getoutput functions as methods, but the
449 464 verbose, debug and header parameters can be set for the instance (at
450 465 creation time or later) so that they don't need to be specified on each
451 466 call.
452 467
453 468 For efficiency reasons, there's no way to override the parameters on a
454 469 per-call basis other than by setting instance attributes. If you need
455 470 local overrides, it's best to directly call system() or getoutput().
456 471
457 472 The following names are provided as alternate options:
458 473 - xsys: alias to system
459 474 - bq: alias to getoutput
460 475
461 476 An instance can then be created as:
462 477 >>> sysexec = SystemExec(verbose=1,debug=0,header='Calling: ')
463 478
464 479 And used as:
465 480 >>> sysexec.xsys('pwd')
466 481 >>> dirlist = sysexec.bq('ls -l')
467 482 """
468 483
469 484 def __init__(self,verbose=0,debug=0,header='',split=0):
470 485 """Specify the instance's values for verbose, debug and header."""
471 486 setattr_list(self,'verbose debug header split')
472 487
473 488 def system(self,cmd):
474 489 """Stateful interface to system(), with the same keyword parameters."""
475 490
476 491 system(cmd,self.verbose,self.debug,self.header)
477 492
478 493 def shell(self,cmd):
479 494 """Stateful interface to shell(), with the same keyword parameters."""
480 495
481 496 shell(cmd,self.verbose,self.debug,self.header)
482 497
483 498 xsys = system # alias
484 499
485 500 def getoutput(self,cmd):
486 501 """Stateful interface to getoutput()."""
487 502
488 503 return getoutput(cmd,self.verbose,self.debug,self.header,self.split)
489 504
490 505 def getoutputerror(self,cmd):
491 506 """Stateful interface to getoutputerror()."""
492 507
493 508 return getoutputerror(cmd,self.verbose,self.debug,self.header,self.split)
494 509
495 510 bq = getoutput # alias
496 511
497 512 #-----------------------------------------------------------------------------
498 513 def mutex_opts(dict,ex_op):
499 514 """Check for presence of mutually exclusive keys in a dict.
500 515
501 516 Call: mutex_opts(dict,[[op1a,op1b],[op2a,op2b]...]"""
502 517 for op1,op2 in ex_op:
503 518 if op1 in dict and op2 in dict:
504 519 raise ValueError,'\n*** ERROR in Arguments *** '\
505 520 'Options '+op1+' and '+op2+' are mutually exclusive.'
506 521
507 522 #-----------------------------------------------------------------------------
508 523 def get_py_filename(name):
509 524 """Return a valid python filename in the current directory.
510 525
511 526 If the given name is not a file, it adds '.py' and searches again.
512 527 Raises IOError with an informative message if the file isn't found."""
513 528
514 529 name = os.path.expanduser(name)
515 530 if not os.path.isfile(name) and not name.endswith('.py'):
516 531 name += '.py'
517 532 if os.path.isfile(name):
518 533 return name
519 534 else:
520 535 raise IOError,'File `%s` not found.' % name
521 536
522 537 #-----------------------------------------------------------------------------
523 538 def filefind(fname,alt_dirs = None):
524 539 """Return the given filename either in the current directory, if it
525 540 exists, or in a specified list of directories.
526 541
527 542 ~ expansion is done on all file and directory names.
528 543
529 544 Upon an unsuccessful search, raise an IOError exception."""
530 545
531 546 if alt_dirs is None:
532 547 try:
533 548 alt_dirs = get_home_dir()
534 549 except HomeDirError:
535 550 alt_dirs = os.getcwd()
536 551 search = [fname] + list_strings(alt_dirs)
537 552 search = map(os.path.expanduser,search)
538 553 #print 'search list for',fname,'list:',search # dbg
539 554 fname = search[0]
540 555 if os.path.isfile(fname):
541 556 return fname
542 557 for direc in search[1:]:
543 558 testname = os.path.join(direc,fname)
544 559 #print 'testname',testname # dbg
545 560 if os.path.isfile(testname):
546 561 return testname
547 562 raise IOError,'File' + `fname` + \
548 563 ' not found in current or supplied directories:' + `alt_dirs`
549 564
550 565 #----------------------------------------------------------------------------
551 566 def file_read(filename):
552 567 """Read a file and close it. Returns the file source."""
553 568 fobj = open(filename,'r');
554 569 source = fobj.read();
555 570 fobj.close()
556 571 return source
557 572
558 573 def file_readlines(filename):
559 574 """Read a file and close it. Returns the file source using readlines()."""
560 575 fobj = open(filename,'r');
561 576 lines = fobj.readlines();
562 577 fobj.close()
563 578 return lines
564 579
565 580 #----------------------------------------------------------------------------
566 581 def target_outdated(target,deps):
567 582 """Determine whether a target is out of date.
568 583
569 584 target_outdated(target,deps) -> 1/0
570 585
571 586 deps: list of filenames which MUST exist.
572 587 target: single filename which may or may not exist.
573 588
574 589 If target doesn't exist or is older than any file listed in deps, return
575 590 true, otherwise return false.
576 591 """
577 592 try:
578 593 target_time = os.path.getmtime(target)
579 594 except os.error:
580 595 return 1
581 596 for dep in deps:
582 597 dep_time = os.path.getmtime(dep)
583 598 if dep_time > target_time:
584 599 #print "For target",target,"Dep failed:",dep # dbg
585 600 #print "times (dep,tar):",dep_time,target_time # dbg
586 601 return 1
587 602 return 0
588 603
589 604 #-----------------------------------------------------------------------------
590 605 def target_update(target,deps,cmd):
591 606 """Update a target with a given command given a list of dependencies.
592 607
593 608 target_update(target,deps,cmd) -> runs cmd if target is outdated.
594 609
595 610 This is just a wrapper around target_outdated() which calls the given
596 611 command if target is outdated."""
597 612
598 613 if target_outdated(target,deps):
599 614 xsys(cmd)
600 615
601 616 #----------------------------------------------------------------------------
602 617 def unquote_ends(istr):
603 618 """Remove a single pair of quotes from the endpoints of a string."""
604 619
605 620 if not istr:
606 621 return istr
607 622 if (istr[0]=="'" and istr[-1]=="'") or \
608 623 (istr[0]=='"' and istr[-1]=='"'):
609 624 return istr[1:-1]
610 625 else:
611 626 return istr
612 627
613 628 #----------------------------------------------------------------------------
614 629 def process_cmdline(argv,names=[],defaults={},usage=''):
615 630 """ Process command-line options and arguments.
616 631
617 632 Arguments:
618 633
619 634 - argv: list of arguments, typically sys.argv.
620 635
621 636 - names: list of option names. See DPyGetOpt docs for details on options
622 637 syntax.
623 638
624 639 - defaults: dict of default values.
625 640
626 641 - usage: optional usage notice to print if a wrong argument is passed.
627 642
628 643 Return a dict of options and a list of free arguments."""
629 644
630 645 getopt = DPyGetOpt.DPyGetOpt()
631 646 getopt.setIgnoreCase(0)
632 647 getopt.parseConfiguration(names)
633 648
634 649 try:
635 650 getopt.processArguments(argv)
636 651 except DPyGetOpt.ArgumentError, exc:
637 652 print usage
638 653 warn('"%s"' % exc,level=4)
639 654
640 655 defaults.update(getopt.optionValues)
641 656 args = getopt.freeValues
642 657
643 658 return defaults,args
644 659
645 660 #----------------------------------------------------------------------------
646 661 def optstr2types(ostr):
647 662 """Convert a string of option names to a dict of type mappings.
648 663
649 664 optstr2types(str) -> {None:'string_opts',int:'int_opts',float:'float_opts'}
650 665
651 666 This is used to get the types of all the options in a string formatted
652 667 with the conventions of DPyGetOpt. The 'type' None is used for options
653 668 which are strings (they need no further conversion). This function's main
654 669 use is to get a typemap for use with read_dict().
655 670 """
656 671
657 672 typeconv = {None:'',int:'',float:''}
658 673 typemap = {'s':None,'i':int,'f':float}
659 674 opt_re = re.compile(r'([\w]*)([^:=]*:?=?)([sif]?)')
660 675
661 676 for w in ostr.split():
662 677 oname,alias,otype = opt_re.match(w).groups()
663 678 if otype == '' or alias == '!': # simple switches are integers too
664 679 otype = 'i'
665 680 typeconv[typemap[otype]] += oname + ' '
666 681 return typeconv
667 682
668 683 #----------------------------------------------------------------------------
669 684 def read_dict(filename,type_conv=None,**opt):
670 685
671 686 """Read a dictionary of key=value pairs from an input file, optionally
672 687 performing conversions on the resulting values.
673 688
674 689 read_dict(filename,type_conv,**opt) -> dict
675 690
676 691 Only one value per line is accepted, the format should be
677 692 # optional comments are ignored
678 693 key value\n
679 694
680 695 Args:
681 696
682 697 - type_conv: A dictionary specifying which keys need to be converted to
683 698 which types. By default all keys are read as strings. This dictionary
684 699 should have as its keys valid conversion functions for strings
685 700 (int,long,float,complex, or your own). The value for each key
686 701 (converter) should be a whitespace separated string containing the names
687 702 of all the entries in the file to be converted using that function. For
688 703 keys to be left alone, use None as the conversion function (only needed
689 704 with purge=1, see below).
690 705
691 706 - opt: dictionary with extra options as below (default in parens)
692 707
693 708 purge(0): if set to 1, all keys *not* listed in type_conv are purged out
694 709 of the dictionary to be returned. If purge is going to be used, the
695 710 set of keys to be left as strings also has to be explicitly specified
696 711 using the (non-existent) conversion function None.
697 712
698 713 fs(None): field separator. This is the key/value separator to be used
699 714 when parsing the file. The None default means any whitespace [behavior
700 715 of string.split()].
701 716
702 717 strip(0): if 1, strip string values of leading/trailinig whitespace.
703 718
704 719 warn(1): warning level if requested keys are not found in file.
705 720 - 0: silently ignore.
706 721 - 1: inform but proceed.
707 722 - 2: raise KeyError exception.
708 723
709 724 no_empty(0): if 1, remove keys with whitespace strings as a value.
710 725
711 726 unique([]): list of keys (or space separated string) which can't be
712 727 repeated. If one such key is found in the file, each new instance
713 728 overwrites the previous one. For keys not listed here, the behavior is
714 729 to make a list of all appearances.
715 730
716 731 Example:
717 732 If the input file test.ini has:
718 733 i 3
719 734 x 4.5
720 735 y 5.5
721 736 s hi ho
722 737 Then:
723 738
724 739 >>> type_conv={int:'i',float:'x',None:'s'}
725 740 >>> read_dict('test.ini')
726 741 {'i': '3', 's': 'hi ho', 'x': '4.5', 'y': '5.5'}
727 742 >>> read_dict('test.ini',type_conv)
728 743 {'i': 3, 's': 'hi ho', 'x': 4.5, 'y': '5.5'}
729 744 >>> read_dict('test.ini',type_conv,purge=1)
730 745 {'i': 3, 's': 'hi ho', 'x': 4.5}
731 746 """
732 747
733 748 # starting config
734 749 opt.setdefault('purge',0)
735 750 opt.setdefault('fs',None) # field sep defaults to any whitespace
736 751 opt.setdefault('strip',0)
737 752 opt.setdefault('warn',1)
738 753 opt.setdefault('no_empty',0)
739 754 opt.setdefault('unique','')
740 755 if type(opt['unique']) in StringTypes:
741 756 unique_keys = qw(opt['unique'])
742 757 elif type(opt['unique']) in (types.TupleType,types.ListType):
743 758 unique_keys = opt['unique']
744 759 else:
745 760 raise ValueError, 'Unique keys must be given as a string, List or Tuple'
746 761
747 762 dict = {}
748 763 # first read in table of values as strings
749 764 file = open(filename,'r')
750 765 for line in file.readlines():
751 766 line = line.strip()
752 767 if len(line) and line[0]=='#': continue
753 768 if len(line)>0:
754 769 lsplit = line.split(opt['fs'],1)
755 770 try:
756 771 key,val = lsplit
757 772 except ValueError:
758 773 key,val = lsplit[0],''
759 774 key = key.strip()
760 775 if opt['strip']: val = val.strip()
761 776 if val == "''" or val == '""': val = ''
762 777 if opt['no_empty'] and (val=='' or val.isspace()):
763 778 continue
764 779 # if a key is found more than once in the file, build a list
765 780 # unless it's in the 'unique' list. In that case, last found in file
766 781 # takes precedence. User beware.
767 782 try:
768 783 if dict[key] and key in unique_keys:
769 784 dict[key] = val
770 785 elif type(dict[key]) is types.ListType:
771 786 dict[key].append(val)
772 787 else:
773 788 dict[key] = [dict[key],val]
774 789 except KeyError:
775 790 dict[key] = val
776 791 # purge if requested
777 792 if opt['purge']:
778 793 accepted_keys = qwflat(type_conv.values())
779 794 for key in dict.keys():
780 795 if key in accepted_keys: continue
781 796 del(dict[key])
782 797 # now convert if requested
783 798 if type_conv==None: return dict
784 799 conversions = type_conv.keys()
785 800 try: conversions.remove(None)
786 801 except: pass
787 802 for convert in conversions:
788 803 for val in qw(type_conv[convert]):
789 804 try:
790 805 dict[val] = convert(dict[val])
791 806 except KeyError,e:
792 807 if opt['warn'] == 0:
793 808 pass
794 809 elif opt['warn'] == 1:
795 810 print >>sys.stderr, 'Warning: key',val,\
796 811 'not found in file',filename
797 812 elif opt['warn'] == 2:
798 813 raise KeyError,e
799 814 else:
800 815 raise ValueError,'Warning level must be 0,1 or 2'
801 816
802 817 return dict
803 818
804 819 #----------------------------------------------------------------------------
805 820 def flag_calls(func):
806 821 """Wrap a function to detect and flag when it gets called.
807 822
808 823 This is a decorator which takes a function and wraps it in a function with
809 824 a 'called' attribute. wrapper.called is initialized to False.
810 825
811 826 The wrapper.called attribute is set to False right before each call to the
812 827 wrapped function, so if the call fails it remains False. After the call
813 828 completes, wrapper.called is set to True and the output is returned.
814 829
815 830 Testing for truth in wrapper.called allows you to determine if a call to
816 831 func() was attempted and succeeded."""
817 832
818 833 def wrapper(*args,**kw):
819 834 wrapper.called = False
820 835 out = func(*args,**kw)
821 836 wrapper.called = True
822 837 return out
823 838
824 839 wrapper.called = False
825 840 wrapper.__doc__ = func.__doc__
826 841 return wrapper
827 842
828 843 #----------------------------------------------------------------------------
829 844 def dhook_wrap(func,*a,**k):
830 845 """Wrap a function call in a sys.displayhook controller.
831 846
832 847 Returns a wrapper around func which calls func, with all its arguments and
833 848 keywords unmodified, using the default sys.displayhook. Since IPython
834 849 modifies sys.displayhook, it breaks the behavior of certain systems that
835 850 rely on the default behavior, notably doctest.
836 851 """
837 852
838 853 def f(*a,**k):
839 854
840 855 dhook_s = sys.displayhook
841 856 sys.displayhook = sys.__displayhook__
842 857 try:
843 858 out = func(*a,**k)
844 859 finally:
845 860 sys.displayhook = dhook_s
846 861
847 862 return out
848 863
849 864 f.__doc__ = func.__doc__
850 865 return f
851 866
852 867 #----------------------------------------------------------------------------
853 868 def doctest_reload():
854 869 """Properly reload doctest to reuse it interactively.
855 870
856 871 This routine:
857 872
858 873 - reloads doctest
859 874
860 875 - resets its global 'master' attribute to None, so that multiple uses of
861 876 the module interactively don't produce cumulative reports.
862 877
863 878 - Monkeypatches its core test runner method to protect it from IPython's
864 879 modified displayhook. Doctest expects the default displayhook behavior
865 880 deep down, so our modification breaks it completely. For this reason, a
866 881 hard monkeypatch seems like a reasonable solution rather than asking
867 882 users to manually use a different doctest runner when under IPython."""
868 883
869 884 import doctest
870 885 reload(doctest)
871 886 doctest.master=None
872 887
873 888 try:
874 889 doctest.DocTestRunner
875 890 except AttributeError:
876 891 # This is only for python 2.3 compatibility, remove once we move to
877 892 # 2.4 only.
878 893 pass
879 894 else:
880 895 doctest.DocTestRunner.run = dhook_wrap(doctest.DocTestRunner.run)
881 896
882 897 #----------------------------------------------------------------------------
883 898 class HomeDirError(Error):
884 899 pass
885 900
886 901 def get_home_dir():
887 902 """Return the closest possible equivalent to a 'home' directory.
888 903
889 904 We first try $HOME. Absent that, on NT it's $HOMEDRIVE\$HOMEPATH.
890 905
891 906 Currently only Posix and NT are implemented, a HomeDirError exception is
892 907 raised for all other OSes. """
893 908
894 909 isdir = os.path.isdir
895 910 env = os.environ
896 911
897 912 # first, check py2exe distribution root directory for _ipython.
898 913 # This overrides all. Normally does not exist.
899 914
900 915 if '\\library.zip\\' in IPython.__file__.lower():
901 916 root, rest = IPython.__file__.lower().split('library.zip')
902 917 if isdir(root + '_ipython'):
903 918 os.environ["IPYKITROOT"] = root.rstrip('\\')
904 919 return root
905 920
906 921 try:
907 922 homedir = env['HOME']
908 923 if not isdir(homedir):
909 924 # in case a user stuck some string which does NOT resolve to a
910 925 # valid path, it's as good as if we hadn't foud it
911 926 raise KeyError
912 927 return homedir
913 928 except KeyError:
914 929 if os.name == 'posix':
915 930 raise HomeDirError,'undefined $HOME, IPython can not proceed.'
916 931 elif os.name == 'nt':
917 932 # For some strange reason, win9x returns 'nt' for os.name.
918 933 try:
919 934 homedir = os.path.join(env['HOMEDRIVE'],env['HOMEPATH'])
920 935 if not isdir(homedir):
921 936 homedir = os.path.join(env['USERPROFILE'])
922 937 if not isdir(homedir):
923 938 raise HomeDirError
924 939 return homedir
925 940 except:
926 941 try:
927 942 # Use the registry to get the 'My Documents' folder.
928 943 import _winreg as wreg
929 944 key = wreg.OpenKey(wreg.HKEY_CURRENT_USER,
930 945 "Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders")
931 946 homedir = wreg.QueryValueEx(key,'Personal')[0]
932 947 key.Close()
933 948 if not isdir(homedir):
934 949 e = ('Invalid "Personal" folder registry key '
935 950 'typically "My Documents".\n'
936 951 'Value: %s\n'
937 952 'This is not a valid directory on your system.' %
938 953 homedir)
939 954 raise HomeDirError(e)
940 955 return homedir
941 956 except HomeDirError:
942 957 raise
943 958 except:
944 959 return 'C:\\'
945 960 elif os.name == 'dos':
946 961 # Desperate, may do absurd things in classic MacOS. May work under DOS.
947 962 return 'C:\\'
948 963 else:
949 964 raise HomeDirError,'support for your operating system not implemented.'
950 965
951 966 #****************************************************************************
952 967 # strings and text
953 968
954 969 class LSString(str):
955 970 """String derivative with a special access attributes.
956 971
957 972 These are normal strings, but with the special attributes:
958 973
959 974 .l (or .list) : value as list (split on newlines).
960 975 .n (or .nlstr): original value (the string itself).
961 976 .s (or .spstr): value as whitespace-separated string.
962 977 .p (or .paths): list of path objects
963 978
964 979 Any values which require transformations are computed only once and
965 980 cached.
966 981
967 982 Such strings are very useful to efficiently interact with the shell, which
968 983 typically only understands whitespace-separated options for commands."""
969 984
970 985 def get_list(self):
971 986 try:
972 987 return self.__list
973 988 except AttributeError:
974 989 self.__list = self.split('\n')
975 990 return self.__list
976 991
977 992 l = list = property(get_list)
978 993
979 994 def get_spstr(self):
980 995 try:
981 996 return self.__spstr
982 997 except AttributeError:
983 998 self.__spstr = self.replace('\n',' ')
984 999 return self.__spstr
985 1000
986 1001 s = spstr = property(get_spstr)
987 1002
988 1003 def get_nlstr(self):
989 1004 return self
990 1005
991 1006 n = nlstr = property(get_nlstr)
992 1007
993 1008 def get_paths(self):
994 1009 try:
995 1010 return self.__paths
996 1011 except AttributeError:
997 1012 self.__paths = [path(p) for p in self.split('\n') if os.path.exists(p)]
998 1013 return self.__paths
999 1014
1000 1015 p = paths = property(get_paths)
1001 1016
1002 1017 def print_lsstring(arg):
1003 1018 """ Prettier (non-repr-like) and more informative printer for LSString """
1004 1019 print "LSString (.p, .n, .l, .s available). Value:"
1005 1020 print arg
1006 1021
1007 1022 print_lsstring = result_display.when_type(LSString)(print_lsstring)
1008 1023
1009 1024 #----------------------------------------------------------------------------
1010 1025 class SList(list):
1011 1026 """List derivative with a special access attributes.
1012 1027
1013 1028 These are normal lists, but with the special attributes:
1014 1029
1015 1030 .l (or .list) : value as list (the list itself).
1016 1031 .n (or .nlstr): value as a string, joined on newlines.
1017 1032 .s (or .spstr): value as a string, joined on spaces.
1018 1033 .p (or .paths): list of path objects
1019 1034
1020 1035 Any values which require transformations are computed only once and
1021 1036 cached."""
1022 1037
1023 1038 def get_list(self):
1024 1039 return self
1025 1040
1026 1041 l = list = property(get_list)
1027 1042
1028 1043 def get_spstr(self):
1029 1044 try:
1030 1045 return self.__spstr
1031 1046 except AttributeError:
1032 1047 self.__spstr = ' '.join(self)
1033 1048 return self.__spstr
1034 1049
1035 1050 s = spstr = property(get_spstr)
1036 1051
1037 1052 def get_nlstr(self):
1038 1053 try:
1039 1054 return self.__nlstr
1040 1055 except AttributeError:
1041 1056 self.__nlstr = '\n'.join(self)
1042 1057 return self.__nlstr
1043 1058
1044 1059 n = nlstr = property(get_nlstr)
1045 1060
1046 1061 def get_paths(self):
1047 1062 try:
1048 1063 return self.__paths
1049 1064 except AttributeError:
1050 1065 self.__paths = [path(p) for p in self if os.path.exists(p)]
1051 1066 return self.__paths
1052 1067
1053 1068 p = paths = property(get_paths)
1054 1069
1055 def grep(self, pattern, prune = False):
1070 def grep(self, pattern, prune = False, field = None):
1056 1071 """ Return all strings matching 'pattern' (a regex or callable)
1057 1072
1058 1073 This is case-insensitive. If prune is true, return all items
1059 1074 NOT matching the pattern.
1060 1075
1076 If field is specified, the match must occur in the specified
1077 whitespace-separated field.
1078
1061 1079 Examples::
1062 1080
1063 1081 a.grep( lambda x: x.startswith('C') )
1064 1082 a.grep('Cha.*log', prune=1)
1083 a.grep('chm', field=-1)
1065 1084 """
1085
1086 def match_target(s):
1087 if field is None:
1088 return s
1089 parts = s.split()
1090 try:
1091 tgt = parts[field]
1092 return tgt
1093 except IndexError:
1094 return ""
1095
1066 1096 if isinstance(pattern, basestring):
1067 1097 pred = lambda x : re.search(pattern, x, re.IGNORECASE)
1068 1098 else:
1069 1099 pred = pattern
1070 1100 if not prune:
1071 return SList([el for el in self if pred(el)])
1101 return SList([el for el in self if pred(match_target(el))])
1072 1102 else:
1073 return SList([el for el in self if not pred(el)])
1103 return SList([el for el in self if not pred(match_target(el))])
1074 1104 def fields(self, *fields):
1075 1105 """ Collect whitespace-separated fields from string list
1076 1106
1077 1107 Allows quick awk-like usage of string lists.
1078 1108
1079 1109 Example data (in var a, created by 'a = !ls -l')::
1080 1110 -rwxrwxrwx 1 ville None 18 Dec 14 2006 ChangeLog
1081 1111 drwxrwxrwx+ 6 ville None 0 Oct 24 18:05 IPython
1082 1112
1083 1113 a.fields(0) is ['-rwxrwxrwx', 'drwxrwxrwx+']
1084 1114 a.fields(1,0) is ['1 -rwxrwxrwx', '6 drwxrwxrwx+']
1085 1115 (note the joining by space).
1116 a.fields(-1) is ['ChangeLog', 'IPython']
1086 1117
1087 1118 IndexErrors are ignored.
1088 1119
1089 1120 Without args, fields() just split()'s the strings.
1090 1121 """
1091 1122 if len(fields) == 0:
1092 1123 return [el.split() for el in self]
1093 1124
1094 1125 res = SList()
1095 1126 for el in [f.split() for f in self]:
1096 1127 lineparts = []
1097 1128
1098 1129 for fd in fields:
1099 1130 try:
1100 1131 lineparts.append(el[fd])
1101 1132 except IndexError:
1102 1133 pass
1103 1134 if lineparts:
1104 1135 res.append(" ".join(lineparts))
1105 1136
1106 1137 return res
1107 1138
1108 1139
1109 1140
1110 1141
1111 1142
1112 1143 def print_slist(arg):
1113 1144 """ Prettier (non-repr-like) and more informative printer for SList """
1114 1145 print "SList (.p, .n, .l, .s, .grep(), .fields() available). Value:"
1115 1146 nlprint(arg)
1116 1147
1117 1148 print_slist = result_display.when_type(SList)(print_slist)
1118 1149
1119 1150
1120 1151
1121 1152 #----------------------------------------------------------------------------
1122 1153 def esc_quotes(strng):
1123 1154 """Return the input string with single and double quotes escaped out"""
1124 1155
1125 1156 return strng.replace('"','\\"').replace("'","\\'")
1126 1157
1127 1158 #----------------------------------------------------------------------------
1128 1159 def make_quoted_expr(s):
1129 1160 """Return string s in appropriate quotes, using raw string if possible.
1130 1161
1131 1162 Effectively this turns string: cd \ao\ao\
1132 1163 to: r"cd \ao\ao\_"[:-1]
1133 1164
1134 1165 Note the use of raw string and padding at the end to allow trailing backslash.
1135 1166
1136 1167 """
1137 1168
1138 1169 tail = ''
1139 1170 tailpadding = ''
1140 1171 raw = ''
1141 1172 if "\\" in s:
1142 1173 raw = 'r'
1143 1174 if s.endswith('\\'):
1144 1175 tail = '[:-1]'
1145 1176 tailpadding = '_'
1146 1177 if '"' not in s:
1147 1178 quote = '"'
1148 1179 elif "'" not in s:
1149 1180 quote = "'"
1150 1181 elif '"""' not in s and not s.endswith('"'):
1151 1182 quote = '"""'
1152 1183 elif "'''" not in s and not s.endswith("'"):
1153 1184 quote = "'''"
1154 1185 else:
1155 1186 # give up, backslash-escaped string will do
1156 1187 return '"%s"' % esc_quotes(s)
1157 1188 res = raw + quote + s + tailpadding + quote + tail
1158 1189 return res
1159 1190
1160 1191
1161 1192 #----------------------------------------------------------------------------
1162 1193 def raw_input_multi(header='', ps1='==> ', ps2='..> ',terminate_str = '.'):
1163 1194 """Take multiple lines of input.
1164 1195
1165 1196 A list with each line of input as a separate element is returned when a
1166 1197 termination string is entered (defaults to a single '.'). Input can also
1167 1198 terminate via EOF (^D in Unix, ^Z-RET in Windows).
1168 1199
1169 1200 Lines of input which end in \\ are joined into single entries (and a
1170 1201 secondary continuation prompt is issued as long as the user terminates
1171 1202 lines with \\). This allows entering very long strings which are still
1172 1203 meant to be treated as single entities.
1173 1204 """
1174 1205
1175 1206 try:
1176 1207 if header:
1177 1208 header += '\n'
1178 1209 lines = [raw_input(header + ps1)]
1179 1210 except EOFError:
1180 1211 return []
1181 1212 terminate = [terminate_str]
1182 1213 try:
1183 1214 while lines[-1:] != terminate:
1184 1215 new_line = raw_input(ps1)
1185 1216 while new_line.endswith('\\'):
1186 1217 new_line = new_line[:-1] + raw_input(ps2)
1187 1218 lines.append(new_line)
1188 1219
1189 1220 return lines[:-1] # don't return the termination command
1190 1221 except EOFError:
1191 1222 print
1192 1223 return lines
1193 1224
1194 1225 #----------------------------------------------------------------------------
1195 1226 def raw_input_ext(prompt='', ps2='... '):
1196 1227 """Similar to raw_input(), but accepts extended lines if input ends with \\."""
1197 1228
1198 1229 line = raw_input(prompt)
1199 1230 while line.endswith('\\'):
1200 1231 line = line[:-1] + raw_input(ps2)
1201 1232 return line
1202 1233
1203 1234 #----------------------------------------------------------------------------
1204 1235 def ask_yes_no(prompt,default=None):
1205 1236 """Asks a question and returns a boolean (y/n) answer.
1206 1237
1207 1238 If default is given (one of 'y','n'), it is used if the user input is
1208 1239 empty. Otherwise the question is repeated until an answer is given.
1209 1240
1210 1241 An EOF is treated as the default answer. If there is no default, an
1211 1242 exception is raised to prevent infinite loops.
1212 1243
1213 1244 Valid answers are: y/yes/n/no (match is not case sensitive)."""
1214 1245
1215 1246 answers = {'y':True,'n':False,'yes':True,'no':False}
1216 1247 ans = None
1217 1248 while ans not in answers.keys():
1218 1249 try:
1219 1250 ans = raw_input(prompt+' ').lower()
1220 1251 if not ans: # response was an empty string
1221 1252 ans = default
1222 1253 except KeyboardInterrupt:
1223 1254 pass
1224 1255 except EOFError:
1225 1256 if default in answers.keys():
1226 1257 ans = default
1227 1258 print
1228 1259 else:
1229 1260 raise
1230 1261
1231 1262 return answers[ans]
1232 1263
1233 1264 #----------------------------------------------------------------------------
1234 1265 def marquee(txt='',width=78,mark='*'):
1235 1266 """Return the input string centered in a 'marquee'."""
1236 1267 if not txt:
1237 1268 return (mark*width)[:width]
1238 1269 nmark = (width-len(txt)-2)/len(mark)/2
1239 1270 if nmark < 0: nmark =0
1240 1271 marks = mark*nmark
1241 1272 return '%s %s %s' % (marks,txt,marks)
1242 1273
1243 1274 #----------------------------------------------------------------------------
1244 1275 class EvalDict:
1245 1276 """
1246 1277 Emulate a dict which evaluates its contents in the caller's frame.
1247 1278
1248 1279 Usage:
1249 1280 >>>number = 19
1250 1281 >>>text = "python"
1251 1282 >>>print "%(text.capitalize())s %(number/9.0).1f rules!" % EvalDict()
1252 1283 """
1253 1284
1254 1285 # This version is due to sismex01@hebmex.com on c.l.py, and is basically a
1255 1286 # modified (shorter) version of:
1256 1287 # http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/66018 by
1257 1288 # Skip Montanaro (skip@pobox.com).
1258 1289
1259 1290 def __getitem__(self, name):
1260 1291 frame = sys._getframe(1)
1261 1292 return eval(name, frame.f_globals, frame.f_locals)
1262 1293
1263 1294 EvalString = EvalDict # for backwards compatibility
1264 1295 #----------------------------------------------------------------------------
1265 1296 def qw(words,flat=0,sep=None,maxsplit=-1):
1266 1297 """Similar to Perl's qw() operator, but with some more options.
1267 1298
1268 1299 qw(words,flat=0,sep=' ',maxsplit=-1) -> words.split(sep,maxsplit)
1269 1300
1270 1301 words can also be a list itself, and with flat=1, the output will be
1271 1302 recursively flattened. Examples:
1272 1303
1273 1304 >>> qw('1 2')
1274 1305 ['1', '2']
1275 1306 >>> qw(['a b','1 2',['m n','p q']])
1276 1307 [['a', 'b'], ['1', '2'], [['m', 'n'], ['p', 'q']]]
1277 1308 >>> qw(['a b','1 2',['m n','p q']],flat=1)
1278 1309 ['a', 'b', '1', '2', 'm', 'n', 'p', 'q'] """
1279 1310
1280 1311 if type(words) in StringTypes:
1281 1312 return [word.strip() for word in words.split(sep,maxsplit)
1282 1313 if word and not word.isspace() ]
1283 1314 if flat:
1284 1315 return flatten(map(qw,words,[1]*len(words)))
1285 1316 return map(qw,words)
1286 1317
1287 1318 #----------------------------------------------------------------------------
1288 1319 def qwflat(words,sep=None,maxsplit=-1):
1289 1320 """Calls qw(words) in flat mode. It's just a convenient shorthand."""
1290 1321 return qw(words,1,sep,maxsplit)
1291 1322
1292 1323 #----------------------------------------------------------------------------
1293 1324 def qw_lol(indata):
1294 1325 """qw_lol('a b') -> [['a','b']],
1295 1326 otherwise it's just a call to qw().
1296 1327
1297 1328 We need this to make sure the modules_some keys *always* end up as a
1298 1329 list of lists."""
1299 1330
1300 1331 if type(indata) in StringTypes:
1301 1332 return [qw(indata)]
1302 1333 else:
1303 1334 return qw(indata)
1304 1335
1305 1336 #-----------------------------------------------------------------------------
1306 1337 def list_strings(arg):
1307 1338 """Always return a list of strings, given a string or list of strings
1308 1339 as input."""
1309 1340
1310 1341 if type(arg) in StringTypes: return [arg]
1311 1342 else: return arg
1312 1343
1313 1344 #----------------------------------------------------------------------------
1314 1345 def grep(pat,list,case=1):
1315 1346 """Simple minded grep-like function.
1316 1347 grep(pat,list) returns occurrences of pat in list, None on failure.
1317 1348
1318 1349 It only does simple string matching, with no support for regexps. Use the
1319 1350 option case=0 for case-insensitive matching."""
1320 1351
1321 1352 # This is pretty crude. At least it should implement copying only references
1322 1353 # to the original data in case it's big. Now it copies the data for output.
1323 1354 out=[]
1324 1355 if case:
1325 1356 for term in list:
1326 1357 if term.find(pat)>-1: out.append(term)
1327 1358 else:
1328 1359 lpat=pat.lower()
1329 1360 for term in list:
1330 1361 if term.lower().find(lpat)>-1: out.append(term)
1331 1362
1332 1363 if len(out): return out
1333 1364 else: return None
1334 1365
1335 1366 #----------------------------------------------------------------------------
1336 1367 def dgrep(pat,*opts):
1337 1368 """Return grep() on dir()+dir(__builtins__).
1338 1369
1339 1370 A very common use of grep() when working interactively."""
1340 1371
1341 1372 return grep(pat,dir(__main__)+dir(__main__.__builtins__),*opts)
1342 1373
1343 1374 #----------------------------------------------------------------------------
1344 1375 def idgrep(pat):
1345 1376 """Case-insensitive dgrep()"""
1346 1377
1347 1378 return dgrep(pat,0)
1348 1379
1349 1380 #----------------------------------------------------------------------------
1350 1381 def igrep(pat,list):
1351 1382 """Synonym for case-insensitive grep."""
1352 1383
1353 1384 return grep(pat,list,case=0)
1354 1385
1355 1386 #----------------------------------------------------------------------------
1356 1387 def indent(str,nspaces=4,ntabs=0):
1357 1388 """Indent a string a given number of spaces or tabstops.
1358 1389
1359 1390 indent(str,nspaces=4,ntabs=0) -> indent str by ntabs+nspaces.
1360 1391 """
1361 1392 if str is None:
1362 1393 return
1363 1394 ind = '\t'*ntabs+' '*nspaces
1364 1395 outstr = '%s%s' % (ind,str.replace(os.linesep,os.linesep+ind))
1365 1396 if outstr.endswith(os.linesep+ind):
1366 1397 return outstr[:-len(ind)]
1367 1398 else:
1368 1399 return outstr
1369 1400
1370 1401 #-----------------------------------------------------------------------------
1371 1402 def native_line_ends(filename,backup=1):
1372 1403 """Convert (in-place) a file to line-ends native to the current OS.
1373 1404
1374 1405 If the optional backup argument is given as false, no backup of the
1375 1406 original file is left. """
1376 1407
1377 1408 backup_suffixes = {'posix':'~','dos':'.bak','nt':'.bak','mac':'.bak'}
1378 1409
1379 1410 bak_filename = filename + backup_suffixes[os.name]
1380 1411
1381 1412 original = open(filename).read()
1382 1413 shutil.copy2(filename,bak_filename)
1383 1414 try:
1384 1415 new = open(filename,'wb')
1385 1416 new.write(os.linesep.join(original.splitlines()))
1386 1417 new.write(os.linesep) # ALWAYS put an eol at the end of the file
1387 1418 new.close()
1388 1419 except:
1389 1420 os.rename(bak_filename,filename)
1390 1421 if not backup:
1391 1422 try:
1392 1423 os.remove(bak_filename)
1393 1424 except:
1394 1425 pass
1395 1426
1396 1427 #----------------------------------------------------------------------------
1397 1428 def get_pager_cmd(pager_cmd = None):
1398 1429 """Return a pager command.
1399 1430
1400 1431 Makes some attempts at finding an OS-correct one."""
1401 1432
1402 1433 if os.name == 'posix':
1403 1434 default_pager_cmd = 'less -r' # -r for color control sequences
1404 1435 elif os.name in ['nt','dos']:
1405 1436 default_pager_cmd = 'type'
1406 1437
1407 1438 if pager_cmd is None:
1408 1439 try:
1409 1440 pager_cmd = os.environ['PAGER']
1410 1441 except:
1411 1442 pager_cmd = default_pager_cmd
1412 1443 return pager_cmd
1413 1444
1414 1445 #-----------------------------------------------------------------------------
1415 1446 def get_pager_start(pager,start):
1416 1447 """Return the string for paging files with an offset.
1417 1448
1418 1449 This is the '+N' argument which less and more (under Unix) accept.
1419 1450 """
1420 1451
1421 1452 if pager in ['less','more']:
1422 1453 if start:
1423 1454 start_string = '+' + str(start)
1424 1455 else:
1425 1456 start_string = ''
1426 1457 else:
1427 1458 start_string = ''
1428 1459 return start_string
1429 1460
1430 1461 #----------------------------------------------------------------------------
1431 1462 # (X)emacs on W32 doesn't like to be bypassed with msvcrt.getch()
1432 1463 if os.name == 'nt' and os.environ.get('TERM','dumb') != 'emacs':
1433 1464 import msvcrt
1434 1465 def page_more():
1435 1466 """ Smart pausing between pages
1436 1467
1437 1468 @return: True if need print more lines, False if quit
1438 1469 """
1439 1470 Term.cout.write('---Return to continue, q to quit--- ')
1440 1471 ans = msvcrt.getch()
1441 1472 if ans in ("q", "Q"):
1442 1473 result = False
1443 1474 else:
1444 1475 result = True
1445 1476 Term.cout.write("\b"*37 + " "*37 + "\b"*37)
1446 1477 return result
1447 1478 else:
1448 1479 def page_more():
1449 1480 ans = raw_input('---Return to continue, q to quit--- ')
1450 1481 if ans.lower().startswith('q'):
1451 1482 return False
1452 1483 else:
1453 1484 return True
1454 1485
1455 1486 esc_re = re.compile(r"(\x1b[^m]+m)")
1456 1487
1457 1488 def page_dumb(strng,start=0,screen_lines=25):
1458 1489 """Very dumb 'pager' in Python, for when nothing else works.
1459 1490
1460 1491 Only moves forward, same interface as page(), except for pager_cmd and
1461 1492 mode."""
1462 1493
1463 1494 out_ln = strng.splitlines()[start:]
1464 1495 screens = chop(out_ln,screen_lines-1)
1465 1496 if len(screens) == 1:
1466 1497 print >>Term.cout, os.linesep.join(screens[0])
1467 1498 else:
1468 1499 last_escape = ""
1469 1500 for scr in screens[0:-1]:
1470 1501 hunk = os.linesep.join(scr)
1471 1502 print >>Term.cout, last_escape + hunk
1472 1503 if not page_more():
1473 1504 return
1474 1505 esc_list = esc_re.findall(hunk)
1475 1506 if len(esc_list) > 0:
1476 1507 last_escape = esc_list[-1]
1477 1508 print >>Term.cout, last_escape + os.linesep.join(screens[-1])
1478 1509
1479 1510 #----------------------------------------------------------------------------
1480 1511 def page(strng,start=0,screen_lines=0,pager_cmd = None):
1481 1512 """Print a string, piping through a pager after a certain length.
1482 1513
1483 1514 The screen_lines parameter specifies the number of *usable* lines of your
1484 1515 terminal screen (total lines minus lines you need to reserve to show other
1485 1516 information).
1486 1517
1487 1518 If you set screen_lines to a number <=0, page() will try to auto-determine
1488 1519 your screen size and will only use up to (screen_size+screen_lines) for
1489 1520 printing, paging after that. That is, if you want auto-detection but need
1490 1521 to reserve the bottom 3 lines of the screen, use screen_lines = -3, and for
1491 1522 auto-detection without any lines reserved simply use screen_lines = 0.
1492 1523
1493 1524 If a string won't fit in the allowed lines, it is sent through the
1494 1525 specified pager command. If none given, look for PAGER in the environment,
1495 1526 and ultimately default to less.
1496 1527
1497 1528 If no system pager works, the string is sent through a 'dumb pager'
1498 1529 written in python, very simplistic.
1499 1530 """
1500 1531
1501 1532
1502 1533 # first, try the hook
1503 1534 ip = IPython.ipapi.get()
1504 1535 if ip:
1505 1536 try:
1506 1537 ip.IP.hooks.show_in_pager(strng)
1507 1538 return
1508 1539 except IPython.ipapi.TryNext:
1509 1540 pass
1510 1541
1511 1542 # Ugly kludge, but calling curses.initscr() flat out crashes in emacs
1512 1543 TERM = os.environ.get('TERM','dumb')
1513 1544 if TERM in ['dumb','emacs'] and os.name != 'nt':
1514 1545 print strng
1515 1546 return
1516 1547 # chop off the topmost part of the string we don't want to see
1517 1548 str_lines = strng.split(os.linesep)[start:]
1518 1549 str_toprint = os.linesep.join(str_lines)
1519 1550 num_newlines = len(str_lines)
1520 1551 len_str = len(str_toprint)
1521 1552
1522 1553 # Dumb heuristics to guesstimate number of on-screen lines the string
1523 1554 # takes. Very basic, but good enough for docstrings in reasonable
1524 1555 # terminals. If someone later feels like refining it, it's not hard.
1525 1556 numlines = max(num_newlines,int(len_str/80)+1)
1526 1557
1527 1558 if os.name == "nt":
1528 1559 screen_lines_def = get_console_size(defaulty=25)[1]
1529 1560 else:
1530 1561 screen_lines_def = 25 # default value if we can't auto-determine
1531 1562
1532 1563 # auto-determine screen size
1533 1564 if screen_lines <= 0:
1534 1565 if TERM=='xterm':
1535 try:
1536 import curses
1537 if hasattr(curses,'initscr'):
1538 use_curses = 1
1539 else:
1540 use_curses = 0
1541 except ImportError:
1542 use_curses = 0
1566 use_curses = USE_CURSES
1543 1567 else:
1544 1568 # curses causes problems on many terminals other than xterm.
1545 use_curses = 0
1569 use_curses = False
1546 1570 if use_curses:
1547 scr = curses.initscr()
1548 screen_lines_real,screen_cols = scr.getmaxyx()
1549 curses.endwin()
1550 screen_lines += screen_lines_real
1551 #print '***Screen size:',screen_lines_real,'lines x',\
1552 #screen_cols,'columns.' # dbg
1571 # There is a bug in curses, where *sometimes* it fails to properly
1572 # initialize, and then after the endwin() call is made, the
1573 # terminal is left in an unusable state. Rather than trying to
1574 # check everytime for this (by requesting and comparing termios
1575 # flags each time), we just save the initial terminal state and
1576 # unconditionally reset it every time. It's cheaper than making
1577 # the checks.
1578 term_flags = termios.tcgetattr(sys.stdout)
1579 scr = curses.initscr()
1580 screen_lines_real,screen_cols = scr.getmaxyx()
1581 curses.endwin()
1582 # Restore terminal state in case endwin() didn't.
1583 termios.tcsetattr(sys.stdout,termios.TCSANOW,term_flags)
1584 # Now we have what we needed: the screen size in rows/columns
1585 screen_lines += screen_lines_real
1586 #print '***Screen size:',screen_lines_real,'lines x',\
1587 #screen_cols,'columns.' # dbg
1553 1588 else:
1554 screen_lines += screen_lines_def
1589 screen_lines += screen_lines_def
1555 1590
1556 1591 #print 'numlines',numlines,'screenlines',screen_lines # dbg
1557 1592 if numlines <= screen_lines :
1558 1593 #print '*** normal print' # dbg
1559 1594 print >>Term.cout, str_toprint
1560 1595 else:
1561 1596 # Try to open pager and default to internal one if that fails.
1562 1597 # All failure modes are tagged as 'retval=1', to match the return
1563 1598 # value of a failed system command. If any intermediate attempt
1564 1599 # sets retval to 1, at the end we resort to our own page_dumb() pager.
1565 1600 pager_cmd = get_pager_cmd(pager_cmd)
1566 1601 pager_cmd += ' ' + get_pager_start(pager_cmd,start)
1567 1602 if os.name == 'nt':
1568 1603 if pager_cmd.startswith('type'):
1569 1604 # The default WinXP 'type' command is failing on complex strings.
1570 1605 retval = 1
1571 1606 else:
1572 1607 tmpname = tempfile.mktemp('.txt')
1573 1608 tmpfile = file(tmpname,'wt')
1574 1609 tmpfile.write(strng)
1575 1610 tmpfile.close()
1576 1611 cmd = "%s < %s" % (pager_cmd,tmpname)
1577 1612 if os.system(cmd):
1578 1613 retval = 1
1579 1614 else:
1580 1615 retval = None
1581 1616 os.remove(tmpname)
1582 1617 else:
1583 1618 try:
1584 1619 retval = None
1585 1620 # if I use popen4, things hang. No idea why.
1586 1621 #pager,shell_out = os.popen4(pager_cmd)
1587 1622 pager = os.popen(pager_cmd,'w')
1588 1623 pager.write(strng)
1589 1624 pager.close()
1590 1625 retval = pager.close() # success returns None
1591 1626 except IOError,msg: # broken pipe when user quits
1592 1627 if msg.args == (32,'Broken pipe'):
1593 1628 retval = None
1594 1629 else:
1595 1630 retval = 1
1596 1631 except OSError:
1597 1632 # Other strange problems, sometimes seen in Win2k/cygwin
1598 1633 retval = 1
1599 1634 if retval is not None:
1600 1635 page_dumb(strng,screen_lines=screen_lines)
1601 1636
1602 1637 #----------------------------------------------------------------------------
1603 1638 def page_file(fname,start = 0, pager_cmd = None):
1604 1639 """Page a file, using an optional pager command and starting line.
1605 1640 """
1606 1641
1607 1642 pager_cmd = get_pager_cmd(pager_cmd)
1608 1643 pager_cmd += ' ' + get_pager_start(pager_cmd,start)
1609 1644
1610 1645 try:
1611 1646 if os.environ['TERM'] in ['emacs','dumb']:
1612 1647 raise EnvironmentError
1613 1648 xsys(pager_cmd + ' ' + fname)
1614 1649 except:
1615 1650 try:
1616 1651 if start > 0:
1617 1652 start -= 1
1618 1653 page(open(fname).read(),start)
1619 1654 except:
1620 1655 print 'Unable to show file',`fname`
1621 1656
1622 1657
1623 1658 #----------------------------------------------------------------------------
1624 1659 def snip_print(str,width = 75,print_full = 0,header = ''):
1625 1660 """Print a string snipping the midsection to fit in width.
1626 1661
1627 1662 print_full: mode control:
1628 1663 - 0: only snip long strings
1629 1664 - 1: send to page() directly.
1630 1665 - 2: snip long strings and ask for full length viewing with page()
1631 1666 Return 1 if snipping was necessary, 0 otherwise."""
1632 1667
1633 1668 if print_full == 1:
1634 1669 page(header+str)
1635 1670 return 0
1636 1671
1637 1672 print header,
1638 1673 if len(str) < width:
1639 1674 print str
1640 1675 snip = 0
1641 1676 else:
1642 1677 whalf = int((width -5)/2)
1643 1678 print str[:whalf] + ' <...> ' + str[-whalf:]
1644 1679 snip = 1
1645 1680 if snip and print_full == 2:
1646 1681 if raw_input(header+' Snipped. View (y/n)? [N]').lower() == 'y':
1647 1682 page(str)
1648 1683 return snip
1649 1684
1650 1685 #****************************************************************************
1651 1686 # lists, dicts and structures
1652 1687
1653 1688 def belong(candidates,checklist):
1654 1689 """Check whether a list of items appear in a given list of options.
1655 1690
1656 1691 Returns a list of 1 and 0, one for each candidate given."""
1657 1692
1658 1693 return [x in checklist for x in candidates]
1659 1694
1660 1695 #----------------------------------------------------------------------------
1661 1696 def uniq_stable(elems):
1662 1697 """uniq_stable(elems) -> list
1663 1698
1664 1699 Return from an iterable, a list of all the unique elements in the input,
1665 1700 but maintaining the order in which they first appear.
1666 1701
1667 1702 A naive solution to this problem which just makes a dictionary with the
1668 1703 elements as keys fails to respect the stability condition, since
1669 1704 dictionaries are unsorted by nature.
1670 1705
1671 1706 Note: All elements in the input must be valid dictionary keys for this
1672 1707 routine to work, as it internally uses a dictionary for efficiency
1673 1708 reasons."""
1674 1709
1675 1710 unique = []
1676 1711 unique_dict = {}
1677 1712 for nn in elems:
1678 1713 if nn not in unique_dict:
1679 1714 unique.append(nn)
1680 1715 unique_dict[nn] = None
1681 1716 return unique
1682 1717
1683 1718 #----------------------------------------------------------------------------
1684 1719 class NLprinter:
1685 1720 """Print an arbitrarily nested list, indicating index numbers.
1686 1721
1687 1722 An instance of this class called nlprint is available and callable as a
1688 1723 function.
1689 1724
1690 1725 nlprint(list,indent=' ',sep=': ') -> prints indenting each level by 'indent'
1691 1726 and using 'sep' to separate the index from the value. """
1692 1727
1693 1728 def __init__(self):
1694 1729 self.depth = 0
1695 1730
1696 1731 def __call__(self,lst,pos='',**kw):
1697 1732 """Prints the nested list numbering levels."""
1698 1733 kw.setdefault('indent',' ')
1699 1734 kw.setdefault('sep',': ')
1700 1735 kw.setdefault('start',0)
1701 1736 kw.setdefault('stop',len(lst))
1702 1737 # we need to remove start and stop from kw so they don't propagate
1703 1738 # into a recursive call for a nested list.
1704 1739 start = kw['start']; del kw['start']
1705 1740 stop = kw['stop']; del kw['stop']
1706 1741 if self.depth == 0 and 'header' in kw.keys():
1707 1742 print kw['header']
1708 1743
1709 1744 for idx in range(start,stop):
1710 1745 elem = lst[idx]
1711 1746 if type(elem)==type([]):
1712 1747 self.depth += 1
1713 1748 self.__call__(elem,itpl('$pos$idx,'),**kw)
1714 1749 self.depth -= 1
1715 1750 else:
1716 1751 printpl(kw['indent']*self.depth+'$pos$idx$kw["sep"]$elem')
1717 1752
1718 1753 nlprint = NLprinter()
1719 1754 #----------------------------------------------------------------------------
1720 1755 def all_belong(candidates,checklist):
1721 1756 """Check whether a list of items ALL appear in a given list of options.
1722 1757
1723 1758 Returns a single 1 or 0 value."""
1724 1759
1725 1760 return 1-(0 in [x in checklist for x in candidates])
1726 1761
1727 1762 #----------------------------------------------------------------------------
1728 1763 def sort_compare(lst1,lst2,inplace = 1):
1729 1764 """Sort and compare two lists.
1730 1765
1731 1766 By default it does it in place, thus modifying the lists. Use inplace = 0
1732 1767 to avoid that (at the cost of temporary copy creation)."""
1733 1768 if not inplace:
1734 1769 lst1 = lst1[:]
1735 1770 lst2 = lst2[:]
1736 1771 lst1.sort(); lst2.sort()
1737 1772 return lst1 == lst2
1738 1773
1739 1774 #----------------------------------------------------------------------------
1740 1775 def mkdict(**kwargs):
1741 1776 """Return a dict from a keyword list.
1742 1777
1743 1778 It's just syntactic sugar for making ditcionary creation more convenient:
1744 1779 # the standard way
1745 1780 >>>data = { 'red' : 1, 'green' : 2, 'blue' : 3 }
1746 1781 # a cleaner way
1747 1782 >>>data = dict(red=1, green=2, blue=3)
1748 1783
1749 1784 If you need more than this, look at the Struct() class."""
1750 1785
1751 1786 return kwargs
1752 1787
1753 1788 #----------------------------------------------------------------------------
1754 1789 def list2dict(lst):
1755 1790 """Takes a list of (key,value) pairs and turns it into a dict."""
1756 1791
1757 1792 dic = {}
1758 1793 for k,v in lst: dic[k] = v
1759 1794 return dic
1760 1795
1761 1796 #----------------------------------------------------------------------------
1762 1797 def list2dict2(lst,default=''):
1763 1798 """Takes a list and turns it into a dict.
1764 1799 Much slower than list2dict, but more versatile. This version can take
1765 1800 lists with sublists of arbitrary length (including sclars)."""
1766 1801
1767 1802 dic = {}
1768 1803 for elem in lst:
1769 1804 if type(elem) in (types.ListType,types.TupleType):
1770 1805 size = len(elem)
1771 1806 if size == 0:
1772 1807 pass
1773 1808 elif size == 1:
1774 1809 dic[elem] = default
1775 1810 else:
1776 1811 k,v = elem[0], elem[1:]
1777 1812 if len(v) == 1: v = v[0]
1778 1813 dic[k] = v
1779 1814 else:
1780 1815 dic[elem] = default
1781 1816 return dic
1782 1817
1783 1818 #----------------------------------------------------------------------------
1784 1819 def flatten(seq):
1785 1820 """Flatten a list of lists (NOT recursive, only works for 2d lists)."""
1786 1821
1787 1822 return [x for subseq in seq for x in subseq]
1788 1823
1789 1824 #----------------------------------------------------------------------------
1790 1825 def get_slice(seq,start=0,stop=None,step=1):
1791 1826 """Get a slice of a sequence with variable step. Specify start,stop,step."""
1792 1827 if stop == None:
1793 1828 stop = len(seq)
1794 1829 item = lambda i: seq[i]
1795 1830 return map(item,xrange(start,stop,step))
1796 1831
1797 1832 #----------------------------------------------------------------------------
1798 1833 def chop(seq,size):
1799 1834 """Chop a sequence into chunks of the given size."""
1800 1835 chunk = lambda i: seq[i:i+size]
1801 1836 return map(chunk,xrange(0,len(seq),size))
1802 1837
1803 1838 #----------------------------------------------------------------------------
1804 1839 # with is a keyword as of python 2.5, so this function is renamed to withobj
1805 1840 # from its old 'with' name.
1806 1841 def with_obj(object, **args):
1807 1842 """Set multiple attributes for an object, similar to Pascal's with.
1808 1843
1809 1844 Example:
1810 1845 with_obj(jim,
1811 1846 born = 1960,
1812 1847 haircolour = 'Brown',
1813 1848 eyecolour = 'Green')
1814 1849
1815 1850 Credit: Greg Ewing, in
1816 1851 http://mail.python.org/pipermail/python-list/2001-May/040703.html.
1817 1852
1818 1853 NOTE: up until IPython 0.7.2, this was called simply 'with', but 'with'
1819 1854 has become a keyword for Python 2.5, so we had to rename it."""
1820 1855
1821 1856 object.__dict__.update(args)
1822 1857
1823 1858 #----------------------------------------------------------------------------
1824 1859 def setattr_list(obj,alist,nspace = None):
1825 1860 """Set a list of attributes for an object taken from a namespace.
1826 1861
1827 1862 setattr_list(obj,alist,nspace) -> sets in obj all the attributes listed in
1828 1863 alist with their values taken from nspace, which must be a dict (something
1829 1864 like locals() will often do) If nspace isn't given, locals() of the
1830 1865 *caller* is used, so in most cases you can omit it.
1831 1866
1832 1867 Note that alist can be given as a string, which will be automatically
1833 1868 split into a list on whitespace. If given as a list, it must be a list of
1834 1869 *strings* (the variable names themselves), not of variables."""
1835 1870
1836 1871 # this grabs the local variables from the *previous* call frame -- that is
1837 1872 # the locals from the function that called setattr_list().
1838 1873 # - snipped from weave.inline()
1839 1874 if nspace is None:
1840 1875 call_frame = sys._getframe().f_back
1841 1876 nspace = call_frame.f_locals
1842 1877
1843 1878 if type(alist) in StringTypes:
1844 1879 alist = alist.split()
1845 1880 for attr in alist:
1846 1881 val = eval(attr,nspace)
1847 1882 setattr(obj,attr,val)
1848 1883
1849 1884 #----------------------------------------------------------------------------
1850 1885 def getattr_list(obj,alist,*args):
1851 1886 """getattr_list(obj,alist[, default]) -> attribute list.
1852 1887
1853 1888 Get a list of named attributes for an object. When a default argument is
1854 1889 given, it is returned when the attribute doesn't exist; without it, an
1855 1890 exception is raised in that case.
1856 1891
1857 1892 Note that alist can be given as a string, which will be automatically
1858 1893 split into a list on whitespace. If given as a list, it must be a list of
1859 1894 *strings* (the variable names themselves), not of variables."""
1860 1895
1861 1896 if type(alist) in StringTypes:
1862 1897 alist = alist.split()
1863 1898 if args:
1864 1899 if len(args)==1:
1865 1900 default = args[0]
1866 1901 return map(lambda attr: getattr(obj,attr,default),alist)
1867 1902 else:
1868 1903 raise ValueError,'getattr_list() takes only one optional argument'
1869 1904 else:
1870 1905 return map(lambda attr: getattr(obj,attr),alist)
1871 1906
1872 1907 #----------------------------------------------------------------------------
1873 1908 def map_method(method,object_list,*argseq,**kw):
1874 1909 """map_method(method,object_list,*args,**kw) -> list
1875 1910
1876 1911 Return a list of the results of applying the methods to the items of the
1877 1912 argument sequence(s). If more than one sequence is given, the method is
1878 1913 called with an argument list consisting of the corresponding item of each
1879 1914 sequence. All sequences must be of the same length.
1880 1915
1881 1916 Keyword arguments are passed verbatim to all objects called.
1882 1917
1883 1918 This is Python code, so it's not nearly as fast as the builtin map()."""
1884 1919
1885 1920 out_list = []
1886 1921 idx = 0
1887 1922 for object in object_list:
1888 1923 try:
1889 1924 handler = getattr(object, method)
1890 1925 except AttributeError:
1891 1926 out_list.append(None)
1892 1927 else:
1893 1928 if argseq:
1894 1929 args = map(lambda lst:lst[idx],argseq)
1895 1930 #print 'ob',object,'hand',handler,'ar',args # dbg
1896 1931 out_list.append(handler(args,**kw))
1897 1932 else:
1898 1933 out_list.append(handler(**kw))
1899 1934 idx += 1
1900 1935 return out_list
1901 1936
1902 1937 #----------------------------------------------------------------------------
1903 1938 def get_class_members(cls):
1904 1939 ret = dir(cls)
1905 1940 if hasattr(cls,'__bases__'):
1906 1941 for base in cls.__bases__:
1907 1942 ret.extend(get_class_members(base))
1908 1943 return ret
1909 1944
1910 1945 #----------------------------------------------------------------------------
1911 1946 def dir2(obj):
1912 1947 """dir2(obj) -> list of strings
1913 1948
1914 1949 Extended version of the Python builtin dir(), which does a few extra
1915 1950 checks, and supports common objects with unusual internals that confuse
1916 1951 dir(), such as Traits and PyCrust.
1917 1952
1918 1953 This version is guaranteed to return only a list of true strings, whereas
1919 1954 dir() returns anything that objects inject into themselves, even if they
1920 1955 are later not really valid for attribute access (many extension libraries
1921 1956 have such bugs).
1922 1957 """
1923 1958
1924 1959 # Start building the attribute list via dir(), and then complete it
1925 1960 # with a few extra special-purpose calls.
1926 1961 words = dir(obj)
1927 1962
1928 1963 if hasattr(obj,'__class__'):
1929 1964 words.append('__class__')
1930 1965 words.extend(get_class_members(obj.__class__))
1931 1966 #if '__base__' in words: 1/0
1932 1967
1933 1968 # Some libraries (such as traits) may introduce duplicates, we want to
1934 1969 # track and clean this up if it happens
1935 1970 may_have_dupes = False
1936 1971
1937 1972 # this is the 'dir' function for objects with Enthought's traits
1938 1973 if hasattr(obj, 'trait_names'):
1939 1974 try:
1940 1975 words.extend(obj.trait_names())
1941 1976 may_have_dupes = True
1942 1977 except TypeError:
1943 1978 # This will happen if `obj` is a class and not an instance.
1944 1979 pass
1945 1980
1946 1981 # Support for PyCrust-style _getAttributeNames magic method.
1947 1982 if hasattr(obj, '_getAttributeNames'):
1948 1983 try:
1949 1984 words.extend(obj._getAttributeNames())
1950 1985 may_have_dupes = True
1951 1986 except TypeError:
1952 1987 # `obj` is a class and not an instance. Ignore
1953 1988 # this error.
1954 1989 pass
1955 1990
1956 1991 if may_have_dupes:
1957 1992 # eliminate possible duplicates, as some traits may also
1958 1993 # appear as normal attributes in the dir() call.
1959 1994 words = list(set(words))
1960 1995 words.sort()
1961 1996
1962 1997 # filter out non-string attributes which may be stuffed by dir() calls
1963 1998 # and poor coding in third-party modules
1964 1999 return [w for w in words if isinstance(w, basestring)]
1965 2000
1966 2001 #----------------------------------------------------------------------------
1967 2002 def import_fail_info(mod_name,fns=None):
1968 2003 """Inform load failure for a module."""
1969 2004
1970 2005 if fns == None:
1971 2006 warn("Loading of %s failed.\n" % (mod_name,))
1972 2007 else:
1973 2008 warn("Loading of %s from %s failed.\n" % (fns,mod_name))
1974 2009
1975 2010 #----------------------------------------------------------------------------
1976 2011 # Proposed popitem() extension, written as a method
1977 2012
1978 2013
1979 2014 class NotGiven: pass
1980 2015
1981 2016 def popkey(dct,key,default=NotGiven):
1982 2017 """Return dct[key] and delete dct[key].
1983 2018
1984 2019 If default is given, return it if dct[key] doesn't exist, otherwise raise
1985 2020 KeyError. """
1986 2021
1987 2022 try:
1988 2023 val = dct[key]
1989 2024 except KeyError:
1990 2025 if default is NotGiven:
1991 2026 raise
1992 2027 else:
1993 2028 return default
1994 2029 else:
1995 2030 del dct[key]
1996 2031 return val
1997 2032
1998 2033 def wrap_deprecated(func, suggest = '<nothing>'):
1999 2034 def newFunc(*args, **kwargs):
2000 2035 warnings.warn("Call to deprecated function %s, use %s instead" %
2001 2036 ( func.__name__, suggest),
2002 2037 category=DeprecationWarning,
2003 2038 stacklevel = 2)
2004 2039 return func(*args, **kwargs)
2005 2040 return newFunc
2006 2041
2007 2042 #*************************** end of file <genutils.py> **********************
2008 2043
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file renamed from IPython/gui/wx/ThreadEx.py to IPython/gui/wx/thread_ex.py
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file chmod 100644 => 100755
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file renamed from doc/ipnb_google_soc.lyx to doc/attic/ipnb_google_soc.lyx
1 NO CONTENT: file renamed from doc/nbexample.py to doc/attic/nbexample.py
1 NO CONTENT: file renamed from doc/nbexample_latex.py to doc/attic/nbexample_latex.py
1 NO CONTENT: file renamed from doc/nbexample_output.py to doc/attic/nbexample_output.py
1 NO CONTENT: file renamed from doc/new_design.lyx to doc/attic/new_design.lyx
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file, binary diff hidden
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file chmod 100644 => 100755
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file chmod 100644 => 100755
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: modified file chmod 100644 => 100755
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
1 NO CONTENT: file was removed
The requested commit or file is too big and content was truncated. Show full diff
General Comments 0
You need to be logged in to leave comments. Login now