##// END OF EJS Templates
Be a little smarter about invisible characters in terminal prompts...
Be a little smarter about invisible characters in terminal prompts This is a partial fix to #8724. Previously, only known color codes were considered to be invisible. Now, it looks for any kind of invisible sequence as defined by the \001 \002 delimiters (which is what readline uses). The situation could still be improved, as it still assumes that the number of invisible characters is constant for a given template. Making this work correctly with the existing API is awkward, so I didn't attempt it, especially since the readline frontend may be removed at some point in the near future.

File last commit:

r18850:500edeb7
r21605:8e996f80
Show More
test_inputsplitter.py
605 lines | 21.4 KiB | text/x-python | PythonLexer
/ IPython / core / tests / test_inputsplitter.py
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 # -*- coding: utf-8 -*-
MinRK
always pass single lines to transform.push...
r17813 """Tests for the inputsplitter module."""
Fernando Perez
Improve docs and comments of some internal tools, and of testing code
r3297
Thomas Kluyver
Convert print statements to print function calls...
r13348 from __future__ import print_function
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
MinRK
always pass single lines to transform.push...
r17813 # Copyright (c) IPython Development Team.
# Distributed under the terms of the Modified BSD License.
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 import unittest
Fernando Perez
Add test for missing input encoding. Back to 100% coverage.
r2718 import sys
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
import nose.tools as nt
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 from IPython.core import inputsplitter as isp
MinRK
always pass single lines to transform.push...
r17813 from IPython.core.inputtransformer import InputTransformer
Thomas Kluyver
Move and combine transformer tests
r10095 from IPython.core.tests.test_inputtransformer import syntax, syntax_ml
Thomas Kluyver
Return command to the next prompt if help was called halfway through a command. Also, ? at the end of a comment should not trigger help.
r4080 from IPython.testing import tools as tt
Thomas Kluyver
Fix various tests in IPython.core for Python 3.
r4895 from IPython.utils import py3compat
Thomas Kluyver
Fix references to raw_input()
r13355 from IPython.utils.py3compat import string_types, input
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663
#-----------------------------------------------------------------------------
# Semi-complete examples (also used as tests)
#-----------------------------------------------------------------------------
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780
# Note: at the bottom, there's a slightly more complete version of this that
# can be useful during development of code here.
Thomas Kluyver
Rename misleading use of raw_input so it's not automatically converted to input by 2to3.
r3119 def mini_interactive_loop(input_func):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 """Minimal example of the logic of an interactive interpreter loop.
This serves as an example, and it is used by the test system with a fake
raw_input that simulates interactive input."""
from IPython.core.inputsplitter import InputSplitter
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = InputSplitter()
# In practice, this input loop would be wrapped in an outside loop to read
# input indefinitely, until some exit/quit command was issued. Here we
# only illustrate the basic inner loop.
while isp.push_accepts_more():
indent = ' '*isp.indent_spaces
prompt = '>>> ' + indent
Thomas Kluyver
Rename misleading use of raw_input so it's not automatically converted to input by 2to3.
r3119 line = indent + input_func(prompt)
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp.push(line)
# Here we just return input so we can use it in a test suite, but a real
# interpreter would instead send it for execution somewhere.
src = isp.source_reset()
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 #print 'Input source was:\n', src # dbg
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 return src
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
#-----------------------------------------------------------------------------
Fernando Perez
Completed full block splitting for block-based frontends.
r2645 # Test utilities, just for local use
#-----------------------------------------------------------------------------
def assemble(block):
"""Assemble a block into multi-line sub-blocks."""
return ['\n'.join(sub_block)+'\n' for sub_block in block]
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663
def pseudo_input(lines):
"""Return a function that acts like raw_input but feeds the input list."""
ilines = iter(lines)
def raw_in(prompt):
try:
return next(ilines)
except StopIteration:
return ''
return raw_in
Fernando Perez
Completed full block splitting for block-based frontends.
r2645 #-----------------------------------------------------------------------------
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 # Tests
#-----------------------------------------------------------------------------
def test_spaces():
tests = [('', 0),
(' ', 1),
('\n', 0),
(' \n', 1),
('x', 0),
(' x', 1),
(' x',2),
(' x',4),
# Note: tabs are counted as a single whitespace!
('\tx', 1),
('\t x', 2),
]
Thomas Kluyver
Return command to the next prompt if help was called halfway through a command. Also, ? at the end of a comment should not trigger help.
r4080 tt.check_pairs(isp.num_ini_spaces, tests)
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
def test_remove_comments():
tests = [('text', 'text'),
('text # comment', 'text '),
('text # comment\n', 'text \n'),
('text # comment \n', 'text \n'),
('line # c \nline\n','line \nline\n'),
('line # c \nline#c2 \nline\nline #c\n\n',
'line \nline\nline\nline \n\n'),
]
Thomas Kluyver
Return command to the next prompt if help was called halfway through a command. Also, ? at the end of a comment should not trigger help.
r4080 tt.check_pairs(isp.remove_comments, tests)
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
def test_get_input_encoding():
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 encoding = isp.get_input_encoding()
Thomas Kluyver
Replace references to unicode and basestring
r13353 nt.assert_true(isinstance(encoding, string_types))
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 # simple-minded check that at least encoding a simple string works with the
# encoding we got.
Thomas Kluyver
Start using py3compat module.
r4731 nt.assert_equal(u'test'.encode(encoding), b'test')
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
Fernando Perez
Add test for missing input encoding. Back to 100% coverage.
r2718 class NoInputEncodingTestCase(unittest.TestCase):
def setUp(self):
self.old_stdin = sys.stdin
class X: pass
fake_stdin = X()
sys.stdin = fake_stdin
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Add test for missing input encoding. Back to 100% coverage.
r2718 def test(self):
# Verify that if sys.stdin has no 'encoding' attribute we do the right
# thing
enc = isp.get_input_encoding()
self.assertEqual(enc, 'ascii')
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Add test for missing input encoding. Back to 100% coverage.
r2718 def tearDown(self):
sys.stdin = self.old_stdin
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 class InputSplitterTestCase(unittest.TestCase):
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 def setUp(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 self.isp = isp.InputSplitter()
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
def test_reset(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = self.isp
isp.push('x=1')
isp.reset()
self.assertEqual(isp._buffer, [])
self.assertEqual(isp.indent_spaces, 0)
self.assertEqual(isp.source, '')
self.assertEqual(isp.code, None)
self.assertEqual(isp._is_complete, False)
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
def test_source(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 self.isp._store('1')
self.isp._store('2')
self.assertEqual(self.isp.source, '1\n2\n')
self.assertTrue(len(self.isp._buffer)>0)
self.assertEqual(self.isp.source_reset(), '1\n2\n')
self.assertEqual(self.isp._buffer, [])
self.assertEqual(self.isp.source, '')
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 def test_indent(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = self.isp # shorthand
isp.push('x=1')
self.assertEqual(isp.indent_spaces, 0)
isp.push('if 1:\n x=1')
self.assertEqual(isp.indent_spaces, 4)
isp.push('y=2\n')
self.assertEqual(isp.indent_spaces, 0)
Fernando Perez
Continue refactoring input handling across clients....
r3085
def test_indent2(self):
isp = self.isp
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp.push('if 1:')
self.assertEqual(isp.indent_spaces, 4)
isp.push(' x=1')
self.assertEqual(isp.indent_spaces, 4)
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 # Blank lines shouldn't change the indent level
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp.push(' '*2)
self.assertEqual(isp.indent_spaces, 4)
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
Fernando Perez
Continue refactoring input handling across clients....
r3085 def test_indent3(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = self.isp
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 # When a multiline statement contains parens or multiline strings, we
# shouldn't get confused.
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp.push("if 1:")
isp.push(" x = (1+\n 2)")
self.assertEqual(isp.indent_spaces, 4)
Bernardo B. Marques
remove all trailling spaces
r4872
Paul Ivanov
fix trailing whitespace from reseting indentation
r4204 def test_indent4(self):
isp = self.isp
# whitespace after ':' should not screw up indent level
isp.push('if 1: \n x=1')
self.assertEqual(isp.indent_spaces, 4)
isp.push('y=2\n')
self.assertEqual(isp.indent_spaces, 0)
isp.push('if 1:\t\n x=1')
self.assertEqual(isp.indent_spaces, 4)
isp.push('y=2\n')
self.assertEqual(isp.indent_spaces, 0)
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
David Warde-Farley
New tests related to issue #142.
r3693 def test_dedent_pass(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = self.isp # shorthand
David Warde-Farley
New tests related to issue #142.
r3693 # should NOT cause dedent
isp.push('if 1:\n passes = 5')
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 self.assertEqual(isp.indent_spaces, 4)
David Warde-Farley
New tests related to issue #142.
r3693 isp.push('if 1:\n pass')
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 self.assertEqual(isp.indent_spaces, 0)
David Warde-Farley
New tests related to issue #142.
r3693 isp.push('if 1:\n pass ')
self.assertEqual(isp.indent_spaces, 0)
Aaron Meurer
`yield`, `break`, and `continue` automatically dedent...
r7824 def test_dedent_break(self):
isp = self.isp # shorthand
# should NOT cause dedent
isp.push('while 1:\n breaks = 5')
self.assertEqual(isp.indent_spaces, 4)
isp.push('while 1:\n break')
self.assertEqual(isp.indent_spaces, 0)
isp.push('while 1:\n break ')
self.assertEqual(isp.indent_spaces, 0)
def test_dedent_continue(self):
isp = self.isp # shorthand
# should NOT cause dedent
isp.push('while 1:\n continues = 5')
self.assertEqual(isp.indent_spaces, 4)
isp.push('while 1:\n continue')
self.assertEqual(isp.indent_spaces, 0)
isp.push('while 1:\n continue ')
self.assertEqual(isp.indent_spaces, 0)
David Warde-Farley
New tests related to issue #142.
r3693 def test_dedent_raise(self):
isp = self.isp # shorthand
# should NOT cause dedent
isp.push('if 1:\n raised = 4')
self.assertEqual(isp.indent_spaces, 4)
isp.push('if 1:\n raise TypeError()')
self.assertEqual(isp.indent_spaces, 0)
isp.push('if 1:\n raise')
self.assertEqual(isp.indent_spaces, 0)
isp.push('if 1:\n raise ')
self.assertEqual(isp.indent_spaces, 0)
def test_dedent_return(self):
isp = self.isp # shorthand
# should NOT cause dedent
isp.push('if 1:\n returning = 4')
self.assertEqual(isp.indent_spaces, 4)
isp.push('if 1:\n return 5 + 493')
self.assertEqual(isp.indent_spaces, 0)
isp.push('if 1:\n return')
self.assertEqual(isp.indent_spaces, 0)
isp.push('if 1:\n return ')
self.assertEqual(isp.indent_spaces, 0)
isp.push('if 1:\n return(0)')
self.assertEqual(isp.indent_spaces, 0)
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 def test_push(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = self.isp
self.assertTrue(isp.push('x=1'))
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
def test_push2(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = self.isp
self.assertFalse(isp.push('if 1:'))
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 for line in [' x=1', '# a comment', ' y=2']:
Thomas Kluyver
Revised input transformation framework.
r10106 print(line)
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 self.assertTrue(isp.push(line))
Bernardo B. Marques
remove all trailling spaces
r4872
Thomas Kluyver
Add test for inputsplitter bug.
r3747 def test_push3(self):
isp = self.isp
isp.push('if True:')
isp.push(' a = 1')
self.assertFalse(isp.push('b = [1,'))
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 def test_push_accepts_more(self):
isp = self.isp
isp.push('x=1')
self.assertFalse(isp.push_accepts_more())
def test_push_accepts_more2(self):
isp = self.isp
isp.push('if 1:')
self.assertTrue(isp.push_accepts_more())
isp.push(' x=1')
self.assertTrue(isp.push_accepts_more())
isp.push('')
self.assertFalse(isp.push_accepts_more())
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 def test_push_accepts_more3(self):
isp = self.isp
isp.push("x = (2+\n3)")
self.assertFalse(isp.push_accepts_more())
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 def test_push_accepts_more4(self):
isp = self.isp
Fernando Perez
Split blockbreaker tests into a separate file and clean up api....
r2633 # When a multiline statement contains parens or multiline strings, we
# shouldn't get confused.
# FIXME: we should be able to better handle de-dents in statements like
# multiline strings and multiline expressions (continued with \ or
# parens). Right now we aren't handling the indentation tracking quite
# correctly with this, though in practice it may not be too much of a
# problem. We'll need to see.
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp.push("if 1:")
isp.push(" x = (2+")
isp.push(" 3)")
self.assertTrue(isp.push_accepts_more())
isp.push(" y = 3")
self.assertTrue(isp.push_accepts_more())
isp.push('')
self.assertFalse(isp.push_accepts_more())
Bernardo B. Marques
remove all trailling spaces
r4872
Thomas Kluyver
Require blank line to end input cell immediately after dedenting....
r3461 def test_push_accepts_more5(self):
isp = self.isp
isp.push('try:')
isp.push(' a = 5')
isp.push('except:')
isp.push(' raise')
Thomas Kluyver
Simplify InputSplitter by stripping out input_mode distinction
r10251 # We want to be able to add an else: block at this point, so it should
# wait for a blank line.
Thomas Kluyver
Require blank line to end input cell immediately after dedenting....
r3461 self.assertTrue(isp.push_accepts_more())
Fernando Perez
Fix bug with lines ending in continuation markers (\)....
r3013
def test_continuation(self):
isp = self.isp
isp.push("import os, \\")
self.assertTrue(isp.push_accepts_more())
isp.push("sys")
self.assertFalse(isp.push_accepts_more())
Fernando Perez
push() now swallows syntax errors and immediately produces a 'ready'...
r2635
def test_syntax_error(self):
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp = self.isp
Fernando Perez
push() now swallows syntax errors and immediately produces a 'ready'...
r2635 # Syntax errors immediately produce a 'ready' block, so the invalid
# Python can be sent to the kernel for evaluation with possible ipython
# special-syntax conversion.
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 isp.push('run foo')
self.assertFalse(isp.push_accepts_more())
Fernando Perez
Completed full block splitting for block-based frontends.
r2645
Fernando Perez
Stop-gap fix for crash with unicode input....
r3126 def test_unicode(self):
self.isp.push(u"Pérez")
self.isp.push(u'\xc3\xa9')
Thomas Kluyver
Further fixes and tweaks for inputsplitter.
r3455 self.isp.push(u"u'\xc3\xa9'")
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663
Aaron Meurer
Line continuations now terminate after one blank line (#2108)...
r7823 def test_line_continuation(self):
""" Test issue #2108."""
isp = self.isp
# A blank line after a line continuation should not accept more
isp.push("1 \\\n\n")
self.assertFalse(isp.push_accepts_more())
# Whitespace after a \ is a SyntaxError. The only way to test that
# here is to test that push doesn't accept more (as with
# test_syntax_error() above).
isp.push(r"1 \ ")
self.assertFalse(isp.push_accepts_more())
# Even if the line is continuable (c.f. the regular Python
# interpreter)
isp.push(r"(1 \ ")
self.assertFalse(isp.push_accepts_more())
Thomas Kluyver
Four possible states for completion reply, & indent hint
r17804 def test_check_complete(self):
Thomas Kluyver
Expose IPython machinery for testing code completeness
r17624 isp = self.isp
Thomas Kluyver
Four possible states for completion reply, & indent hint
r17804 self.assertEqual(isp.check_complete("a = 1"), ('complete', None))
self.assertEqual(isp.check_complete("for a in range(5):"), ('incomplete', 4))
self.assertEqual(isp.check_complete("raise = 2"), ('invalid', None))
self.assertEqual(isp.check_complete("a = [1,\n2,"), ('incomplete', 0))
Min RK
SyntaxWarning in compile indicates invalid input
r18850 self.assertEqual(isp.check_complete("def a():\n x=1\n global x"), ('invalid', None))
Thomas Kluyver
Expose IPython machinery for testing code completeness
r17624
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 class InteractiveLoopTestCase(unittest.TestCase):
"""Tests for an interactive loop like a python shell.
"""
def check_ns(self, lines, ns):
"""Validate that the given input lines produce the resulting namespace.
Note: the input lines are given exactly as they would be typed in an
auto-indenting environment, as mini_interactive_loop above already does
auto-indenting and prepends spaces to the input.
"""
src = mini_interactive_loop(pseudo_input(lines))
test_ns = {}
Thomas Kluyver
Fix exec statements for Py 3...
r13350 exec(src, test_ns)
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 # We can't check that the provided ns is identical to the test_ns,
# because Python fills test_ns with extra keys (copyright, etc). But
# we can check that the given dict is *contained* in test_ns
Thomas Kluyver
Fix references to dict.iteritems and dict.itervalues
r13361 for k,v in ns.items():
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 self.assertEqual(test_ns[k], v)
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 def test_simple(self):
self.check_ns(['x=1'], dict(x=1))
def test_simple2(self):
self.check_ns(['if 1:', 'x=2'], dict(x=2))
def test_xy(self):
self.check_ns(['x=1; y=2'], dict(x=1, y=2))
def test_abc(self):
self.check_ns(['if 1:','a=1','b=2','c=3'], dict(a=1, b=2, c=3))
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Renamed to inputsplitter, added more tests and examples....
r2663 def test_multi(self):
self.check_ns(['x =(1+','1+','2)'], dict(x=4))
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
First pass of input syntax transformation support
r2719
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 class IPythonInputTestCase(InputSplitterTestCase):
"""By just creating a new class whose .isp is a different instance, we
re-run the same test battery on the new input splitter.
In addition, this runs the tests over the syntax and syntax_ml dicts that
were tested by individual functions, as part of the OO interface.
Fernando Perez
Add support for accessing raw data to inputsplitter....
r3080
It also makes some checks on the raw buffer storage.
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 """
Fernando Perez
Fix bug with IPythonInputSplitter in block input mode.
r2861
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 def setUp(self):
Thomas Kluyver
Simplify InputSplitter by stripping out input_mode distinction
r10251 self.isp = isp.IPythonInputSplitter()
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780
def test_syntax(self):
"""Call all single-line syntax tests from the main object"""
isp = self.isp
Thomas Kluyver
Fix references to dict.iteritems and dict.itervalues
r13361 for example in syntax.values():
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 for raw, out_t in example:
if raw.startswith(' '):
continue
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Fix '%%cellm?' case, make tests more stringent to catch error.
r7000 isp.push(raw+'\n')
Thomas Kluyver
Simplify IPythonInputSplitter API
r13912 out_raw = isp.source_raw
out = isp.source_reset()
Thomas Kluyver
Reuse common code for inputsplitter and prefilter.
r4746 self.assertEqual(out.rstrip(), out_t,
tt.pair_fail_msg.format("inputsplitter",raw, out_t, out))
Fernando Perez
Add support for accessing raw data to inputsplitter....
r3080 self.assertEqual(out_raw.rstrip(), raw.rstrip())
Fernando Perez
Fix bug with IPythonInputSplitter in block input mode.
r2861
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 def test_syntax_multiline(self):
isp = self.isp
Thomas Kluyver
Fix references to dict.iteritems and dict.itervalues
r13361 for example in syntax_ml.values():
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 for line_pairs in example:
Thomas Kluyver
Fix tests in IPython.core
r10097 out_t_parts = []
raw_parts = []
Fernando Perez
Add support for accessing raw data to inputsplitter....
r3080 for lraw, out_t_part in line_pairs:
Thomas Kluyver
Fix tests in IPython.core
r10097 if out_t_part is not None:
out_t_parts.append(out_t_part)
if lraw is not None:
isp.push(lraw)
raw_parts.append(lraw)
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780
Thomas Kluyver
Simplify IPythonInputSplitter API
r13912 out_raw = isp.source_raw
out = isp.source_reset()
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 out_t = '\n'.join(out_t_parts).rstrip()
Fernando Perez
Add support for accessing raw data to inputsplitter....
r3080 raw = '\n'.join(raw_parts).rstrip()
self.assertEqual(out.rstrip(), out_t)
self.assertEqual(out_raw.rstrip(), raw)
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Add tests for new method.
r7488 def test_syntax_multiline_cell(self):
isp = self.isp
Thomas Kluyver
Fix references to dict.iteritems and dict.itervalues
r13361 for example in syntax_ml.values():
Aaron Meurer
Line continuations now terminate after one blank line (#2108)...
r7823
Fernando Perez
Add tests for new method.
r7488 out_t_parts = []
for line_pairs in example:
Thomas Kluyver
Fix tests in IPython.core
r10097 raw = '\n'.join(r for r, _ in line_pairs if r is not None)
out_t = '\n'.join(t for _,t in line_pairs if t is not None)
Fernando Perez
Add tests for new method.
r7488 out = isp.transform_cell(raw)
# Match ignoring trailing whitespace
self.assertEqual(out.rstrip(), out_t.rstrip())
MinRK
test that cell magic preempts other transformers
r11459
def test_cellmagic_preempt(self):
isp = self.isp
for raw, name, line, cell in [
("%%cellm a\nIn[1]:", u'cellm', u'a', u'In[1]:'),
Thomas Kluyver
Only allow '>>>' prompt without space afterwards if line is blank...
r17038 ("%%cellm \nline\n>>> hi", u'cellm', u'', u'line\n>>> hi'),
(">>> %%cellm \nline\n>>> hi", u'cellm', u'', u'line\nhi'),
("%%cellm \n>>> hi", u'cellm', u'', u'hi'),
MinRK
test that cell magic preempts other transformers
r11459 ("%%cellm \nline1\nline2", u'cellm', u'', u'line1\nline2'),
("%%cellm \nline1\\\\\nline2", u'cellm', u'', u'line1\\\\\nline2'),
]:
expected = "get_ipython().run_cell_magic(%r, %r, %r)" % (
name, line, cell
)
out = isp.transform_cell(raw)
self.assertEqual(out.rstrip(), expected.rstrip())
MinRK
always pass single lines to transform.push...
r17813
def test_multiline_passthrough(self):
isp = self.isp
class CommentTransformer(InputTransformer):
def __init__(self):
self._lines = []
def push(self, line):
self._lines.append(line + '#')
def reset(self):
text = '\n'.join(self._lines)
self._lines = []
return text
MinRK
test that cell magic preempts other transformers
r11459
MinRK
always pass single lines to transform.push...
r17813 isp.physical_line_transforms.insert(0, CommentTransformer())
MinRK
test that cell magic preempts other transformers
r11459
MinRK
always pass single lines to transform.push...
r17813 for raw, expected in [
("a=5", "a=5#"),
("%ls foo", "get_ipython().magic(%r)" % u'ls foo#'),
("!ls foo\n%ls bar", "get_ipython().system(%r)\nget_ipython().magic(%r)" % (
u'ls foo#', u'ls bar#'
)),
("1\n2\n3\n%ls foo\n4\n5", "1#\n2#\n3#\nget_ipython().magic(%r)\n4#\n5#" % u'ls foo#'),
]:
out = isp.transform_cell(raw)
self.assertEqual(out.rstrip(), expected.rstrip())
Fernando Perez
Fix bug with IPythonInputSplitter in block input mode.
r2861
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 #-----------------------------------------------------------------------------
Fernando Perez
Fix bug with IPythonInputSplitter in block input mode.
r2861 # Main - use as a script, mostly for developer experiments
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 #-----------------------------------------------------------------------------
if __name__ == '__main__':
# A simple demo for interactive experimentation. This code will not get
Fernando Perez
Fix bug with IPythonInputSplitter in block input mode.
r2861 # picked up by any test suite.
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 from IPython.core.inputsplitter import InputSplitter, IPythonInputSplitter
Fernando Perez
Final cleanups responding to Brian's code review....
r2782
# configure here the syntax to use, prompt and whether to autoindent
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 #isp, start_prompt = InputSplitter(), '>>> '
isp, start_prompt = IPythonInputSplitter(), 'In> '
autoindent = True
#autoindent = False
Bernardo B. Marques
remove all trailling spaces
r4872
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 try:
while True:
prompt = start_prompt
while isp.push_accepts_more():
indent = ' '*isp.indent_spaces
if autoindent:
Thomas Kluyver
Fix references to raw_input()
r13355 line = indent + input(prompt+indent)
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 else:
Thomas Kluyver
Fix references to raw_input()
r13355 line = input(prompt)
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 isp.push(line)
prompt = '... '
# Here we just return input so we can use it in a test suite, but a
# real interpreter would instead send it for execution somewhere.
Fernando Perez
Final documentation changes from code review with Brian, ready to merge.
r2828 #src = isp.source; raise EOFError # dbg
Thomas Kluyver
Simplify IPythonInputSplitter API
r13912 raw = isp.source_raw
src = isp.source_reset()
Thomas Kluyver
Convert print statements to print function calls...
r13348 print('Input source was:\n', src)
print('Raw source was:\n', raw)
Fernando Perez
Completed first pass of inputsplitter with IPython syntax....
r2780 except EOFError:
Thomas Kluyver
Convert print statements to print function calls...
r13348 print('Bye')
Fernando Perez
Clean up implementation of cell magics in inputsplitter....
r6985
# Tests for cell magics support
def test_last_blank():
nt.assert_false(isp.last_blank(''))
nt.assert_false(isp.last_blank('abc'))
nt.assert_false(isp.last_blank('abc\n'))
nt.assert_false(isp.last_blank('abc\na'))
nt.assert_true(isp.last_blank('\n'))
nt.assert_true(isp.last_blank('\n '))
nt.assert_true(isp.last_blank('abc\n '))
nt.assert_true(isp.last_blank('abc\n\n'))
nt.assert_true(isp.last_blank('abc\nd\n\n'))
nt.assert_true(isp.last_blank('abc\nd\ne\n\n'))
nt.assert_true(isp.last_blank('abc \n \n \n\n'))
def test_last_two_blanks():
nt.assert_false(isp.last_two_blanks(''))
nt.assert_false(isp.last_two_blanks('abc'))
nt.assert_false(isp.last_two_blanks('abc\n'))
nt.assert_false(isp.last_two_blanks('abc\n\na'))
nt.assert_false(isp.last_two_blanks('abc\n \n'))
nt.assert_false(isp.last_two_blanks('abc\n\n'))
nt.assert_true(isp.last_two_blanks('\n\n'))
nt.assert_true(isp.last_two_blanks('\n\n '))
nt.assert_true(isp.last_two_blanks('\n \n'))
nt.assert_true(isp.last_two_blanks('abc\n\n '))
nt.assert_true(isp.last_two_blanks('abc\n\n\n'))
nt.assert_true(isp.last_two_blanks('abc\n\n \n'))
nt.assert_true(isp.last_two_blanks('abc\n\n \n '))
nt.assert_true(isp.last_two_blanks('abc\n\n \n \n'))
nt.assert_true(isp.last_two_blanks('abc\nd\n\n\n'))
nt.assert_true(isp.last_two_blanks('abc\nd\ne\nf\n\n\n'))
Fernando Perez
Fix test failures under Python 3....
r7004 class CellMagicsCommon(object):
Aaron Meurer
Line continuations now terminate after one blank line (#2108)...
r7823
Fernando Perez
Clean up implementation of cell magics in inputsplitter....
r6985 def test_whole_cell(self):
src = "%%cellm line\nbody\n"
Thomas Kluyver
Simplify IPythonInputSplitter API
r13912 out = self.sp.transform_cell(src)
Thomas Kluyver
Fix tests in IPython.core
r10097 ref = u"get_ipython().run_cell_magic({u}'cellm', {u}'line', {u}'body')\n"
Fernando Perez
Fix test failures under Python 3....
r7004 nt.assert_equal(out, py3compat.u_format(ref))
Thomas Kluyver
Allow IPythonInputSplitter to accept cell magics containing blank lines
r10252
def test_cellmagic_help(self):
self.sp.push('%%cellm?')
nt.assert_false(self.sp.push_accepts_more())
Fernando Perez
Fix test failures under Python 3....
r7004
def tearDown(self):
self.sp.reset()
class CellModeCellMagics(CellMagicsCommon, unittest.TestCase):
Thomas Kluyver
Allow IPythonInputSplitter to accept cell magics containing blank lines
r10252 sp = isp.IPythonInputSplitter(line_input_checker=False)
Fernando Perez
Clean up implementation of cell magics in inputsplitter....
r6985
def test_incremental(self):
sp = self.sp
Thomas Kluyver
Allow IPythonInputSplitter to accept cell magics containing blank lines
r10252 sp.push('%%cellm firstline\n')
Fernando Perez
Clean up implementation of cell magics in inputsplitter....
r6985 nt.assert_true(sp.push_accepts_more()) #1
Thomas Kluyver
Allow IPythonInputSplitter to accept cell magics containing blank lines
r10252 sp.push('line2\n')
nt.assert_true(sp.push_accepts_more()) #2
sp.push('\n')
# This should accept a blank line and carry on until the cell is reset
nt.assert_true(sp.push_accepts_more()) #3
Fernando Perez
Clean up implementation of cell magics in inputsplitter....
r6985
Fernando Perez
Fix test failures under Python 3....
r7004 class LineModeCellMagics(CellMagicsCommon, unittest.TestCase):
Thomas Kluyver
Allow IPythonInputSplitter to accept cell magics containing blank lines
r10252 sp = isp.IPythonInputSplitter(line_input_checker=True)
Fernando Perez
Clean up implementation of cell magics in inputsplitter....
r6985
def test_incremental(self):
sp = self.sp
sp.push('%%cellm line2\n')
nt.assert_true(sp.push_accepts_more()) #1
sp.push('\n')
Thomas Kluyver
Allow IPythonInputSplitter to accept cell magics containing blank lines
r10252 # In this case, a blank line should end the cell magic
Fernando Perez
Clean up implementation of cell magics in inputsplitter....
r6985 nt.assert_false(sp.push_accepts_more()) #2