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