Show More
@@ -0,0 +1,14 b'' | |||||
|
1 | class InputList(list): | |||
|
2 | """Class to store user input. | |||
|
3 | ||||
|
4 | It's basically a list, but slices return a string instead of a list, thus | |||
|
5 | allowing things like (assuming 'In' is an instance): | |||
|
6 | ||||
|
7 | exec In[4:7] | |||
|
8 | ||||
|
9 | or | |||
|
10 | ||||
|
11 | exec In[5:9] + In[14] + In[21:25]""" | |||
|
12 | ||||
|
13 | def __getslice__(self,i,j): | |||
|
14 | return ''.join(list.__getslice__(self,i,j)) |
1 | NO CONTENT: new file 100644 |
|
NO CONTENT: new file 100644 |
This diff has been collapsed as it changes many lines, (523 lines changed) Show them Hide them | |||||
@@ -0,0 +1,523 b'' | |||||
|
1 | # -*- coding: utf-8 -*- | |||
|
2 | """Subclass of InteractiveShell for terminal based frontends.""" | |||
|
3 | ||||
|
4 | #----------------------------------------------------------------------------- | |||
|
5 | # Copyright (C) 2001 Janko Hauser <jhauser@zscout.de> | |||
|
6 | # Copyright (C) 2001-2007 Fernando Perez. <fperez@colorado.edu> | |||
|
7 | # Copyright (C) 2008-2010 The IPython Development Team | |||
|
8 | # | |||
|
9 | # Distributed under the terms of the BSD License. The full license is in | |||
|
10 | # the file COPYING, distributed as part of this software. | |||
|
11 | #----------------------------------------------------------------------------- | |||
|
12 | ||||
|
13 | #----------------------------------------------------------------------------- | |||
|
14 | # Imports | |||
|
15 | #----------------------------------------------------------------------------- | |||
|
16 | ||||
|
17 | import __builtin__ | |||
|
18 | import bdb | |||
|
19 | from contextlib import nested | |||
|
20 | import os | |||
|
21 | import re | |||
|
22 | import sys | |||
|
23 | ||||
|
24 | from IPython.core.error import TryNext | |||
|
25 | from IPython.core.usage import interactive_usage, default_banner | |||
|
26 | from IPython.core.inputlist import InputList | |||
|
27 | from IPython.core.interactiveshell import InteractiveShell, InteractiveShellABC | |||
|
28 | from IPython.lib.inputhook import enable_gui | |||
|
29 | from IPython.lib.pylabtools import pylab_activate | |||
|
30 | from IPython.utils.terminal import toggle_set_term_title, set_term_title | |||
|
31 | from IPython.utils.process import abbrev_cwd | |||
|
32 | from IPython.utils.warn import warn | |||
|
33 | from IPython.utils.text import num_ini_spaces | |||
|
34 | from IPython.utils.traitlets import Int, Str, CBool | |||
|
35 | ||||
|
36 | ||||
|
37 | #----------------------------------------------------------------------------- | |||
|
38 | # Utilities | |||
|
39 | #----------------------------------------------------------------------------- | |||
|
40 | ||||
|
41 | ||||
|
42 | def get_default_editor(): | |||
|
43 | try: | |||
|
44 | ed = os.environ['EDITOR'] | |||
|
45 | except KeyError: | |||
|
46 | if os.name == 'posix': | |||
|
47 | ed = 'vi' # the only one guaranteed to be there! | |||
|
48 | else: | |||
|
49 | ed = 'notepad' # same in Windows! | |||
|
50 | return ed | |||
|
51 | ||||
|
52 | ||||
|
53 | # store the builtin raw_input globally, and use this always, in case user code | |||
|
54 | # overwrites it (like wx.py.PyShell does) | |||
|
55 | raw_input_original = raw_input | |||
|
56 | ||||
|
57 | ||||
|
58 | #----------------------------------------------------------------------------- | |||
|
59 | # Main class | |||
|
60 | #----------------------------------------------------------------------------- | |||
|
61 | ||||
|
62 | ||||
|
63 | class TerminalInteractiveShell(InteractiveShell): | |||
|
64 | ||||
|
65 | autoedit_syntax = CBool(False, config=True) | |||
|
66 | banner = Str('') | |||
|
67 | banner1 = Str(default_banner, config=True) | |||
|
68 | banner2 = Str('', config=True) | |||
|
69 | confirm_exit = CBool(True, config=True) | |||
|
70 | # This display_banner only controls whether or not self.show_banner() | |||
|
71 | # is called when mainloop/interact are called. The default is False | |||
|
72 | # because for the terminal based application, the banner behavior | |||
|
73 | # is controlled by Global.display_banner, which IPythonApp looks at | |||
|
74 | # to determine if *it* should call show_banner() by hand or not. | |||
|
75 | display_banner = CBool(False) # This isn't configurable! | |||
|
76 | embedded = CBool(False) | |||
|
77 | embedded_active = CBool(False) | |||
|
78 | editor = Str(get_default_editor(), config=True) | |||
|
79 | exit_now = CBool(False) | |||
|
80 | pager = Str('less', config=True) | |||
|
81 | ||||
|
82 | screen_length = Int(0, config=True) | |||
|
83 | term_title = CBool(False, config=True) | |||
|
84 | ||||
|
85 | def __init__(self, config=None, ipython_dir=None, user_ns=None, | |||
|
86 | user_global_ns=None, custom_exceptions=((),None), | |||
|
87 | usage=None, banner1=None, banner2=None, | |||
|
88 | display_banner=None): | |||
|
89 | ||||
|
90 | super(TerminalInteractiveShell, self).__init__( | |||
|
91 | config=config, ipython_dir=ipython_dir, user_ns=user_ns, | |||
|
92 | user_global_ns=user_global_ns, custom_exceptions=custom_exceptions | |||
|
93 | ) | |||
|
94 | self.init_term_title() | |||
|
95 | self.init_usage(usage) | |||
|
96 | self.init_banner(banner1, banner2, display_banner) | |||
|
97 | ||||
|
98 | #------------------------------------------------------------------------- | |||
|
99 | # Things related to the terminal | |||
|
100 | #------------------------------------------------------------------------- | |||
|
101 | ||||
|
102 | @property | |||
|
103 | def usable_screen_length(self): | |||
|
104 | if self.screen_length == 0: | |||
|
105 | return 0 | |||
|
106 | else: | |||
|
107 | num_lines_bot = self.separate_in.count('\n')+1 | |||
|
108 | return self.screen_length - num_lines_bot | |||
|
109 | ||||
|
110 | def init_term_title(self): | |||
|
111 | # Enable or disable the terminal title. | |||
|
112 | if self.term_title: | |||
|
113 | toggle_set_term_title(True) | |||
|
114 | set_term_title('IPython: ' + abbrev_cwd()) | |||
|
115 | else: | |||
|
116 | toggle_set_term_title(False) | |||
|
117 | ||||
|
118 | #------------------------------------------------------------------------- | |||
|
119 | # Things related to the banner and usage | |||
|
120 | #------------------------------------------------------------------------- | |||
|
121 | ||||
|
122 | def _banner1_changed(self): | |||
|
123 | self.compute_banner() | |||
|
124 | ||||
|
125 | def _banner2_changed(self): | |||
|
126 | self.compute_banner() | |||
|
127 | ||||
|
128 | def _term_title_changed(self, name, new_value): | |||
|
129 | self.init_term_title() | |||
|
130 | ||||
|
131 | def init_banner(self, banner1, banner2, display_banner): | |||
|
132 | if banner1 is not None: | |||
|
133 | self.banner1 = banner1 | |||
|
134 | if banner2 is not None: | |||
|
135 | self.banner2 = banner2 | |||
|
136 | if display_banner is not None: | |||
|
137 | self.display_banner = display_banner | |||
|
138 | self.compute_banner() | |||
|
139 | ||||
|
140 | def show_banner(self, banner=None): | |||
|
141 | if banner is None: | |||
|
142 | banner = self.banner | |||
|
143 | self.write(banner) | |||
|
144 | ||||
|
145 | def compute_banner(self): | |||
|
146 | self.banner = self.banner1 + '\n' | |||
|
147 | if self.profile: | |||
|
148 | self.banner += '\nIPython profile: %s\n' % self.profile | |||
|
149 | if self.banner2: | |||
|
150 | self.banner += '\n' + self.banner2 + '\n' | |||
|
151 | ||||
|
152 | def init_usage(self, usage=None): | |||
|
153 | if usage is None: | |||
|
154 | self.usage = interactive_usage | |||
|
155 | else: | |||
|
156 | self.usage = usage | |||
|
157 | ||||
|
158 | #------------------------------------------------------------------------- | |||
|
159 | # Mainloop and code execution logic | |||
|
160 | #------------------------------------------------------------------------- | |||
|
161 | ||||
|
162 | def mainloop(self, display_banner=None): | |||
|
163 | """Start the mainloop. | |||
|
164 | ||||
|
165 | If an optional banner argument is given, it will override the | |||
|
166 | internally created default banner. | |||
|
167 | """ | |||
|
168 | ||||
|
169 | with nested(self.builtin_trap, self.display_trap): | |||
|
170 | ||||
|
171 | # if you run stuff with -c <cmd>, raw hist is not updated | |||
|
172 | # ensure that it's in sync | |||
|
173 | if len(self.input_hist) != len (self.input_hist_raw): | |||
|
174 | self.input_hist_raw = InputList(self.input_hist) | |||
|
175 | ||||
|
176 | while 1: | |||
|
177 | try: | |||
|
178 | self.interact(display_banner=display_banner) | |||
|
179 | #self.interact_with_readline() | |||
|
180 | # XXX for testing of a readline-decoupled repl loop, call | |||
|
181 | # interact_with_readline above | |||
|
182 | break | |||
|
183 | except KeyboardInterrupt: | |||
|
184 | # this should not be necessary, but KeyboardInterrupt | |||
|
185 | # handling seems rather unpredictable... | |||
|
186 | self.write("\nKeyboardInterrupt in interact()\n") | |||
|
187 | ||||
|
188 | def interact(self, display_banner=None): | |||
|
189 | """Closely emulate the interactive Python console.""" | |||
|
190 | ||||
|
191 | # batch run -> do not interact | |||
|
192 | if self.exit_now: | |||
|
193 | return | |||
|
194 | ||||
|
195 | if display_banner is None: | |||
|
196 | display_banner = self.display_banner | |||
|
197 | if display_banner: | |||
|
198 | self.show_banner() | |||
|
199 | ||||
|
200 | more = 0 | |||
|
201 | ||||
|
202 | # Mark activity in the builtins | |||
|
203 | __builtin__.__dict__['__IPYTHON__active'] += 1 | |||
|
204 | ||||
|
205 | if self.has_readline: | |||
|
206 | self.readline_startup_hook(self.pre_readline) | |||
|
207 | # exit_now is set by a call to %Exit or %Quit, through the | |||
|
208 | # ask_exit callback. | |||
|
209 | ||||
|
210 | while not self.exit_now: | |||
|
211 | self.hooks.pre_prompt_hook() | |||
|
212 | if more: | |||
|
213 | try: | |||
|
214 | prompt = self.hooks.generate_prompt(True) | |||
|
215 | except: | |||
|
216 | self.showtraceback() | |||
|
217 | if self.autoindent: | |||
|
218 | self.rl_do_indent = True | |||
|
219 | ||||
|
220 | else: | |||
|
221 | try: | |||
|
222 | prompt = self.hooks.generate_prompt(False) | |||
|
223 | except: | |||
|
224 | self.showtraceback() | |||
|
225 | try: | |||
|
226 | line = self.raw_input(prompt, more) | |||
|
227 | if self.exit_now: | |||
|
228 | # quick exit on sys.std[in|out] close | |||
|
229 | break | |||
|
230 | if self.autoindent: | |||
|
231 | self.rl_do_indent = False | |||
|
232 | ||||
|
233 | except KeyboardInterrupt: | |||
|
234 | #double-guard against keyboardinterrupts during kbdint handling | |||
|
235 | try: | |||
|
236 | self.write('\nKeyboardInterrupt\n') | |||
|
237 | self.resetbuffer() | |||
|
238 | # keep cache in sync with the prompt counter: | |||
|
239 | self.outputcache.prompt_count -= 1 | |||
|
240 | ||||
|
241 | if self.autoindent: | |||
|
242 | self.indent_current_nsp = 0 | |||
|
243 | more = 0 | |||
|
244 | except KeyboardInterrupt: | |||
|
245 | pass | |||
|
246 | except EOFError: | |||
|
247 | if self.autoindent: | |||
|
248 | self.rl_do_indent = False | |||
|
249 | if self.has_readline: | |||
|
250 | self.readline_startup_hook(None) | |||
|
251 | self.write('\n') | |||
|
252 | self.exit() | |||
|
253 | except bdb.BdbQuit: | |||
|
254 | warn('The Python debugger has exited with a BdbQuit exception.\n' | |||
|
255 | 'Because of how pdb handles the stack, it is impossible\n' | |||
|
256 | 'for IPython to properly format this particular exception.\n' | |||
|
257 | 'IPython will resume normal operation.') | |||
|
258 | except: | |||
|
259 | # exceptions here are VERY RARE, but they can be triggered | |||
|
260 | # asynchronously by signal handlers, for example. | |||
|
261 | self.showtraceback() | |||
|
262 | else: | |||
|
263 | more = self.push_line(line) | |||
|
264 | if (self.SyntaxTB.last_syntax_error and | |||
|
265 | self.autoedit_syntax): | |||
|
266 | self.edit_syntax_error() | |||
|
267 | ||||
|
268 | # We are off again... | |||
|
269 | __builtin__.__dict__['__IPYTHON__active'] -= 1 | |||
|
270 | ||||
|
271 | # Turn off the exit flag, so the mainloop can be restarted if desired | |||
|
272 | self.exit_now = False | |||
|
273 | ||||
|
274 | def raw_input(self,prompt='',continue_prompt=False): | |||
|
275 | """Write a prompt and read a line. | |||
|
276 | ||||
|
277 | The returned line does not include the trailing newline. | |||
|
278 | When the user enters the EOF key sequence, EOFError is raised. | |||
|
279 | ||||
|
280 | Optional inputs: | |||
|
281 | ||||
|
282 | - prompt(''): a string to be printed to prompt the user. | |||
|
283 | ||||
|
284 | - continue_prompt(False): whether this line is the first one or a | |||
|
285 | continuation in a sequence of inputs. | |||
|
286 | """ | |||
|
287 | # growl.notify("raw_input: ", "prompt = %r\ncontinue_prompt = %s" % (prompt, continue_prompt)) | |||
|
288 | ||||
|
289 | # Code run by the user may have modified the readline completer state. | |||
|
290 | # We must ensure that our completer is back in place. | |||
|
291 | ||||
|
292 | if self.has_readline: | |||
|
293 | self.set_completer() | |||
|
294 | ||||
|
295 | try: | |||
|
296 | line = raw_input_original(prompt).decode(self.stdin_encoding) | |||
|
297 | except ValueError: | |||
|
298 | warn("\n********\nYou or a %run:ed script called sys.stdin.close()" | |||
|
299 | " or sys.stdout.close()!\nExiting IPython!") | |||
|
300 | self.ask_exit() | |||
|
301 | return "" | |||
|
302 | ||||
|
303 | # Try to be reasonably smart about not re-indenting pasted input more | |||
|
304 | # than necessary. We do this by trimming out the auto-indent initial | |||
|
305 | # spaces, if the user's actual input started itself with whitespace. | |||
|
306 | #debugx('self.buffer[-1]') | |||
|
307 | ||||
|
308 | if self.autoindent: | |||
|
309 | if num_ini_spaces(line) > self.indent_current_nsp: | |||
|
310 | line = line[self.indent_current_nsp:] | |||
|
311 | self.indent_current_nsp = 0 | |||
|
312 | ||||
|
313 | # store the unfiltered input before the user has any chance to modify | |||
|
314 | # it. | |||
|
315 | if line.strip(): | |||
|
316 | if continue_prompt: | |||
|
317 | self.input_hist_raw[-1] += '%s\n' % line | |||
|
318 | if self.has_readline and self.readline_use: | |||
|
319 | try: | |||
|
320 | histlen = self.readline.get_current_history_length() | |||
|
321 | if histlen > 1: | |||
|
322 | newhist = self.input_hist_raw[-1].rstrip() | |||
|
323 | self.readline.remove_history_item(histlen-1) | |||
|
324 | self.readline.replace_history_item(histlen-2, | |||
|
325 | newhist.encode(self.stdin_encoding)) | |||
|
326 | except AttributeError: | |||
|
327 | pass # re{move,place}_history_item are new in 2.4. | |||
|
328 | else: | |||
|
329 | self.input_hist_raw.append('%s\n' % line) | |||
|
330 | # only entries starting at first column go to shadow history | |||
|
331 | if line.lstrip() == line: | |||
|
332 | self.shadowhist.add(line.strip()) | |||
|
333 | elif not continue_prompt: | |||
|
334 | self.input_hist_raw.append('\n') | |||
|
335 | try: | |||
|
336 | lineout = self.prefilter_manager.prefilter_lines(line,continue_prompt) | |||
|
337 | except: | |||
|
338 | # blanket except, in case a user-defined prefilter crashes, so it | |||
|
339 | # can't take all of ipython with it. | |||
|
340 | self.showtraceback() | |||
|
341 | return '' | |||
|
342 | else: | |||
|
343 | return lineout | |||
|
344 | ||||
|
345 | # TODO: The following three methods are an early attempt to refactor | |||
|
346 | # the main code execution logic. We don't use them, but they may be | |||
|
347 | # helpful when we refactor the code execution logic further. | |||
|
348 | # def interact_prompt(self): | |||
|
349 | # """ Print the prompt (in read-eval-print loop) | |||
|
350 | # | |||
|
351 | # Provided for those who want to implement their own read-eval-print loop (e.g. GUIs), not | |||
|
352 | # used in standard IPython flow. | |||
|
353 | # """ | |||
|
354 | # if self.more: | |||
|
355 | # try: | |||
|
356 | # prompt = self.hooks.generate_prompt(True) | |||
|
357 | # except: | |||
|
358 | # self.showtraceback() | |||
|
359 | # if self.autoindent: | |||
|
360 | # self.rl_do_indent = True | |||
|
361 | # | |||
|
362 | # else: | |||
|
363 | # try: | |||
|
364 | # prompt = self.hooks.generate_prompt(False) | |||
|
365 | # except: | |||
|
366 | # self.showtraceback() | |||
|
367 | # self.write(prompt) | |||
|
368 | # | |||
|
369 | # def interact_handle_input(self,line): | |||
|
370 | # """ Handle the input line (in read-eval-print loop) | |||
|
371 | # | |||
|
372 | # Provided for those who want to implement their own read-eval-print loop (e.g. GUIs), not | |||
|
373 | # used in standard IPython flow. | |||
|
374 | # """ | |||
|
375 | # if line.lstrip() == line: | |||
|
376 | # self.shadowhist.add(line.strip()) | |||
|
377 | # lineout = self.prefilter_manager.prefilter_lines(line,self.more) | |||
|
378 | # | |||
|
379 | # if line.strip(): | |||
|
380 | # if self.more: | |||
|
381 | # self.input_hist_raw[-1] += '%s\n' % line | |||
|
382 | # else: | |||
|
383 | # self.input_hist_raw.append('%s\n' % line) | |||
|
384 | # | |||
|
385 | # | |||
|
386 | # self.more = self.push_line(lineout) | |||
|
387 | # if (self.SyntaxTB.last_syntax_error and | |||
|
388 | # self.autoedit_syntax): | |||
|
389 | # self.edit_syntax_error() | |||
|
390 | # | |||
|
391 | # def interact_with_readline(self): | |||
|
392 | # """ Demo of using interact_handle_input, interact_prompt | |||
|
393 | # | |||
|
394 | # This is the main read-eval-print loop. If you need to implement your own (e.g. for GUI), | |||
|
395 | # it should work like this. | |||
|
396 | # """ | |||
|
397 | # self.readline_startup_hook(self.pre_readline) | |||
|
398 | # while not self.exit_now: | |||
|
399 | # self.interact_prompt() | |||
|
400 | # if self.more: | |||
|
401 | # self.rl_do_indent = True | |||
|
402 | # else: | |||
|
403 | # self.rl_do_indent = False | |||
|
404 | # line = raw_input_original().decode(self.stdin_encoding) | |||
|
405 | # self.interact_handle_input(line) | |||
|
406 | ||||
|
407 | #------------------------------------------------------------------------- | |||
|
408 | # Methods to support auto-editing of SyntaxErrors. | |||
|
409 | #------------------------------------------------------------------------- | |||
|
410 | ||||
|
411 | def edit_syntax_error(self): | |||
|
412 | """The bottom half of the syntax error handler called in the main loop. | |||
|
413 | ||||
|
414 | Loop until syntax error is fixed or user cancels. | |||
|
415 | """ | |||
|
416 | ||||
|
417 | while self.SyntaxTB.last_syntax_error: | |||
|
418 | # copy and clear last_syntax_error | |||
|
419 | err = self.SyntaxTB.clear_err_state() | |||
|
420 | if not self._should_recompile(err): | |||
|
421 | return | |||
|
422 | try: | |||
|
423 | # may set last_syntax_error again if a SyntaxError is raised | |||
|
424 | self.safe_execfile(err.filename,self.user_ns) | |||
|
425 | except: | |||
|
426 | self.showtraceback() | |||
|
427 | else: | |||
|
428 | try: | |||
|
429 | f = file(err.filename) | |||
|
430 | try: | |||
|
431 | # This should be inside a display_trap block and I | |||
|
432 | # think it is. | |||
|
433 | sys.displayhook(f.read()) | |||
|
434 | finally: | |||
|
435 | f.close() | |||
|
436 | except: | |||
|
437 | self.showtraceback() | |||
|
438 | ||||
|
439 | def _should_recompile(self,e): | |||
|
440 | """Utility routine for edit_syntax_error""" | |||
|
441 | ||||
|
442 | if e.filename in ('<ipython console>','<input>','<string>', | |||
|
443 | '<console>','<BackgroundJob compilation>', | |||
|
444 | None): | |||
|
445 | ||||
|
446 | return False | |||
|
447 | try: | |||
|
448 | if (self.autoedit_syntax and | |||
|
449 | not self.ask_yes_no('Return to editor to correct syntax error? ' | |||
|
450 | '[Y/n] ','y')): | |||
|
451 | return False | |||
|
452 | except EOFError: | |||
|
453 | return False | |||
|
454 | ||||
|
455 | def int0(x): | |||
|
456 | try: | |||
|
457 | return int(x) | |||
|
458 | except TypeError: | |||
|
459 | return 0 | |||
|
460 | # always pass integer line and offset values to editor hook | |||
|
461 | try: | |||
|
462 | self.hooks.fix_error_editor(e.filename, | |||
|
463 | int0(e.lineno),int0(e.offset),e.msg) | |||
|
464 | except TryNext: | |||
|
465 | warn('Could not open editor') | |||
|
466 | return False | |||
|
467 | return True | |||
|
468 | ||||
|
469 | #------------------------------------------------------------------------- | |||
|
470 | # Things related to GUI support and pylab | |||
|
471 | #------------------------------------------------------------------------- | |||
|
472 | ||||
|
473 | def enable_pylab(self, gui=None): | |||
|
474 | """Activate pylab support at runtime. | |||
|
475 | ||||
|
476 | This turns on support for matplotlib, preloads into the interactive | |||
|
477 | namespace all of numpy and pylab, and configures IPython to correcdtly | |||
|
478 | interact with the GUI event loop. The GUI backend to be used can be | |||
|
479 | optionally selected with the optional :param:`gui` argument. | |||
|
480 | ||||
|
481 | Parameters | |||
|
482 | ---------- | |||
|
483 | gui : optional, string | |||
|
484 | ||||
|
485 | If given, dictates the choice of matplotlib GUI backend to use | |||
|
486 | (should be one of IPython's supported backends, 'tk', 'qt', 'wx' or | |||
|
487 | 'gtk'), otherwise we use the default chosen by matplotlib (as | |||
|
488 | dictated by the matplotlib build-time options plus the user's | |||
|
489 | matplotlibrc configuration file). | |||
|
490 | """ | |||
|
491 | # We want to prevent the loading of pylab to pollute the user's | |||
|
492 | # namespace as shown by the %who* magics, so we execute the activation | |||
|
493 | # code in an empty namespace, and we update *both* user_ns and | |||
|
494 | # user_ns_hidden with this information. | |||
|
495 | ns = {} | |||
|
496 | gui = pylab_activate(ns, gui) | |||
|
497 | self.user_ns.update(ns) | |||
|
498 | self.user_ns_hidden.update(ns) | |||
|
499 | # Now we must activate the gui pylab wants to use, and fix %run to take | |||
|
500 | # plot updates into account | |||
|
501 | enable_gui(gui) | |||
|
502 | self.magic_run = self._pylab_magic_run | |||
|
503 | ||||
|
504 | #------------------------------------------------------------------------- | |||
|
505 | # Things related to exiting | |||
|
506 | #------------------------------------------------------------------------- | |||
|
507 | ||||
|
508 | def ask_exit(self): | |||
|
509 | """ Ask the shell to exit. Can be overiden and used as a callback. """ | |||
|
510 | self.exit_now = True | |||
|
511 | ||||
|
512 | def exit(self): | |||
|
513 | """Handle interactive exit. | |||
|
514 | ||||
|
515 | This method calls the ask_exit callback.""" | |||
|
516 | if self.confirm_exit: | |||
|
517 | if self.ask_yes_no('Do you really want to exit ([y]/n)?','y'): | |||
|
518 | self.ask_exit() | |||
|
519 | else: | |||
|
520 | self.ask_exit() | |||
|
521 | ||||
|
522 | ||||
|
523 | InteractiveShellABC.register(TerminalInteractiveShell) |
1 | NO CONTENT: new file 100644 |
|
NO CONTENT: new file 100644 |
1 | NO CONTENT: new file 100644 |
|
NO CONTENT: new file 100644 |
@@ -0,0 +1,22 b'' | |||||
|
1 | import __builtin__ | |||
|
2 | ||||
|
3 | from session import extract_header | |||
|
4 | ||||
|
5 | class DisplayHook(object): | |||
|
6 | ||||
|
7 | def __init__(self, session, pub_socket): | |||
|
8 | self.session = session | |||
|
9 | self.pub_socket = pub_socket | |||
|
10 | self.parent_header = {} | |||
|
11 | ||||
|
12 | def __call__(self, obj): | |||
|
13 | if obj is None: | |||
|
14 | return | |||
|
15 | ||||
|
16 | __builtin__._ = obj | |||
|
17 | msg = self.session.msg(u'pyout', {u'data':repr(obj)}, | |||
|
18 | parent=self.parent_header) | |||
|
19 | self.pub_socket.send_json(msg) | |||
|
20 | ||||
|
21 | def set_parent(self, parent): | |||
|
22 | self.parent_header = extract_header(parent) No newline at end of file |
@@ -0,0 +1,42 b'' | |||||
|
1 | import os | |||
|
2 | import time | |||
|
3 | from threading import Thread | |||
|
4 | ||||
|
5 | ||||
|
6 | class ExitPollerUnix(Thread): | |||
|
7 | """ A Unix-specific daemon thread that terminates the program immediately | |||
|
8 | when the parent process no longer exists. | |||
|
9 | """ | |||
|
10 | ||||
|
11 | def __init__(self): | |||
|
12 | super(ExitPollerUnix, self).__init__() | |||
|
13 | self.daemon = True | |||
|
14 | ||||
|
15 | def run(self): | |||
|
16 | # We cannot use os.waitpid because it works only for child processes. | |||
|
17 | from errno import EINTR | |||
|
18 | while True: | |||
|
19 | try: | |||
|
20 | if os.getppid() == 1: | |||
|
21 | os._exit(1) | |||
|
22 | time.sleep(1.0) | |||
|
23 | except OSError, e: | |||
|
24 | if e.errno == EINTR: | |||
|
25 | continue | |||
|
26 | raise | |||
|
27 | ||||
|
28 | class ExitPollerWindows(Thread): | |||
|
29 | """ A Windows-specific daemon thread that terminates the program immediately | |||
|
30 | when a Win32 handle is signaled. | |||
|
31 | """ | |||
|
32 | ||||
|
33 | def __init__(self, handle): | |||
|
34 | super(ExitPollerWindows, self).__init__() | |||
|
35 | self.daemon = True | |||
|
36 | self.handle = handle | |||
|
37 | ||||
|
38 | def run(self): | |||
|
39 | from _subprocess import WaitForSingleObject, WAIT_OBJECT_0, INFINITE | |||
|
40 | result = WaitForSingleObject(self.handle, INFINITE) | |||
|
41 | if result == WAIT_OBJECT_0: | |||
|
42 | os._exit(1) No newline at end of file |
@@ -0,0 +1,77 b'' | |||||
|
1 | import sys | |||
|
2 | import time | |||
|
3 | from cStringIO import StringIO | |||
|
4 | ||||
|
5 | from session import extract_header, Message | |||
|
6 | ||||
|
7 | #----------------------------------------------------------------------------- | |||
|
8 | # Stream classes | |||
|
9 | #----------------------------------------------------------------------------- | |||
|
10 | ||||
|
11 | class OutStream(object): | |||
|
12 | """A file like object that publishes the stream to a 0MQ PUB socket.""" | |||
|
13 | ||||
|
14 | # The time interval between automatic flushes, in seconds. | |||
|
15 | flush_interval = 0.05 | |||
|
16 | ||||
|
17 | def __init__(self, session, pub_socket, name): | |||
|
18 | self.session = session | |||
|
19 | self.pub_socket = pub_socket | |||
|
20 | self.name = name | |||
|
21 | self.parent_header = {} | |||
|
22 | self._new_buffer() | |||
|
23 | ||||
|
24 | def set_parent(self, parent): | |||
|
25 | self.parent_header = extract_header(parent) | |||
|
26 | ||||
|
27 | def close(self): | |||
|
28 | self.pub_socket = None | |||
|
29 | ||||
|
30 | def flush(self): | |||
|
31 | if self.pub_socket is None: | |||
|
32 | raise ValueError(u'I/O operation on closed file') | |||
|
33 | else: | |||
|
34 | data = self._buffer.getvalue() | |||
|
35 | if data: | |||
|
36 | content = {u'name':self.name, u'data':data} | |||
|
37 | msg = self.session.msg(u'stream', content=content, | |||
|
38 | parent=self.parent_header) | |||
|
39 | print>>sys.__stdout__, Message(msg) | |||
|
40 | self.pub_socket.send_json(msg) | |||
|
41 | ||||
|
42 | self._buffer.close() | |||
|
43 | self._new_buffer() | |||
|
44 | ||||
|
45 | def isatty(self): | |||
|
46 | return False | |||
|
47 | ||||
|
48 | def next(self): | |||
|
49 | raise IOError('Read not supported on a write only stream.') | |||
|
50 | ||||
|
51 | def read(self, size=-1): | |||
|
52 | raise IOError('Read not supported on a write only stream.') | |||
|
53 | ||||
|
54 | def readline(self, size=-1): | |||
|
55 | raise IOError('Read not supported on a write only stream.') | |||
|
56 | ||||
|
57 | def write(self, string): | |||
|
58 | if self.pub_socket is None: | |||
|
59 | raise ValueError('I/O operation on closed file') | |||
|
60 | else: | |||
|
61 | self._buffer.write(string) | |||
|
62 | current_time = time.time() | |||
|
63 | if self._start <= 0: | |||
|
64 | self._start = current_time | |||
|
65 | elif current_time - self._start > self.flush_interval: | |||
|
66 | self.flush() | |||
|
67 | ||||
|
68 | def writelines(self, sequence): | |||
|
69 | if self.pub_socket is None: | |||
|
70 | raise ValueError('I/O operation on closed file') | |||
|
71 | else: | |||
|
72 | for string in sequence: | |||
|
73 | self.write(string) | |||
|
74 | ||||
|
75 | def _new_buffer(self): | |||
|
76 | self._buffer = StringIO() | |||
|
77 | self._start = -1 No newline at end of file |
@@ -0,0 +1,367 b'' | |||||
|
1 | #!/usr/bin/env python | |||
|
2 | """A simple interactive kernel that talks to a frontend over 0MQ. | |||
|
3 | ||||
|
4 | Things to do: | |||
|
5 | ||||
|
6 | * Implement `set_parent` logic. Right before doing exec, the Kernel should | |||
|
7 | call set_parent on all the PUB objects with the message about to be executed. | |||
|
8 | * Implement random port and security key logic. | |||
|
9 | * Implement control messages. | |||
|
10 | * Implement event loop and poll version. | |||
|
11 | """ | |||
|
12 | ||||
|
13 | #----------------------------------------------------------------------------- | |||
|
14 | # Imports | |||
|
15 | #----------------------------------------------------------------------------- | |||
|
16 | ||||
|
17 | # Standard library imports. | |||
|
18 | import __builtin__ | |||
|
19 | from code import CommandCompiler | |||
|
20 | import os | |||
|
21 | import sys | |||
|
22 | import time | |||
|
23 | import traceback | |||
|
24 | ||||
|
25 | # System library imports. | |||
|
26 | import zmq | |||
|
27 | ||||
|
28 | # Local imports. | |||
|
29 | from IPython.config.configurable import Configurable | |||
|
30 | from IPython.zmq.zmqshell import ZMQInteractiveShell | |||
|
31 | from IPython.external.argparse import ArgumentParser | |||
|
32 | from IPython.utils.traitlets import Instance | |||
|
33 | from IPython.zmq.session import Session, Message | |||
|
34 | from completer import KernelCompleter | |||
|
35 | from iostream import OutStream | |||
|
36 | from displayhook import DisplayHook | |||
|
37 | from exitpoller import ExitPollerUnix, ExitPollerWindows | |||
|
38 | ||||
|
39 | #----------------------------------------------------------------------------- | |||
|
40 | # Main kernel class | |||
|
41 | #----------------------------------------------------------------------------- | |||
|
42 | ||||
|
43 | class Kernel(Configurable): | |||
|
44 | ||||
|
45 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |||
|
46 | session = Instance('IPython.zmq.session.Session') | |||
|
47 | reply_socket = Instance('zmq.Socket') | |||
|
48 | pub_socket = Instance('zmq.Socket') | |||
|
49 | req_socket = Instance('zmq.Socket') | |||
|
50 | ||||
|
51 | def __init__(self, **kwargs): | |||
|
52 | super(Kernel, self).__init__(**kwargs) | |||
|
53 | self.shell = ZMQInteractiveShell.instance() | |||
|
54 | ||||
|
55 | # Build dict of handlers for message types | |||
|
56 | msg_types = [ 'execute_request', 'complete_request', | |||
|
57 | 'object_info_request' ] | |||
|
58 | self.handlers = {} | |||
|
59 | for msg_type in msg_types: | |||
|
60 | self.handlers[msg_type] = getattr(self, msg_type) | |||
|
61 | ||||
|
62 | def abort_queue(self): | |||
|
63 | while True: | |||
|
64 | try: | |||
|
65 | ident = self.reply_socket.recv(zmq.NOBLOCK) | |||
|
66 | except zmq.ZMQError, e: | |||
|
67 | if e.errno == zmq.EAGAIN: | |||
|
68 | break | |||
|
69 | else: | |||
|
70 | assert self.reply_socket.rcvmore(), "Unexpected missing message part." | |||
|
71 | msg = self.reply_socket.recv_json() | |||
|
72 | print>>sys.__stdout__, "Aborting:" | |||
|
73 | print>>sys.__stdout__, Message(msg) | |||
|
74 | msg_type = msg['msg_type'] | |||
|
75 | reply_type = msg_type.split('_')[0] + '_reply' | |||
|
76 | reply_msg = self.session.msg(reply_type, {'status' : 'aborted'}, msg) | |||
|
77 | print>>sys.__stdout__, Message(reply_msg) | |||
|
78 | self.reply_socket.send(ident,zmq.SNDMORE) | |||
|
79 | self.reply_socket.send_json(reply_msg) | |||
|
80 | # We need to wait a bit for requests to come in. This can probably | |||
|
81 | # be set shorter for true asynchronous clients. | |||
|
82 | time.sleep(0.1) | |||
|
83 | ||||
|
84 | def execute_request(self, ident, parent): | |||
|
85 | try: | |||
|
86 | code = parent[u'content'][u'code'] | |||
|
87 | except: | |||
|
88 | print>>sys.__stderr__, "Got bad msg: " | |||
|
89 | print>>sys.__stderr__, Message(parent) | |||
|
90 | return | |||
|
91 | pyin_msg = self.session.msg(u'pyin',{u'code':code}, parent=parent) | |||
|
92 | self.pub_socket.send_json(pyin_msg) | |||
|
93 | ||||
|
94 | try: | |||
|
95 | # Replace raw_input. Note that is not sufficient to replace | |||
|
96 | # raw_input in the user namespace. | |||
|
97 | raw_input = lambda prompt='': self.raw_input(prompt, ident, parent) | |||
|
98 | __builtin__.raw_input = raw_input | |||
|
99 | ||||
|
100 | # Configure the display hook. | |||
|
101 | sys.displayhook.set_parent(parent) | |||
|
102 | ||||
|
103 | self.shell.runlines(code) | |||
|
104 | # exec comp_code in self.user_ns, self.user_ns | |||
|
105 | except: | |||
|
106 | etype, evalue, tb = sys.exc_info() | |||
|
107 | tb = traceback.format_exception(etype, evalue, tb) | |||
|
108 | exc_content = { | |||
|
109 | u'status' : u'error', | |||
|
110 | u'traceback' : tb, | |||
|
111 | u'ename' : unicode(etype.__name__), | |||
|
112 | u'evalue' : unicode(evalue) | |||
|
113 | } | |||
|
114 | exc_msg = self.session.msg(u'pyerr', exc_content, parent) | |||
|
115 | self.pub_socket.send_json(exc_msg) | |||
|
116 | reply_content = exc_content | |||
|
117 | else: | |||
|
118 | reply_content = {'status' : 'ok'} | |||
|
119 | ||||
|
120 | # Flush output before sending the reply. | |||
|
121 | sys.stderr.flush() | |||
|
122 | sys.stdout.flush() | |||
|
123 | ||||
|
124 | # Send the reply. | |||
|
125 | reply_msg = self.session.msg(u'execute_reply', reply_content, parent) | |||
|
126 | print>>sys.__stdout__, Message(reply_msg) | |||
|
127 | self.reply_socket.send(ident, zmq.SNDMORE) | |||
|
128 | self.reply_socket.send_json(reply_msg) | |||
|
129 | if reply_msg['content']['status'] == u'error': | |||
|
130 | self.abort_queue() | |||
|
131 | ||||
|
132 | def raw_input(self, prompt, ident, parent): | |||
|
133 | # Flush output before making the request. | |||
|
134 | sys.stderr.flush() | |||
|
135 | sys.stdout.flush() | |||
|
136 | ||||
|
137 | # Send the input request. | |||
|
138 | content = dict(prompt=prompt) | |||
|
139 | msg = self.session.msg(u'input_request', content, parent) | |||
|
140 | self.req_socket.send_json(msg) | |||
|
141 | ||||
|
142 | # Await a response. | |||
|
143 | reply = self.req_socket.recv_json() | |||
|
144 | try: | |||
|
145 | value = reply['content']['value'] | |||
|
146 | except: | |||
|
147 | print>>sys.__stderr__, "Got bad raw_input reply: " | |||
|
148 | print>>sys.__stderr__, Message(parent) | |||
|
149 | value = '' | |||
|
150 | return value | |||
|
151 | ||||
|
152 | def complete_request(self, ident, parent): | |||
|
153 | matches = {'matches' : self.complete(parent), | |||
|
154 | 'status' : 'ok'} | |||
|
155 | completion_msg = self.session.send(self.reply_socket, 'complete_reply', | |||
|
156 | matches, parent, ident) | |||
|
157 | print >> sys.__stdout__, completion_msg | |||
|
158 | ||||
|
159 | def complete(self, msg): | |||
|
160 | return self.shell.complete(msg.content.line) | |||
|
161 | ||||
|
162 | def object_info_request(self, ident, parent): | |||
|
163 | context = parent['content']['oname'].split('.') | |||
|
164 | object_info = self.object_info(context) | |||
|
165 | msg = self.session.send(self.reply_socket, 'object_info_reply', | |||
|
166 | object_info, parent, ident) | |||
|
167 | print >> sys.__stdout__, msg | |||
|
168 | ||||
|
169 | def object_info(self, context): | |||
|
170 | symbol, leftover = self.symbol_from_context(context) | |||
|
171 | if symbol is not None and not leftover: | |||
|
172 | doc = getattr(symbol, '__doc__', '') | |||
|
173 | else: | |||
|
174 | doc = '' | |||
|
175 | object_info = dict(docstring = doc) | |||
|
176 | return object_info | |||
|
177 | ||||
|
178 | def symbol_from_context(self, context): | |||
|
179 | if not context: | |||
|
180 | return None, context | |||
|
181 | ||||
|
182 | base_symbol_string = context[0] | |||
|
183 | symbol = self.shell.user_ns.get(base_symbol_string, None) | |||
|
184 | if symbol is None: | |||
|
185 | symbol = __builtin__.__dict__.get(base_symbol_string, None) | |||
|
186 | if symbol is None: | |||
|
187 | return None, context | |||
|
188 | ||||
|
189 | context = context[1:] | |||
|
190 | for i, name in enumerate(context): | |||
|
191 | new_symbol = getattr(symbol, name, None) | |||
|
192 | if new_symbol is None: | |||
|
193 | return symbol, context[i:] | |||
|
194 | else: | |||
|
195 | symbol = new_symbol | |||
|
196 | ||||
|
197 | return symbol, [] | |||
|
198 | ||||
|
199 | def start(self): | |||
|
200 | while True: | |||
|
201 | ident = self.reply_socket.recv() | |||
|
202 | assert self.reply_socket.rcvmore(), "Missing message part." | |||
|
203 | msg = self.reply_socket.recv_json() | |||
|
204 | omsg = Message(msg) | |||
|
205 | print>>sys.__stdout__ | |||
|
206 | print>>sys.__stdout__, omsg | |||
|
207 | handler = self.handlers.get(omsg.msg_type, None) | |||
|
208 | if handler is None: | |||
|
209 | print >> sys.__stderr__, "UNKNOWN MESSAGE TYPE:", omsg | |||
|
210 | else: | |||
|
211 | handler(ident, omsg) | |||
|
212 | ||||
|
213 | #----------------------------------------------------------------------------- | |||
|
214 | # Kernel main and launch functions | |||
|
215 | #----------------------------------------------------------------------------- | |||
|
216 | ||||
|
217 | def bind_port(socket, ip, port): | |||
|
218 | """ Binds the specified ZMQ socket. If the port is less than zero, a random | |||
|
219 | port is chosen. Returns the port that was bound. | |||
|
220 | """ | |||
|
221 | connection = 'tcp://%s' % ip | |||
|
222 | if port <= 0: | |||
|
223 | port = socket.bind_to_random_port(connection) | |||
|
224 | else: | |||
|
225 | connection += ':%i' % port | |||
|
226 | socket.bind(connection) | |||
|
227 | return port | |||
|
228 | ||||
|
229 | ||||
|
230 | def main(): | |||
|
231 | """ Main entry point for launching a kernel. | |||
|
232 | """ | |||
|
233 | # Parse command line arguments. | |||
|
234 | parser = ArgumentParser() | |||
|
235 | parser.add_argument('--ip', type=str, default='127.0.0.1', | |||
|
236 | help='set the kernel\'s IP address [default: local]') | |||
|
237 | parser.add_argument('--xrep', type=int, metavar='PORT', default=0, | |||
|
238 | help='set the XREP channel port [default: random]') | |||
|
239 | parser.add_argument('--pub', type=int, metavar='PORT', default=0, | |||
|
240 | help='set the PUB channel port [default: random]') | |||
|
241 | parser.add_argument('--req', type=int, metavar='PORT', default=0, | |||
|
242 | help='set the REQ channel port [default: random]') | |||
|
243 | if sys.platform == 'win32': | |||
|
244 | parser.add_argument('--parent', type=int, metavar='HANDLE', | |||
|
245 | default=0, help='kill this process if the process ' | |||
|
246 | 'with HANDLE dies') | |||
|
247 | else: | |||
|
248 | parser.add_argument('--parent', action='store_true', | |||
|
249 | help='kill this process if its parent dies') | |||
|
250 | namespace = parser.parse_args() | |||
|
251 | ||||
|
252 | # Create a context, a session, and the kernel sockets. | |||
|
253 | print >>sys.__stdout__, "Starting the kernel..." | |||
|
254 | context = zmq.Context() | |||
|
255 | session = Session(username=u'kernel') | |||
|
256 | ||||
|
257 | reply_socket = context.socket(zmq.XREP) | |||
|
258 | xrep_port = bind_port(reply_socket, namespace.ip, namespace.xrep) | |||
|
259 | print >>sys.__stdout__, "XREP Channel on port", xrep_port | |||
|
260 | ||||
|
261 | pub_socket = context.socket(zmq.PUB) | |||
|
262 | pub_port = bind_port(pub_socket, namespace.ip, namespace.pub) | |||
|
263 | print >>sys.__stdout__, "PUB Channel on port", pub_port | |||
|
264 | ||||
|
265 | req_socket = context.socket(zmq.XREQ) | |||
|
266 | req_port = bind_port(req_socket, namespace.ip, namespace.req) | |||
|
267 | print >>sys.__stdout__, "REQ Channel on port", req_port | |||
|
268 | ||||
|
269 | # Redirect input streams. This needs to be done before the Kernel is done | |||
|
270 | # because currently the Kernel creates a ZMQInteractiveShell, which | |||
|
271 | # holds references to sys.stdout and sys.stderr. | |||
|
272 | sys.stdout = OutStream(session, pub_socket, u'stdout') | |||
|
273 | sys.stderr = OutStream(session, pub_socket, u'stderr') | |||
|
274 | # Set a displayhook. | |||
|
275 | sys.displayhook = DisplayHook(session, pub_socket) | |||
|
276 | ||||
|
277 | # Create the kernel. | |||
|
278 | kernel = Kernel( | |||
|
279 | session=session, reply_socket=reply_socket, | |||
|
280 | pub_socket=pub_socket, req_socket=req_socket | |||
|
281 | ) | |||
|
282 | ||||
|
283 | # Configure this kernel/process to die on parent termination, if necessary. | |||
|
284 | if namespace.parent: | |||
|
285 | if sys.platform == 'win32': | |||
|
286 | poller = ExitPollerWindows(namespace.parent) | |||
|
287 | else: | |||
|
288 | poller = ExitPollerUnix() | |||
|
289 | poller.start() | |||
|
290 | ||||
|
291 | # Start the kernel mainloop. | |||
|
292 | kernel.start() | |||
|
293 | ||||
|
294 | ||||
|
295 | def launch_kernel(xrep_port=0, pub_port=0, req_port=0, independent=False): | |||
|
296 | """ Launches a localhost kernel, binding to the specified ports. | |||
|
297 | ||||
|
298 | Parameters | |||
|
299 | ---------- | |||
|
300 | xrep_port : int, optional | |||
|
301 | The port to use for XREP channel. | |||
|
302 | ||||
|
303 | pub_port : int, optional | |||
|
304 | The port to use for the SUB channel. | |||
|
305 | ||||
|
306 | req_port : int, optional | |||
|
307 | The port to use for the REQ (raw input) channel. | |||
|
308 | ||||
|
309 | independent : bool, optional (default False) | |||
|
310 | If set, the kernel process is guaranteed to survive if this process | |||
|
311 | dies. If not set, an effort is made to ensure that the kernel is killed | |||
|
312 | when this process dies. Note that in this case it is still good practice | |||
|
313 | to kill kernels manually before exiting. | |||
|
314 | ||||
|
315 | Returns | |||
|
316 | ------- | |||
|
317 | A tuple of form: | |||
|
318 | (kernel_process, xrep_port, pub_port, req_port) | |||
|
319 | where kernel_process is a Popen object and the ports are integers. | |||
|
320 | """ | |||
|
321 | import socket | |||
|
322 | from subprocess import Popen | |||
|
323 | ||||
|
324 | # Find open ports as necessary. | |||
|
325 | ports = [] | |||
|
326 | ports_needed = int(xrep_port <= 0) + int(pub_port <= 0) + int(req_port <= 0) | |||
|
327 | for i in xrange(ports_needed): | |||
|
328 | sock = socket.socket() | |||
|
329 | sock.bind(('', 0)) | |||
|
330 | ports.append(sock) | |||
|
331 | for i, sock in enumerate(ports): | |||
|
332 | port = sock.getsockname()[1] | |||
|
333 | sock.close() | |||
|
334 | ports[i] = port | |||
|
335 | if xrep_port <= 0: | |||
|
336 | xrep_port = ports.pop(0) | |||
|
337 | if pub_port <= 0: | |||
|
338 | pub_port = ports.pop(0) | |||
|
339 | if req_port <= 0: | |||
|
340 | req_port = ports.pop(0) | |||
|
341 | ||||
|
342 | # Spawn a kernel. | |||
|
343 | command = 'from IPython.zmq.ipkernel import main; main()' | |||
|
344 | arguments = [ sys.executable, '-c', command, '--xrep', str(xrep_port), | |||
|
345 | '--pub', str(pub_port), '--req', str(req_port) ] | |||
|
346 | if independent: | |||
|
347 | if sys.platform == 'win32': | |||
|
348 | proc = Popen(['start', '/b'] + arguments, shell=True) | |||
|
349 | else: | |||
|
350 | proc = Popen(arguments, preexec_fn=lambda: os.setsid()) | |||
|
351 | else: | |||
|
352 | if sys.platform == 'win32': | |||
|
353 | from _subprocess import DuplicateHandle, GetCurrentProcess, \ | |||
|
354 | DUPLICATE_SAME_ACCESS | |||
|
355 | pid = GetCurrentProcess() | |||
|
356 | handle = DuplicateHandle(pid, pid, pid, 0, | |||
|
357 | True, # Inheritable by new processes. | |||
|
358 | DUPLICATE_SAME_ACCESS) | |||
|
359 | proc = Popen(arguments + ['--parent', str(int(handle))]) | |||
|
360 | else: | |||
|
361 | proc = Popen(arguments + ['--parent']) | |||
|
362 | ||||
|
363 | return proc, xrep_port, pub_port, req_port | |||
|
364 | ||||
|
365 | ||||
|
366 | if __name__ == '__main__': | |||
|
367 | main() |
@@ -0,0 +1,31 b'' | |||||
|
1 | import sys | |||
|
2 | from subprocess import Popen, PIPE | |||
|
3 | from IPython.core.interactiveshell import InteractiveShell, InteractiveShellABC | |||
|
4 | ||||
|
5 | ||||
|
6 | class ZMQInteractiveShell(InteractiveShell): | |||
|
7 | """A subclass of InteractiveShell for ZMQ.""" | |||
|
8 | ||||
|
9 | def system(self, cmd): | |||
|
10 | cmd = self.var_expand(cmd, depth=2) | |||
|
11 | sys.stdout.flush() | |||
|
12 | sys.stderr.flush() | |||
|
13 | p = Popen(cmd, shell=True, stdout=PIPE, stderr=PIPE) | |||
|
14 | for line in p.stdout.read().split('\n'): | |||
|
15 | if len(line) > 0: | |||
|
16 | print line | |||
|
17 | for line in p.stderr.read().split('\n'): | |||
|
18 | if len(line) > 0: | |||
|
19 | print line | |||
|
20 | return p.wait() | |||
|
21 | ||||
|
22 | def init_io(self): | |||
|
23 | # This will just use sys.stdout and sys.stderr. If you want to | |||
|
24 | # override sys.stdout and sys.stderr themselves, you need to do that | |||
|
25 | # *before* instantiating this class, because Term holds onto | |||
|
26 | # references to the underlying streams. | |||
|
27 | import IPython.utils.io | |||
|
28 | Term = IPython.utils.io.IOTerm() | |||
|
29 | IPython.utils.io.Term = Term | |||
|
30 | ||||
|
31 | InteractiveShellABC.register(ZMQInteractiveShell) |
@@ -40,10 +40,9 b' sys.path.append(os.path.join(os.path.dirname(__file__), "extensions"))' | |||||
40 | from .config.loader import Config |
|
40 | from .config.loader import Config | |
41 | from .core import release |
|
41 | from .core import release | |
42 | from .core.application import Application |
|
42 | from .core.application import Application | |
43 | from .core.ipapp import IPythonApp |
|
43 | from .frontend.terminal.embed import embed | |
44 | from .core.embed import embed |
|
|||
45 | from .core.error import TryNext |
|
44 | from .core.error import TryNext | |
46 |
from .core.i |
|
45 | from .core.interactiveshell import InteractiveShell | |
47 | from .testing import test |
|
46 | from .testing import test | |
48 |
|
47 | |||
49 | from .lib import ( |
|
48 | from .lib import ( |
@@ -47,15 +47,15 b' c = get_config()' | |||||
47 |
|
47 | |||
48 | # c.InteractiveShell.autocall = 1 |
|
48 | # c.InteractiveShell.autocall = 1 | |
49 |
|
49 | |||
50 | # c.InteractiveShell.autoedit_syntax = False |
|
50 | # c.TerminalInteractiveShell.autoedit_syntax = False | |
51 |
|
51 | |||
52 | # c.InteractiveShell.autoindent = True |
|
52 | # c.InteractiveShell.autoindent = True | |
53 |
|
53 | |||
54 | # c.InteractiveShell.automagic = False |
|
54 | # c.InteractiveShell.automagic = False | |
55 |
|
55 | |||
56 | # c.InteractiveShell.banner1 = 'This if for overriding the default IPython banner' |
|
56 | # c.TerminalTerminalInteractiveShell.banner1 = 'This if for overriding the default IPython banner' | |
57 |
|
57 | |||
58 | # c.InteractiveShell.banner2 = "This is for extra banner text" |
|
58 | # c.TerminalTerminalInteractiveShell.banner2 = "This is for extra banner text" | |
59 |
|
59 | |||
60 | # c.InteractiveShell.cache_size = 1000 |
|
60 | # c.InteractiveShell.cache_size = 1000 | |
61 |
|
61 | |||
@@ -63,11 +63,11 b' c = get_config()' | |||||
63 |
|
63 | |||
64 | # c.InteractiveShell.color_info = True |
|
64 | # c.InteractiveShell.color_info = True | |
65 |
|
65 | |||
66 | # c.InteractiveShell.confirm_exit = True |
|
66 | # c.TerminalInteractiveShell.confirm_exit = True | |
67 |
|
67 | |||
68 | # c.InteractiveShell.deep_reload = False |
|
68 | # c.InteractiveShell.deep_reload = False | |
69 |
|
69 | |||
70 | # c.InteractiveShell.editor = 'nano' |
|
70 | # c.TerminalInteractiveShell.editor = 'nano' | |
71 |
|
71 | |||
72 | # c.InteractiveShell.logstart = True |
|
72 | # c.InteractiveShell.logstart = True | |
73 |
|
73 | |||
@@ -77,7 +77,7 b' c = get_config()' | |||||
77 |
|
77 | |||
78 | # c.InteractiveShell.object_info_string_level = 0 |
|
78 | # c.InteractiveShell.object_info_string_level = 0 | |
79 |
|
79 | |||
80 | # c.InteractiveShell.pager = 'less' |
|
80 | # c.TerminalInteractiveShell.pager = 'less' | |
81 |
|
81 | |||
82 | # c.InteractiveShell.pdb = False |
|
82 | # c.InteractiveShell.pdb = False | |
83 |
|
83 | |||
@@ -114,7 +114,7 b' c = get_config()' | |||||
114 | # c.InteractiveShell.readline_merge_completions = True |
|
114 | # c.InteractiveShell.readline_merge_completions = True | |
115 | # c.InteractiveShell.readline_omit__names = 0 |
|
115 | # c.InteractiveShell.readline_omit__names = 0 | |
116 |
|
116 | |||
117 | # c.InteractiveShell.screen_length = 0 |
|
117 | # c.TerminalInteractiveShell.screen_length = 0 | |
118 |
|
118 | |||
119 | # c.InteractiveShell.separate_in = '\n' |
|
119 | # c.InteractiveShell.separate_in = '\n' | |
120 | # c.InteractiveShell.separate_out = '' |
|
120 | # c.InteractiveShell.separate_out = '' | |
@@ -124,7 +124,7 b' c = get_config()' | |||||
124 |
|
124 | |||
125 | # c.InteractiveShell.system_verbose = True |
|
125 | # c.InteractiveShell.system_verbose = True | |
126 |
|
126 | |||
127 | # c.InteractiveShell.term_title = False |
|
127 | # c.TerminalInteractiveShell.term_title = False | |
128 |
|
128 | |||
129 | # c.InteractiveShell.wildcards_case_sensitive = True |
|
129 | # c.InteractiveShell.wildcards_case_sensitive = True | |
130 |
|
130 |
@@ -104,7 +104,7 b' class AliasManager(Configurable):' | |||||
104 |
|
104 | |||
105 | default_aliases = List(default_aliases(), config=True) |
|
105 | default_aliases = List(default_aliases(), config=True) | |
106 | user_aliases = List(default_value=[], config=True) |
|
106 | user_aliases = List(default_value=[], config=True) | |
107 |
shell = Instance('IPython.core.i |
|
107 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
108 |
|
108 | |||
109 | def __init__(self, shell=None, config=None): |
|
109 | def __init__(self, shell=None, config=None): | |
110 | super(AliasManager, self).__init__(shell=shell, config=config) |
|
110 | super(AliasManager, self).__init__(shell=shell, config=config) |
@@ -37,7 +37,7 b' BuiltinUndefined = __BuiltinUndefined()' | |||||
37 |
|
37 | |||
38 | class BuiltinTrap(Configurable): |
|
38 | class BuiltinTrap(Configurable): | |
39 |
|
39 | |||
40 |
shell = Instance('IPython.core.i |
|
40 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
41 |
|
41 | |||
42 | def __init__(self, shell=None): |
|
42 | def __init__(self, shell=None): | |
43 | super(BuiltinTrap, self).__init__(shell=shell, config=None) |
|
43 | super(BuiltinTrap, self).__init__(shell=shell, config=None) |
@@ -32,7 +32,7 b' import sys' | |||||
32 | from IPython.utils import PyColorize |
|
32 | from IPython.utils import PyColorize | |
33 | from IPython.core import ipapi |
|
33 | from IPython.core import ipapi | |
34 | from IPython.utils import coloransi |
|
34 | from IPython.utils import coloransi | |
35 |
|
|
35 | import IPython.utils.io | |
36 | from IPython.core.excolors import exception_colors |
|
36 | from IPython.core.excolors import exception_colors | |
37 |
|
37 | |||
38 | # See if we can use pydb. |
|
38 | # See if we can use pydb. | |
@@ -171,7 +171,7 b' class Pdb(OldPdb):' | |||||
171 |
|
171 | |||
172 | # Parent constructor: |
|
172 | # Parent constructor: | |
173 | if has_pydb and completekey is None: |
|
173 | if has_pydb and completekey is None: | |
174 | OldPdb.__init__(self,stdin=stdin,stdout=Term.cout) |
|
174 | OldPdb.__init__(self,stdin=stdin,stdout=IPython.utils.io.Term.cout) | |
175 | else: |
|
175 | else: | |
176 | OldPdb.__init__(self,completekey,stdin,stdout) |
|
176 | OldPdb.__init__(self,completekey,stdin,stdout) | |
177 |
|
177 | |||
@@ -184,7 +184,7 b' class Pdb(OldPdb):' | |||||
184 |
|
184 | |||
185 | if self.is_pydb: |
|
185 | if self.is_pydb: | |
186 |
|
186 | |||
187 |
# i |
|
187 | # interactiveshell.py's ipalias seems to want pdb's checkline | |
188 | # which located in pydb.fn |
|
188 | # which located in pydb.fn | |
189 | import pydb.fns |
|
189 | import pydb.fns | |
190 | self.checkline = lambda filename, lineno: \ |
|
190 | self.checkline = lambda filename, lineno: \ | |
@@ -279,7 +279,7 b' class Pdb(OldPdb):' | |||||
279 | def print_stack_entry(self,frame_lineno,prompt_prefix='\n-> ', |
|
279 | def print_stack_entry(self,frame_lineno,prompt_prefix='\n-> ', | |
280 | context = 3): |
|
280 | context = 3): | |
281 | #frame, lineno = frame_lineno |
|
281 | #frame, lineno = frame_lineno | |
282 | print >>Term.cout, self.format_stack_entry(frame_lineno, '', context) |
|
282 | print >>IPython.utils.io.Term.cout, self.format_stack_entry(frame_lineno, '', context) | |
283 |
|
283 | |||
284 | # vds: >> |
|
284 | # vds: >> | |
285 | frame, lineno = frame_lineno |
|
285 | frame, lineno = frame_lineno | |
@@ -419,7 +419,7 b' class Pdb(OldPdb):' | |||||
419 | src.append(line) |
|
419 | src.append(line) | |
420 | self.lineno = lineno |
|
420 | self.lineno = lineno | |
421 |
|
421 | |||
422 | print >>Term.cout, ''.join(src) |
|
422 | print >>IPython.utils.io.Term.cout, ''.join(src) | |
423 |
|
423 | |||
424 | except KeyboardInterrupt: |
|
424 | except KeyboardInterrupt: | |
425 | pass |
|
425 | pass |
@@ -53,7 +53,7 b' class ExtensionManager(Configurable):' | |||||
53 | is added to ``sys.path`` automatically. |
|
53 | is added to ``sys.path`` automatically. | |
54 | """ |
|
54 | """ | |
55 |
|
55 | |||
56 |
shell = Instance('IPython.core.i |
|
56 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
57 |
|
57 | |||
58 | def __init__(self, shell=None, config=None): |
|
58 | def __init__(self, shell=None, config=None): | |
59 | super(ExtensionManager, self).__init__(shell=shell, config=config) |
|
59 | super(ExtensionManager, self).__init__(shell=shell, config=config) |
@@ -5,7 +5,8 b'' | |||||
5 | import fnmatch |
|
5 | import fnmatch | |
6 | import os |
|
6 | import os | |
7 |
|
7 | |||
8 | from IPython.utils.io import Term, ask_yes_no |
|
8 | import IPython.utils.io | |
|
9 | from IPython.utils.io import ask_yes_no | |||
9 | from IPython.utils.warn import warn |
|
10 | from IPython.utils.warn import warn | |
10 | from IPython.core import ipapi |
|
11 | from IPython.core import ipapi | |
11 |
|
12 | |||
@@ -62,7 +63,7 b" def magic_history(self, parameter_s = ''):" | |||||
62 | try: |
|
63 | try: | |
63 | outfname = opts['f'] |
|
64 | outfname = opts['f'] | |
64 | except KeyError: |
|
65 | except KeyError: | |
65 | outfile = Term.cout # default |
|
66 | outfile = IPython.utils.io.Term.cout # default | |
66 | # We don't want to close stdout at the end! |
|
67 | # We don't want to close stdout at the end! | |
67 | close_at_end = False |
|
68 | close_at_end = False | |
68 | else: |
|
69 | else: | |
@@ -101,7 +102,7 b" def magic_history(self, parameter_s = ''):" | |||||
101 | init, final = map(int, args) |
|
102 | init, final = map(int, args) | |
102 | else: |
|
103 | else: | |
103 | warn('%hist takes 0, 1 or 2 arguments separated by spaces.') |
|
104 | warn('%hist takes 0, 1 or 2 arguments separated by spaces.') | |
104 | print >> Term.cout, self.magic_hist.__doc__ |
|
105 | print >> IPython.utils.io.Term.cout, self.magic_hist.__doc__ | |
105 | return |
|
106 | return | |
106 |
|
107 | |||
107 | width = len(str(final)) |
|
108 | width = len(str(final)) |
@@ -46,7 +46,7 b' import sys' | |||||
46 |
|
46 | |||
47 | from pprint import PrettyPrinter |
|
47 | from pprint import PrettyPrinter | |
48 |
|
48 | |||
49 |
|
|
49 | import IPython.utils.io | |
50 | from IPython.utils.process import shell |
|
50 | from IPython.utils.process import shell | |
51 |
|
51 | |||
52 | from IPython.core.error import TryNext |
|
52 | from IPython.core.error import TryNext | |
@@ -175,13 +175,13 b' def result_display(self,arg):' | |||||
175 | # So that multi-line strings line up with the left column of |
|
175 | # So that multi-line strings line up with the left column of | |
176 | # the screen, instead of having the output prompt mess up |
|
176 | # the screen, instead of having the output prompt mess up | |
177 | # their first line. |
|
177 | # their first line. | |
178 | Term.cout.write('\n') |
|
178 | IPython.utils.io.Term.cout.write('\n') | |
179 | print >>Term.cout, out |
|
179 | print >>IPython.utils.io.Term.cout, out | |
180 | else: |
|
180 | else: | |
181 | # By default, the interactive prompt uses repr() to display results, |
|
181 | # By default, the interactive prompt uses repr() to display results, | |
182 | # so we should honor this. Users who'd rather use a different |
|
182 | # so we should honor this. Users who'd rather use a different | |
183 | # mechanism can easily override this hook. |
|
183 | # mechanism can easily override this hook. | |
184 | print >>Term.cout, repr(arg) |
|
184 | print >>IPython.utils.io.Term.cout, repr(arg) | |
185 | # the default display hook doesn't manipulate the value to put in history |
|
185 | # the default display hook doesn't manipulate the value to put in history | |
186 | return None |
|
186 | return None | |
187 |
|
187 |
This diff has been collapsed as it changes many lines, (647 lines changed) Show them Hide them | |||||
@@ -19,7 +19,6 b' from __future__ import absolute_import' | |||||
19 |
|
19 | |||
20 | import __builtin__ |
|
20 | import __builtin__ | |
21 | import abc |
|
21 | import abc | |
22 | import bdb |
|
|||
23 | import codeop |
|
22 | import codeop | |
24 | import exceptions |
|
23 | import exceptions | |
25 | import new |
|
24 | import new | |
@@ -39,35 +38,28 b' from IPython.core.alias import AliasManager' | |||||
39 | from IPython.core.builtin_trap import BuiltinTrap |
|
38 | from IPython.core.builtin_trap import BuiltinTrap | |
40 | from IPython.config.configurable import Configurable |
|
39 | from IPython.config.configurable import Configurable | |
41 | from IPython.core.display_trap import DisplayTrap |
|
40 | from IPython.core.display_trap import DisplayTrap | |
42 |
from IPython.core.error import |
|
41 | from IPython.core.error import UsageError | |
43 | from IPython.core.extensions import ExtensionManager |
|
42 | from IPython.core.extensions import ExtensionManager | |
44 | from IPython.core.fakemodule import FakeModule, init_fakemod_dict |
|
43 | from IPython.core.fakemodule import FakeModule, init_fakemod_dict | |
|
44 | from IPython.core.inputlist import InputList | |||
45 | from IPython.core.logger import Logger |
|
45 | from IPython.core.logger import Logger | |
46 | from IPython.core.magic import Magic |
|
46 | from IPython.core.magic import Magic | |
47 | from IPython.core.plugin import PluginManager |
|
47 | from IPython.core.plugin import PluginManager | |
48 | from IPython.core.prefilter import PrefilterManager |
|
48 | from IPython.core.prefilter import PrefilterManager | |
49 | from IPython.core.prompts import CachedOutput |
|
49 | from IPython.core.prompts import CachedOutput | |
50 | from IPython.core.usage import interactive_usage, default_banner |
|
|||
51 | import IPython.core.hooks |
|
50 | import IPython.core.hooks | |
52 | from IPython.external.Itpl import ItplNS |
|
51 | from IPython.external.Itpl import ItplNS | |
53 | from IPython.lib.inputhook import enable_gui |
|
|||
54 | from IPython.lib.backgroundjobs import BackgroundJobManager |
|
|||
55 | from IPython.lib.pylabtools import pylab_activate |
|
|||
56 | from IPython.utils import PyColorize |
|
52 | from IPython.utils import PyColorize | |
57 | from IPython.utils import pickleshare |
|
53 | from IPython.utils import pickleshare | |
58 | from IPython.utils.doctestreload import doctest_reload |
|
54 | from IPython.utils.doctestreload import doctest_reload | |
59 | from IPython.utils.ipstruct import Struct |
|
55 | from IPython.utils.ipstruct import Struct | |
60 | from IPython.utils.io import Term, ask_yes_no |
|
56 | import IPython.utils.io | |
|
57 | from IPython.utils.io import ask_yes_no | |||
61 | from IPython.utils.path import get_home_dir, get_ipython_dir, HomeDirError |
|
58 | from IPython.utils.path import get_home_dir, get_ipython_dir, HomeDirError | |
62 |
from IPython.utils.process import |
|
59 | from IPython.utils.process import getoutput, getoutputerror | |
63 | abbrev_cwd, |
|
|||
64 | getoutput, |
|
|||
65 | getoutputerror |
|
|||
66 | ) |
|
|||
67 | # import IPython.utils.rlineimpl as readline |
|
|||
68 | from IPython.utils.strdispatch import StrDispatch |
|
60 | from IPython.utils.strdispatch import StrDispatch | |
69 | from IPython.utils.syspathcontext import prepended_to_syspath |
|
61 | from IPython.utils.syspathcontext import prepended_to_syspath | |
70 | from IPython.utils.terminal import toggle_set_term_title, set_term_title |
|
62 | from IPython.utils.text import num_ini_spaces | |
71 | from IPython.utils.warn import warn, error, fatal |
|
63 | from IPython.utils.warn import warn, error, fatal | |
72 | from IPython.utils.traitlets import ( |
|
64 | from IPython.utils.traitlets import ( | |
73 | Int, Str, CBool, CaselessStrEnum, Enum, List, Unicode, Instance |
|
65 | Int, Str, CBool, CaselessStrEnum, Enum, List, Unicode, Instance | |
@@ -80,10 +72,6 b' from IPython.utils.traitlets import (' | |||||
80 | # Globals |
|
72 | # Globals | |
81 | #----------------------------------------------------------------------------- |
|
73 | #----------------------------------------------------------------------------- | |
82 |
|
74 | |||
83 | # store the builtin raw_input globally, and use this always, in case user code |
|
|||
84 | # overwrites it (like wx.py.PyShell does) |
|
|||
85 | raw_input_original = raw_input |
|
|||
86 |
|
||||
87 | # compiled regexps for autoindent management |
|
75 | # compiled regexps for autoindent management | |
88 | dedent_re = re.compile(r'^\s+raise|^\s+return|^\s+pass') |
|
76 | dedent_re = re.compile(r'^\s+raise|^\s+return|^\s+pass') | |
89 |
|
77 | |||
@@ -91,18 +79,9 b" dedent_re = re.compile(r'^\\s+raise|^\\s+return|^\\s+pass')" | |||||
91 | # Utilities |
|
79 | # Utilities | |
92 | #----------------------------------------------------------------------------- |
|
80 | #----------------------------------------------------------------------------- | |
93 |
|
81 | |||
94 | ini_spaces_re = re.compile(r'^(\s+)') |
|
82 | # store the builtin raw_input globally, and use this always, in case user code | |
95 |
|
83 | # overwrites it (like wx.py.PyShell does) | ||
96 |
|
84 | raw_input_original = raw_input | ||
97 | def num_ini_spaces(strng): |
|
|||
98 | """Return the number of initial spaces in a string""" |
|
|||
99 |
|
||||
100 | ini_spaces = ini_spaces_re.match(strng) |
|
|||
101 | if ini_spaces: |
|
|||
102 | return ini_spaces.end() |
|
|||
103 | else: |
|
|||
104 | return 0 |
|
|||
105 |
|
||||
106 |
|
85 | |||
107 | def softspace(file, newvalue): |
|
86 | def softspace(file, newvalue): | |
108 | """Copied from code.py, to remove the dependency""" |
|
87 | """Copied from code.py, to remove the dependency""" | |
@@ -126,22 +105,6 b' class SpaceInInput(exceptions.Exception): pass' | |||||
126 |
|
105 | |||
127 | class Bunch: pass |
|
106 | class Bunch: pass | |
128 |
|
107 | |||
129 | class InputList(list): |
|
|||
130 | """Class to store user input. |
|
|||
131 |
|
||||
132 | It's basically a list, but slices return a string instead of a list, thus |
|
|||
133 | allowing things like (assuming 'In' is an instance): |
|
|||
134 |
|
||||
135 | exec In[4:7] |
|
|||
136 |
|
||||
137 | or |
|
|||
138 |
|
||||
139 | exec In[5:9] + In[14] + In[21:25]""" |
|
|||
140 |
|
||||
141 | def __getslice__(self,i,j): |
|
|||
142 | return ''.join(list.__getslice__(self,i,j)) |
|
|||
143 |
|
||||
144 |
|
||||
145 | class SyntaxTB(ultratb.ListTB): |
|
108 | class SyntaxTB(ultratb.ListTB): | |
146 | """Extension which holds some state: the last exception value""" |
|
109 | """Extension which holds some state: the last exception value""" | |
147 |
|
110 | |||
@@ -160,17 +123,6 b' class SyntaxTB(ultratb.ListTB):' | |||||
160 | return e |
|
123 | return e | |
161 |
|
124 | |||
162 |
|
125 | |||
163 | def get_default_editor(): |
|
|||
164 | try: |
|
|||
165 | ed = os.environ['EDITOR'] |
|
|||
166 | except KeyError: |
|
|||
167 | if os.name == 'posix': |
|
|||
168 | ed = 'vi' # the only one guaranteed to be there! |
|
|||
169 | else: |
|
|||
170 | ed = 'notepad' # same in Windows! |
|
|||
171 | return ed |
|
|||
172 |
|
||||
173 |
|
||||
174 | def get_default_colors(): |
|
126 | def get_default_colors(): | |
175 | if sys.platform=='darwin': |
|
127 | if sys.platform=='darwin': | |
176 | return "LightBG" |
|
128 | return "LightBG" | |
@@ -201,28 +153,16 b' class InteractiveShell(Configurable, Magic):' | |||||
201 | """An enhanced, interactive shell for Python.""" |
|
153 | """An enhanced, interactive shell for Python.""" | |
202 |
|
154 | |||
203 | autocall = Enum((0,1,2), default_value=1, config=True) |
|
155 | autocall = Enum((0,1,2), default_value=1, config=True) | |
204 | autoedit_syntax = CBool(False, config=True) |
|
156 | # TODO: remove all autoindent logic and put into frontends. | |
|
157 | # We can't do this yet because even runlines uses the autoindent. | |||
205 | autoindent = CBool(True, config=True) |
|
158 | autoindent = CBool(True, config=True) | |
206 | automagic = CBool(True, config=True) |
|
159 | automagic = CBool(True, config=True) | |
207 | banner = Str('') |
|
|||
208 | banner1 = Str(default_banner, config=True) |
|
|||
209 | banner2 = Str('', config=True) |
|
|||
210 | cache_size = Int(1000, config=True) |
|
160 | cache_size = Int(1000, config=True) | |
211 | color_info = CBool(True, config=True) |
|
161 | color_info = CBool(True, config=True) | |
212 | colors = CaselessStrEnum(('NoColor','LightBG','Linux'), |
|
162 | colors = CaselessStrEnum(('NoColor','LightBG','Linux'), | |
213 | default_value=get_default_colors(), config=True) |
|
163 | default_value=get_default_colors(), config=True) | |
214 | confirm_exit = CBool(True, config=True) |
|
|||
215 | debug = CBool(False, config=True) |
|
164 | debug = CBool(False, config=True) | |
216 | deep_reload = CBool(False, config=True) |
|
165 | deep_reload = CBool(False, config=True) | |
217 | # This display_banner only controls whether or not self.show_banner() |
|
|||
218 | # is called when mainloop/interact are called. The default is False |
|
|||
219 | # because for the terminal based application, the banner behavior |
|
|||
220 | # is controlled by Global.display_banner, which IPythonApp looks at |
|
|||
221 | # to determine if *it* should call show_banner() by hand or not. |
|
|||
222 | display_banner = CBool(False) # This isn't configurable! |
|
|||
223 | embedded = CBool(False) |
|
|||
224 | embedded_active = CBool(False) |
|
|||
225 | editor = Str(get_default_editor(), config=True) |
|
|||
226 | filename = Str("<ipython console>") |
|
166 | filename = Str("<ipython console>") | |
227 | ipython_dir= Unicode('', config=True) # Set to get_ipython_dir() in __init__ |
|
167 | ipython_dir= Unicode('', config=True) # Set to get_ipython_dir() in __init__ | |
228 | logstart = CBool(False, config=True) |
|
168 | logstart = CBool(False, config=True) | |
@@ -230,7 +170,6 b' class InteractiveShell(Configurable, Magic):' | |||||
230 | logappend = Str('', config=True) |
|
170 | logappend = Str('', config=True) | |
231 | object_info_string_level = Enum((0,1,2), default_value=0, |
|
171 | object_info_string_level = Enum((0,1,2), default_value=0, | |
232 | config=True) |
|
172 | config=True) | |
233 | pager = Str('less', config=True) |
|
|||
234 | pdb = CBool(False, config=True) |
|
173 | pdb = CBool(False, config=True) | |
235 | pprint = CBool(True, config=True) |
|
174 | pprint = CBool(True, config=True) | |
236 | profile = Str('', config=True) |
|
175 | profile = Str('', config=True) | |
@@ -240,6 +179,8 b' class InteractiveShell(Configurable, Magic):' | |||||
240 | prompts_pad_left = CBool(True, config=True) |
|
179 | prompts_pad_left = CBool(True, config=True) | |
241 | quiet = CBool(False, config=True) |
|
180 | quiet = CBool(False, config=True) | |
242 |
|
181 | |||
|
182 | # The readline stuff will eventually be moved to the terminal subclass | |||
|
183 | # but for now, we can't do that as readline is welded in everywhere. | |||
243 | readline_use = CBool(True, config=True) |
|
184 | readline_use = CBool(True, config=True) | |
244 | readline_merge_completions = CBool(True, config=True) |
|
185 | readline_merge_completions = CBool(True, config=True) | |
245 | readline_omit__names = Enum((0,1,2), default_value=0, config=True) |
|
186 | readline_omit__names = Enum((0,1,2), default_value=0, config=True) | |
@@ -262,26 +203,17 b' class InteractiveShell(Configurable, Magic):' | |||||
262 | '"\C-u": unix-line-discard', |
|
203 | '"\C-u": unix-line-discard', | |
263 | ], allow_none=False, config=True) |
|
204 | ], allow_none=False, config=True) | |
264 |
|
205 | |||
265 | screen_length = Int(0, config=True) |
|
206 | # TODO: this part of prompt management should be moved to the frontends. | |
266 |
|
||||
267 | # Use custom TraitTypes that convert '0'->'' and '\\n'->'\n' |
|
207 | # Use custom TraitTypes that convert '0'->'' and '\\n'->'\n' | |
268 | separate_in = SeparateStr('\n', config=True) |
|
208 | separate_in = SeparateStr('\n', config=True) | |
269 | separate_out = SeparateStr('', config=True) |
|
209 | separate_out = SeparateStr('', config=True) | |
270 | separate_out2 = SeparateStr('', config=True) |
|
210 | separate_out2 = SeparateStr('', config=True) | |
271 |
|
||||
272 | system_header = Str('IPython system call: ', config=True) |
|
211 | system_header = Str('IPython system call: ', config=True) | |
273 | system_verbose = CBool(False, config=True) |
|
212 | system_verbose = CBool(False, config=True) | |
274 | term_title = CBool(False, config=True) |
|
|||
275 | wildcards_case_sensitive = CBool(True, config=True) |
|
213 | wildcards_case_sensitive = CBool(True, config=True) | |
276 | xmode = CaselessStrEnum(('Context','Plain', 'Verbose'), |
|
214 | xmode = CaselessStrEnum(('Context','Plain', 'Verbose'), | |
277 | default_value='Context', config=True) |
|
215 | default_value='Context', config=True) | |
278 |
|
216 | |||
279 | autoexec = List(allow_none=False) |
|
|||
280 |
|
||||
281 | # class attribute to indicate whether the class supports threads or not. |
|
|||
282 | # Subclasses with thread support should override this as needed. |
|
|||
283 | isthreaded = False |
|
|||
284 |
|
||||
285 | # Subcomponents of InteractiveShell |
|
217 | # Subcomponents of InteractiveShell | |
286 | alias_manager = Instance('IPython.core.alias.AliasManager') |
|
218 | alias_manager = Instance('IPython.core.alias.AliasManager') | |
287 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') |
|
219 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') | |
@@ -290,9 +222,8 b' class InteractiveShell(Configurable, Magic):' | |||||
290 | extension_manager = Instance('IPython.core.extensions.ExtensionManager') |
|
222 | extension_manager = Instance('IPython.core.extensions.ExtensionManager') | |
291 | plugin_manager = Instance('IPython.core.plugin.PluginManager') |
|
223 | plugin_manager = Instance('IPython.core.plugin.PluginManager') | |
292 |
|
224 | |||
293 |
def __init__(self, config=None, ipython_dir=None, |
|
225 | def __init__(self, config=None, ipython_dir=None, | |
294 | user_ns=None, user_global_ns=None, |
|
226 | user_ns=None, user_global_ns=None, | |
295 | banner1=None, banner2=None, display_banner=None, |
|
|||
296 | custom_exceptions=((),None)): |
|
227 | custom_exceptions=((),None)): | |
297 |
|
228 | |||
298 | # This is where traits with a config_key argument are updated |
|
229 | # This is where traits with a config_key argument are updated | |
@@ -302,9 +233,6 b' class InteractiveShell(Configurable, Magic):' | |||||
302 | # These are relatively independent and stateless |
|
233 | # These are relatively independent and stateless | |
303 | self.init_ipython_dir(ipython_dir) |
|
234 | self.init_ipython_dir(ipython_dir) | |
304 | self.init_instance_attrs() |
|
235 | self.init_instance_attrs() | |
305 | self.init_term_title() |
|
|||
306 | self.init_usage(usage) |
|
|||
307 | self.init_banner(banner1, banner2, display_banner) |
|
|||
308 |
|
236 | |||
309 | # Create namespaces (user_ns, user_global_ns, etc.) |
|
237 | # Create namespaces (user_ns, user_global_ns, etc.) | |
310 | self.init_create_namespaces(user_ns, user_global_ns) |
|
238 | self.init_create_namespaces(user_ns, user_global_ns) | |
@@ -323,12 +251,16 b' class InteractiveShell(Configurable, Magic):' | |||||
323 | self.init_syntax_highlighting() |
|
251 | self.init_syntax_highlighting() | |
324 | self.init_hooks() |
|
252 | self.init_hooks() | |
325 | self.init_pushd_popd_magic() |
|
253 | self.init_pushd_popd_magic() | |
|
254 | # TODO: init_io() needs to happen before init_traceback handlers | |||
|
255 | # because the traceback handlers hardcode the stdout/stderr streams. | |||
|
256 | # This logic in in debugger.Pdb and should eventually be changed. | |||
|
257 | self.init_io() | |||
326 | self.init_traceback_handlers(custom_exceptions) |
|
258 | self.init_traceback_handlers(custom_exceptions) | |
327 | self.init_user_ns() |
|
259 | self.init_user_ns() | |
328 | self.init_logger() |
|
260 | self.init_logger() | |
329 | self.init_alias() |
|
261 | self.init_alias() | |
330 | self.init_builtins() |
|
262 | self.init_builtins() | |
331 |
|
263 | |||
332 | # pre_config_initialization |
|
264 | # pre_config_initialization | |
333 | self.init_shadow_hist() |
|
265 | self.init_shadow_hist() | |
334 |
|
266 | |||
@@ -366,27 +298,10 b' class InteractiveShell(Configurable, Magic):' | |||||
366 | # Trait changed handlers |
|
298 | # Trait changed handlers | |
367 | #------------------------------------------------------------------------- |
|
299 | #------------------------------------------------------------------------- | |
368 |
|
300 | |||
369 | def _banner1_changed(self): |
|
|||
370 | self.compute_banner() |
|
|||
371 |
|
||||
372 | def _banner2_changed(self): |
|
|||
373 | self.compute_banner() |
|
|||
374 |
|
||||
375 | def _ipython_dir_changed(self, name, new): |
|
301 | def _ipython_dir_changed(self, name, new): | |
376 | if not os.path.isdir(new): |
|
302 | if not os.path.isdir(new): | |
377 | os.makedirs(new, mode = 0777) |
|
303 | os.makedirs(new, mode = 0777) | |
378 |
|
304 | |||
379 | @property |
|
|||
380 | def usable_screen_length(self): |
|
|||
381 | if self.screen_length == 0: |
|
|||
382 | return 0 |
|
|||
383 | else: |
|
|||
384 | num_lines_bot = self.separate_in.count('\n')+1 |
|
|||
385 | return self.screen_length - num_lines_bot |
|
|||
386 |
|
||||
387 | def _term_title_changed(self, name, new_value): |
|
|||
388 | self.init_term_title() |
|
|||
389 |
|
||||
390 | def set_autoindent(self,value=None): |
|
305 | def set_autoindent(self,value=None): | |
391 | """Set the autoindent flag, checking for readline support. |
|
306 | """Set the autoindent flag, checking for readline support. | |
392 |
|
307 | |||
@@ -421,7 +336,6 b' class InteractiveShell(Configurable, Magic):' | |||||
421 | self.config.Global.ipython_dir = self.ipython_dir |
|
336 | self.config.Global.ipython_dir = self.ipython_dir | |
422 |
|
337 | |||
423 | def init_instance_attrs(self): |
|
338 | def init_instance_attrs(self): | |
424 | self.jobs = BackgroundJobManager() |
|
|||
425 | self.more = False |
|
339 | self.more = False | |
426 |
|
340 | |||
427 | # command compiler |
|
341 | # command compiler | |
@@ -443,9 +357,6 b' class InteractiveShell(Configurable, Magic):' | |||||
443 | # item which gets cleared once run. |
|
357 | # item which gets cleared once run. | |
444 | self.code_to_run = None |
|
358 | self.code_to_run = None | |
445 |
|
359 | |||
446 | # Flag to mark unconditional exit |
|
|||
447 | self.exit_now = False |
|
|||
448 |
|
||||
449 | # Temporary files used for various purposes. Deleted at exit. |
|
360 | # Temporary files used for various purposes. Deleted at exit. | |
450 | self.tempfiles = [] |
|
361 | self.tempfiles = [] | |
451 |
|
362 | |||
@@ -459,20 +370,6 b' class InteractiveShell(Configurable, Magic):' | |||||
459 | # Indentation management |
|
370 | # Indentation management | |
460 | self.indent_current_nsp = 0 |
|
371 | self.indent_current_nsp = 0 | |
461 |
|
372 | |||
462 | def init_term_title(self): |
|
|||
463 | # Enable or disable the terminal title. |
|
|||
464 | if self.term_title: |
|
|||
465 | toggle_set_term_title(True) |
|
|||
466 | set_term_title('IPython: ' + abbrev_cwd()) |
|
|||
467 | else: |
|
|||
468 | toggle_set_term_title(False) |
|
|||
469 |
|
||||
470 | def init_usage(self, usage=None): |
|
|||
471 | if usage is None: |
|
|||
472 | self.usage = interactive_usage |
|
|||
473 | else: |
|
|||
474 | self.usage = usage |
|
|||
475 |
|
||||
476 | def init_encoding(self): |
|
373 | def init_encoding(self): | |
477 | # Get system encoding at startup time. Certain terminals (like Emacs |
|
374 | # Get system encoding at startup time. Certain terminals (like Emacs | |
478 | # under Win32 have it set to None, and we need to have a known valid |
|
375 | # under Win32 have it set to None, and we need to have a known valid | |
@@ -519,6 +416,17 b' class InteractiveShell(Configurable, Magic):' | |||||
519 | 'NoColor', |
|
416 | 'NoColor', | |
520 | self.object_info_string_level) |
|
417 | self.object_info_string_level) | |
521 |
|
418 | |||
|
419 | def init_io(self): | |||
|
420 | import IPython.utils.io | |||
|
421 | if sys.platform == 'win32' and readline.have_readline and \ | |||
|
422 | self.readline_use: | |||
|
423 | Term = IPython.utils.io.IOTerm( | |||
|
424 | cout=readline._outputfile,cerr=readline._outputfile | |||
|
425 | ) | |||
|
426 | else: | |||
|
427 | Term = IPython.utils.io.IOTerm() | |||
|
428 | IPython.utils.io.Term = Term | |||
|
429 | ||||
522 | def init_prompts(self): |
|
430 | def init_prompts(self): | |
523 | # Initialize cache, set in/out prompts and printing system |
|
431 | # Initialize cache, set in/out prompts and printing system | |
524 | self.outputcache = CachedOutput(self, |
|
432 | self.outputcache = CachedOutput(self, | |
@@ -550,31 +458,6 b' class InteractiveShell(Configurable, Magic):' | |||||
550 | warn("doctest module does not exist.") |
|
458 | warn("doctest module does not exist.") | |
551 |
|
459 | |||
552 | #------------------------------------------------------------------------- |
|
460 | #------------------------------------------------------------------------- | |
553 | # Things related to the banner |
|
|||
554 | #------------------------------------------------------------------------- |
|
|||
555 |
|
||||
556 | def init_banner(self, banner1, banner2, display_banner): |
|
|||
557 | if banner1 is not None: |
|
|||
558 | self.banner1 = banner1 |
|
|||
559 | if banner2 is not None: |
|
|||
560 | self.banner2 = banner2 |
|
|||
561 | if display_banner is not None: |
|
|||
562 | self.display_banner = display_banner |
|
|||
563 | self.compute_banner() |
|
|||
564 |
|
||||
565 | def show_banner(self, banner=None): |
|
|||
566 | if banner is None: |
|
|||
567 | banner = self.banner |
|
|||
568 | self.write(banner) |
|
|||
569 |
|
||||
570 | def compute_banner(self): |
|
|||
571 | self.banner = self.banner1 + '\n' |
|
|||
572 | if self.profile: |
|
|||
573 | self.banner += '\nIPython profile: %s\n' % self.profile |
|
|||
574 | if self.banner2: |
|
|||
575 | self.banner += '\n' + self.banner2 + '\n' |
|
|||
576 |
|
||||
577 | #------------------------------------------------------------------------- |
|
|||
578 | # Things related to injections into the sys module |
|
461 | # Things related to injections into the sys module | |
579 | #------------------------------------------------------------------------- |
|
462 | #------------------------------------------------------------------------- | |
580 |
|
463 | |||
@@ -762,11 +645,6 b' class InteractiveShell(Configurable, Magic):' | |||||
762 |
|
645 | |||
763 | # notify the actual exception handlers |
|
646 | # notify the actual exception handlers | |
764 | self.InteractiveTB.call_pdb = val |
|
647 | self.InteractiveTB.call_pdb = val | |
765 | if self.isthreaded: |
|
|||
766 | try: |
|
|||
767 | self.sys_excepthook.call_pdb = val |
|
|||
768 | except: |
|
|||
769 | warn('Failed to activate pdb for threaded exception handler') |
|
|||
770 |
|
648 | |||
771 | call_pdb = property(_get_call_pdb,_set_call_pdb,None, |
|
649 | call_pdb = property(_get_call_pdb,_set_call_pdb,None, | |
772 | 'Control auto-activation of pdb at exceptions') |
|
650 | 'Control auto-activation of pdb at exceptions') | |
@@ -1404,64 +1282,6 b' class InteractiveShell(Configurable, Magic):' | |||||
1404 | value = msg, (filename, lineno, offset, line) |
|
1282 | value = msg, (filename, lineno, offset, line) | |
1405 | self.SyntaxTB(etype,value,[]) |
|
1283 | self.SyntaxTB(etype,value,[]) | |
1406 |
|
1284 | |||
1407 | def edit_syntax_error(self): |
|
|||
1408 | """The bottom half of the syntax error handler called in the main loop. |
|
|||
1409 |
|
||||
1410 | Loop until syntax error is fixed or user cancels. |
|
|||
1411 | """ |
|
|||
1412 |
|
||||
1413 | while self.SyntaxTB.last_syntax_error: |
|
|||
1414 | # copy and clear last_syntax_error |
|
|||
1415 | err = self.SyntaxTB.clear_err_state() |
|
|||
1416 | if not self._should_recompile(err): |
|
|||
1417 | return |
|
|||
1418 | try: |
|
|||
1419 | # may set last_syntax_error again if a SyntaxError is raised |
|
|||
1420 | self.safe_execfile(err.filename,self.user_ns) |
|
|||
1421 | except: |
|
|||
1422 | self.showtraceback() |
|
|||
1423 | else: |
|
|||
1424 | try: |
|
|||
1425 | f = file(err.filename) |
|
|||
1426 | try: |
|
|||
1427 | # This should be inside a display_trap block and I |
|
|||
1428 | # think it is. |
|
|||
1429 | sys.displayhook(f.read()) |
|
|||
1430 | finally: |
|
|||
1431 | f.close() |
|
|||
1432 | except: |
|
|||
1433 | self.showtraceback() |
|
|||
1434 |
|
||||
1435 | def _should_recompile(self,e): |
|
|||
1436 | """Utility routine for edit_syntax_error""" |
|
|||
1437 |
|
||||
1438 | if e.filename in ('<ipython console>','<input>','<string>', |
|
|||
1439 | '<console>','<BackgroundJob compilation>', |
|
|||
1440 | None): |
|
|||
1441 |
|
||||
1442 | return False |
|
|||
1443 | try: |
|
|||
1444 | if (self.autoedit_syntax and |
|
|||
1445 | not self.ask_yes_no('Return to editor to correct syntax error? ' |
|
|||
1446 | '[Y/n] ','y')): |
|
|||
1447 | return False |
|
|||
1448 | except EOFError: |
|
|||
1449 | return False |
|
|||
1450 |
|
||||
1451 | def int0(x): |
|
|||
1452 | try: |
|
|||
1453 | return int(x) |
|
|||
1454 | except TypeError: |
|
|||
1455 | return 0 |
|
|||
1456 | # always pass integer line and offset values to editor hook |
|
|||
1457 | try: |
|
|||
1458 | self.hooks.fix_error_editor(e.filename, |
|
|||
1459 | int0(e.lineno),int0(e.offset),e.msg) |
|
|||
1460 | except TryNext: |
|
|||
1461 | warn('Could not open editor') |
|
|||
1462 | return False |
|
|||
1463 | return True |
|
|||
1464 |
|
||||
1465 | #------------------------------------------------------------------------- |
|
1285 | #------------------------------------------------------------------------- | |
1466 | # Things related to tab completion |
|
1286 | # Things related to tab completion | |
1467 | #------------------------------------------------------------------------- |
|
1287 | #------------------------------------------------------------------------- | |
@@ -1641,13 +1461,12 b' class InteractiveShell(Configurable, Magic):' | |||||
1641 |
|
1461 | |||
1642 | self.rl_next_input = s |
|
1462 | self.rl_next_input = s | |
1643 |
|
1463 | |||
|
1464 | # Maybe move this to the terminal subclass? | |||
1644 | def pre_readline(self): |
|
1465 | def pre_readline(self): | |
1645 | """readline hook to be used at the start of each line. |
|
1466 | """readline hook to be used at the start of each line. | |
1646 |
|
1467 | |||
1647 | Currently it handles auto-indent only.""" |
|
1468 | Currently it handles auto-indent only.""" | |
1648 |
|
1469 | |||
1649 | #debugx('self.indent_current_nsp','pre_readline:') |
|
|||
1650 |
|
||||
1651 | if self.rl_do_indent: |
|
1470 | if self.rl_do_indent: | |
1652 | self.readline.insert_text(self._indent_current_str()) |
|
1471 | self.readline.insert_text(self._indent_current_str()) | |
1653 | if self.rl_next_input is not None: |
|
1472 | if self.rl_next_input is not None: | |
@@ -1773,6 +1592,17 b' class InteractiveShell(Configurable, Magic):' | |||||
1773 | self.plugin_manager = PluginManager(config=self.config) |
|
1592 | self.plugin_manager = PluginManager(config=self.config) | |
1774 |
|
1593 | |||
1775 | #------------------------------------------------------------------------- |
|
1594 | #------------------------------------------------------------------------- | |
|
1595 | # Things related to the prefilter | |||
|
1596 | #------------------------------------------------------------------------- | |||
|
1597 | ||||
|
1598 | def init_prefilter(self): | |||
|
1599 | self.prefilter_manager = PrefilterManager(shell=self, config=self.config) | |||
|
1600 | # Ultimately this will be refactored in the new interpreter code, but | |||
|
1601 | # for now, we should expose the main prefilter method (there's legacy | |||
|
1602 | # code out there that may rely on this). | |||
|
1603 | self.prefilter = self.prefilter_manager.prefilter_lines | |||
|
1604 | ||||
|
1605 | #------------------------------------------------------------------------- | |||
1776 | # Things related to the running of code |
|
1606 | # Things related to the running of code | |
1777 | #------------------------------------------------------------------------- |
|
1607 | #------------------------------------------------------------------------- | |
1778 |
|
1608 | |||
@@ -1789,177 +1619,6 b' class InteractiveShell(Configurable, Magic):' | |||||
1789 | with nested(self.builtin_trap,): |
|
1619 | with nested(self.builtin_trap,): | |
1790 | return eval(expr, self.user_global_ns, self.user_ns) |
|
1620 | return eval(expr, self.user_global_ns, self.user_ns) | |
1791 |
|
1621 | |||
1792 | def mainloop(self, display_banner=None): |
|
|||
1793 | """Start the mainloop. |
|
|||
1794 |
|
||||
1795 | If an optional banner argument is given, it will override the |
|
|||
1796 | internally created default banner. |
|
|||
1797 | """ |
|
|||
1798 |
|
||||
1799 | with nested(self.builtin_trap, self.display_trap): |
|
|||
1800 |
|
||||
1801 | # if you run stuff with -c <cmd>, raw hist is not updated |
|
|||
1802 | # ensure that it's in sync |
|
|||
1803 | if len(self.input_hist) != len (self.input_hist_raw): |
|
|||
1804 | self.input_hist_raw = InputList(self.input_hist) |
|
|||
1805 |
|
||||
1806 | while 1: |
|
|||
1807 | try: |
|
|||
1808 | self.interact(display_banner=display_banner) |
|
|||
1809 | #self.interact_with_readline() |
|
|||
1810 | # XXX for testing of a readline-decoupled repl loop, call |
|
|||
1811 | # interact_with_readline above |
|
|||
1812 | break |
|
|||
1813 | except KeyboardInterrupt: |
|
|||
1814 | # this should not be necessary, but KeyboardInterrupt |
|
|||
1815 | # handling seems rather unpredictable... |
|
|||
1816 | self.write("\nKeyboardInterrupt in interact()\n") |
|
|||
1817 |
|
||||
1818 | def interact_prompt(self): |
|
|||
1819 | """ Print the prompt (in read-eval-print loop) |
|
|||
1820 |
|
||||
1821 | Provided for those who want to implement their own read-eval-print loop (e.g. GUIs), not |
|
|||
1822 | used in standard IPython flow. |
|
|||
1823 | """ |
|
|||
1824 | if self.more: |
|
|||
1825 | try: |
|
|||
1826 | prompt = self.hooks.generate_prompt(True) |
|
|||
1827 | except: |
|
|||
1828 | self.showtraceback() |
|
|||
1829 | if self.autoindent: |
|
|||
1830 | self.rl_do_indent = True |
|
|||
1831 |
|
||||
1832 | else: |
|
|||
1833 | try: |
|
|||
1834 | prompt = self.hooks.generate_prompt(False) |
|
|||
1835 | except: |
|
|||
1836 | self.showtraceback() |
|
|||
1837 | self.write(prompt) |
|
|||
1838 |
|
||||
1839 | def interact_handle_input(self,line): |
|
|||
1840 | """ Handle the input line (in read-eval-print loop) |
|
|||
1841 |
|
||||
1842 | Provided for those who want to implement their own read-eval-print loop (e.g. GUIs), not |
|
|||
1843 | used in standard IPython flow. |
|
|||
1844 | """ |
|
|||
1845 | if line.lstrip() == line: |
|
|||
1846 | self.shadowhist.add(line.strip()) |
|
|||
1847 | lineout = self.prefilter_manager.prefilter_lines(line,self.more) |
|
|||
1848 |
|
||||
1849 | if line.strip(): |
|
|||
1850 | if self.more: |
|
|||
1851 | self.input_hist_raw[-1] += '%s\n' % line |
|
|||
1852 | else: |
|
|||
1853 | self.input_hist_raw.append('%s\n' % line) |
|
|||
1854 |
|
||||
1855 |
|
||||
1856 | self.more = self.push_line(lineout) |
|
|||
1857 | if (self.SyntaxTB.last_syntax_error and |
|
|||
1858 | self.autoedit_syntax): |
|
|||
1859 | self.edit_syntax_error() |
|
|||
1860 |
|
||||
1861 | def interact_with_readline(self): |
|
|||
1862 | """ Demo of using interact_handle_input, interact_prompt |
|
|||
1863 |
|
||||
1864 | This is the main read-eval-print loop. If you need to implement your own (e.g. for GUI), |
|
|||
1865 | it should work like this. |
|
|||
1866 | """ |
|
|||
1867 | self.readline_startup_hook(self.pre_readline) |
|
|||
1868 | while not self.exit_now: |
|
|||
1869 | self.interact_prompt() |
|
|||
1870 | if self.more: |
|
|||
1871 | self.rl_do_indent = True |
|
|||
1872 | else: |
|
|||
1873 | self.rl_do_indent = False |
|
|||
1874 | line = raw_input_original().decode(self.stdin_encoding) |
|
|||
1875 | self.interact_handle_input(line) |
|
|||
1876 |
|
||||
1877 | def interact(self, display_banner=None): |
|
|||
1878 | """Closely emulate the interactive Python console.""" |
|
|||
1879 |
|
||||
1880 | # batch run -> do not interact |
|
|||
1881 | if self.exit_now: |
|
|||
1882 | return |
|
|||
1883 |
|
||||
1884 | if display_banner is None: |
|
|||
1885 | display_banner = self.display_banner |
|
|||
1886 | if display_banner: |
|
|||
1887 | self.show_banner() |
|
|||
1888 |
|
||||
1889 | more = 0 |
|
|||
1890 |
|
||||
1891 | # Mark activity in the builtins |
|
|||
1892 | __builtin__.__dict__['__IPYTHON__active'] += 1 |
|
|||
1893 |
|
||||
1894 | if self.has_readline: |
|
|||
1895 | self.readline_startup_hook(self.pre_readline) |
|
|||
1896 | # exit_now is set by a call to %Exit or %Quit, through the |
|
|||
1897 | # ask_exit callback. |
|
|||
1898 |
|
||||
1899 | while not self.exit_now: |
|
|||
1900 | self.hooks.pre_prompt_hook() |
|
|||
1901 | if more: |
|
|||
1902 | try: |
|
|||
1903 | prompt = self.hooks.generate_prompt(True) |
|
|||
1904 | except: |
|
|||
1905 | self.showtraceback() |
|
|||
1906 | if self.autoindent: |
|
|||
1907 | self.rl_do_indent = True |
|
|||
1908 |
|
||||
1909 | else: |
|
|||
1910 | try: |
|
|||
1911 | prompt = self.hooks.generate_prompt(False) |
|
|||
1912 | except: |
|
|||
1913 | self.showtraceback() |
|
|||
1914 | try: |
|
|||
1915 | line = self.raw_input(prompt, more) |
|
|||
1916 | if self.exit_now: |
|
|||
1917 | # quick exit on sys.std[in|out] close |
|
|||
1918 | break |
|
|||
1919 | if self.autoindent: |
|
|||
1920 | self.rl_do_indent = False |
|
|||
1921 |
|
||||
1922 | except KeyboardInterrupt: |
|
|||
1923 | #double-guard against keyboardinterrupts during kbdint handling |
|
|||
1924 | try: |
|
|||
1925 | self.write('\nKeyboardInterrupt\n') |
|
|||
1926 | self.resetbuffer() |
|
|||
1927 | # keep cache in sync with the prompt counter: |
|
|||
1928 | self.outputcache.prompt_count -= 1 |
|
|||
1929 |
|
||||
1930 | if self.autoindent: |
|
|||
1931 | self.indent_current_nsp = 0 |
|
|||
1932 | more = 0 |
|
|||
1933 | except KeyboardInterrupt: |
|
|||
1934 | pass |
|
|||
1935 | except EOFError: |
|
|||
1936 | if self.autoindent: |
|
|||
1937 | self.rl_do_indent = False |
|
|||
1938 | if self.has_readline: |
|
|||
1939 | self.readline_startup_hook(None) |
|
|||
1940 | self.write('\n') |
|
|||
1941 | self.exit() |
|
|||
1942 | except bdb.BdbQuit: |
|
|||
1943 | warn('The Python debugger has exited with a BdbQuit exception.\n' |
|
|||
1944 | 'Because of how pdb handles the stack, it is impossible\n' |
|
|||
1945 | 'for IPython to properly format this particular exception.\n' |
|
|||
1946 | 'IPython will resume normal operation.') |
|
|||
1947 | except: |
|
|||
1948 | # exceptions here are VERY RARE, but they can be triggered |
|
|||
1949 | # asynchronously by signal handlers, for example. |
|
|||
1950 | self.showtraceback() |
|
|||
1951 | else: |
|
|||
1952 | more = self.push_line(line) |
|
|||
1953 | if (self.SyntaxTB.last_syntax_error and |
|
|||
1954 | self.autoedit_syntax): |
|
|||
1955 | self.edit_syntax_error() |
|
|||
1956 |
|
||||
1957 | # We are off again... |
|
|||
1958 | __builtin__.__dict__['__IPYTHON__active'] -= 1 |
|
|||
1959 |
|
||||
1960 | # Turn off the exit flag, so the mainloop can be restarted if desired |
|
|||
1961 | self.exit_now = False |
|
|||
1962 |
|
||||
1963 | def safe_execfile(self, fname, *where, **kw): |
|
1622 | def safe_execfile(self, fname, *where, **kw): | |
1964 | """A safe version of the builtin execfile(). |
|
1623 | """A safe version of the builtin execfile(). | |
1965 |
|
1624 | |||
@@ -2057,43 +1716,6 b' class InteractiveShell(Configurable, Magic):' | |||||
2057 | except: |
|
1716 | except: | |
2058 | self.showtraceback() |
|
1717 | self.showtraceback() | |
2059 | warn('Unknown failure executing file: <%s>' % fname) |
|
1718 | warn('Unknown failure executing file: <%s>' % fname) | |
2060 |
|
||||
2061 | def _is_secondary_block_start(self, s): |
|
|||
2062 | if not s.endswith(':'): |
|
|||
2063 | return False |
|
|||
2064 | if (s.startswith('elif') or |
|
|||
2065 | s.startswith('else') or |
|
|||
2066 | s.startswith('except') or |
|
|||
2067 | s.startswith('finally')): |
|
|||
2068 | return True |
|
|||
2069 |
|
||||
2070 | def cleanup_ipy_script(self, script): |
|
|||
2071 | """Make a script safe for self.runlines() |
|
|||
2072 |
|
||||
2073 | Currently, IPython is lines based, with blocks being detected by |
|
|||
2074 | empty lines. This is a problem for block based scripts that may |
|
|||
2075 | not have empty lines after blocks. This script adds those empty |
|
|||
2076 | lines to make scripts safe for running in the current line based |
|
|||
2077 | IPython. |
|
|||
2078 | """ |
|
|||
2079 | res = [] |
|
|||
2080 | lines = script.splitlines() |
|
|||
2081 | level = 0 |
|
|||
2082 |
|
||||
2083 | for l in lines: |
|
|||
2084 | lstripped = l.lstrip() |
|
|||
2085 | stripped = l.strip() |
|
|||
2086 | if not stripped: |
|
|||
2087 | continue |
|
|||
2088 | newlevel = len(l) - len(lstripped) |
|
|||
2089 | if level > 0 and newlevel == 0 and \ |
|
|||
2090 | not self._is_secondary_block_start(stripped): |
|
|||
2091 | # add empty line |
|
|||
2092 | res.append('') |
|
|||
2093 | res.append(l) |
|
|||
2094 | level = newlevel |
|
|||
2095 |
|
||||
2096 | return '\n'.join(res) + '\n' |
|
|||
2097 |
|
1719 | |||
2098 | def runlines(self, lines, clean=False): |
|
1720 | def runlines(self, lines, clean=False): | |
2099 | """Run a string of one or more lines of source. |
|
1721 | """Run a string of one or more lines of source. | |
@@ -2108,7 +1730,7 b' class InteractiveShell(Configurable, Magic):' | |||||
2108 | lines = '\n'.join(lines) |
|
1730 | lines = '\n'.join(lines) | |
2109 |
|
1731 | |||
2110 | if clean: |
|
1732 | if clean: | |
2111 | lines = self.cleanup_ipy_script(lines) |
|
1733 | lines = self._cleanup_ipy_script(lines) | |
2112 |
|
1734 | |||
2113 | # We must start with a clean buffer, in case this is run from an |
|
1735 | # We must start with a clean buffer, in case this is run from an | |
2114 | # interactive IPython session (via a magic, for example). |
|
1736 | # interactive IPython session (via a magic, for example). | |
@@ -2272,6 +1894,47 b' class InteractiveShell(Configurable, Magic):' | |||||
2272 | self.resetbuffer() |
|
1894 | self.resetbuffer() | |
2273 | return more |
|
1895 | return more | |
2274 |
|
1896 | |||
|
1897 | def resetbuffer(self): | |||
|
1898 | """Reset the input buffer.""" | |||
|
1899 | self.buffer[:] = [] | |||
|
1900 | ||||
|
1901 | def _is_secondary_block_start(self, s): | |||
|
1902 | if not s.endswith(':'): | |||
|
1903 | return False | |||
|
1904 | if (s.startswith('elif') or | |||
|
1905 | s.startswith('else') or | |||
|
1906 | s.startswith('except') or | |||
|
1907 | s.startswith('finally')): | |||
|
1908 | return True | |||
|
1909 | ||||
|
1910 | def _cleanup_ipy_script(self, script): | |||
|
1911 | """Make a script safe for self.runlines() | |||
|
1912 | ||||
|
1913 | Currently, IPython is lines based, with blocks being detected by | |||
|
1914 | empty lines. This is a problem for block based scripts that may | |||
|
1915 | not have empty lines after blocks. This script adds those empty | |||
|
1916 | lines to make scripts safe for running in the current line based | |||
|
1917 | IPython. | |||
|
1918 | """ | |||
|
1919 | res = [] | |||
|
1920 | lines = script.splitlines() | |||
|
1921 | level = 0 | |||
|
1922 | ||||
|
1923 | for l in lines: | |||
|
1924 | lstripped = l.lstrip() | |||
|
1925 | stripped = l.strip() | |||
|
1926 | if not stripped: | |||
|
1927 | continue | |||
|
1928 | newlevel = len(l) - len(lstripped) | |||
|
1929 | if level > 0 and newlevel == 0 and \ | |||
|
1930 | not self._is_secondary_block_start(stripped): | |||
|
1931 | # add empty line | |||
|
1932 | res.append('') | |||
|
1933 | res.append(l) | |||
|
1934 | level = newlevel | |||
|
1935 | ||||
|
1936 | return '\n'.join(res) + '\n' | |||
|
1937 | ||||
2275 | def _autoindent_update(self,line): |
|
1938 | def _autoindent_update(self,line): | |
2276 | """Keep track of the indent level.""" |
|
1939 | """Keep track of the indent level.""" | |
2277 |
|
1940 | |||
@@ -2290,91 +1953,12 b' class InteractiveShell(Configurable, Magic):' | |||||
2290 | else: |
|
1953 | else: | |
2291 | self.indent_current_nsp = 0 |
|
1954 | self.indent_current_nsp = 0 | |
2292 |
|
1955 | |||
2293 | def resetbuffer(self): |
|
|||
2294 | """Reset the input buffer.""" |
|
|||
2295 | self.buffer[:] = [] |
|
|||
2296 |
|
||||
2297 | def raw_input(self,prompt='',continue_prompt=False): |
|
|||
2298 | """Write a prompt and read a line. |
|
|||
2299 |
|
||||
2300 | The returned line does not include the trailing newline. |
|
|||
2301 | When the user enters the EOF key sequence, EOFError is raised. |
|
|||
2302 |
|
||||
2303 | Optional inputs: |
|
|||
2304 |
|
||||
2305 | - prompt(''): a string to be printed to prompt the user. |
|
|||
2306 |
|
||||
2307 | - continue_prompt(False): whether this line is the first one or a |
|
|||
2308 | continuation in a sequence of inputs. |
|
|||
2309 | """ |
|
|||
2310 | # growl.notify("raw_input: ", "prompt = %r\ncontinue_prompt = %s" % (prompt, continue_prompt)) |
|
|||
2311 |
|
||||
2312 | # Code run by the user may have modified the readline completer state. |
|
|||
2313 | # We must ensure that our completer is back in place. |
|
|||
2314 |
|
||||
2315 | if self.has_readline: |
|
|||
2316 | self.set_completer() |
|
|||
2317 |
|
||||
2318 | try: |
|
|||
2319 | line = raw_input_original(prompt).decode(self.stdin_encoding) |
|
|||
2320 | except ValueError: |
|
|||
2321 | warn("\n********\nYou or a %run:ed script called sys.stdin.close()" |
|
|||
2322 | " or sys.stdout.close()!\nExiting IPython!") |
|
|||
2323 | self.ask_exit() |
|
|||
2324 | return "" |
|
|||
2325 |
|
||||
2326 | # Try to be reasonably smart about not re-indenting pasted input more |
|
|||
2327 | # than necessary. We do this by trimming out the auto-indent initial |
|
|||
2328 | # spaces, if the user's actual input started itself with whitespace. |
|
|||
2329 | #debugx('self.buffer[-1]') |
|
|||
2330 |
|
||||
2331 | if self.autoindent: |
|
|||
2332 | if num_ini_spaces(line) > self.indent_current_nsp: |
|
|||
2333 | line = line[self.indent_current_nsp:] |
|
|||
2334 | self.indent_current_nsp = 0 |
|
|||
2335 |
|
||||
2336 | # store the unfiltered input before the user has any chance to modify |
|
|||
2337 | # it. |
|
|||
2338 | if line.strip(): |
|
|||
2339 | if continue_prompt: |
|
|||
2340 | self.input_hist_raw[-1] += '%s\n' % line |
|
|||
2341 | if self.has_readline and self.readline_use: |
|
|||
2342 | try: |
|
|||
2343 | histlen = self.readline.get_current_history_length() |
|
|||
2344 | if histlen > 1: |
|
|||
2345 | newhist = self.input_hist_raw[-1].rstrip() |
|
|||
2346 | self.readline.remove_history_item(histlen-1) |
|
|||
2347 | self.readline.replace_history_item(histlen-2, |
|
|||
2348 | newhist.encode(self.stdin_encoding)) |
|
|||
2349 | except AttributeError: |
|
|||
2350 | pass # re{move,place}_history_item are new in 2.4. |
|
|||
2351 | else: |
|
|||
2352 | self.input_hist_raw.append('%s\n' % line) |
|
|||
2353 | # only entries starting at first column go to shadow history |
|
|||
2354 | if line.lstrip() == line: |
|
|||
2355 | self.shadowhist.add(line.strip()) |
|
|||
2356 | elif not continue_prompt: |
|
|||
2357 | self.input_hist_raw.append('\n') |
|
|||
2358 | try: |
|
|||
2359 | lineout = self.prefilter_manager.prefilter_lines(line,continue_prompt) |
|
|||
2360 | except: |
|
|||
2361 | # blanket except, in case a user-defined prefilter crashes, so it |
|
|||
2362 | # can't take all of ipython with it. |
|
|||
2363 | self.showtraceback() |
|
|||
2364 | return '' |
|
|||
2365 | else: |
|
|||
2366 | return lineout |
|
|||
2367 |
|
||||
2368 | #------------------------------------------------------------------------- |
|
1956 | #------------------------------------------------------------------------- | |
2369 |
# Things related to |
|
1957 | # Things related to GUI support and pylab | |
2370 | #------------------------------------------------------------------------- |
|
1958 | #------------------------------------------------------------------------- | |
2371 |
|
1959 | |||
2372 | def init_prefilter(self): |
|
1960 | def enable_pylab(self, gui=None): | |
2373 | self.prefilter_manager = PrefilterManager(shell=self, config=self.config) |
|
1961 | raise NotImplementedError('Implement enable_pylab in a subclass') | |
2374 | # Ultimately this will be refactored in the new interpreter code, but |
|
|||
2375 | # for now, we should expose the main prefilter method (there's legacy |
|
|||
2376 | # code out there that may rely on this). |
|
|||
2377 | self.prefilter = self.prefilter_manager.prefilter_lines |
|
|||
2378 |
|
1962 | |||
2379 | #------------------------------------------------------------------------- |
|
1963 | #------------------------------------------------------------------------- | |
2380 | # Utilities |
|
1964 | # Utilities | |
@@ -2426,13 +2010,15 b' class InteractiveShell(Configurable, Magic):' | |||||
2426 | tmp_file.close() |
|
2010 | tmp_file.close() | |
2427 | return filename |
|
2011 | return filename | |
2428 |
|
2012 | |||
|
2013 | # TODO: This should be removed when Term is refactored. | |||
2429 | def write(self,data): |
|
2014 | def write(self,data): | |
2430 | """Write a string to the default output""" |
|
2015 | """Write a string to the default output""" | |
2431 | Term.cout.write(data) |
|
2016 | IPython.utils.io.Term.cout.write(data) | |
2432 |
|
2017 | |||
|
2018 | # TODO: This should be removed when Term is refactored. | |||
2433 | def write_err(self,data): |
|
2019 | def write_err(self,data): | |
2434 | """Write a string to the default error output""" |
|
2020 | """Write a string to the default error output""" | |
2435 | Term.cerr.write(data) |
|
2021 | IPython.utils.io.Term.cerr.write(data) | |
2436 |
|
2022 | |||
2437 | def ask_yes_no(self,prompt,default=True): |
|
2023 | def ask_yes_no(self,prompt,default=True): | |
2438 | if self.quiet: |
|
2024 | if self.quiet: | |
@@ -2440,58 +2026,9 b' class InteractiveShell(Configurable, Magic):' | |||||
2440 | return ask_yes_no(prompt,default) |
|
2026 | return ask_yes_no(prompt,default) | |
2441 |
|
2027 | |||
2442 | #------------------------------------------------------------------------- |
|
2028 | #------------------------------------------------------------------------- | |
2443 | # Things related to GUI support and pylab |
|
|||
2444 | #------------------------------------------------------------------------- |
|
|||
2445 |
|
||||
2446 | def enable_pylab(self, gui=None): |
|
|||
2447 | """Activate pylab support at runtime. |
|
|||
2448 |
|
||||
2449 | This turns on support for matplotlib, preloads into the interactive |
|
|||
2450 | namespace all of numpy and pylab, and configures IPython to correcdtly |
|
|||
2451 | interact with the GUI event loop. The GUI backend to be used can be |
|
|||
2452 | optionally selected with the optional :param:`gui` argument. |
|
|||
2453 |
|
||||
2454 | Parameters |
|
|||
2455 | ---------- |
|
|||
2456 | gui : optional, string |
|
|||
2457 |
|
||||
2458 | If given, dictates the choice of matplotlib GUI backend to use |
|
|||
2459 | (should be one of IPython's supported backends, 'tk', 'qt', 'wx' or |
|
|||
2460 | 'gtk'), otherwise we use the default chosen by matplotlib (as |
|
|||
2461 | dictated by the matplotlib build-time options plus the user's |
|
|||
2462 | matplotlibrc configuration file). |
|
|||
2463 | """ |
|
|||
2464 | # We want to prevent the loading of pylab to pollute the user's |
|
|||
2465 | # namespace as shown by the %who* magics, so we execute the activation |
|
|||
2466 | # code in an empty namespace, and we update *both* user_ns and |
|
|||
2467 | # user_ns_hidden with this information. |
|
|||
2468 | ns = {} |
|
|||
2469 | gui = pylab_activate(ns, gui) |
|
|||
2470 | self.user_ns.update(ns) |
|
|||
2471 | self.user_ns_hidden.update(ns) |
|
|||
2472 | # Now we must activate the gui pylab wants to use, and fix %run to take |
|
|||
2473 | # plot updates into account |
|
|||
2474 | enable_gui(gui) |
|
|||
2475 | self.magic_run = self._pylab_magic_run |
|
|||
2476 |
|
||||
2477 | #------------------------------------------------------------------------- |
|
|||
2478 | # Things related to IPython exiting |
|
2029 | # Things related to IPython exiting | |
2479 | #------------------------------------------------------------------------- |
|
2030 | #------------------------------------------------------------------------- | |
2480 |
|
2031 | |||
2481 | def ask_exit(self): |
|
|||
2482 | """ Ask the shell to exit. Can be overiden and used as a callback. """ |
|
|||
2483 | self.exit_now = True |
|
|||
2484 |
|
||||
2485 | def exit(self): |
|
|||
2486 | """Handle interactive exit. |
|
|||
2487 |
|
||||
2488 | This method calls the ask_exit callback.""" |
|
|||
2489 | if self.confirm_exit: |
|
|||
2490 | if self.ask_yes_no('Do you really want to exit ([y]/n)?','y'): |
|
|||
2491 | self.ask_exit() |
|
|||
2492 | else: |
|
|||
2493 | self.ask_exit() |
|
|||
2494 |
|
||||
2495 | def atexit_operations(self): |
|
2032 | def atexit_operations(self): | |
2496 | """This will be executed at the time of exit. |
|
2033 | """This will be executed at the time of exit. | |
2497 |
|
2034 |
@@ -25,6 +25,6 b' has been made into a component, this module will be sent to deathrow.' | |||||
25 |
|
25 | |||
26 | def get(): |
|
26 | def get(): | |
27 | """Get the global InteractiveShell instance.""" |
|
27 | """Get the global InteractiveShell instance.""" | |
28 |
from IPython. |
|
28 | from IPython.frontend.terminal.interactiveshell import TerminalInteractiveShell | |
29 | return InteractiveShell.instance() |
|
29 | return TerminalInteractiveShell.instance() | |
30 |
|
30 |
@@ -7,7 +7,7 b'' | |||||
7 | # the file COPYING, distributed as part of this software. |
|
7 | # the file COPYING, distributed as part of this software. | |
8 | #***************************************************************************** |
|
8 | #***************************************************************************** | |
9 |
|
9 | |||
10 |
|
|
10 | import IPython.utils.io | |
11 | from IPython.core.autocall import IPyAutocall |
|
11 | from IPython.core.autocall import IPyAutocall | |
12 |
|
12 | |||
13 | class Macro(IPyAutocall): |
|
13 | class Macro(IPyAutocall): | |
@@ -32,7 +32,7 b' class Macro(IPyAutocall):' | |||||
32 | return 'IPython.macro.Macro(%s)' % repr(self.value) |
|
32 | return 'IPython.macro.Macro(%s)' % repr(self.value) | |
33 |
|
33 | |||
34 | def __call__(self,*args): |
|
34 | def __call__(self,*args): | |
35 | Term.cout.flush() |
|
35 | IPython.utils.io.Term.cout.flush() | |
36 | self._ip.user_ns['_margv'] = args |
|
36 | self._ip.user_ns['_margv'] = args | |
37 | self._ip.runlines(self.value) |
|
37 | self._ip.runlines(self.value) | |
38 |
|
38 |
@@ -58,7 +58,8 b' from IPython.lib.pylabtools import mpl_runner' | |||||
58 | from IPython.lib.inputhook import enable_gui |
|
58 | from IPython.lib.inputhook import enable_gui | |
59 | from IPython.external.Itpl import itpl, printpl |
|
59 | from IPython.external.Itpl import itpl, printpl | |
60 | from IPython.testing import decorators as testdec |
|
60 | from IPython.testing import decorators as testdec | |
61 |
from IPython.utils.io import |
|
61 | from IPython.utils.io import file_read, nlprint | |
|
62 | import IPython.utils.io | |||
62 | from IPython.utils.path import get_py_filename |
|
63 | from IPython.utils.path import get_py_filename | |
63 | from IPython.utils.process import arg_split, abbrev_cwd |
|
64 | from IPython.utils.process import arg_split, abbrev_cwd | |
64 | from IPython.utils.terminal import set_term_title |
|
65 | from IPython.utils.terminal import set_term_title | |
@@ -1699,7 +1700,7 b' Currently the magic system has the following functions:\\n"""' | |||||
1699 | # set the __file__ global in the script's namespace |
|
1700 | # set the __file__ global in the script's namespace | |
1700 | prog_ns['__file__'] = filename |
|
1701 | prog_ns['__file__'] = filename | |
1701 |
|
1702 | |||
1702 |
# pickle fix. See i |
|
1703 | # pickle fix. See interactiveshell for an explanation. But we need to make sure | |
1703 | # that, if we overwrite __main__, we replace it at the end |
|
1704 | # that, if we overwrite __main__, we replace it at the end | |
1704 | main_mod_name = prog_ns['__name__'] |
|
1705 | main_mod_name = prog_ns['__name__'] | |
1705 |
|
1706 | |||
@@ -2524,13 +2525,6 b' Currently the magic system has the following functions:\\n"""' | |||||
2524 | except: |
|
2525 | except: | |
2525 | xmode_switch_err('user') |
|
2526 | xmode_switch_err('user') | |
2526 |
|
2527 | |||
2527 | # threaded shells use a special handler in sys.excepthook |
|
|||
2528 | if shell.isthreaded: |
|
|||
2529 | try: |
|
|||
2530 | shell.sys_excepthook.set_mode(mode=new_mode) |
|
|||
2531 | except: |
|
|||
2532 | xmode_switch_err('threaded') |
|
|||
2533 |
|
||||
2534 | def magic_colors(self,parameter_s = ''): |
|
2528 | def magic_colors(self,parameter_s = ''): | |
2535 | """Switch color scheme for prompts, info system and exception handlers. |
|
2529 | """Switch color scheme for prompts, info system and exception handlers. | |
2536 |
|
2530 | |||
@@ -2585,13 +2579,6 b' Defaulting color scheme to \'NoColor\'"""' | |||||
2585 | except: |
|
2579 | except: | |
2586 | color_switch_err('exception') |
|
2580 | color_switch_err('exception') | |
2587 |
|
2581 | |||
2588 | # threaded shells use a verbose traceback in sys.excepthook |
|
|||
2589 | if shell.isthreaded: |
|
|||
2590 | try: |
|
|||
2591 | shell.sys_excepthook.set_colors(scheme=new_scheme) |
|
|||
2592 | except: |
|
|||
2593 | color_switch_err('system exception handler') |
|
|||
2594 |
|
||||
2595 | # Set info (for 'object?') colors |
|
2582 | # Set info (for 'object?') colors | |
2596 | if shell.color_info: |
|
2583 | if shell.color_info: | |
2597 | try: |
|
2584 | try: | |
@@ -3107,7 +3094,7 b' Defaulting color scheme to \'NoColor\'"""' | |||||
3107 | # If all looks ok, proceed |
|
3094 | # If all looks ok, proceed | |
3108 | out,err = self.shell.getoutputerror(cmd) |
|
3095 | out,err = self.shell.getoutputerror(cmd) | |
3109 | if err: |
|
3096 | if err: | |
3110 | print >> Term.cerr,err |
|
3097 | print >> IPython.utils.io.Term.cerr, err | |
3111 | if opts.has_key('l'): |
|
3098 | if opts.has_key('l'): | |
3112 | out = SList(out.split('\n')) |
|
3099 | out = SList(out.split('\n')) | |
3113 | else: |
|
3100 | else: | |
@@ -3157,52 +3144,9 b' Defaulting color scheme to \'NoColor\'"""' | |||||
3157 | if parameter_s: |
|
3144 | if parameter_s: | |
3158 | out,err = self.shell.getoutputerror(parameter_s) |
|
3145 | out,err = self.shell.getoutputerror(parameter_s) | |
3159 | if err: |
|
3146 | if err: | |
3160 | print >> Term.cerr,err |
|
3147 | print >> IPython.utils.io.Term.cerr, err | |
3161 | return SList(out.split('\n')) |
|
3148 | return SList(out.split('\n')) | |
3162 |
|
3149 | |||
3163 | def magic_bg(self, parameter_s=''): |
|
|||
3164 | """Run a job in the background, in a separate thread. |
|
|||
3165 |
|
||||
3166 | For example, |
|
|||
3167 |
|
||||
3168 | %bg myfunc(x,y,z=1) |
|
|||
3169 |
|
||||
3170 | will execute 'myfunc(x,y,z=1)' in a background thread. As soon as the |
|
|||
3171 | execution starts, a message will be printed indicating the job |
|
|||
3172 | number. If your job number is 5, you can use |
|
|||
3173 |
|
||||
3174 | myvar = jobs.result(5) or myvar = jobs[5].result |
|
|||
3175 |
|
||||
3176 | to assign this result to variable 'myvar'. |
|
|||
3177 |
|
||||
3178 | IPython has a job manager, accessible via the 'jobs' object. You can |
|
|||
3179 | type jobs? to get more information about it, and use jobs.<TAB> to see |
|
|||
3180 | its attributes. All attributes not starting with an underscore are |
|
|||
3181 | meant for public use. |
|
|||
3182 |
|
||||
3183 | In particular, look at the jobs.new() method, which is used to create |
|
|||
3184 | new jobs. This magic %bg function is just a convenience wrapper |
|
|||
3185 | around jobs.new(), for expression-based jobs. If you want to create a |
|
|||
3186 | new job with an explicit function object and arguments, you must call |
|
|||
3187 | jobs.new() directly. |
|
|||
3188 |
|
||||
3189 | The jobs.new docstring also describes in detail several important |
|
|||
3190 | caveats associated with a thread-based model for background job |
|
|||
3191 | execution. Type jobs.new? for details. |
|
|||
3192 |
|
||||
3193 | You can check the status of all jobs with jobs.status(). |
|
|||
3194 |
|
||||
3195 | The jobs variable is set by IPython into the Python builtin namespace. |
|
|||
3196 | If you ever declare a variable named 'jobs', you will shadow this |
|
|||
3197 | name. You can either delete your global jobs variable to regain |
|
|||
3198 | access to the job manager, or make a new name and assign it manually |
|
|||
3199 | to the manager (stored in IPython's namespace). For example, to |
|
|||
3200 | assign the job manager to the Jobs name, use: |
|
|||
3201 |
|
||||
3202 | Jobs = __builtins__.jobs""" |
|
|||
3203 |
|
||||
3204 | self.shell.jobs.new(parameter_s,self.shell.user_ns) |
|
|||
3205 |
|
||||
3206 | def magic_r(self, parameter_s=''): |
|
3150 | def magic_r(self, parameter_s=''): | |
3207 | """Repeat previous input. |
|
3151 | """Repeat previous input. | |
3208 |
|
3152 | |||
@@ -3327,10 +3271,10 b' Defaulting color scheme to \'NoColor\'"""' | |||||
3327 | def _get_pasted_lines(self, sentinel): |
|
3271 | def _get_pasted_lines(self, sentinel): | |
3328 | """ Yield pasted lines until the user enters the given sentinel value. |
|
3272 | """ Yield pasted lines until the user enters the given sentinel value. | |
3329 | """ |
|
3273 | """ | |
3330 |
from IPython.core import i |
|
3274 | from IPython.core import interactiveshell | |
3331 | print "Pasting code; enter '%s' alone on the line to stop." % sentinel |
|
3275 | print "Pasting code; enter '%s' alone on the line to stop." % sentinel | |
3332 | while True: |
|
3276 | while True: | |
3333 |
l = i |
|
3277 | l = interactiveshell.raw_input_original(':') | |
3334 | if l == sentinel: |
|
3278 | if l == sentinel: | |
3335 | return |
|
3279 | return | |
3336 | else: |
|
3280 | else: |
@@ -30,7 +30,7 b' import types' | |||||
30 | from IPython.core.page import page |
|
30 | from IPython.core.page import page | |
31 | from IPython.external.Itpl import itpl |
|
31 | from IPython.external.Itpl import itpl | |
32 | from IPython.utils import PyColorize |
|
32 | from IPython.utils import PyColorize | |
33 |
|
|
33 | import IPython.utils.io | |
34 | from IPython.utils.text import indent |
|
34 | from IPython.utils.text import indent | |
35 | from IPython.utils.wildcard import list_namespace |
|
35 | from IPython.utils.wildcard import list_namespace | |
36 | from IPython.utils.coloransi import * |
|
36 | from IPython.utils.coloransi import * | |
@@ -249,7 +249,7 b' class Inspector:' | |||||
249 | if output is None: |
|
249 | if output is None: | |
250 | self.noinfo('definition header',oname) |
|
250 | self.noinfo('definition header',oname) | |
251 | else: |
|
251 | else: | |
252 | print >>Term.cout, header,self.format(output), |
|
252 | print >>IPython.utils.io.Term.cout, header,self.format(output), | |
253 |
|
253 | |||
254 | def pdoc(self,obj,oname='',formatter = None): |
|
254 | def pdoc(self,obj,oname='',formatter = None): | |
255 | """Print the docstring for any object. |
|
255 | """Print the docstring for any object. |
@@ -36,7 +36,7 b' from IPython.core import ipapi' | |||||
36 | from IPython.core.error import TryNext |
|
36 | from IPython.core.error import TryNext | |
37 | from IPython.utils.cursesimport import use_curses |
|
37 | from IPython.utils.cursesimport import use_curses | |
38 | from IPython.utils.data import chop |
|
38 | from IPython.utils.data import chop | |
39 |
|
|
39 | import IPython.utils.io | |
40 | from IPython.utils.process import xsys |
|
40 | from IPython.utils.process import xsys | |
41 | from IPython.utils.terminal import get_terminal_size |
|
41 | from IPython.utils.terminal import get_terminal_size | |
42 |
|
42 | |||
@@ -56,18 +56,18 b' def page_dumb(strng, start=0, screen_lines=25):' | |||||
56 | out_ln = strng.splitlines()[start:] |
|
56 | out_ln = strng.splitlines()[start:] | |
57 | screens = chop(out_ln,screen_lines-1) |
|
57 | screens = chop(out_ln,screen_lines-1) | |
58 | if len(screens) == 1: |
|
58 | if len(screens) == 1: | |
59 | print >>Term.cout, os.linesep.join(screens[0]) |
|
59 | print >>IPython.utils.io.Term.cout, os.linesep.join(screens[0]) | |
60 | else: |
|
60 | else: | |
61 | last_escape = "" |
|
61 | last_escape = "" | |
62 | for scr in screens[0:-1]: |
|
62 | for scr in screens[0:-1]: | |
63 | hunk = os.linesep.join(scr) |
|
63 | hunk = os.linesep.join(scr) | |
64 | print >>Term.cout, last_escape + hunk |
|
64 | print >>IPython.utils.io.Term.cout, last_escape + hunk | |
65 | if not page_more(): |
|
65 | if not page_more(): | |
66 | return |
|
66 | return | |
67 | esc_list = esc_re.findall(hunk) |
|
67 | esc_list = esc_re.findall(hunk) | |
68 | if len(esc_list) > 0: |
|
68 | if len(esc_list) > 0: | |
69 | last_escape = esc_list[-1] |
|
69 | last_escape = esc_list[-1] | |
70 | print >>Term.cout, last_escape + os.linesep.join(screens[-1]) |
|
70 | print >>IPython.utils.io.Term.cout, last_escape + os.linesep.join(screens[-1]) | |
71 |
|
71 | |||
72 |
|
72 | |||
73 | def page(strng, start=0, screen_lines=0, pager_cmd=None): |
|
73 | def page(strng, start=0, screen_lines=0, pager_cmd=None): | |
@@ -156,7 +156,7 b' def page(strng, start=0, screen_lines=0, pager_cmd=None):' | |||||
156 | #print 'numlines',numlines,'screenlines',screen_lines # dbg |
|
156 | #print 'numlines',numlines,'screenlines',screen_lines # dbg | |
157 | if numlines <= screen_lines : |
|
157 | if numlines <= screen_lines : | |
158 | #print '*** normal print' # dbg |
|
158 | #print '*** normal print' # dbg | |
159 | print >>Term.cout, str_toprint |
|
159 | print >>IPython.utils.io.Term.cout, str_toprint | |
160 | else: |
|
160 | else: | |
161 | # Try to open pager and default to internal one if that fails. |
|
161 | # Try to open pager and default to internal one if that fails. | |
162 | # All failure modes are tagged as 'retval=1', to match the return |
|
162 | # All failure modes are tagged as 'retval=1', to match the return | |
@@ -262,13 +262,13 b" if os.name == 'nt' and os.environ.get('TERM','dumb') != 'emacs':" | |||||
262 |
|
262 | |||
263 | @return: True if need print more lines, False if quit |
|
263 | @return: True if need print more lines, False if quit | |
264 | """ |
|
264 | """ | |
265 | Term.cout.write('---Return to continue, q to quit--- ') |
|
265 | IPython.utils.io.Term.cout.write('---Return to continue, q to quit--- ') | |
266 | ans = msvcrt.getch() |
|
266 | ans = msvcrt.getch() | |
267 | if ans in ("q", "Q"): |
|
267 | if ans in ("q", "Q"): | |
268 | result = False |
|
268 | result = False | |
269 | else: |
|
269 | else: | |
270 | result = True |
|
270 | result = True | |
271 | Term.cout.write("\b"*37 + " "*37 + "\b"*37) |
|
271 | IPython.utils.io.Term.cout.write("\b"*37 + " "*37 + "\b"*37) | |
272 | return result |
|
272 | return result | |
273 | else: |
|
273 | else: | |
274 | def page_more(): |
|
274 | def page_more(): |
@@ -36,7 +36,7 b' from IPython.core.splitinput import split_user_input' | |||||
36 | from IPython.core.page import page |
|
36 | from IPython.core.page import page | |
37 |
|
37 | |||
38 | from IPython.utils.traitlets import List, Int, Any, Str, CBool, Bool, Instance |
|
38 | from IPython.utils.traitlets import List, Int, Any, Str, CBool, Bool, Instance | |
39 |
|
|
39 | import IPython.utils.io | |
40 | from IPython.utils.text import make_quoted_expr |
|
40 | from IPython.utils.text import make_quoted_expr | |
41 | from IPython.utils.autoattr import auto_attr |
|
41 | from IPython.utils.autoattr import auto_attr | |
42 |
|
42 | |||
@@ -210,7 +210,7 b' class PrefilterManager(Configurable):' | |||||
210 | """ |
|
210 | """ | |
211 |
|
211 | |||
212 | multi_line_specials = CBool(True, config=True) |
|
212 | multi_line_specials = CBool(True, config=True) | |
213 |
shell = Instance('IPython.core.i |
|
213 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
214 |
|
214 | |||
215 | def __init__(self, shell=None, config=None): |
|
215 | def __init__(self, shell=None, config=None): | |
216 | super(PrefilterManager, self).__init__(shell=shell, config=config) |
|
216 | super(PrefilterManager, self).__init__(shell=shell, config=config) | |
@@ -453,7 +453,7 b' class PrefilterTransformer(Configurable):' | |||||
453 | priority = Int(100, config=True) |
|
453 | priority = Int(100, config=True) | |
454 | # Transformers don't currently use shell or prefilter_manager, but as we |
|
454 | # Transformers don't currently use shell or prefilter_manager, but as we | |
455 | # move away from checkers and handlers, they will need them. |
|
455 | # move away from checkers and handlers, they will need them. | |
456 |
shell = Instance('IPython.core.i |
|
456 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
457 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') |
|
457 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') | |
458 | enabled = Bool(True, config=True) |
|
458 | enabled = Bool(True, config=True) | |
459 |
|
459 | |||
@@ -561,7 +561,7 b' class PrefilterChecker(Configurable):' | |||||
561 | """Inspect an input line and return a handler for that line.""" |
|
561 | """Inspect an input line and return a handler for that line.""" | |
562 |
|
562 | |||
563 | priority = Int(100, config=True) |
|
563 | priority = Int(100, config=True) | |
564 |
shell = Instance('IPython.core.i |
|
564 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
565 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') |
|
565 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') | |
566 | enabled = Bool(True, config=True) |
|
566 | enabled = Bool(True, config=True) | |
567 |
|
567 | |||
@@ -754,7 +754,7 b' class PrefilterHandler(Configurable):' | |||||
754 |
|
754 | |||
755 | handler_name = Str('normal') |
|
755 | handler_name = Str('normal') | |
756 | esc_strings = List([]) |
|
756 | esc_strings = List([]) | |
757 |
shell = Instance('IPython.core.i |
|
757 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
758 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') |
|
758 | prefilter_manager = Instance('IPython.core.prefilter.PrefilterManager') | |
759 |
|
759 | |||
760 | def __init__(self, shell=None, prefilter_manager=None, config=None): |
|
760 | def __init__(self, shell=None, prefilter_manager=None, config=None): | |
@@ -922,7 +922,7 b' class AutoHandler(PrefilterHandler):' | |||||
922 | # plain ascii works better w/ pyreadline, on some machines, so |
|
922 | # plain ascii works better w/ pyreadline, on some machines, so | |
923 | # we use it and only print uncolored rewrite if we have unicode |
|
923 | # we use it and only print uncolored rewrite if we have unicode | |
924 | rw = str(rw) |
|
924 | rw = str(rw) | |
925 | print >>Term.cout, rw |
|
925 | print >>IPython.utils.io.Term.cout, rw | |
926 | except UnicodeEncodeError: |
|
926 | except UnicodeEncodeError: | |
927 | print "-------------->" + newcmd |
|
927 | print "-------------->" + newcmd | |
928 |
|
928 |
@@ -25,7 +25,7 b' from IPython.core.error import TryNext' | |||||
25 | from IPython.utils import coloransi |
|
25 | from IPython.utils import coloransi | |
26 | import IPython.utils.generics |
|
26 | import IPython.utils.generics | |
27 | from IPython.utils.warn import warn |
|
27 | from IPython.utils.warn import warn | |
28 |
|
|
28 | import IPython.utils.io | |
29 |
|
29 | |||
30 | #**************************************************************************** |
|
30 | #**************************************************************************** | |
31 | #Color schemes for Prompts. |
|
31 | #Color schemes for Prompts. | |
@@ -537,7 +537,7 b' class CachedOutput:' | |||||
537 | except KeyError: |
|
537 | except KeyError: | |
538 | pass |
|
538 | pass | |
539 | if arg is not None: |
|
539 | if arg is not None: | |
540 | cout_write = Term.cout.write # fast lookup |
|
540 | cout_write = IPython.utils.io.Term.cout.write # fast lookup | |
541 | # first handle the cache and counters |
|
541 | # first handle the cache and counters | |
542 |
|
542 | |||
543 | # do not print output if input ends in ';' |
|
543 | # do not print output if input ends in ';' | |
@@ -577,7 +577,7 b' class CachedOutput:' | |||||
577 | if self.logger.log_output: |
|
577 | if self.logger.log_output: | |
578 | self.logger.log_write(repr(arg),'output') |
|
578 | self.logger.log_write(repr(arg),'output') | |
579 | cout_write(self.output_sep2) |
|
579 | cout_write(self.output_sep2) | |
580 | Term.cout.flush() |
|
580 | IPython.utils.io.Term.cout.flush() | |
581 |
|
581 | |||
582 | def _display(self,arg): |
|
582 | def _display(self,arg): | |
583 | """Default printer method, uses pprint. |
|
583 | """Default printer method, uses pprint. |
@@ -30,7 +30,7 b' import re' | |||||
30 | # RegExp for splitting line contents into pre-char//first word-method//rest. |
|
30 | # RegExp for splitting line contents into pre-char//first word-method//rest. | |
31 | # For clarity, each group in on one line. |
|
31 | # For clarity, each group in on one line. | |
32 |
|
32 | |||
33 |
# WARNING: update the regexp if the escapes in i |
|
33 | # WARNING: update the regexp if the escapes in interactiveshell are changed, as they | |
34 | # are hardwired in. |
|
34 | # are hardwired in. | |
35 |
|
35 | |||
36 | # Although it's not solely driven by the regex, note that: |
|
36 | # Although it's not solely driven by the regex, note that: |
@@ -25,8 +25,8 b' def test_import_hooks():' | |||||
25 | def test_import_ipapi(): |
|
25 | def test_import_ipapi(): | |
26 | from IPython.core import ipapi |
|
26 | from IPython.core import ipapi | |
27 |
|
27 | |||
28 |
def test_import_i |
|
28 | def test_import_interactiveshell(): | |
29 |
from IPython.core import i |
|
29 | from IPython.core import interactiveshell | |
30 |
|
30 | |||
31 | def test_import_logger(): |
|
31 | def test_import_logger(): | |
32 | from IPython.core import logger |
|
32 | from IPython.core import logger | |
@@ -40,9 +40,6 b' def test_import_magic():' | |||||
40 | def test_import_oinspect(): |
|
40 | def test_import_oinspect(): | |
41 | from IPython.core import oinspect |
|
41 | from IPython.core import oinspect | |
42 |
|
42 | |||
43 | def test_import_outputtrap(): |
|
|||
44 | from IPython.core import outputtrap |
|
|||
45 |
|
||||
46 | def test_import_prefilter(): |
|
43 | def test_import_prefilter(): | |
47 | from IPython.core import prefilter |
|
44 | from IPython.core import prefilter | |
48 |
|
45 |
@@ -1,4 +1,4 b'' | |||||
1 |
"""Tests for the key i |
|
1 | """Tests for the key interactiveshell module, where the main ipython class is defined. | |
2 | """ |
|
2 | """ | |
3 | #----------------------------------------------------------------------------- |
|
3 | #----------------------------------------------------------------------------- | |
4 | # Module imports |
|
4 | # Module imports | |
@@ -60,7 +60,7 b' def test_reset():' | |||||
60 |
|
60 | |||
61 |
|
61 | |||
62 | # Tests for reporting of exceptions in various modes, handling of SystemExit, |
|
62 | # Tests for reporting of exceptions in various modes, handling of SystemExit, | |
63 |
# and %tb functionality. This is really a mix of testing ultraTB and i |
|
63 | # and %tb functionality. This is really a mix of testing ultraTB and interactiveshell. | |
64 |
|
64 | |||
65 | def doctest_tb_plain(): |
|
65 | def doctest_tb_plain(): | |
66 | """ |
|
66 | """ |
@@ -95,7 +95,7 b' from IPython.core import debugger, ipapi' | |||||
95 | from IPython.core.display_trap import DisplayTrap |
|
95 | from IPython.core.display_trap import DisplayTrap | |
96 | from IPython.core.excolors import exception_colors |
|
96 | from IPython.core.excolors import exception_colors | |
97 | from IPython.utils.data import uniq_stable |
|
97 | from IPython.utils.data import uniq_stable | |
98 |
|
|
98 | import IPython.utils.io | |
99 | from IPython.utils.warn import info, error |
|
99 | from IPython.utils.warn import info, error | |
100 |
|
100 | |||
101 | # Globals |
|
101 | # Globals | |
@@ -313,14 +313,11 b' def _format_traceback_lines(lnum, index, lines, Colors, lvals=None,scheme=None):' | |||||
313 | class TBTools: |
|
313 | class TBTools: | |
314 | """Basic tools used by all traceback printer classes.""" |
|
314 | """Basic tools used by all traceback printer classes.""" | |
315 |
|
315 | |||
316 | #: Default output stream, can be overridden at call time. A special value |
|
316 | # This attribute us used in globalipapp.py to have stdout used for | |
317 | #: of 'stdout' *as a string* can be given to force extraction of sys.stdout |
|
317 | # writting exceptions. This is needed so nose can trap them. This attribute | |
318 | #: at runtime. This allows testing exception printing with doctests, that |
|
318 | # should be None (the default, which will use IPython.utils.io.Term) or | |
319 | #: swap sys.stdout just at execution time. |
|
319 | # the string 'stdout' which will cause the override to sys.stdout. | |
320 | #: Warning: be VERY careful to set this to one of the Term streams, NEVER |
|
320 | out_stream = None | |
321 | #: directly to sys.stdout/err, because under win32 the Term streams come from |
|
|||
322 | #: pyreadline and know how to handle color correctly, whie stdout/err don't. |
|
|||
323 | out_stream = Term.cerr |
|
|||
324 |
|
321 | |||
325 | def __init__(self,color_scheme = 'NoColor',call_pdb=False): |
|
322 | def __init__(self,color_scheme = 'NoColor',call_pdb=False): | |
326 | # Whether to call the interactive pdb debugger after printing |
|
323 | # Whether to call the interactive pdb debugger after printing | |
@@ -384,9 +381,9 b' class ListTB(TBTools):' | |||||
384 | TBTools.__init__(self,color_scheme = color_scheme,call_pdb=0) |
|
381 | TBTools.__init__(self,color_scheme = color_scheme,call_pdb=0) | |
385 |
|
382 | |||
386 | def __call__(self, etype, value, elist): |
|
383 | def __call__(self, etype, value, elist): | |
387 | Term.cout.flush() |
|
384 | IPython.utils.io.Term.cout.flush() | |
388 | Term.cerr.write(self.text(etype,value,elist)) |
|
385 | IPython.utils.io.Term.cerr.write(self.text(etype,value,elist)) | |
389 | Term.cerr.write('\n') |
|
386 | IPython.utils.io.Term.cerr.write('\n') | |
390 |
|
387 | |||
391 | def text(self, etype, value, elist, context=5): |
|
388 | def text(self, etype, value, elist, context=5): | |
392 | """Return a color formatted string with the traceback info. |
|
389 | """Return a color formatted string with the traceback info. | |
@@ -535,10 +532,13 b' class ListTB(TBTools):' | |||||
535 | """ |
|
532 | """ | |
536 | # This method needs to use __call__ from *this* class, not the one from |
|
533 | # This method needs to use __call__ from *this* class, not the one from | |
537 | # a subclass whose signature or behavior may be different |
|
534 | # a subclass whose signature or behavior may be different | |
538 | Term.cout.flush() |
|
535 | if self.out_stream == 'stdout': | |
539 | ostream = sys.stdout if self.out_stream == 'stdout' else Term.cerr |
|
536 | ostream = sys.stdout | |
|
537 | else: | |||
|
538 | ostream = IPython.utils.io.Term.cerr | |||
|
539 | ostream.flush() | |||
540 | ostream.write(ListTB.text(self, etype, value, [])) |
|
540 | ostream.write(ListTB.text(self, etype, value, [])) | |
541 |
ostream.flush() |
|
541 | ostream.flush() | |
542 |
|
542 | |||
543 | def _some_str(self, value): |
|
543 | def _some_str(self, value): | |
544 | # Lifted from traceback.py |
|
544 | # Lifted from traceback.py | |
@@ -659,7 +659,7 b' class VerboseTB(TBTools):' | |||||
659 | # So far, I haven't been able to find an isolated example to |
|
659 | # So far, I haven't been able to find an isolated example to | |
660 | # reproduce the problem. |
|
660 | # reproduce the problem. | |
661 | inspect_error() |
|
661 | inspect_error() | |
662 | traceback.print_exc(file=Term.cerr) |
|
662 | traceback.print_exc(file=IPython.utils.io.Term.cerr) | |
663 | info('\nUnfortunately, your original traceback can not be constructed.\n') |
|
663 | info('\nUnfortunately, your original traceback can not be constructed.\n') | |
664 | return '' |
|
664 | return '' | |
665 |
|
665 | |||
@@ -696,7 +696,7 b' class VerboseTB(TBTools):' | |||||
696 | # able to remove this try/except when 2.4 becomes a |
|
696 | # able to remove this try/except when 2.4 becomes a | |
697 | # requirement. Bug details at http://python.org/sf/1005466 |
|
697 | # requirement. Bug details at http://python.org/sf/1005466 | |
698 | inspect_error() |
|
698 | inspect_error() | |
699 | traceback.print_exc(file=Term.cerr) |
|
699 | traceback.print_exc(file=IPython.utils.io.Term.cerr) | |
700 | info("\nIPython's exception reporting continues...\n") |
|
700 | info("\nIPython's exception reporting continues...\n") | |
701 |
|
701 | |||
702 | if func == '?': |
|
702 | if func == '?': | |
@@ -717,7 +717,7 b' class VerboseTB(TBTools):' | |||||
717 | # and barfs out. At some point I should dig into this one |
|
717 | # and barfs out. At some point I should dig into this one | |
718 | # and file a bug report about it. |
|
718 | # and file a bug report about it. | |
719 | inspect_error() |
|
719 | inspect_error() | |
720 | traceback.print_exc(file=Term.cerr) |
|
720 | traceback.print_exc(file=IPython.utils.io.Term.cerr) | |
721 | info("\nIPython's exception reporting continues...\n") |
|
721 | info("\nIPython's exception reporting continues...\n") | |
722 | call = tpl_call_fail % func |
|
722 | call = tpl_call_fail % func | |
723 |
|
723 | |||
@@ -910,9 +910,9 b' class VerboseTB(TBTools):' | |||||
910 | def handler(self, info=None): |
|
910 | def handler(self, info=None): | |
911 | (etype, evalue, etb) = info or sys.exc_info() |
|
911 | (etype, evalue, etb) = info or sys.exc_info() | |
912 | self.tb = etb |
|
912 | self.tb = etb | |
913 | Term.cout.flush() |
|
913 | IPython.utils.io.Term.cout.flush() | |
914 | Term.cerr.write(self.text(etype, evalue, etb)) |
|
914 | IPython.utils.io.Term.cerr.write(self.text(etype, evalue, etb)) | |
915 | Term.cerr.write('\n') |
|
915 | IPython.utils.io.Term.cerr.write('\n') | |
916 |
|
916 | |||
917 | # Changed so an instance can just be called as VerboseTB_inst() and print |
|
917 | # Changed so an instance can just be called as VerboseTB_inst() and print | |
918 | # out the right info on its own. |
|
918 | # out the right info on its own. | |
@@ -1032,8 +1032,11 b' class AutoFormattedTB(FormattedTB):' | |||||
1032 | given at initialization time. """ |
|
1032 | given at initialization time. """ | |
1033 |
|
1033 | |||
1034 | if out is None: |
|
1034 | if out is None: | |
1035 |
|
|
1035 | if self.out_stream == 'stdout': | |
1036 | Term.cout.flush() |
|
1036 | out = sys.stdout | |
|
1037 | else: | |||
|
1038 | out = IPython.utils.io.Term.cerr | |||
|
1039 | out.flush() | |||
1037 | if tb_offset is not None: |
|
1040 | if tb_offset is not None: | |
1038 | tb_offset, self.tb_offset = self.tb_offset, tb_offset |
|
1041 | tb_offset, self.tb_offset = self.tb_offset, tb_offset | |
1039 | out.write(self.text(etype, evalue, etb)) |
|
1042 | out.write(self.text(etype, evalue, etb)) |
1 | NO CONTENT: file renamed from IPython/Shell.py to IPython/deathrow/Shell.py |
|
NO CONTENT: file renamed from IPython/Shell.py to IPython/deathrow/Shell.py |
@@ -24,7 +24,7 b' import locale' | |||||
24 | from thread_ex import ThreadEx |
|
24 | from thread_ex import ThreadEx | |
25 |
|
25 | |||
26 | from IPython.core import iplib |
|
26 | from IPython.core import iplib | |
27 |
|
|
27 | import IPython.utils.io | |
28 |
|
28 | |||
29 | ############################################################################## |
|
29 | ############################################################################## | |
30 | class _Helper(object): |
|
30 | class _Helper(object): |
@@ -133,7 +133,7 b' from IPython.external import simplegeneric' | |||||
133 | from IPython.external import path |
|
133 | from IPython.external import path | |
134 |
|
134 | |||
135 | try: |
|
135 | try: | |
136 |
|
|
136 | import IPython.utils.io | |
137 | from IPython.utils import generics |
|
137 | from IPython.utils import generics | |
138 | except ImportError: |
|
138 | except ImportError: | |
139 | Term = None |
|
139 | Term = None |
1 | NO CONTENT: file renamed from IPython/iplib.py to IPython/deathrow/iplib.py |
|
NO CONTENT: file renamed from IPython/iplib.py to IPython/deathrow/iplib.py |
1 | NO CONTENT: file renamed from IPython/scripts/ipython-wx to IPython/deathrow/ipython-wx |
|
NO CONTENT: file renamed from IPython/scripts/ipython-wx to IPython/deathrow/ipython-wx |
1 | NO CONTENT: file renamed from IPython/scripts/ipythonx to IPython/deathrow/ipythonx |
|
NO CONTENT: file renamed from IPython/scripts/ipythonx to IPython/deathrow/ipythonx |
@@ -31,7 +31,7 b' from IPython.kernel.core.redirector_output_trap import RedirectorOutputTrap' | |||||
31 |
|
31 | |||
32 | from IPython.kernel.core.sync_traceback_trap import SyncTracebackTrap |
|
32 | from IPython.kernel.core.sync_traceback_trap import SyncTracebackTrap | |
33 |
|
33 | |||
34 |
|
|
34 | import IPython.utils.io | |
35 |
|
35 | |||
36 | from linefrontendbase import LineFrontEndBase, common_prefix |
|
36 | from linefrontendbase import LineFrontEndBase, common_prefix | |
37 |
|
37 |
1 | NO CONTENT: file renamed from IPython/core/outputtrap.py to IPython/deathrow/outputtrap.py |
|
NO CONTENT: file renamed from IPython/core/outputtrap.py to IPython/deathrow/outputtrap.py |
@@ -14,7 +14,7 b' from IPython.core.iplib import InteractiveShell' | |||||
14 | from IPython.utils.ipstruct import Struct |
|
14 | from IPython.utils.ipstruct import Struct | |
15 | import Queue,thread,threading,signal |
|
15 | import Queue,thread,threading,signal | |
16 | from signal import signal, SIGINT |
|
16 | from signal import signal, SIGINT | |
17 |
|
|
17 | import IPython.utils.io, ask_yes_no | |
18 | from IPython.utils.warn import warn, error |
|
18 | from IPython.utils.warn import warn, error | |
19 | from IPython.utils.decorators import flag_calls |
|
19 | from IPython.utils.decorators import flag_calls | |
20 | from IPython.core import shellglobals |
|
20 | from IPython.core import shellglobals |
@@ -36,7 +36,7 b' class ParalleMagic(Plugin):' | |||||
36 |
|
36 | |||
37 | active_multiengine_client = Any() |
|
37 | active_multiengine_client = Any() | |
38 | verbose = Bool(False, config=True) |
|
38 | verbose = Bool(False, config=True) | |
39 |
shell = Instance('IPython.core.i |
|
39 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
40 |
|
40 | |||
41 | def __init__(self, shell=None, config=None): |
|
41 | def __init__(self, shell=None, config=None): | |
42 | super(ParalleMagic, self).__init__(shell=shell, config=config) |
|
42 | super(ParalleMagic, self).__init__(shell=shell, config=config) |
@@ -39,7 +39,7 b' from IPython.core.error import TryNext' | |||||
39 | from IPython.external import pretty |
|
39 | from IPython.external import pretty | |
40 | from IPython.core.plugin import Plugin |
|
40 | from IPython.core.plugin import Plugin | |
41 | from IPython.utils.traitlets import Bool, List, Instance |
|
41 | from IPython.utils.traitlets import Bool, List, Instance | |
42 |
|
|
42 | import IPython.utils.io | |
43 | from IPython.utils.autoattr import auto_attr |
|
43 | from IPython.utils.autoattr import auto_attr | |
44 | from IPython.utils.importstring import import_item |
|
44 | from IPython.utils.importstring import import_item | |
45 |
|
45 | |||
@@ -55,7 +55,7 b' class PrettyResultDisplay(Plugin):' | |||||
55 | """A component for pretty printing on steroids.""" |
|
55 | """A component for pretty printing on steroids.""" | |
56 |
|
56 | |||
57 | verbose = Bool(False, config=True) |
|
57 | verbose = Bool(False, config=True) | |
58 |
shell = Instance('IPython.core.i |
|
58 | shell = Instance('IPython.core.interactiveshell.InteractiveShellABC') | |
59 |
|
59 | |||
60 | # A list of (type, func_name), like |
|
60 | # A list of (type, func_name), like | |
61 | # [(dict, 'my_dict_printer')] |
|
61 | # [(dict, 'my_dict_printer')] | |
@@ -100,8 +100,8 b' class PrettyResultDisplay(Plugin):' | |||||
100 | # So that multi-line strings line up with the left column of |
|
100 | # So that multi-line strings line up with the left column of | |
101 | # the screen, instead of having the output prompt mess up |
|
101 | # the screen, instead of having the output prompt mess up | |
102 | # their first line. |
|
102 | # their first line. | |
103 | Term.cout.write('\n') |
|
103 | IPython.utils.io.Term.cout.write('\n') | |
104 | print >>Term.cout, out |
|
104 | print >>IPython.utils.io.Term.cout, out | |
105 | else: |
|
105 | else: | |
106 | raise TryNext |
|
106 | raise TryNext | |
107 |
|
107 |
@@ -18,7 +18,7 b' Simple tests for :mod:`IPython.extensions.pretty`.' | |||||
18 | from unittest import TestCase |
|
18 | from unittest import TestCase | |
19 |
|
19 | |||
20 | from IPython.config.configurable import Configurable |
|
20 | from IPython.config.configurable import Configurable | |
21 |
from IPython.core.i |
|
21 | from IPython.core.interactiveshell import InteractiveShellABC | |
22 | from IPython.extensions import pretty as pretty_ext |
|
22 | from IPython.extensions import pretty as pretty_ext | |
23 | from IPython.external import pretty |
|
23 | from IPython.external import pretty | |
24 | from IPython.testing import decorators as dec |
|
24 | from IPython.testing import decorators as dec |
@@ -30,8 +30,8 b' import sys' | |||||
30 | from contextlib import nested |
|
30 | from contextlib import nested | |
31 |
|
31 | |||
32 | from IPython.core import ultratb |
|
32 | from IPython.core import ultratb | |
33 |
from IPython. |
|
33 | from IPython.frontend.terminal.interactiveshell import TerminalInteractiveShell | |
34 |
from IPython. |
|
34 | from IPython.frontend.terminal.ipapp import load_default_config | |
35 |
|
35 | |||
36 | from IPython.utils.traitlets import Bool, Str, CBool |
|
36 | from IPython.utils.traitlets import Bool, Str, CBool | |
37 | from IPython.utils.io import ask_yes_no |
|
37 | from IPython.utils.io import ask_yes_no | |
@@ -59,7 +59,7 b" def kill_embedded(self,parameter_s=''):" | |||||
59 | print "This embedded IPython will not reactivate anymore once you exit." |
|
59 | print "This embedded IPython will not reactivate anymore once you exit." | |
60 |
|
60 | |||
61 |
|
61 | |||
62 | class InteractiveShellEmbed(InteractiveShell): |
|
62 | class InteractiveShellEmbed(TerminalInteractiveShell): | |
63 |
|
63 | |||
64 | dummy_mode = Bool(False) |
|
64 | dummy_mode = Bool(False) | |
65 | exit_msg = Str('') |
|
65 | exit_msg = Str('') | |
@@ -69,18 +69,19 b' class InteractiveShellEmbed(InteractiveShell):' | |||||
69 | # is True by default. |
|
69 | # is True by default. | |
70 | display_banner = CBool(True) |
|
70 | display_banner = CBool(True) | |
71 |
|
71 | |||
72 |
def __init__(self |
|
72 | def __init__(self, config=None, ipython_dir=None, user_ns=None, | |
73 |
user_ns=None, |
|
73 | user_global_ns=None, custom_exceptions=((),None), | |
74 |
banner1=None, banner2=None, |
|
74 | usage=None, banner1=None, banner2=None, | |
75 |
|
|
75 | display_banner=None, exit_msg=u''): | |
76 |
|
76 | |||
77 | self.save_sys_ipcompleter() |
|
77 | self.save_sys_ipcompleter() | |
78 |
|
78 | |||
79 | super(InteractiveShellEmbed,self).__init__( |
|
79 | super(InteractiveShellEmbed,self).__init__( | |
80 |
|
|
80 | config=config, ipython_dir=ipython_dir, user_ns=user_ns, | |
81 |
|
|
81 | user_global_ns=user_global_ns, custom_exceptions=custom_exceptions, | |
82 |
banner1=banner1, banner2=banner2, |
|
82 | usage=usage, banner1=banner1, banner2=banner2, | |
83 | custom_exceptions=custom_exceptions) |
|
83 | display_banner=display_banner | |
|
84 | ) | |||
84 |
|
85 | |||
85 | self.exit_msg = exit_msg |
|
86 | self.exit_msg = exit_msg | |
86 | self.define_magic("kill_embedded", kill_embedded) |
|
87 | self.define_magic("kill_embedded", kill_embedded) | |
@@ -240,8 +241,7 b' class InteractiveShellEmbed(InteractiveShell):' | |||||
240 | _embedded_shell = None |
|
241 | _embedded_shell = None | |
241 |
|
242 | |||
242 |
|
243 | |||
243 | def embed(header='', config=None, usage=None, banner1=None, banner2=None, |
|
244 | def embed(**kwargs): | |
244 | display_banner=True, exit_msg=''): |
|
|||
245 | """Call this to embed IPython at the current point in your program. |
|
245 | """Call this to embed IPython at the current point in your program. | |
246 |
|
246 | |||
247 | The first invocation of this will create an :class:`InteractiveShellEmbed` |
|
247 | The first invocation of this will create an :class:`InteractiveShellEmbed` | |
@@ -261,15 +261,12 b" def embed(header='', config=None, usage=None, banner1=None, banner2=None," | |||||
261 | Full customization can be done by passing a :class:`Struct` in as the |
|
261 | Full customization can be done by passing a :class:`Struct` in as the | |
262 | config argument. |
|
262 | config argument. | |
263 | """ |
|
263 | """ | |
|
264 | config = kwargs.get('config') | |||
|
265 | header = kwargs.pop('header', u'') | |||
264 | if config is None: |
|
266 | if config is None: | |
265 | config = load_default_config() |
|
267 | config = load_default_config() | |
266 | config.InteractiveShellEmbed = config.InteractiveShell |
|
268 | config.InteractiveShellEmbed = config.TerminalInteractiveShell | |
267 | global _embedded_shell |
|
269 | global _embedded_shell | |
268 | if _embedded_shell is None: |
|
270 | if _embedded_shell is None: | |
269 | _embedded_shell = InteractiveShellEmbed( |
|
271 | _embedded_shell = InteractiveShellEmbed(**kwargs) | |
270 | config=config, usage=usage, |
|
|||
271 | banner1=banner1, banner2=banner2, |
|
|||
272 | display_banner=display_banner, exit_msg=exit_msg |
|
|||
273 | ) |
|
|||
274 | _embedded_shell(header=header, stack_depth=2) |
|
272 | _embedded_shell(header=header, stack_depth=2) | |
275 |
|
@@ -31,14 +31,14 b' import sys' | |||||
31 | from IPython.core import release |
|
31 | from IPython.core import release | |
32 | from IPython.core.crashhandler import CrashHandler |
|
32 | from IPython.core.crashhandler import CrashHandler | |
33 | from IPython.core.application import Application, BaseAppConfigLoader |
|
33 | from IPython.core.application import Application, BaseAppConfigLoader | |
34 |
from IPython. |
|
34 | from IPython.frontend.terminal.interactiveshell import TerminalInteractiveShell | |
35 | from IPython.config.loader import ( |
|
35 | from IPython.config.loader import ( | |
36 | Config, |
|
36 | Config, | |
37 | PyFileConfigLoader |
|
37 | PyFileConfigLoader | |
38 | ) |
|
38 | ) | |
39 | from IPython.lib import inputhook |
|
39 | from IPython.lib import inputhook | |
40 | from IPython.utils.path import filefind, get_ipython_dir |
|
40 | from IPython.utils.path import filefind, get_ipython_dir | |
41 | from . import usage |
|
41 | from IPython.core import usage | |
42 |
|
42 | |||
43 | #----------------------------------------------------------------------------- |
|
43 | #----------------------------------------------------------------------------- | |
44 | # Globals, utilities and helpers |
|
44 | # Globals, utilities and helpers | |
@@ -99,10 +99,10 b' class IPAppConfigLoader(BaseAppConfigLoader):' | |||||
99 | action='store_false', dest='InteractiveShell.automagic', |
|
99 | action='store_false', dest='InteractiveShell.automagic', | |
100 | help='Turn off the auto calling of magic commands.') |
|
100 | help='Turn off the auto calling of magic commands.') | |
101 | paa('--autoedit-syntax', |
|
101 | paa('--autoedit-syntax', | |
102 | action='store_true', dest='InteractiveShell.autoedit_syntax', |
|
102 | action='store_true', dest='TerminalInteractiveShell.autoedit_syntax', | |
103 | help='Turn on auto editing of files with syntax errors.') |
|
103 | help='Turn on auto editing of files with syntax errors.') | |
104 | paa('--no-autoedit-syntax', |
|
104 | paa('--no-autoedit-syntax', | |
105 | action='store_false', dest='InteractiveShell.autoedit_syntax', |
|
105 | action='store_false', dest='TerminalInteractiveShell.autoedit_syntax', | |
106 | help='Turn off auto editing of files with syntax errors.') |
|
106 | help='Turn off auto editing of files with syntax errors.') | |
107 | paa('--banner', |
|
107 | paa('--banner', | |
108 | action='store_true', dest='Global.display_banner', |
|
108 | action='store_true', dest='Global.display_banner', | |
@@ -143,13 +143,13 b' class IPAppConfigLoader(BaseAppConfigLoader):' | |||||
143 | action='store_false', dest='InteractiveShell.color_info', |
|
143 | action='store_false', dest='InteractiveShell.color_info', | |
144 | help="Disable using colors for info related things.") |
|
144 | help="Disable using colors for info related things.") | |
145 | paa('--confirm-exit', |
|
145 | paa('--confirm-exit', | |
146 | action='store_true', dest='InteractiveShell.confirm_exit', |
|
146 | action='store_true', dest='TerminalInteractiveShell.confirm_exit', | |
147 | help= |
|
147 | help= | |
148 | """Set to confirm when you try to exit IPython with an EOF (Control-D |
|
148 | """Set to confirm when you try to exit IPython with an EOF (Control-D | |
149 | in Unix, Control-Z/Enter in Windows). By typing 'exit', 'quit' or |
|
149 | in Unix, Control-Z/Enter in Windows). By typing 'exit', 'quit' or | |
150 | '%%Exit', you can force a direct exit without any confirmation.""") |
|
150 | '%%Exit', you can force a direct exit without any confirmation.""") | |
151 | paa('--no-confirm-exit', |
|
151 | paa('--no-confirm-exit', | |
152 | action='store_false', dest='InteractiveShell.confirm_exit', |
|
152 | action='store_false', dest='TerminalInteractiveShell.confirm_exit', | |
153 | help="Don't prompt the user when exiting.") |
|
153 | help="Don't prompt the user when exiting.") | |
154 | paa('--deep-reload', |
|
154 | paa('--deep-reload', | |
155 | action='store_true', dest='InteractiveShell.deep_reload', |
|
155 | action='store_true', dest='InteractiveShell.deep_reload', | |
@@ -167,9 +167,9 b' class IPAppConfigLoader(BaseAppConfigLoader):' | |||||
167 | action='store_false', dest='InteractiveShell.deep_reload', |
|
167 | action='store_false', dest='InteractiveShell.deep_reload', | |
168 | help="Disable deep (recursive) reloading by default.") |
|
168 | help="Disable deep (recursive) reloading by default.") | |
169 | paa('--editor', |
|
169 | paa('--editor', | |
170 | type=str, dest='InteractiveShell.editor', |
|
170 | type=str, dest='TerminalInteractiveShell.editor', | |
171 | help="Set the editor used by IPython (default to $EDITOR/vi/notepad).", |
|
171 | help="Set the editor used by IPython (default to $EDITOR/vi/notepad).", | |
172 | metavar='InteractiveShell.editor') |
|
172 | metavar='TerminalInteractiveShell.editor') | |
173 | paa('--log','-l', |
|
173 | paa('--log','-l', | |
174 | action='store_true', dest='InteractiveShell.logstart', |
|
174 | action='store_true', dest='InteractiveShell.logstart', | |
175 | help="Start logging to the default log file (./ipython_log.py).") |
|
175 | help="Start logging to the default log file (./ipython_log.py).") | |
@@ -228,7 +228,7 b' class IPAppConfigLoader(BaseAppConfigLoader):' | |||||
228 | action='store_false', dest='InteractiveShell.readline_use', |
|
228 | action='store_false', dest='InteractiveShell.readline_use', | |
229 | help="Disable readline for command line usage.") |
|
229 | help="Disable readline for command line usage.") | |
230 | paa('--screen-length','-sl', |
|
230 | paa('--screen-length','-sl', | |
231 | type=int, dest='InteractiveShell.screen_length', |
|
231 | type=int, dest='TerminalInteractiveShell.screen_length', | |
232 | help= |
|
232 | help= | |
233 | """Number of lines of your screen, used to control printing of very |
|
233 | """Number of lines of your screen, used to control printing of very | |
234 | long strings. Strings longer than this number of lines will be sent |
|
234 | long strings. Strings longer than this number of lines will be sent | |
@@ -239,7 +239,7 b' class IPAppConfigLoader(BaseAppConfigLoader):' | |||||
239 | internally). If for some reason this isn't working well (it needs |
|
239 | internally). If for some reason this isn't working well (it needs | |
240 | curses support), specify it yourself. Otherwise don't change the |
|
240 | curses support), specify it yourself. Otherwise don't change the | |
241 | default.""", |
|
241 | default.""", | |
242 | metavar='InteractiveShell.screen_length') |
|
242 | metavar='TerminalInteractiveShell.screen_length') | |
243 | paa('--separate-in','-si', |
|
243 | paa('--separate-in','-si', | |
244 | type=str, dest='InteractiveShell.separate_in', |
|
244 | type=str, dest='InteractiveShell.separate_in', | |
245 | help="Separator before input prompts. Default '\\n'.", |
|
245 | help="Separator before input prompts. Default '\\n'.", | |
@@ -256,10 +256,10 b' class IPAppConfigLoader(BaseAppConfigLoader):' | |||||
256 | action='store_true', dest='Global.nosep', |
|
256 | action='store_true', dest='Global.nosep', | |
257 | help="Eliminate all spacing between prompts.") |
|
257 | help="Eliminate all spacing between prompts.") | |
258 | paa('--term-title', |
|
258 | paa('--term-title', | |
259 | action='store_true', dest='InteractiveShell.term_title', |
|
259 | action='store_true', dest='TerminalInteractiveShell.term_title', | |
260 | help="Enable auto setting the terminal title.") |
|
260 | help="Enable auto setting the terminal title.") | |
261 | paa('--no-term-title', |
|
261 | paa('--no-term-title', | |
262 | action='store_false', dest='InteractiveShell.term_title', |
|
262 | action='store_false', dest='TerminalInteractiveShell.term_title', | |
263 | help="Disable auto setting the terminal title.") |
|
263 | help="Disable auto setting the terminal title.") | |
264 | paa('--xmode', |
|
264 | paa('--xmode', | |
265 | type=str, dest='InteractiveShell.xmode', |
|
265 | type=str, dest='InteractiveShell.xmode', | |
@@ -476,7 +476,7 b' class IPythonApp(Application):' | |||||
476 | sys.path.insert(0, '') |
|
476 | sys.path.insert(0, '') | |
477 |
|
477 | |||
478 | # Create an InteractiveShell instance. |
|
478 | # Create an InteractiveShell instance. | |
479 | self.shell = InteractiveShell.instance(config=self.master_config) |
|
479 | self.shell = TerminalInteractiveShell.instance(config=self.master_config) | |
480 |
|
480 | |||
481 | def post_construct(self): |
|
481 | def post_construct(self): | |
482 | """Do actions after construct, but before starting the app.""" |
|
482 | """Do actions after construct, but before starting the app.""" |
@@ -1,6 +1,6 b'' | |||||
1 | #!/usr/bin/env python |
|
1 | #!/usr/bin/env python | |
2 | # -*- coding: utf-8 -*- |
|
2 | # -*- coding: utf-8 -*- | |
3 |
|
3 | |||
4 |
from IPython. |
|
4 | from IPython.frontend.terminal.ipapp import launch_new_instance | |
5 |
|
5 | |||
6 | launch_new_instance() |
|
6 | launch_new_instance() |
@@ -32,7 +32,7 b' class IConfiguredObjectFactory(zi.Interface):' | |||||
32 | subclass of :class:`IPython.config.configurable.Configurable`. |
|
32 | subclass of :class:`IPython.config.configurable.Configurable`. | |
33 | """ |
|
33 | """ | |
34 |
|
34 | |||
35 | def __init__(config): |
|
35 | def __init__(config=None): | |
36 | """Get ready to configure the object using config.""" |
|
36 | """Get ready to configure the object using config.""" | |
37 |
|
37 | |||
38 | def create(): |
|
38 | def create(): |
@@ -32,7 +32,7 b' from IPython.external.Itpl import ItplNS' | |||||
32 | from IPython.utils import coloransi |
|
32 | from IPython.utils import coloransi | |
33 | from IPython.core import release |
|
33 | from IPython.core import release | |
34 | from IPython.core.error import TryNext |
|
34 | from IPython.core.error import TryNext | |
35 |
|
|
35 | import IPython.utils.io | |
36 | from IPython.utils.warn import warn |
|
36 | from IPython.utils.warn import warn | |
37 | import IPython.utils.generics |
|
37 | import IPython.utils.generics | |
38 |
|
38 |
@@ -212,8 +212,8 b' class FCServiceFactory(AdaptedConfiguredObjectFactory):' | |||||
212 | reuse_furls = Bool(False, config=True) |
|
212 | reuse_furls = Bool(False, config=True) | |
213 | interfaces = Instance(klass=Config, kw={}, allow_none=False, config=True) |
|
213 | interfaces = Instance(klass=Config, kw={}, allow_none=False, config=True) | |
214 |
|
214 | |||
215 | def __init__(self, config, adaptee): |
|
215 | def __init__(self, config=None, adaptee=None): | |
216 | super(FCServiceFactory, self).__init__(config, adaptee) |
|
216 | super(FCServiceFactory, self).__init__(config=config, adaptee=adaptee) | |
217 | self._check_reuse_furls() |
|
217 | self._check_reuse_furls() | |
218 |
|
218 | |||
219 | def _ip_changed(self, name, old, new): |
|
219 | def _ip_changed(self, name, old, new): |
@@ -225,7 +225,7 b' class IPControllerApp(ApplicationWithClusterDir):' | |||||
225 | controller_service.setServiceParent(self.main_service) |
|
225 | controller_service.setServiceParent(self.main_service) | |
226 | # The client tub and all its refereceables |
|
226 | # The client tub and all its refereceables | |
227 | try: |
|
227 | try: | |
228 | csfactory = FCClientServiceFactory(self.master_config, controller_service) |
|
228 | csfactory = FCClientServiceFactory(config=self.master_config, adaptee=controller_service) | |
229 | except FURLError, e: |
|
229 | except FURLError, e: | |
230 | log.err(e) |
|
230 | log.err(e) | |
231 | self.exit(0) |
|
231 | self.exit(0) | |
@@ -233,7 +233,7 b' class IPControllerApp(ApplicationWithClusterDir):' | |||||
233 | client_service.setServiceParent(self.main_service) |
|
233 | client_service.setServiceParent(self.main_service) | |
234 | # The engine tub |
|
234 | # The engine tub | |
235 | try: |
|
235 | try: | |
236 | esfactory = FCEngineServiceFactory(self.master_config, controller_service) |
|
236 | esfactory = FCEngineServiceFactory(config=self.master_config, adaptee=controller_service) | |
237 | except FURLError, e: |
|
237 | except FURLError, e: | |
238 | log.err(e) |
|
238 | log.err(e) | |
239 | self.exit(0) |
|
239 | self.exit(0) |
@@ -176,7 +176,8 b' import shlex' | |||||
176 | import sys |
|
176 | import sys | |
177 |
|
177 | |||
178 | from IPython.utils.PyColorize import Parser |
|
178 | from IPython.utils.PyColorize import Parser | |
179 |
from IPython.utils.io import file_read, file_readlines |
|
179 | from IPython.utils.io import file_read, file_readlines | |
|
180 | import IPython.utils.io | |||
180 | from IPython.utils.text import marquee |
|
181 | from IPython.utils.text import marquee | |
181 |
|
182 | |||
182 | __all__ = ['Demo','IPythonDemo','LineDemo','IPythonLineDemo','DemoError'] |
|
183 | __all__ = ['Demo','IPythonDemo','LineDemo','IPythonLineDemo','DemoError'] | |
@@ -318,7 +319,7 b' class Demo(object):' | |||||
318 |
|
319 | |||
319 | if index is None: |
|
320 | if index is None: | |
320 | if self.finished: |
|
321 | if self.finished: | |
321 | print >>Term.cout, 'Demo finished. Use <demo_name>.reset() if you want to rerun it.' |
|
322 | print >>IPython.utils.io.Term.cout, 'Demo finished. Use <demo_name>.reset() if you want to rerun it.' | |
322 | return None |
|
323 | return None | |
323 | index = self.block_index |
|
324 | index = self.block_index | |
324 | else: |
|
325 | else: | |
@@ -387,9 +388,9 b' class Demo(object):' | |||||
387 | if index is None: |
|
388 | if index is None: | |
388 | return |
|
389 | return | |
389 |
|
390 | |||
390 | print >>Term.cout, self.marquee('<%s> block # %s (%s remaining)' % |
|
391 | print >>IPython.utils.io.Term.cout, self.marquee('<%s> block # %s (%s remaining)' % | |
391 | (self.title,index,self.nblocks-index-1)) |
|
392 | (self.title,index,self.nblocks-index-1)) | |
392 | print >>Term.cout,(self.src_blocks_colored[index]) |
|
393 | print >>IPython.utils.io.Term.cout,(self.src_blocks_colored[index]) | |
393 | sys.stdout.flush() |
|
394 | sys.stdout.flush() | |
394 |
|
395 | |||
395 | def show_all(self): |
|
396 | def show_all(self): | |
@@ -402,12 +403,12 b' class Demo(object):' | |||||
402 | marquee = self.marquee |
|
403 | marquee = self.marquee | |
403 | for index,block in enumerate(self.src_blocks_colored): |
|
404 | for index,block in enumerate(self.src_blocks_colored): | |
404 | if silent[index]: |
|
405 | if silent[index]: | |
405 | print >>Term.cout, marquee('<%s> SILENT block # %s (%s remaining)' % |
|
406 | print >>IPython.utils.io.Term.cout, marquee('<%s> SILENT block # %s (%s remaining)' % | |
406 | (title,index,nblocks-index-1)) |
|
407 | (title,index,nblocks-index-1)) | |
407 | else: |
|
408 | else: | |
408 | print >>Term.cout, marquee('<%s> block # %s (%s remaining)' % |
|
409 | print >>IPython.utils.io.Term.cout, marquee('<%s> block # %s (%s remaining)' % | |
409 | (title,index,nblocks-index-1)) |
|
410 | (title,index,nblocks-index-1)) | |
410 | print >>Term.cout, block, |
|
411 | print >>IPython.utils.io.Term.cout, block, | |
411 | sys.stdout.flush() |
|
412 | sys.stdout.flush() | |
412 |
|
413 | |||
413 | def runlines(self,source): |
|
414 | def runlines(self,source): | |
@@ -432,18 +433,18 b' class Demo(object):' | |||||
432 | next_block = self.src_blocks[index] |
|
433 | next_block = self.src_blocks[index] | |
433 | self.block_index += 1 |
|
434 | self.block_index += 1 | |
434 | if self._silent[index]: |
|
435 | if self._silent[index]: | |
435 | print >>Term.cout, marquee('Executing silent block # %s (%s remaining)' % |
|
436 | print >>IPython.utils.io.Term.cout, marquee('Executing silent block # %s (%s remaining)' % | |
436 | (index,self.nblocks-index-1)) |
|
437 | (index,self.nblocks-index-1)) | |
437 | else: |
|
438 | else: | |
438 | self.pre_cmd() |
|
439 | self.pre_cmd() | |
439 | self.show(index) |
|
440 | self.show(index) | |
440 | if self.auto_all or self._auto[index]: |
|
441 | if self.auto_all or self._auto[index]: | |
441 | print >>Term.cout, marquee('output:') |
|
442 | print >>IPython.utils.io.Term.cout, marquee('output:') | |
442 | else: |
|
443 | else: | |
443 | print >>Term.cout, marquee('Press <q> to quit, <Enter> to execute...'), |
|
444 | print >>IPython.utils.io.Term.cout, marquee('Press <q> to quit, <Enter> to execute...'), | |
444 | ans = raw_input().strip() |
|
445 | ans = raw_input().strip() | |
445 | if ans: |
|
446 | if ans: | |
446 | print >>Term.cout, marquee('Block NOT executed') |
|
447 | print >>IPython.utils.io.Term.cout, marquee('Block NOT executed') | |
447 | return |
|
448 | return | |
448 | try: |
|
449 | try: | |
449 | save_argv = sys.argv |
|
450 | save_argv = sys.argv | |
@@ -461,10 +462,10 b' class Demo(object):' | |||||
461 | if self.block_index == self.nblocks: |
|
462 | if self.block_index == self.nblocks: | |
462 | mq1 = self.marquee('END OF DEMO') |
|
463 | mq1 = self.marquee('END OF DEMO') | |
463 | if mq1: |
|
464 | if mq1: | |
464 | # avoid spurious print >>Term.cout,s if empty marquees are used |
|
465 | # avoid spurious print >>IPython.utils.io.Term.cout,s if empty marquees are used | |
465 | print >>Term.cout |
|
466 | print >>IPython.utils.io.Term.cout | |
466 | print >>Term.cout, mq1 |
|
467 | print >>IPython.utils.io.Term.cout, mq1 | |
467 | print >>Term.cout, self.marquee('Use <demo_name>.reset() if you want to rerun it.') |
|
468 | print >>IPython.utils.io.Term.cout, self.marquee('Use <demo_name>.reset() if you want to rerun it.') | |
468 | self.finished = True |
|
469 | self.finished = True | |
469 |
|
470 | |||
470 | # These methods are meant to be overridden by subclasses who may wish to |
|
471 | # These methods are meant to be overridden by subclasses who may wish to |
@@ -114,8 +114,7 b' def start_ipython():' | |||||
114 | return |
|
114 | return | |
115 | start_ipython.already_called = True |
|
115 | start_ipython.already_called = True | |
116 |
|
116 | |||
117 | # Ok, first time we're called, go ahead |
|
117 | from IPython.frontend.terminal import interactiveshell | |
118 | from IPython.core import iplib |
|
|||
119 |
|
118 | |||
120 | def xsys(cmd): |
|
119 | def xsys(cmd): | |
121 | """Execute a command and print its output. |
|
120 | """Execute a command and print its output. | |
@@ -136,7 +135,7 b' def start_ipython():' | |||||
136 | config = tools.default_config() |
|
135 | config = tools.default_config() | |
137 |
|
136 | |||
138 | # Create and initialize our test-friendly IPython instance. |
|
137 | # Create and initialize our test-friendly IPython instance. | |
139 |
shell = i |
|
138 | shell = interactiveshell.TerminalInteractiveShell.instance( | |
140 | config=config, |
|
139 | config=config, | |
141 | user_ns=ipnsdict(), user_global_ns={} |
|
140 | user_ns=ipnsdict(), user_global_ns={} | |
142 | ) |
|
141 | ) |
@@ -153,10 +153,6 b' def make_exclude():' | |||||
153 | ipjoin = lambda *paths: pjoin('IPython', *paths) |
|
153 | ipjoin = lambda *paths: pjoin('IPython', *paths) | |
154 |
|
154 | |||
155 | exclusions = [ipjoin('external'), |
|
155 | exclusions = [ipjoin('external'), | |
156 | # Deprecated old Shell and iplib modules, skip to avoid |
|
|||
157 | # warnings |
|
|||
158 | ipjoin('Shell'), |
|
|||
159 | ipjoin('iplib'), |
|
|||
160 | pjoin('IPython_doctest_plugin'), |
|
156 | pjoin('IPython_doctest_plugin'), | |
161 | ipjoin('quarantine'), |
|
157 | ipjoin('quarantine'), | |
162 | ipjoin('deathrow'), |
|
158 | ipjoin('deathrow'), |
@@ -8,7 +8,7 b' NOSE=nosetests -vvs --with-ipdoctest --doctest-tests --doctest-extension=txt \\' | |||||
8 | SRC=ipdoctest.py setup.py ../decorators.py |
|
8 | SRC=ipdoctest.py setup.py ../decorators.py | |
9 |
|
9 | |||
10 | # Default target for clean 'make' |
|
10 | # Default target for clean 'make' | |
11 | default: iplib |
|
11 | default: interactiveshell | |
12 |
|
12 | |||
13 | # The actual plugin installation |
|
13 | # The actual plugin installation | |
14 | plugin: IPython_doctest_plugin.egg-info |
|
14 | plugin: IPython_doctest_plugin.egg-info | |
@@ -39,8 +39,8 b' magic: plugin' | |||||
39 | excolors: plugin |
|
39 | excolors: plugin | |
40 | $(NOSE) IPython.core.excolors |
|
40 | $(NOSE) IPython.core.excolors | |
41 |
|
41 | |||
42 | iplib: plugin |
|
42 | interactiveshell: plugin | |
43 |
$(NOSE) IPython.core.i |
|
43 | $(NOSE) IPython.core.interactiveshell | |
44 |
|
44 | |||
45 | strd: plugin |
|
45 | strd: plugin | |
46 | $(NOSE) IPython.core.strdispatch |
|
46 | $(NOSE) IPython.core.strdispatch | |
@@ -61,7 +61,7 b' sr: rtest strd' | |||||
61 |
|
61 | |||
62 | base: dtest rtest test strd deco |
|
62 | base: dtest rtest test strd deco | |
63 |
|
63 | |||
64 |
quick: base i |
|
64 | quick: base interactiveshell ipipe | |
65 |
|
65 | |||
66 | all: base ipython |
|
66 | all: base ipython | |
67 |
|
67 |
@@ -164,9 +164,9 b' def default_argv():' | |||||
164 | def default_config(): |
|
164 | def default_config(): | |
165 | """Return a config object with good defaults for testing.""" |
|
165 | """Return a config object with good defaults for testing.""" | |
166 | config = Config() |
|
166 | config = Config() | |
167 | config.InteractiveShell.colors = 'NoColor' |
|
167 | config.TerminalInteractiveShell.colors = 'NoColor' | |
168 | config.InteractiveShell.term_title = False, |
|
168 | config.TerminalTerminalInteractiveShell.term_title = False, | |
169 | config.InteractiveShell.autocall = 0 |
|
169 | config.TerminalInteractiveShell.autocall = 0 | |
170 | return config |
|
170 | return config | |
171 |
|
171 | |||
172 |
|
172 |
@@ -65,21 +65,10 b' class IOTerm:' | |||||
65 | # In the future, having IPython channel all its I/O operations through |
|
65 | # In the future, having IPython channel all its I/O operations through | |
66 | # this class will make it easier to embed it into other environments which |
|
66 | # this class will make it easier to embed it into other environments which | |
67 | # are not a normal terminal (such as a GUI-based shell) |
|
67 | # are not a normal terminal (such as a GUI-based shell) | |
68 | def __init__(self,cin=None,cout=None,cerr=None): |
|
68 | def __init__(self, cin=None, cout=None, cerr=None): | |
69 | self.cin = IOStream(cin,sys.stdin) |
|
69 | self.cin = IOStream(cin, sys.stdin) | |
70 | self.cout = IOStream(cout,sys.stdout) |
|
70 | self.cout = IOStream(cout, sys.stdout) | |
71 | self.cerr = IOStream(cerr,sys.stderr) |
|
71 | self.cerr = IOStream(cerr, sys.stderr) | |
72 |
|
||||
73 |
|
||||
74 | # Global variable to be used for all I/O |
|
|||
75 | Term = IOTerm() |
|
|||
76 |
|
||||
77 |
|
||||
78 | import IPython.utils.rlineimpl as readline |
|
|||
79 | # Remake Term to use the readline i/o facilities |
|
|||
80 | if sys.platform == 'win32' and readline.have_readline: |
|
|||
81 |
|
||||
82 | Term = IOTerm(cout=readline._outputfile,cerr=readline._outputfile) |
|
|||
83 |
|
72 | |||
84 |
|
73 | |||
85 | class Tee(object): |
|
74 | class Tee(object): |
@@ -77,7 +77,7 b' def find_cmd(cmd):' | |||||
77 |
|
77 | |||
78 | from IPython.utils.path import get_ipython_module_path |
|
78 | from IPython.utils.path import get_ipython_module_path | |
79 | from IPython.utils.process import pycmd2argv |
|
79 | from IPython.utils.process import pycmd2argv | |
80 |
argv = pycmd2argv(get_ipython_module_path('IPython. |
|
80 | argv = pycmd2argv(get_ipython_module_path('IPython.frontend.terminal.ipapp')) | |
81 |
|
81 | |||
82 | Parameters |
|
82 | Parameters | |
83 | ---------- |
|
83 | ---------- |
@@ -255,7 +255,7 b' def test_get_ipython_package_dir():' | |||||
255 |
|
255 | |||
256 |
|
256 | |||
257 | def test_get_ipython_module_path(): |
|
257 | def test_get_ipython_module_path(): | |
258 |
ipapp_path = path.get_ipython_module_path('IPython. |
|
258 | ipapp_path = path.get_ipython_module_path('IPython.frontend.terminal.ipapp') | |
259 | nt.assert_true(os.path.isfile(ipapp_path)) |
|
259 | nt.assert_true(os.path.isfile(ipapp_path)) | |
260 |
|
260 | |||
261 |
|
261 |
@@ -471,3 +471,14 b" def marquee(txt='',width=78,mark='*'):" | |||||
471 | return '%s %s %s' % (marks,txt,marks) |
|
471 | return '%s %s %s' % (marks,txt,marks) | |
472 |
|
472 | |||
473 |
|
473 | |||
|
474 | ini_spaces_re = re.compile(r'^(\s+)') | |||
|
475 | ||||
|
476 | def num_ini_spaces(strng): | |||
|
477 | """Return the number of initial spaces in a string""" | |||
|
478 | ||||
|
479 | ini_spaces = ini_spaces_re.match(strng) | |||
|
480 | if ini_spaces: | |||
|
481 | return ini_spaces.end() | |||
|
482 | else: | |||
|
483 | return 0 | |||
|
484 |
@@ -16,7 +16,7 b" Utilities for warnings. Shoudn't we just use the built in warnings module." | |||||
16 |
|
16 | |||
17 | import sys |
|
17 | import sys | |
18 |
|
18 | |||
19 |
|
|
19 | import IPython.utils.io | |
20 |
|
20 | |||
21 | #----------------------------------------------------------------------------- |
|
21 | #----------------------------------------------------------------------------- | |
22 | # Code |
|
22 | # Code | |
@@ -25,7 +25,7 b' from IPython.utils.io import Term' | |||||
25 | def warn(msg,level=2,exit_val=1): |
|
25 | def warn(msg,level=2,exit_val=1): | |
26 | """Standard warning printer. Gives formatting consistency. |
|
26 | """Standard warning printer. Gives formatting consistency. | |
27 |
|
27 | |||
28 | Output is sent to Term.cerr (sys.stderr by default). |
|
28 | Output is sent to IPython.utils.io.Term.cerr (sys.stderr by default). | |
29 |
|
29 | |||
30 | Options: |
|
30 | Options: | |
31 |
|
31 | |||
@@ -41,9 +41,9 b' def warn(msg,level=2,exit_val=1):' | |||||
41 |
|
41 | |||
42 | if level>0: |
|
42 | if level>0: | |
43 | header = ['','','WARNING: ','ERROR: ','FATAL ERROR: '] |
|
43 | header = ['','','WARNING: ','ERROR: ','FATAL ERROR: '] | |
44 | print >> Term.cerr, '%s%s' % (header[level],msg) |
|
44 | print >> IPython.utils.io.Term.cerr, '%s%s' % (header[level],msg) | |
45 | if level == 4: |
|
45 | if level == 4: | |
46 | print >> Term.cerr,'Exiting.\n' |
|
46 | print >> IPython.utils.io.Term.cerr,'Exiting.\n' | |
47 | sys.exit(exit_val) |
|
47 | sys.exit(exit_val) | |
48 |
|
48 | |||
49 |
|
49 |
@@ -30,7 +30,7 b' from zmq.eventloop import ioloop' | |||||
30 |
|
30 | |||
31 | # Local imports. |
|
31 | # Local imports. | |
32 | from IPython.utils.traitlets import HasTraits, Any, Instance, Type, TCPAddress |
|
32 | from IPython.utils.traitlets import HasTraits, Any, Instance, Type, TCPAddress | |
33 | from kernel import launch_kernel |
|
33 | from ipkernel import launch_kernel | |
34 | from session import Session |
|
34 | from session import Session | |
35 |
|
35 | |||
36 | #----------------------------------------------------------------------------- |
|
36 | #----------------------------------------------------------------------------- |
@@ -3,7 +3,6 b'' | |||||
3 |
|
3 | |||
4 | Things to do: |
|
4 | Things to do: | |
5 |
|
5 | |||
6 | * Finish implementing `raw_input`. |
|
|||
7 | * Implement `set_parent` logic. Right before doing exec, the Kernel should |
|
6 | * Implement `set_parent` logic. Right before doing exec, the Kernel should | |
8 | call set_parent on all the PUB objects with the message about to be executed. |
|
7 | call set_parent on all the PUB objects with the message about to be executed. | |
9 | * Implement random port and security key logic. |
|
8 | * Implement random port and security key logic. | |
@@ -18,10 +17,8 b' Things to do:' | |||||
18 | # Standard library imports. |
|
17 | # Standard library imports. | |
19 | import __builtin__ |
|
18 | import __builtin__ | |
20 | from code import CommandCompiler |
|
19 | from code import CommandCompiler | |
21 | from cStringIO import StringIO |
|
|||
22 | import os |
|
20 | import os | |
23 | import sys |
|
21 | import sys | |
24 | from threading import Thread |
|
|||
25 | import time |
|
22 | import time | |
26 | import traceback |
|
23 | import traceback | |
27 |
|
24 | |||
@@ -30,100 +27,16 b' import zmq' | |||||
30 |
|
27 | |||
31 | # Local imports. |
|
28 | # Local imports. | |
32 | from IPython.external.argparse import ArgumentParser |
|
29 | from IPython.external.argparse import ArgumentParser | |
33 |
from session import Session, Message |
|
30 | from session import Session, Message | |
34 | from completer import KernelCompleter |
|
31 | from completer import KernelCompleter | |
|
32 | from iostream import OutStream | |||
|
33 | from displayhook import DisplayHook | |||
|
34 | from exitpoller import ExitPollerUnix, ExitPollerWindows | |||
35 |
|
35 | |||
36 | #----------------------------------------------------------------------------- |
|
36 | #----------------------------------------------------------------------------- | |
37 | # Kernel and stream classes |
|
37 | # Main kernel class | |
38 | #----------------------------------------------------------------------------- |
|
38 | #----------------------------------------------------------------------------- | |
39 |
|
39 | |||
40 | class OutStream(object): |
|
|||
41 | """A file like object that publishes the stream to a 0MQ PUB socket.""" |
|
|||
42 |
|
||||
43 | # The time interval between automatic flushes, in seconds. |
|
|||
44 | flush_interval = 0.05 |
|
|||
45 |
|
||||
46 | def __init__(self, session, pub_socket, name): |
|
|||
47 | self.session = session |
|
|||
48 | self.pub_socket = pub_socket |
|
|||
49 | self.name = name |
|
|||
50 | self.parent_header = {} |
|
|||
51 | self._new_buffer() |
|
|||
52 |
|
||||
53 | def set_parent(self, parent): |
|
|||
54 | self.parent_header = extract_header(parent) |
|
|||
55 |
|
||||
56 | def close(self): |
|
|||
57 | self.pub_socket = None |
|
|||
58 |
|
||||
59 | def flush(self): |
|
|||
60 | if self.pub_socket is None: |
|
|||
61 | raise ValueError(u'I/O operation on closed file') |
|
|||
62 | else: |
|
|||
63 | data = self._buffer.getvalue() |
|
|||
64 | if data: |
|
|||
65 | content = {u'name':self.name, u'data':data} |
|
|||
66 | msg = self.session.msg(u'stream', content=content, |
|
|||
67 | parent=self.parent_header) |
|
|||
68 | print>>sys.__stdout__, Message(msg) |
|
|||
69 | self.pub_socket.send_json(msg) |
|
|||
70 |
|
||||
71 | self._buffer.close() |
|
|||
72 | self._new_buffer() |
|
|||
73 |
|
||||
74 | def isatty(self): |
|
|||
75 | return False |
|
|||
76 |
|
||||
77 | def next(self): |
|
|||
78 | raise IOError('Read not supported on a write only stream.') |
|
|||
79 |
|
||||
80 | def read(self, size=-1): |
|
|||
81 | raise IOError('Read not supported on a write only stream.') |
|
|||
82 |
|
||||
83 | def readline(self, size=-1): |
|
|||
84 | raise IOError('Read not supported on a write only stream.') |
|
|||
85 |
|
||||
86 | def write(self, string): |
|
|||
87 | if self.pub_socket is None: |
|
|||
88 | raise ValueError('I/O operation on closed file') |
|
|||
89 | else: |
|
|||
90 | self._buffer.write(string) |
|
|||
91 | current_time = time.time() |
|
|||
92 | if self._start <= 0: |
|
|||
93 | self._start = current_time |
|
|||
94 | elif current_time - self._start > self.flush_interval: |
|
|||
95 | self.flush() |
|
|||
96 |
|
||||
97 | def writelines(self, sequence): |
|
|||
98 | if self.pub_socket is None: |
|
|||
99 | raise ValueError('I/O operation on closed file') |
|
|||
100 | else: |
|
|||
101 | for string in sequence: |
|
|||
102 | self.write(string) |
|
|||
103 |
|
||||
104 | def _new_buffer(self): |
|
|||
105 | self._buffer = StringIO() |
|
|||
106 | self._start = -1 |
|
|||
107 |
|
||||
108 |
|
||||
109 | class DisplayHook(object): |
|
|||
110 |
|
||||
111 | def __init__(self, session, pub_socket): |
|
|||
112 | self.session = session |
|
|||
113 | self.pub_socket = pub_socket |
|
|||
114 | self.parent_header = {} |
|
|||
115 |
|
||||
116 | def __call__(self, obj): |
|
|||
117 | if obj is not None: |
|
|||
118 | __builtin__._ = obj |
|
|||
119 | msg = self.session.msg(u'pyout', {u'data':repr(obj)}, |
|
|||
120 | parent=self.parent_header) |
|
|||
121 | self.pub_socket.send_json(msg) |
|
|||
122 |
|
||||
123 | def set_parent(self, parent): |
|
|||
124 | self.parent_header = extract_header(parent) |
|
|||
125 |
|
||||
126 |
|
||||
127 | class Kernel(object): |
|
40 | class Kernel(object): | |
128 |
|
41 | |||
129 | # The global kernel instance. |
|
42 | # The global kernel instance. | |
@@ -267,7 +180,6 b' class Kernel(object):' | |||||
267 |
|
180 | |||
268 | exec comp_code in self.user_ns, self.user_ns |
|
181 | exec comp_code in self.user_ns, self.user_ns | |
269 | except: |
|
182 | except: | |
270 | result = u'error' |
|
|||
271 | etype, evalue, tb = sys.exc_info() |
|
183 | etype, evalue, tb = sys.exc_info() | |
272 | tb = traceback.format_exception(etype, evalue, tb) |
|
184 | tb = traceback.format_exception(etype, evalue, tb) | |
273 | exc_content = { |
|
185 | exc_content = { | |
@@ -388,45 +300,6 b' class Kernel(object):' | |||||
388 | # Kernel main and launch functions |
|
300 | # Kernel main and launch functions | |
389 | #----------------------------------------------------------------------------- |
|
301 | #----------------------------------------------------------------------------- | |
390 |
|
302 | |||
391 | class ExitPollerUnix(Thread): |
|
|||
392 | """ A Unix-specific daemon thread that terminates the program immediately |
|
|||
393 | when the parent process no longer exists. |
|
|||
394 | """ |
|
|||
395 |
|
||||
396 | def __init__(self): |
|
|||
397 | super(ExitPollerUnix, self).__init__() |
|
|||
398 | self.daemon = True |
|
|||
399 |
|
||||
400 | def run(self): |
|
|||
401 | # We cannot use os.waitpid because it works only for child processes. |
|
|||
402 | from errno import EINTR |
|
|||
403 | while True: |
|
|||
404 | try: |
|
|||
405 | if os.getppid() == 1: |
|
|||
406 | os._exit(1) |
|
|||
407 | time.sleep(1.0) |
|
|||
408 | except OSError, e: |
|
|||
409 | if e.errno == EINTR: |
|
|||
410 | continue |
|
|||
411 | raise |
|
|||
412 |
|
||||
413 | class ExitPollerWindows(Thread): |
|
|||
414 | """ A Windows-specific daemon thread that terminates the program immediately |
|
|||
415 | when a Win32 handle is signaled. |
|
|||
416 | """ |
|
|||
417 |
|
||||
418 | def __init__(self, handle): |
|
|||
419 | super(ExitPollerWindows, self).__init__() |
|
|||
420 | self.daemon = True |
|
|||
421 | self.handle = handle |
|
|||
422 |
|
||||
423 | def run(self): |
|
|||
424 | from _subprocess import WaitForSingleObject, WAIT_OBJECT_0, INFINITE |
|
|||
425 | result = WaitForSingleObject(self.handle, INFINITE) |
|
|||
426 | if result == WAIT_OBJECT_0: |
|
|||
427 | os._exit(1) |
|
|||
428 |
|
||||
429 |
|
||||
430 | def bind_port(socket, ip, port): |
|
303 | def bind_port(socket, ip, port): | |
431 | """ Binds the specified ZMQ socket. If the port is zero, a random port is |
|
304 | """ Binds the specified ZMQ socket. If the port is zero, a random port is | |
432 | chosen. Returns the port that was bound. |
|
305 | chosen. Returns the port that was bound. | |
@@ -566,7 +439,7 b' def launch_kernel(xrep_port=0, pub_port=0, req_port=0,' | |||||
566 | req_port = ports.pop(0) |
|
439 | req_port = ports.pop(0) | |
567 |
|
440 | |||
568 | # Build the kernel launch command. |
|
441 | # Build the kernel launch command. | |
569 | command = 'from IPython.zmq.kernel import main; main()' |
|
442 | command = 'from IPython.zmq.pykernel import main; main()' | |
570 | arguments = [ sys.executable, '-c', command, '--xrep', str(xrep_port), |
|
443 | arguments = [ sys.executable, '-c', command, '--xrep', str(xrep_port), | |
571 | '--pub', str(pub_port), '--req', str(req_port) ] |
|
444 | '--pub', str(pub_port), '--req', str(req_port) ] | |
572 | if pylab: |
|
445 | if pylab: |
@@ -13,4 +13,6 b' this_dir = os.path.dirname(os.path.abspath(__file__))' | |||||
13 | sys.path.insert(0, this_dir) |
|
13 | sys.path.insert(0, this_dir) | |
14 |
|
14 | |||
15 | # Now proceed with execution |
|
15 | # Now proceed with execution | |
16 | execfile(os.path.join(this_dir, 'IPython', 'scripts', 'ipython')) |
|
16 | execfile(os.path.join( | |
|
17 | this_dir, 'IPython', 'frontend', 'terminal', 'scripts', 'ipython' | |||
|
18 | )) |
@@ -35,8 +35,6 b' def install():' | |||||
35 | 'ipcontroller', |
|
35 | 'ipcontroller', | |
36 | 'ipengine', |
|
36 | 'ipengine', | |
37 | 'ipcluster', |
|
37 | 'ipcluster', | |
38 | 'ipythonx', |
|
|||
39 | 'ipython-wx', |
|
|||
40 | 'irunner' |
|
38 | 'irunner' | |
41 | ] |
|
39 | ] | |
42 | scripts = pjoin(prefix,'scripts') |
|
40 | scripts = pjoin(prefix,'scripts') |
@@ -207,12 +207,11 b" if 'setuptools' in sys.modules:" | |||||
207 | setuptools_extra_args['zip_safe'] = False |
|
207 | setuptools_extra_args['zip_safe'] = False | |
208 | setuptools_extra_args['entry_points'] = { |
|
208 | setuptools_extra_args['entry_points'] = { | |
209 | 'console_scripts': [ |
|
209 | 'console_scripts': [ | |
210 |
'ipython = IPython. |
|
210 | 'ipython = IPython.frontend.terminal.ipapp:launch_new_instance', | |
211 | 'pycolor = IPython.utils.PyColorize:main', |
|
211 | 'pycolor = IPython.utils.PyColorize:main', | |
212 | 'ipcontroller = IPython.kernel.ipcontrollerapp:launch_new_instance', |
|
212 | 'ipcontroller = IPython.kernel.ipcontrollerapp:launch_new_instance', | |
213 | 'ipengine = IPython.kernel.ipengineapp:launch_new_instance', |
|
213 | 'ipengine = IPython.kernel.ipengineapp:launch_new_instance', | |
214 | 'ipcluster = IPython.kernel.ipclusterapp:launch_new_instance', |
|
214 | 'ipcluster = IPython.kernel.ipclusterapp:launch_new_instance', | |
215 | 'ipythonx = IPython.frontend.wx.ipythonx:main', |
|
|||
216 | 'iptest = IPython.testing.iptest:main', |
|
215 | 'iptest = IPython.testing.iptest:main', | |
217 | 'irunner = IPython.lib.irunner:main' |
|
216 | 'irunner = IPython.lib.irunner:main' | |
218 | ] |
|
217 | ] |
@@ -111,6 +111,7 b' def find_packages():' | |||||
111 | add_package(packages, 'frontend') |
|
111 | add_package(packages, 'frontend') | |
112 | add_package(packages, 'frontend.qt') |
|
112 | add_package(packages, 'frontend.qt') | |
113 | add_package(packages, 'frontend.qt.console') |
|
113 | add_package(packages, 'frontend.qt.console') | |
|
114 | add_package(packages, 'frontend.terminal', config=False, tests=True, scripts=True) | |||
114 | add_package(packages, 'kernel', config=False, tests=True, scripts=True) |
|
115 | add_package(packages, 'kernel', config=False, tests=True, scripts=True) | |
115 | add_package(packages, 'kernel.core', config=False, tests=True) |
|
116 | add_package(packages, 'kernel.core', config=False, tests=True) | |
116 | add_package(packages, 'lib', tests=True) |
|
117 | add_package(packages, 'lib', tests=True) | |
@@ -254,12 +255,11 b' def find_scripts():' | |||||
254 | """ |
|
255 | """ | |
255 | kernel_scripts = pjoin('IPython','kernel','scripts') |
|
256 | kernel_scripts = pjoin('IPython','kernel','scripts') | |
256 | main_scripts = pjoin('IPython','scripts') |
|
257 | main_scripts = pjoin('IPython','scripts') | |
|
258 | frontend_terminal_scripts = pjoin('IPython','frontend','terminal','scripts') | |||
257 | scripts = [pjoin(kernel_scripts, 'ipengine'), |
|
259 | scripts = [pjoin(kernel_scripts, 'ipengine'), | |
258 | pjoin(kernel_scripts, 'ipcontroller'), |
|
260 | pjoin(kernel_scripts, 'ipcontroller'), | |
259 | pjoin(kernel_scripts, 'ipcluster'), |
|
261 | pjoin(kernel_scripts, 'ipcluster'), | |
260 |
pjoin(m |
|
262 | pjoin(frontend_terminal_scripts, 'ipython'), | |
261 | pjoin(main_scripts, 'ipythonx'), |
|
|||
262 | pjoin(main_scripts, 'ipython-wx'), |
|
|||
263 | pjoin(main_scripts, 'pycolor'), |
|
263 | pjoin(main_scripts, 'pycolor'), | |
264 | pjoin(main_scripts, 'irunner'), |
|
264 | pjoin(main_scripts, 'irunner'), | |
265 | pjoin(main_scripts, 'iptest') |
|
265 | pjoin(main_scripts, 'iptest') |
General Comments 0
You need to be logged in to leave comments.
Login now