##// END OF EJS Templates
Move functions into magic methods....
Fernando Perez -
Show More
@@ -1,684 +1,676
1 # -*- coding: utf-8 -*-
1 # -*- coding: utf-8 -*-
2 """Subclass of InteractiveShell for terminal based frontends."""
2 """Subclass of InteractiveShell for terminal based frontends."""
3
3
4 #-----------------------------------------------------------------------------
4 #-----------------------------------------------------------------------------
5 # Copyright (C) 2001 Janko Hauser <jhauser@zscout.de>
5 # Copyright (C) 2001 Janko Hauser <jhauser@zscout.de>
6 # Copyright (C) 2001-2007 Fernando Perez. <fperez@colorado.edu>
6 # Copyright (C) 2001-2007 Fernando Perez. <fperez@colorado.edu>
7 # Copyright (C) 2008-2011 The IPython Development Team
7 # Copyright (C) 2008-2011 The IPython Development Team
8 #
8 #
9 # Distributed under the terms of the BSD License. The full license is in
9 # Distributed under the terms of the BSD License. The full license is in
10 # the file COPYING, distributed as part of this software.
10 # the file COPYING, distributed as part of this software.
11 #-----------------------------------------------------------------------------
11 #-----------------------------------------------------------------------------
12
12
13 #-----------------------------------------------------------------------------
13 #-----------------------------------------------------------------------------
14 # Imports
14 # Imports
15 #-----------------------------------------------------------------------------
15 #-----------------------------------------------------------------------------
16
16
17 import bdb
17 import bdb
18 import os
18 import os
19 import re
19 import re
20 import sys
20 import sys
21 import textwrap
21 import textwrap
22
22
23 # We need to use nested to support python 2.6, once we move to >=2.7, we can
23 # We need to use nested to support python 2.6, once we move to >=2.7, we can
24 # use the with keyword's new builtin support for nested managers
24 # use the with keyword's new builtin support for nested managers
25 try:
25 try:
26 from contextlib import nested
26 from contextlib import nested
27 except:
27 except:
28 from IPython.utils.nested_context import nested
28 from IPython.utils.nested_context import nested
29
29
30 from IPython.core.error import TryNext, UsageError
30 from IPython.core.error import TryNext, UsageError
31 from IPython.core.usage import interactive_usage, default_banner
31 from IPython.core.usage import interactive_usage, default_banner
32 from IPython.core.interactiveshell import InteractiveShell, InteractiveShellABC
32 from IPython.core.interactiveshell import InteractiveShell, InteractiveShellABC
33 from IPython.core.magic import Magics, magics_class, line_magic
33 from IPython.core.magic import Magics, magics_class, line_magic
34 from IPython.testing.skipdoctest import skip_doctest
34 from IPython.testing.skipdoctest import skip_doctest
35 from IPython.utils.encoding import get_stream_enc
35 from IPython.utils.encoding import get_stream_enc
36 from IPython.utils import py3compat
36 from IPython.utils import py3compat
37 from IPython.utils.terminal import toggle_set_term_title, set_term_title
37 from IPython.utils.terminal import toggle_set_term_title, set_term_title
38 from IPython.utils.process import abbrev_cwd
38 from IPython.utils.process import abbrev_cwd
39 from IPython.utils.warn import warn, error
39 from IPython.utils.warn import warn, error
40 from IPython.utils.text import num_ini_spaces, SList
40 from IPython.utils.text import num_ini_spaces, SList
41 from IPython.utils.traitlets import Integer, CBool, Unicode
41 from IPython.utils.traitlets import Integer, CBool, Unicode
42
42
43 #-----------------------------------------------------------------------------
43 #-----------------------------------------------------------------------------
44 # Utilities
44 # Utilities
45 #-----------------------------------------------------------------------------
45 #-----------------------------------------------------------------------------
46
46
47 def get_default_editor():
47 def get_default_editor():
48 try:
48 try:
49 ed = os.environ['EDITOR']
49 ed = os.environ['EDITOR']
50 except KeyError:
50 except KeyError:
51 if os.name == 'posix':
51 if os.name == 'posix':
52 ed = 'vi' # the only one guaranteed to be there!
52 ed = 'vi' # the only one guaranteed to be there!
53 else:
53 else:
54 ed = 'notepad' # same in Windows!
54 ed = 'notepad' # same in Windows!
55 return ed
55 return ed
56
56
57
57
58 def get_pasted_lines(sentinel, l_input=py3compat.input):
58 def get_pasted_lines(sentinel, l_input=py3compat.input):
59 """ Yield pasted lines until the user enters the given sentinel value.
59 """ Yield pasted lines until the user enters the given sentinel value.
60 """
60 """
61 print "Pasting code; enter '%s' alone on the line to stop or use Ctrl-D." \
61 print "Pasting code; enter '%s' alone on the line to stop or use Ctrl-D." \
62 % sentinel
62 % sentinel
63 while True:
63 while True:
64 try:
64 try:
65 l = l_input(':')
65 l = l_input(':')
66 if l == sentinel:
66 if l == sentinel:
67 return
67 return
68 else:
68 else:
69 yield l
69 yield l
70 except EOFError:
70 except EOFError:
71 print '<EOF>'
71 print '<EOF>'
72 return
72 return
73
73
74
74
75 def strip_email_quotes(raw_lines):
75 def strip_email_quotes(raw_lines):
76 """ Strip email quotation marks at the beginning of each line.
76 """ Strip email quotation marks at the beginning of each line.
77
77
78 We don't do any more input transofrmations here because the main shell's
78 We don't do any more input transofrmations here because the main shell's
79 prefiltering handles other cases.
79 prefiltering handles other cases.
80 """
80 """
81 lines = [re.sub(r'^\s*(\s?>)+', '', l) for l in raw_lines]
81 lines = [re.sub(r'^\s*(\s?>)+', '', l) for l in raw_lines]
82 return '\n'.join(lines) + '\n'
82 return '\n'.join(lines) + '\n'
83
83
84
84
85 # These two functions are needed by the %paste/%cpaste magics. In practice
85 #------------------------------------------------------------------------
86 # they are basically methods (they take the shell as their first argument), but
86 # Terminal-specific magics
87 # we leave them as standalone functions because eventually the magics
87 #------------------------------------------------------------------------
88 # themselves will become separate objects altogether. At that point, the
88
89 # magics will have access to the shell object, and these functions can be made
89 @magics_class
90 # methods of the magic object, but not of the shell.
90 class TerminalMagics(Magics):
91
91
92 def store_or_execute(shell, block, name):
92 def store_or_execute(self, block, name):
93 """ Execute a block, or store it in a variable, per the user's request.
93 """ Execute a block, or store it in a variable, per the user's request.
94 """
94 """
95 # Dedent and prefilter so what we store matches what is executed by
95 # Dedent and prefilter so what we store matches what is executed by
96 # run_cell.
96 # run_cell.
97 b = shell.prefilter(textwrap.dedent(block))
97 b = self.shell.prefilter(textwrap.dedent(block))
98
98
99 if name:
99 if name:
100 # If storing it for further editing, run the prefilter on it
100 # If storing it for further editing, run the prefilter on it
101 shell.user_ns[name] = SList(b.splitlines())
101 self.shell.user_ns[name] = SList(b.splitlines())
102 print "Block assigned to '%s'" % name
102 print "Block assigned to '%s'" % name
103 else:
103 else:
104 shell.user_ns['pasted_block'] = b
104 self.shell.user_ns['pasted_block'] = b
105 shell.run_cell(b)
105 self.shell.run_cell(b)
106
106
107
107
108 def rerun_pasted(shell, name='pasted_block'):
108 def rerun_pasted(self, name='pasted_block'):
109 """ Rerun a previously pasted command.
109 """ Rerun a previously pasted command.
110 """
110 """
111 b = shell.user_ns.get(name)
111 b = self.shell.user_ns.get(name)
112
112
113 # Sanity checks
113 # Sanity checks
114 if b is None:
114 if b is None:
115 raise UsageError('No previous pasted block available')
115 raise UsageError('No previous pasted block available')
116 if not isinstance(b, basestring):
116 if not isinstance(b, basestring):
117 raise UsageError(
117 raise UsageError(
118 "Variable 'pasted_block' is not a string, can't execute")
118 "Variable 'pasted_block' is not a string, can't execute")
119
119
120 print "Re-executing '%s...' (%d chars)"% (b.split('\n',1)[0], len(b))
120 print "Re-executing '%s...' (%d chars)"% (b.split('\n',1)[0], len(b))
121 shell.run_cell(b)
121 self.shell.run_cell(b)
122
123
124 #------------------------------------------------------------------------
125 # Terminal-specific magics
126 #------------------------------------------------------------------------
127
128 @magics_class
129 class TerminalMagics(Magics):
130
122
131 @line_magic
123 @line_magic
132 def autoindent(self, parameter_s = ''):
124 def autoindent(self, parameter_s = ''):
133 """Toggle autoindent on/off (if available)."""
125 """Toggle autoindent on/off (if available)."""
134
126
135 self.shell.set_autoindent()
127 self.shell.set_autoindent()
136 print "Automatic indentation is:",['OFF','ON'][self.shell.autoindent]
128 print "Automatic indentation is:",['OFF','ON'][self.shell.autoindent]
137
129
138 @skip_doctest
130 @skip_doctest
139 @line_magic
131 @line_magic
140 def cpaste(self, parameter_s=''):
132 def cpaste(self, parameter_s=''):
141 """Paste & execute a pre-formatted code block from clipboard.
133 """Paste & execute a pre-formatted code block from clipboard.
142
134
143 You must terminate the block with '--' (two minus-signs) or Ctrl-D
135 You must terminate the block with '--' (two minus-signs) or Ctrl-D
144 alone on the line. You can also provide your own sentinel with '%paste
136 alone on the line. You can also provide your own sentinel with '%paste
145 -s %%' ('%%' is the new sentinel for this operation)
137 -s %%' ('%%' is the new sentinel for this operation)
146
138
147 The block is dedented prior to execution to enable execution of method
139 The block is dedented prior to execution to enable execution of method
148 definitions. '>' and '+' characters at the beginning of a line are
140 definitions. '>' and '+' characters at the beginning of a line are
149 ignored, to allow pasting directly from e-mails, diff files and
141 ignored, to allow pasting directly from e-mails, diff files and
150 doctests (the '...' continuation prompt is also stripped). The
142 doctests (the '...' continuation prompt is also stripped). The
151 executed block is also assigned to variable named 'pasted_block' for
143 executed block is also assigned to variable named 'pasted_block' for
152 later editing with '%edit pasted_block'.
144 later editing with '%edit pasted_block'.
153
145
154 You can also pass a variable name as an argument, e.g. '%cpaste foo'.
146 You can also pass a variable name as an argument, e.g. '%cpaste foo'.
155 This assigns the pasted block to variable 'foo' as string, without
147 This assigns the pasted block to variable 'foo' as string, without
156 dedenting or executing it (preceding >>> and + is still stripped)
148 dedenting or executing it (preceding >>> and + is still stripped)
157
149
158 '%cpaste -r' re-executes the block previously entered by cpaste.
150 '%cpaste -r' re-executes the block previously entered by cpaste.
159
151
160 Do not be alarmed by garbled output on Windows (it's a readline bug).
152 Do not be alarmed by garbled output on Windows (it's a readline bug).
161 Just press enter and type -- (and press enter again) and the block
153 Just press enter and type -- (and press enter again) and the block
162 will be what was just pasted.
154 will be what was just pasted.
163
155
164 IPython statements (magics, shell escapes) are not supported (yet).
156 IPython statements (magics, shell escapes) are not supported (yet).
165
157
166 See also
158 See also
167 --------
159 --------
168 paste: automatically pull code from clipboard.
160 paste: automatically pull code from clipboard.
169
161
170 Examples
162 Examples
171 --------
163 --------
172 ::
164 ::
173
165
174 In [8]: %cpaste
166 In [8]: %cpaste
175 Pasting code; enter '--' alone on the line to stop.
167 Pasting code; enter '--' alone on the line to stop.
176 :>>> a = ["world!", "Hello"]
168 :>>> a = ["world!", "Hello"]
177 :>>> print " ".join(sorted(a))
169 :>>> print " ".join(sorted(a))
178 :--
170 :--
179 Hello world!
171 Hello world!
180 """
172 """
181
173
182 opts, name = self.parse_options(parameter_s, 'rs:', mode='string')
174 opts, name = self.parse_options(parameter_s, 'rs:', mode='string')
183 if 'r' in opts:
175 if 'r' in opts:
184 rerun_pasted(self.shell)
176 self.rerun_pasted()
185 return
177 return
186
178
187 sentinel = opts.get('s', '--')
179 sentinel = opts.get('s', '--')
188 block = strip_email_quotes(get_pasted_lines(sentinel))
180 block = strip_email_quotes(get_pasted_lines(sentinel))
189 store_or_execute(self.shell, block, name)
181 self.store_or_execute(block, name)
190
182
191 @line_magic
183 @line_magic
192 def paste(self, parameter_s=''):
184 def paste(self, parameter_s=''):
193 """Paste & execute a pre-formatted code block from clipboard.
185 """Paste & execute a pre-formatted code block from clipboard.
194
186
195 The text is pulled directly from the clipboard without user
187 The text is pulled directly from the clipboard without user
196 intervention and printed back on the screen before execution (unless
188 intervention and printed back on the screen before execution (unless
197 the -q flag is given to force quiet mode).
189 the -q flag is given to force quiet mode).
198
190
199 The block is dedented prior to execution to enable execution of method
191 The block is dedented prior to execution to enable execution of method
200 definitions. '>' and '+' characters at the beginning of a line are
192 definitions. '>' and '+' characters at the beginning of a line are
201 ignored, to allow pasting directly from e-mails, diff files and
193 ignored, to allow pasting directly from e-mails, diff files and
202 doctests (the '...' continuation prompt is also stripped). The
194 doctests (the '...' continuation prompt is also stripped). The
203 executed block is also assigned to variable named 'pasted_block' for
195 executed block is also assigned to variable named 'pasted_block' for
204 later editing with '%edit pasted_block'.
196 later editing with '%edit pasted_block'.
205
197
206 You can also pass a variable name as an argument, e.g. '%paste foo'.
198 You can also pass a variable name as an argument, e.g. '%paste foo'.
207 This assigns the pasted block to variable 'foo' as string, without
199 This assigns the pasted block to variable 'foo' as string, without
208 dedenting or executing it (preceding >>> and + is still stripped)
200 dedenting or executing it (preceding >>> and + is still stripped)
209
201
210 Options
202 Options
211 -------
203 -------
212
204
213 -r: re-executes the block previously entered by cpaste.
205 -r: re-executes the block previously entered by cpaste.
214
206
215 -q: quiet mode: do not echo the pasted text back to the terminal.
207 -q: quiet mode: do not echo the pasted text back to the terminal.
216
208
217 IPython statements (magics, shell escapes) are not supported (yet).
209 IPython statements (magics, shell escapes) are not supported (yet).
218
210
219 See also
211 See also
220 --------
212 --------
221 cpaste: manually paste code into terminal until you mark its end.
213 cpaste: manually paste code into terminal until you mark its end.
222 """
214 """
223 opts, name = self.parse_options(parameter_s, 'rq', mode='string')
215 opts, name = self.parse_options(parameter_s, 'rq', mode='string')
224 if 'r' in opts:
216 if 'r' in opts:
225 rerun_pasted(self.shell)
217 self.rerun_pasted()
226 return
218 return
227 try:
219 try:
228 text = self.shell.hooks.clipboard_get()
220 text = self.shell.hooks.clipboard_get()
229 block = strip_email_quotes(text.splitlines())
221 block = strip_email_quotes(text.splitlines())
230 except TryNext as clipboard_exc:
222 except TryNext as clipboard_exc:
231 message = getattr(clipboard_exc, 'args')
223 message = getattr(clipboard_exc, 'args')
232 if message:
224 if message:
233 error(message[0])
225 error(message[0])
234 else:
226 else:
235 error('Could not get text from the clipboard.')
227 error('Could not get text from the clipboard.')
236 return
228 return
237
229
238 # By default, echo back to terminal unless quiet mode is requested
230 # By default, echo back to terminal unless quiet mode is requested
239 if 'q' not in opts:
231 if 'q' not in opts:
240 write = self.shell.write
232 write = self.shell.write
241 write(self.shell.pycolorize(block))
233 write(self.shell.pycolorize(block))
242 if not block.endswith('\n'):
234 if not block.endswith('\n'):
243 write('\n')
235 write('\n')
244 write("## -- End pasted text --\n")
236 write("## -- End pasted text --\n")
245
237
246 store_or_execute(self.shell, block, name)
238 self.store_or_execute(block, name)
247
239
248 # Class-level: add a '%cls' magic only on Windows
240 # Class-level: add a '%cls' magic only on Windows
249 if sys.platform == 'win32':
241 if sys.platform == 'win32':
250 @line_magic
242 @line_magic
251 def cls(self, s):
243 def cls(self, s):
252 """Clear screen.
244 """Clear screen.
253 """
245 """
254 os.system("cls")
246 os.system("cls")
255
247
256 #-----------------------------------------------------------------------------
248 #-----------------------------------------------------------------------------
257 # Main class
249 # Main class
258 #-----------------------------------------------------------------------------
250 #-----------------------------------------------------------------------------
259
251
260 class TerminalInteractiveShell(InteractiveShell):
252 class TerminalInteractiveShell(InteractiveShell):
261
253
262 autoedit_syntax = CBool(False, config=True,
254 autoedit_syntax = CBool(False, config=True,
263 help="auto editing of files with syntax errors.")
255 help="auto editing of files with syntax errors.")
264 banner = Unicode('')
256 banner = Unicode('')
265 banner1 = Unicode(default_banner, config=True,
257 banner1 = Unicode(default_banner, config=True,
266 help="""The part of the banner to be printed before the profile"""
258 help="""The part of the banner to be printed before the profile"""
267 )
259 )
268 banner2 = Unicode('', config=True,
260 banner2 = Unicode('', config=True,
269 help="""The part of the banner to be printed after the profile"""
261 help="""The part of the banner to be printed after the profile"""
270 )
262 )
271 confirm_exit = CBool(True, config=True,
263 confirm_exit = CBool(True, config=True,
272 help="""
264 help="""
273 Set to confirm when you try to exit IPython with an EOF (Control-D
265 Set to confirm when you try to exit IPython with an EOF (Control-D
274 in Unix, Control-Z/Enter in Windows). By typing 'exit' or 'quit',
266 in Unix, Control-Z/Enter in Windows). By typing 'exit' or 'quit',
275 you can force a direct exit without any confirmation.""",
267 you can force a direct exit without any confirmation.""",
276 )
268 )
277 # This display_banner only controls whether or not self.show_banner()
269 # This display_banner only controls whether or not self.show_banner()
278 # is called when mainloop/interact are called. The default is False
270 # is called when mainloop/interact are called. The default is False
279 # because for the terminal based application, the banner behavior
271 # because for the terminal based application, the banner behavior
280 # is controlled by Global.display_banner, which IPythonApp looks at
272 # is controlled by Global.display_banner, which IPythonApp looks at
281 # to determine if *it* should call show_banner() by hand or not.
273 # to determine if *it* should call show_banner() by hand or not.
282 display_banner = CBool(False) # This isn't configurable!
274 display_banner = CBool(False) # This isn't configurable!
283 embedded = CBool(False)
275 embedded = CBool(False)
284 embedded_active = CBool(False)
276 embedded_active = CBool(False)
285 editor = Unicode(get_default_editor(), config=True,
277 editor = Unicode(get_default_editor(), config=True,
286 help="Set the editor used by IPython (default to $EDITOR/vi/notepad)."
278 help="Set the editor used by IPython (default to $EDITOR/vi/notepad)."
287 )
279 )
288 pager = Unicode('less', config=True,
280 pager = Unicode('less', config=True,
289 help="The shell program to be used for paging.")
281 help="The shell program to be used for paging.")
290
282
291 screen_length = Integer(0, config=True,
283 screen_length = Integer(0, config=True,
292 help=
284 help=
293 """Number of lines of your screen, used to control printing of very
285 """Number of lines of your screen, used to control printing of very
294 long strings. Strings longer than this number of lines will be sent
286 long strings. Strings longer than this number of lines will be sent
295 through a pager instead of directly printed. The default value for
287 through a pager instead of directly printed. The default value for
296 this is 0, which means IPython will auto-detect your screen size every
288 this is 0, which means IPython will auto-detect your screen size every
297 time it needs to print certain potentially long strings (this doesn't
289 time it needs to print certain potentially long strings (this doesn't
298 change the behavior of the 'print' keyword, it's only triggered
290 change the behavior of the 'print' keyword, it's only triggered
299 internally). If for some reason this isn't working well (it needs
291 internally). If for some reason this isn't working well (it needs
300 curses support), specify it yourself. Otherwise don't change the
292 curses support), specify it yourself. Otherwise don't change the
301 default.""",
293 default.""",
302 )
294 )
303 term_title = CBool(False, config=True,
295 term_title = CBool(False, config=True,
304 help="Enable auto setting the terminal title."
296 help="Enable auto setting the terminal title."
305 )
297 )
306
298
307 # In the terminal, GUI control is done via PyOS_InputHook
299 # In the terminal, GUI control is done via PyOS_InputHook
308 from IPython.lib.inputhook import enable_gui
300 from IPython.lib.inputhook import enable_gui
309 enable_gui = staticmethod(enable_gui)
301 enable_gui = staticmethod(enable_gui)
310
302
311 def __init__(self, config=None, ipython_dir=None, profile_dir=None,
303 def __init__(self, config=None, ipython_dir=None, profile_dir=None,
312 user_ns=None, user_module=None, custom_exceptions=((),None),
304 user_ns=None, user_module=None, custom_exceptions=((),None),
313 usage=None, banner1=None, banner2=None, display_banner=None):
305 usage=None, banner1=None, banner2=None, display_banner=None):
314
306
315 super(TerminalInteractiveShell, self).__init__(
307 super(TerminalInteractiveShell, self).__init__(
316 config=config, profile_dir=profile_dir, user_ns=user_ns,
308 config=config, profile_dir=profile_dir, user_ns=user_ns,
317 user_module=user_module, custom_exceptions=custom_exceptions
309 user_module=user_module, custom_exceptions=custom_exceptions
318 )
310 )
319 # use os.system instead of utils.process.system by default,
311 # use os.system instead of utils.process.system by default,
320 # because piped system doesn't make sense in the Terminal:
312 # because piped system doesn't make sense in the Terminal:
321 self.system = self.system_raw
313 self.system = self.system_raw
322
314
323 self.init_term_title()
315 self.init_term_title()
324 self.init_usage(usage)
316 self.init_usage(usage)
325 self.init_banner(banner1, banner2, display_banner)
317 self.init_banner(banner1, banner2, display_banner)
326
318
327 #-------------------------------------------------------------------------
319 #-------------------------------------------------------------------------
328 # Things related to the terminal
320 # Things related to the terminal
329 #-------------------------------------------------------------------------
321 #-------------------------------------------------------------------------
330
322
331 @property
323 @property
332 def usable_screen_length(self):
324 def usable_screen_length(self):
333 if self.screen_length == 0:
325 if self.screen_length == 0:
334 return 0
326 return 0
335 else:
327 else:
336 num_lines_bot = self.separate_in.count('\n')+1
328 num_lines_bot = self.separate_in.count('\n')+1
337 return self.screen_length - num_lines_bot
329 return self.screen_length - num_lines_bot
338
330
339 def init_term_title(self):
331 def init_term_title(self):
340 # Enable or disable the terminal title.
332 # Enable or disable the terminal title.
341 if self.term_title:
333 if self.term_title:
342 toggle_set_term_title(True)
334 toggle_set_term_title(True)
343 set_term_title('IPython: ' + abbrev_cwd())
335 set_term_title('IPython: ' + abbrev_cwd())
344 else:
336 else:
345 toggle_set_term_title(False)
337 toggle_set_term_title(False)
346
338
347 #-------------------------------------------------------------------------
339 #-------------------------------------------------------------------------
348 # Things related to aliases
340 # Things related to aliases
349 #-------------------------------------------------------------------------
341 #-------------------------------------------------------------------------
350
342
351 def init_alias(self):
343 def init_alias(self):
352 # The parent class defines aliases that can be safely used with any
344 # The parent class defines aliases that can be safely used with any
353 # frontend.
345 # frontend.
354 super(TerminalInteractiveShell, self).init_alias()
346 super(TerminalInteractiveShell, self).init_alias()
355
347
356 # Now define aliases that only make sense on the terminal, because they
348 # Now define aliases that only make sense on the terminal, because they
357 # need direct access to the console in a way that we can't emulate in
349 # need direct access to the console in a way that we can't emulate in
358 # GUI or web frontend
350 # GUI or web frontend
359 if os.name == 'posix':
351 if os.name == 'posix':
360 aliases = [('clear', 'clear'), ('more', 'more'), ('less', 'less'),
352 aliases = [('clear', 'clear'), ('more', 'more'), ('less', 'less'),
361 ('man', 'man')]
353 ('man', 'man')]
362 elif os.name == 'nt':
354 elif os.name == 'nt':
363 aliases = [('cls', 'cls')]
355 aliases = [('cls', 'cls')]
364
356
365
357
366 for name, cmd in aliases:
358 for name, cmd in aliases:
367 self.alias_manager.define_alias(name, cmd)
359 self.alias_manager.define_alias(name, cmd)
368
360
369 #-------------------------------------------------------------------------
361 #-------------------------------------------------------------------------
370 # Things related to the banner and usage
362 # Things related to the banner and usage
371 #-------------------------------------------------------------------------
363 #-------------------------------------------------------------------------
372
364
373 def _banner1_changed(self):
365 def _banner1_changed(self):
374 self.compute_banner()
366 self.compute_banner()
375
367
376 def _banner2_changed(self):
368 def _banner2_changed(self):
377 self.compute_banner()
369 self.compute_banner()
378
370
379 def _term_title_changed(self, name, new_value):
371 def _term_title_changed(self, name, new_value):
380 self.init_term_title()
372 self.init_term_title()
381
373
382 def init_banner(self, banner1, banner2, display_banner):
374 def init_banner(self, banner1, banner2, display_banner):
383 if banner1 is not None:
375 if banner1 is not None:
384 self.banner1 = banner1
376 self.banner1 = banner1
385 if banner2 is not None:
377 if banner2 is not None:
386 self.banner2 = banner2
378 self.banner2 = banner2
387 if display_banner is not None:
379 if display_banner is not None:
388 self.display_banner = display_banner
380 self.display_banner = display_banner
389 self.compute_banner()
381 self.compute_banner()
390
382
391 def show_banner(self, banner=None):
383 def show_banner(self, banner=None):
392 if banner is None:
384 if banner is None:
393 banner = self.banner
385 banner = self.banner
394 self.write(banner)
386 self.write(banner)
395
387
396 def compute_banner(self):
388 def compute_banner(self):
397 self.banner = self.banner1
389 self.banner = self.banner1
398 if self.profile and self.profile != 'default':
390 if self.profile and self.profile != 'default':
399 self.banner += '\nIPython profile: %s\n' % self.profile
391 self.banner += '\nIPython profile: %s\n' % self.profile
400 if self.banner2:
392 if self.banner2:
401 self.banner += '\n' + self.banner2
393 self.banner += '\n' + self.banner2
402
394
403 def init_usage(self, usage=None):
395 def init_usage(self, usage=None):
404 if usage is None:
396 if usage is None:
405 self.usage = interactive_usage
397 self.usage = interactive_usage
406 else:
398 else:
407 self.usage = usage
399 self.usage = usage
408
400
409 #-------------------------------------------------------------------------
401 #-------------------------------------------------------------------------
410 # Mainloop and code execution logic
402 # Mainloop and code execution logic
411 #-------------------------------------------------------------------------
403 #-------------------------------------------------------------------------
412
404
413 def mainloop(self, display_banner=None):
405 def mainloop(self, display_banner=None):
414 """Start the mainloop.
406 """Start the mainloop.
415
407
416 If an optional banner argument is given, it will override the
408 If an optional banner argument is given, it will override the
417 internally created default banner.
409 internally created default banner.
418 """
410 """
419
411
420 with nested(self.builtin_trap, self.display_trap):
412 with nested(self.builtin_trap, self.display_trap):
421
413
422 while 1:
414 while 1:
423 try:
415 try:
424 self.interact(display_banner=display_banner)
416 self.interact(display_banner=display_banner)
425 #self.interact_with_readline()
417 #self.interact_with_readline()
426 # XXX for testing of a readline-decoupled repl loop, call
418 # XXX for testing of a readline-decoupled repl loop, call
427 # interact_with_readline above
419 # interact_with_readline above
428 break
420 break
429 except KeyboardInterrupt:
421 except KeyboardInterrupt:
430 # this should not be necessary, but KeyboardInterrupt
422 # this should not be necessary, but KeyboardInterrupt
431 # handling seems rather unpredictable...
423 # handling seems rather unpredictable...
432 self.write("\nKeyboardInterrupt in interact()\n")
424 self.write("\nKeyboardInterrupt in interact()\n")
433
425
434 def _replace_rlhist_multiline(self, source_raw, hlen_before_cell):
426 def _replace_rlhist_multiline(self, source_raw, hlen_before_cell):
435 """Store multiple lines as a single entry in history"""
427 """Store multiple lines as a single entry in history"""
436
428
437 # do nothing without readline or disabled multiline
429 # do nothing without readline or disabled multiline
438 if not self.has_readline or not self.multiline_history:
430 if not self.has_readline or not self.multiline_history:
439 return hlen_before_cell
431 return hlen_before_cell
440
432
441 # windows rl has no remove_history_item
433 # windows rl has no remove_history_item
442 if not hasattr(self.readline, "remove_history_item"):
434 if not hasattr(self.readline, "remove_history_item"):
443 return hlen_before_cell
435 return hlen_before_cell
444
436
445 # skip empty cells
437 # skip empty cells
446 if not source_raw.rstrip():
438 if not source_raw.rstrip():
447 return hlen_before_cell
439 return hlen_before_cell
448
440
449 # nothing changed do nothing, e.g. when rl removes consecutive dups
441 # nothing changed do nothing, e.g. when rl removes consecutive dups
450 hlen = self.readline.get_current_history_length()
442 hlen = self.readline.get_current_history_length()
451 if hlen == hlen_before_cell:
443 if hlen == hlen_before_cell:
452 return hlen_before_cell
444 return hlen_before_cell
453
445
454 for i in range(hlen - hlen_before_cell):
446 for i in range(hlen - hlen_before_cell):
455 self.readline.remove_history_item(hlen - i - 1)
447 self.readline.remove_history_item(hlen - i - 1)
456 stdin_encoding = get_stream_enc(sys.stdin, 'utf-8')
448 stdin_encoding = get_stream_enc(sys.stdin, 'utf-8')
457 self.readline.add_history(py3compat.unicode_to_str(source_raw.rstrip(),
449 self.readline.add_history(py3compat.unicode_to_str(source_raw.rstrip(),
458 stdin_encoding))
450 stdin_encoding))
459 return self.readline.get_current_history_length()
451 return self.readline.get_current_history_length()
460
452
461 def interact(self, display_banner=None):
453 def interact(self, display_banner=None):
462 """Closely emulate the interactive Python console."""
454 """Closely emulate the interactive Python console."""
463
455
464 # batch run -> do not interact
456 # batch run -> do not interact
465 if self.exit_now:
457 if self.exit_now:
466 return
458 return
467
459
468 if display_banner is None:
460 if display_banner is None:
469 display_banner = self.display_banner
461 display_banner = self.display_banner
470
462
471 if isinstance(display_banner, basestring):
463 if isinstance(display_banner, basestring):
472 self.show_banner(display_banner)
464 self.show_banner(display_banner)
473 elif display_banner:
465 elif display_banner:
474 self.show_banner()
466 self.show_banner()
475
467
476 more = False
468 more = False
477
469
478 if self.has_readline:
470 if self.has_readline:
479 self.readline_startup_hook(self.pre_readline)
471 self.readline_startup_hook(self.pre_readline)
480 hlen_b4_cell = self.readline.get_current_history_length()
472 hlen_b4_cell = self.readline.get_current_history_length()
481 else:
473 else:
482 hlen_b4_cell = 0
474 hlen_b4_cell = 0
483 # exit_now is set by a call to %Exit or %Quit, through the
475 # exit_now is set by a call to %Exit or %Quit, through the
484 # ask_exit callback.
476 # ask_exit callback.
485
477
486 while not self.exit_now:
478 while not self.exit_now:
487 self.hooks.pre_prompt_hook()
479 self.hooks.pre_prompt_hook()
488 if more:
480 if more:
489 try:
481 try:
490 prompt = self.prompt_manager.render('in2')
482 prompt = self.prompt_manager.render('in2')
491 except:
483 except:
492 self.showtraceback()
484 self.showtraceback()
493 if self.autoindent:
485 if self.autoindent:
494 self.rl_do_indent = True
486 self.rl_do_indent = True
495
487
496 else:
488 else:
497 try:
489 try:
498 prompt = self.separate_in + self.prompt_manager.render('in')
490 prompt = self.separate_in + self.prompt_manager.render('in')
499 except:
491 except:
500 self.showtraceback()
492 self.showtraceback()
501 try:
493 try:
502 line = self.raw_input(prompt)
494 line = self.raw_input(prompt)
503 if self.exit_now:
495 if self.exit_now:
504 # quick exit on sys.std[in|out] close
496 # quick exit on sys.std[in|out] close
505 break
497 break
506 if self.autoindent:
498 if self.autoindent:
507 self.rl_do_indent = False
499 self.rl_do_indent = False
508
500
509 except KeyboardInterrupt:
501 except KeyboardInterrupt:
510 #double-guard against keyboardinterrupts during kbdint handling
502 #double-guard against keyboardinterrupts during kbdint handling
511 try:
503 try:
512 self.write('\nKeyboardInterrupt\n')
504 self.write('\nKeyboardInterrupt\n')
513 source_raw = self.input_splitter.source_raw_reset()[1]
505 source_raw = self.input_splitter.source_raw_reset()[1]
514 hlen_b4_cell = \
506 hlen_b4_cell = \
515 self._replace_rlhist_multiline(source_raw, hlen_b4_cell)
507 self._replace_rlhist_multiline(source_raw, hlen_b4_cell)
516 more = False
508 more = False
517 except KeyboardInterrupt:
509 except KeyboardInterrupt:
518 pass
510 pass
519 except EOFError:
511 except EOFError:
520 if self.autoindent:
512 if self.autoindent:
521 self.rl_do_indent = False
513 self.rl_do_indent = False
522 if self.has_readline:
514 if self.has_readline:
523 self.readline_startup_hook(None)
515 self.readline_startup_hook(None)
524 self.write('\n')
516 self.write('\n')
525 self.exit()
517 self.exit()
526 except bdb.BdbQuit:
518 except bdb.BdbQuit:
527 warn('The Python debugger has exited with a BdbQuit exception.\n'
519 warn('The Python debugger has exited with a BdbQuit exception.\n'
528 'Because of how pdb handles the stack, it is impossible\n'
520 'Because of how pdb handles the stack, it is impossible\n'
529 'for IPython to properly format this particular exception.\n'
521 'for IPython to properly format this particular exception.\n'
530 'IPython will resume normal operation.')
522 'IPython will resume normal operation.')
531 except:
523 except:
532 # exceptions here are VERY RARE, but they can be triggered
524 # exceptions here are VERY RARE, but they can be triggered
533 # asynchronously by signal handlers, for example.
525 # asynchronously by signal handlers, for example.
534 self.showtraceback()
526 self.showtraceback()
535 else:
527 else:
536 self.input_splitter.push(line)
528 self.input_splitter.push(line)
537 more = self.input_splitter.push_accepts_more()
529 more = self.input_splitter.push_accepts_more()
538 if (self.SyntaxTB.last_syntax_error and
530 if (self.SyntaxTB.last_syntax_error and
539 self.autoedit_syntax):
531 self.autoedit_syntax):
540 self.edit_syntax_error()
532 self.edit_syntax_error()
541 if not more:
533 if not more:
542 source_raw = self.input_splitter.source_raw_reset()[1]
534 source_raw = self.input_splitter.source_raw_reset()[1]
543 self.run_cell(source_raw, store_history=True)
535 self.run_cell(source_raw, store_history=True)
544 hlen_b4_cell = \
536 hlen_b4_cell = \
545 self._replace_rlhist_multiline(source_raw, hlen_b4_cell)
537 self._replace_rlhist_multiline(source_raw, hlen_b4_cell)
546
538
547 # Turn off the exit flag, so the mainloop can be restarted if desired
539 # Turn off the exit flag, so the mainloop can be restarted if desired
548 self.exit_now = False
540 self.exit_now = False
549
541
550 def raw_input(self, prompt=''):
542 def raw_input(self, prompt=''):
551 """Write a prompt and read a line.
543 """Write a prompt and read a line.
552
544
553 The returned line does not include the trailing newline.
545 The returned line does not include the trailing newline.
554 When the user enters the EOF key sequence, EOFError is raised.
546 When the user enters the EOF key sequence, EOFError is raised.
555
547
556 Optional inputs:
548 Optional inputs:
557
549
558 - prompt(''): a string to be printed to prompt the user.
550 - prompt(''): a string to be printed to prompt the user.
559
551
560 - continue_prompt(False): whether this line is the first one or a
552 - continue_prompt(False): whether this line is the first one or a
561 continuation in a sequence of inputs.
553 continuation in a sequence of inputs.
562 """
554 """
563 # Code run by the user may have modified the readline completer state.
555 # Code run by the user may have modified the readline completer state.
564 # We must ensure that our completer is back in place.
556 # We must ensure that our completer is back in place.
565
557
566 if self.has_readline:
558 if self.has_readline:
567 self.set_readline_completer()
559 self.set_readline_completer()
568
560
569 # raw_input expects str, but we pass it unicode sometimes
561 # raw_input expects str, but we pass it unicode sometimes
570 prompt = py3compat.cast_bytes_py2(prompt)
562 prompt = py3compat.cast_bytes_py2(prompt)
571
563
572 try:
564 try:
573 line = py3compat.str_to_unicode(self.raw_input_original(prompt))
565 line = py3compat.str_to_unicode(self.raw_input_original(prompt))
574 except ValueError:
566 except ValueError:
575 warn("\n********\nYou or a %run:ed script called sys.stdin.close()"
567 warn("\n********\nYou or a %run:ed script called sys.stdin.close()"
576 " or sys.stdout.close()!\nExiting IPython!\n")
568 " or sys.stdout.close()!\nExiting IPython!\n")
577 self.ask_exit()
569 self.ask_exit()
578 return ""
570 return ""
579
571
580 # Try to be reasonably smart about not re-indenting pasted input more
572 # Try to be reasonably smart about not re-indenting pasted input more
581 # than necessary. We do this by trimming out the auto-indent initial
573 # than necessary. We do this by trimming out the auto-indent initial
582 # spaces, if the user's actual input started itself with whitespace.
574 # spaces, if the user's actual input started itself with whitespace.
583 if self.autoindent:
575 if self.autoindent:
584 if num_ini_spaces(line) > self.indent_current_nsp:
576 if num_ini_spaces(line) > self.indent_current_nsp:
585 line = line[self.indent_current_nsp:]
577 line = line[self.indent_current_nsp:]
586 self.indent_current_nsp = 0
578 self.indent_current_nsp = 0
587
579
588 return line
580 return line
589
581
590 #-------------------------------------------------------------------------
582 #-------------------------------------------------------------------------
591 # Methods to support auto-editing of SyntaxErrors.
583 # Methods to support auto-editing of SyntaxErrors.
592 #-------------------------------------------------------------------------
584 #-------------------------------------------------------------------------
593
585
594 def edit_syntax_error(self):
586 def edit_syntax_error(self):
595 """The bottom half of the syntax error handler called in the main loop.
587 """The bottom half of the syntax error handler called in the main loop.
596
588
597 Loop until syntax error is fixed or user cancels.
589 Loop until syntax error is fixed or user cancels.
598 """
590 """
599
591
600 while self.SyntaxTB.last_syntax_error:
592 while self.SyntaxTB.last_syntax_error:
601 # copy and clear last_syntax_error
593 # copy and clear last_syntax_error
602 err = self.SyntaxTB.clear_err_state()
594 err = self.SyntaxTB.clear_err_state()
603 if not self._should_recompile(err):
595 if not self._should_recompile(err):
604 return
596 return
605 try:
597 try:
606 # may set last_syntax_error again if a SyntaxError is raised
598 # may set last_syntax_error again if a SyntaxError is raised
607 self.safe_execfile(err.filename,self.user_ns)
599 self.safe_execfile(err.filename,self.user_ns)
608 except:
600 except:
609 self.showtraceback()
601 self.showtraceback()
610 else:
602 else:
611 try:
603 try:
612 f = open(err.filename)
604 f = open(err.filename)
613 try:
605 try:
614 # This should be inside a display_trap block and I
606 # This should be inside a display_trap block and I
615 # think it is.
607 # think it is.
616 sys.displayhook(f.read())
608 sys.displayhook(f.read())
617 finally:
609 finally:
618 f.close()
610 f.close()
619 except:
611 except:
620 self.showtraceback()
612 self.showtraceback()
621
613
622 def _should_recompile(self,e):
614 def _should_recompile(self,e):
623 """Utility routine for edit_syntax_error"""
615 """Utility routine for edit_syntax_error"""
624
616
625 if e.filename in ('<ipython console>','<input>','<string>',
617 if e.filename in ('<ipython console>','<input>','<string>',
626 '<console>','<BackgroundJob compilation>',
618 '<console>','<BackgroundJob compilation>',
627 None):
619 None):
628
620
629 return False
621 return False
630 try:
622 try:
631 if (self.autoedit_syntax and
623 if (self.autoedit_syntax and
632 not self.ask_yes_no('Return to editor to correct syntax error? '
624 not self.ask_yes_no('Return to editor to correct syntax error? '
633 '[Y/n] ','y')):
625 '[Y/n] ','y')):
634 return False
626 return False
635 except EOFError:
627 except EOFError:
636 return False
628 return False
637
629
638 def int0(x):
630 def int0(x):
639 try:
631 try:
640 return int(x)
632 return int(x)
641 except TypeError:
633 except TypeError:
642 return 0
634 return 0
643 # always pass integer line and offset values to editor hook
635 # always pass integer line and offset values to editor hook
644 try:
636 try:
645 self.hooks.fix_error_editor(e.filename,
637 self.hooks.fix_error_editor(e.filename,
646 int0(e.lineno),int0(e.offset),e.msg)
638 int0(e.lineno),int0(e.offset),e.msg)
647 except TryNext:
639 except TryNext:
648 warn('Could not open editor')
640 warn('Could not open editor')
649 return False
641 return False
650 return True
642 return True
651
643
652 #-------------------------------------------------------------------------
644 #-------------------------------------------------------------------------
653 # Things related to exiting
645 # Things related to exiting
654 #-------------------------------------------------------------------------
646 #-------------------------------------------------------------------------
655
647
656 def ask_exit(self):
648 def ask_exit(self):
657 """ Ask the shell to exit. Can be overiden and used as a callback. """
649 """ Ask the shell to exit. Can be overiden and used as a callback. """
658 self.exit_now = True
650 self.exit_now = True
659
651
660 def exit(self):
652 def exit(self):
661 """Handle interactive exit.
653 """Handle interactive exit.
662
654
663 This method calls the ask_exit callback."""
655 This method calls the ask_exit callback."""
664 if self.confirm_exit:
656 if self.confirm_exit:
665 if self.ask_yes_no('Do you really want to exit ([y]/n)?','y'):
657 if self.ask_yes_no('Do you really want to exit ([y]/n)?','y'):
666 self.ask_exit()
658 self.ask_exit()
667 else:
659 else:
668 self.ask_exit()
660 self.ask_exit()
669
661
670 #-------------------------------------------------------------------------
662 #-------------------------------------------------------------------------
671 # Things related to magics
663 # Things related to magics
672 #-------------------------------------------------------------------------
664 #-------------------------------------------------------------------------
673
665
674 def init_magics(self):
666 def init_magics(self):
675 super(TerminalInteractiveShell, self).init_magics()
667 super(TerminalInteractiveShell, self).init_magics()
676 self.register_magics(TerminalMagics)
668 self.register_magics(TerminalMagics)
677
669
678 def showindentationerror(self):
670 def showindentationerror(self):
679 super(TerminalInteractiveShell, self).showindentationerror()
671 super(TerminalInteractiveShell, self).showindentationerror()
680 print("If you want to paste code into IPython, try the "
672 print("If you want to paste code into IPython, try the "
681 "%paste and %cpaste magic functions.")
673 "%paste and %cpaste magic functions.")
682
674
683
675
684 InteractiveShellABC.register(TerminalInteractiveShell)
676 InteractiveShellABC.register(TerminalInteractiveShell)
General Comments 0
You need to be logged in to leave comments. Login now