##// END OF EJS Templates
Merge branch 'master' into inputtransformer2
Thomas Kluyver -
r24401:1ae28d28 merge
parent child Browse files
Show More
@@ -0,0 +1,33 b''
1 BSD 3-Clause License
2
3 - Copyright (c) 2008-Present, IPython Development Team
4 - Copyright (c) 2001-2007, Fernando Perez <fernando.perez@colorado.edu>
5 - Copyright (c) 2001, Janko Hauser <jhauser@zscout.de>
6 - Copyright (c) 2001, Nathaniel Gray <n8gray@caltech.edu>
7
8 All rights reserved.
9
10 Redistribution and use in source and binary forms, with or without
11 modification, are permitted provided that the following conditions are met:
12
13 * Redistributions of source code must retain the above copyright notice, this
14 list of conditions and the following disclaimer.
15
16 * Redistributions in binary form must reproduce the above copyright notice,
17 this list of conditions and the following disclaimer in the documentation
18 and/or other materials provided with the distribution.
19
20 * Neither the name of the copyright holder nor the names of its
21 contributors may be used to endorse or promote products derived from
22 this software without specific prior written permission.
23
24 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
25 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
27 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
28 FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
30 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
31 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
32 OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
33 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
@@ -0,0 +1,7 b''
1 A couple of unused function and methods have been deprecated and will be removed
2 in future versions:
3
4 - ``IPython.utils.io.raw_print_err``
5 - ``IPython.utils.io.raw_print``
6
7
@@ -2,10 +2,10 b''
2 language: python
2 language: python
3 python:
3 python:
4 - "nightly"
4 - "nightly"
5 - "3.7-dev"
5 - 3.6
6 - 3.6
6 - 3.5
7 - 3.5
7 - 3.4
8 - 3.4
8 - 3.3
9 sudo: false
9 sudo: false
10 env:
10 env:
11 global:
11 global:
@@ -16,9 +16,10 b' before_install:'
16 install:
16 install:
17 - pip install setuptools pip --upgrade
17 - pip install setuptools pip --upgrade
18 - pip install -e file://$PWD#egg=ipython[test] --upgrade
18 - pip install -e file://$PWD#egg=ipython[test] --upgrade
19 - pip install codecov --upgrade
19 - pip install codecov check-manifest --upgrade
20 - sudo apt-get install graphviz
20 - sudo apt-get install graphviz
21 script:
21 script:
22 - check-manifest
22 - cd /tmp && iptest --coverage xml && cd -
23 - cd /tmp && iptest --coverage xml && cd -
23 # On the latest Python only, make sure that the docs build.
24 # On the latest Python only, make sure that the docs build.
24 - |
25 - |
@@ -3,39 +3,8 b''
3 =============================
3 =============================
4
4
5 IPython is licensed under the terms of the Modified BSD License (also known as
5 IPython is licensed under the terms of the Modified BSD License (also known as
6 New or Revised or 3-Clause BSD), as follows:
6 New or Revised or 3-Clause BSD). See the LICENSE file.
7
7
8 - Copyright (c) 2008-2014, IPython Development Team
9 - Copyright (c) 2001-2007, Fernando Perez <fernando.perez@colorado.edu>
10 - Copyright (c) 2001, Janko Hauser <jhauser@zscout.de>
11 - Copyright (c) 2001, Nathaniel Gray <n8gray@caltech.edu>
12
13 All rights reserved.
14
15 Redistribution and use in source and binary forms, with or without
16 modification, are permitted provided that the following conditions are met:
17
18 Redistributions of source code must retain the above copyright notice, this
19 list of conditions and the following disclaimer.
20
21 Redistributions in binary form must reproduce the above copyright notice, this
22 list of conditions and the following disclaimer in the documentation and/or
23 other materials provided with the distribution.
24
25 Neither the name of the IPython Development Team nor the names of its
26 contributors may be used to endorse or promote products derived from this
27 software without specific prior written permission.
28
29 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
30 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
31 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
32 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
33 FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
34 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
35 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
36 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
37 OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
38 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39
8
40 About the IPython Development Team
9 About the IPython Development Team
41 ----------------------------------
10 ----------------------------------
@@ -45,9 +14,7 b' Fernando Perez began IPython in 2001 based on code from Janko Hauser'
45 the project lead.
14 the project lead.
46
15
47 The IPython Development Team is the set of all contributors to the IPython
16 The IPython Development Team is the set of all contributors to the IPython
48 project. This includes all of the IPython subprojects. A full list with
17 project. This includes all of the IPython subprojects.
49 details is kept in the documentation directory, in the file
50 ``about/credits.txt``.
51
18
52 The core team that coordinates development on GitHub can be found here:
19 The core team that coordinates development on GitHub can be found here:
53 https://github.com/ipython/.
20 https://github.com/ipython/.
@@ -27,12 +27,12 b' import sys'
27 #-----------------------------------------------------------------------------
27 #-----------------------------------------------------------------------------
28
28
29 # Don't forget to also update setup.py when this changes!
29 # Don't forget to also update setup.py when this changes!
30 if sys.version_info < (3,3):
30 if sys.version_info < (3,4):
31 raise ImportError(
31 raise ImportError(
32 """
32 """
33 IPython 6.0+ does not support Python 2.6, 2.7, 3.0, 3.1, or 3.2.
33 IPython 7.0+ supports Python 3.4 and above.
34 When using Python 2.7, please install IPython 5.x LTS Long Term Support version.
34 When using Python 2.7, please install IPython 5.x LTS Long Term Support version.
35 Beginning with IPython 6.0, Python 3.3 and above is required.
35 Python 3.3 was supported up to IPython 6.x.
36
36
37 See IPython `README.rst` file for more information:
37 See IPython `README.rst` file for more information:
38
38
@@ -6,7 +6,7 b' Shim to maintain backwards compatibility with old IPython.consoleapp imports.'
6
6
7 from warnings import warn
7 from warnings import warn
8
8
9 warn("The `IPython.consoleapp` package has been deprecated. "
9 warn("The `IPython.consoleapp` package has been deprecated since IPython 4.0."
10 "You should import from jupyter_client.consoleapp instead.")
10 "You should import from jupyter_client.consoleapp instead.", stacklevel=2)
11
11
12 from jupyter_client.consoleapp import *
12 from jupyter_client.consoleapp import *
@@ -90,13 +90,31 b' class CachingCompiler(codeop.Compile):'
90 # stdlib that call it outside our control go through our codepath
90 # stdlib that call it outside our control go through our codepath
91 # (otherwise we'd lose our tracebacks).
91 # (otherwise we'd lose our tracebacks).
92 linecache.checkcache = check_linecache_ipython
92 linecache.checkcache = check_linecache_ipython
93
94
95 def _fix_module_ds(self, module):
96 """
97 Starting in python 3.7 the AST for mule have changed, and if
98 the first expressions encountered is a string it is attached to the
99 `docstring` attribute of the `Module` ast node.
100
101 This breaks IPython, as if this string is the only expression, IPython
102 will not return it as the result of the current cell.
103 """
104 from ast import Str, Expr, Module, fix_missing_locations
105 docstring = getattr(module, 'docstring', None)
106 if not docstring:
107 return module
108 new_body=[Expr(Str(docstring, lineno=1, col_offset=0), lineno=1, col_offset=0)]
109 new_body.extend(module.body)
110 return fix_missing_locations(Module(new_body))
93
111
94 def ast_parse(self, source, filename='<unknown>', symbol='exec'):
112 def ast_parse(self, source, filename='<unknown>', symbol='exec'):
95 """Parse code to an AST with the current compiler flags active.
113 """Parse code to an AST with the current compiler flags active.
96
114
97 Arguments are exactly the same as ast.parse (in the standard library),
115 Arguments are exactly the same as ast.parse (in the standard library),
98 and are passed to the built-in compile function."""
116 and are passed to the built-in compile function."""
99 return compile(source, filename, symbol, self.flags | PyCF_ONLY_AST, 1)
117 return self._fix_module_ds(compile(source, filename, symbol, self.flags | PyCF_ONLY_AST, 1))
100
118
101 def reset_compiler_flags(self):
119 def reset_compiler_flags(self):
102 """Reset compiler flags to default state."""
120 """Reset compiler flags to default state."""
@@ -576,9 +576,9 b' class Completer(Configurable):'
576 """
576 """
577 ).tag(config=True)
577 ).tag(config=True)
578
578
579 use_jedi = Bool(default_value=JEDI_INSTALLED,
579 use_jedi = Bool(default_value=False,
580 help="Experimental: Use Jedi to generate autocompletions. "
580 help="Experimental: Use Jedi to generate autocompletions. "
581 "Default to True if jedi is installed").tag(config=True)
581 "Off by default.").tag(config=True)
582
582
583 jedi_compute_type_timeout = Int(default_value=400,
583 jedi_compute_type_timeout = Int(default_value=400,
584 help="""Experimental: restrict time (in milliseconds) during which Jedi can compute types.
584 help="""Experimental: restrict time (in milliseconds) during which Jedi can compute types.
@@ -683,7 +683,7 b' class Completer(Configurable):'
683 Assuming the text is of the form NAME.NAME....[NAME], and is
683 Assuming the text is of the form NAME.NAME....[NAME], and is
684 evaluatable in self.namespace or self.global_namespace, it will be
684 evaluatable in self.namespace or self.global_namespace, it will be
685 evaluated and its attributes (as revealed by dir()) are used as
685 evaluated and its attributes (as revealed by dir()) are used as
686 possible completions. (For class instances, class members are are
686 possible completions. (For class instances, class members are
687 also considered.)
687 also considered.)
688
688
689 WARNING: this can still invoke arbitrary C code, if an object
689 WARNING: this can still invoke arbitrary C code, if an object
@@ -869,7 +869,7 b' def position_to_cursor(text:str, offset:int)->Tuple[int, int]:'
869
869
870 """
870 """
871
871
872 assert 0 < offset <= len(text) , "0 < %s <= %s" % (offset , len(text))
872 assert 0 <= offset <= len(text) , "0 <= %s <= %s" % (offset , len(text))
873
873
874 before = text[:offset]
874 before = text[:offset]
875 blines = before.split('\n') # ! splitnes trim trailing \n
875 blines = before.split('\n') # ! splitnes trim trailing \n
@@ -949,8 +949,8 b' def _formatparamchildren(parameter) -> str:'
949
949
950 Jedi does not expose a simple way to get `param=value` from its API.
950 Jedi does not expose a simple way to get `param=value` from its API.
951
951
952 Prameter
952 Parameter
953 ========
953 =========
954
954
955 parameter:
955 parameter:
956 Jedi's function `Param`
956 Jedi's function `Param`
@@ -1340,7 +1340,6 b' class IPCompleter(Completer):'
1340 namespaces.append(self.global_namespace)
1340 namespaces.append(self.global_namespace)
1341
1341
1342 completion_filter = lambda x:x
1342 completion_filter = lambda x:x
1343 # cursor_pos is an it, jedi wants line and column
1344 offset = cursor_to_position(text, cursor_line, cursor_column)
1343 offset = cursor_to_position(text, cursor_line, cursor_column)
1345 # filter output if we are completing for object members
1344 # filter output if we are completing for object members
1346 if offset:
1345 if offset:
@@ -1356,7 +1355,7 b' class IPCompleter(Completer):'
1356 raise ValueError("Don't understand self.omit__names == {}".format(self.omit__names))
1355 raise ValueError("Don't understand self.omit__names == {}".format(self.omit__names))
1357
1356
1358 interpreter = jedi.Interpreter(
1357 interpreter = jedi.Interpreter(
1359 text, namespaces, column=cursor_column, line=cursor_line + 1)
1358 text[:offset], namespaces, column=cursor_column, line=cursor_line + 1)
1360 try_jedi = True
1359 try_jedi = True
1361
1360
1362 try:
1361 try:
@@ -1371,7 +1370,7 b' class IPCompleter(Completer):'
1371 next_to_last_tree = interpreter._get_module().tree_node.children[-2]
1370 next_to_last_tree = interpreter._get_module().tree_node.children[-2]
1372 completing_string = False
1371 completing_string = False
1373 if isinstance(next_to_last_tree, ErrorLeaf):
1372 if isinstance(next_to_last_tree, ErrorLeaf):
1374 completing_string = next_to_last_tree.value[0] in {'"', "'"}
1373 completing_string = next_to_last_tree.value.lstrip()[0] in {'"', "'"}
1375 # if we are in a string jedi is likely not the right candidate for
1374 # if we are in a string jedi is likely not the right candidate for
1376 # now. Skip it.
1375 # now. Skip it.
1377 try_jedi = not completing_string
1376 try_jedi = not completing_string
@@ -1805,11 +1804,16 b' class IPCompleter(Completer):'
1805 category=ProvisionalCompleterWarning, stacklevel=2)
1804 category=ProvisionalCompleterWarning, stacklevel=2)
1806
1805
1807 seen = set()
1806 seen = set()
1808 for c in self._completions(text, offset, _timeout=self.jedi_compute_type_timeout/1000):
1807 try:
1809 if c and (c in seen):
1808 for c in self._completions(text, offset, _timeout=self.jedi_compute_type_timeout/1000):
1810 continue
1809 if c and (c in seen):
1811 yield c
1810 continue
1812 seen.add(c)
1811 yield c
1812 seen.add(c)
1813 except KeyboardInterrupt:
1814 """if completions take too long and users send keyboard interrupt,
1815 do not crash and return ASAP. """
1816 pass
1813
1817
1814 def _completions(self, full_text: str, offset: int, *, _timeout)->Iterator[Completion]:
1818 def _completions(self, full_text: str, offset: int, *, _timeout)->Iterator[Completion]:
1815 """
1819 """
@@ -667,7 +667,7 b' class Pretty(TextDisplayObject):'
667 class HTML(TextDisplayObject):
667 class HTML(TextDisplayObject):
668
668
669 def _repr_html_(self):
669 def _repr_html_(self):
670 return self.data
670 return self._data_and_metadata()
671
671
672 def __html__(self):
672 def __html__(self):
673 """
673 """
@@ -681,20 +681,23 b' class HTML(TextDisplayObject):'
681 class Markdown(TextDisplayObject):
681 class Markdown(TextDisplayObject):
682
682
683 def _repr_markdown_(self):
683 def _repr_markdown_(self):
684 return self.data
684 return self._data_and_metadata()
685
685
686
686
687 class Math(TextDisplayObject):
687 class Math(TextDisplayObject):
688
688
689 def _repr_latex_(self):
689 def _repr_latex_(self):
690 s = self.data.strip('$')
690 s = "$$%s$$" % self.data.strip('$')
691 return "$$%s$$" % s
691 if self.metadata:
692 return s, deepcopy(self.metadata)
693 else:
694 return s
692
695
693
696
694 class Latex(TextDisplayObject):
697 class Latex(TextDisplayObject):
695
698
696 def _repr_latex_(self):
699 def _repr_latex_(self):
697 return self.data
700 return self._data_and_metadata()
698
701
699
702
700 class SVG(DisplayObject):
703 class SVG(DisplayObject):
@@ -317,4 +317,4 b' class CapturingDisplayHook(object):'
317 if result is None:
317 if result is None:
318 return
318 return
319 format_dict, md_dict = self.shell.display_formatter.format(result)
319 format_dict, md_dict = self.shell.display_formatter.format(result)
320 self.outputs.append((format_dict, md_dict))
320 self.outputs.append({ 'data': format_dict, 'metadata': md_dict })
@@ -7,18 +7,13 b''
7 import os
7 import os
8 import os.path
8 import os.path
9 import sys
9 import sys
10 from importlib import import_module
10 from importlib import import_module, reload
11
11
12 from traitlets.config.configurable import Configurable
12 from traitlets.config.configurable import Configurable
13 from IPython.utils.path import ensure_dir_exists, compress_user
13 from IPython.utils.path import ensure_dir_exists, compress_user
14 from IPython.utils.decorators import undoc
14 from IPython.utils.decorators import undoc
15 from traitlets import Instance
15 from traitlets import Instance
16
16
17 try:
18 from importlib import reload
19 except ImportError :
20 ## deprecated since 3.4
21 from imp import reload
22
17
23 #-----------------------------------------------------------------------------
18 #-----------------------------------------------------------------------------
24 # Main class
19 # Main class
@@ -20,7 +20,7 b' import threading'
20 from traitlets.config.configurable import LoggingConfigurable
20 from traitlets.config.configurable import LoggingConfigurable
21 from decorator import decorator
21 from decorator import decorator
22 from IPython.utils.decorators import undoc
22 from IPython.utils.decorators import undoc
23 from IPython.utils.path import locate_profile
23 from IPython.paths import locate_profile
24 from traitlets import (
24 from traitlets import (
25 Any, Bool, Dict, Instance, Integer, List, Unicode, TraitError,
25 Any, Bool, Dict, Instance, Integer, List, Unicode, TraitError,
26 default, observe,
26 default, observe,
@@ -170,7 +170,7 b' class SeparateUnicode(Unicode):'
170 class DummyMod(object):
170 class DummyMod(object):
171 """A dummy module used for IPython's interactive module when
171 """A dummy module used for IPython's interactive module when
172 a namespace must be assigned to the module's __dict__."""
172 a namespace must be assigned to the module's __dict__."""
173 pass
173 __spec__ = None
174
174
175
175
176 class ExecutionInfo(object):
176 class ExecutionInfo(object):
@@ -748,7 +748,7 b' class InteractiveShell(SingletonConfigurable):'
748
748
749 # executable path should end like /bin/python or \\scripts\\python.exe
749 # executable path should end like /bin/python or \\scripts\\python.exe
750 p_exe_up2 = os.path.dirname(os.path.dirname(p))
750 p_exe_up2 = os.path.dirname(os.path.dirname(p))
751 if p_exe_up2 and os.path.samefile(p_exe_up2, p_venv):
751 if p_exe_up2 and os.path.exists(p_venv) and os.path.samefile(p_exe_up2, p_venv):
752 # Our exe is inside the virtualenv, don't need to do anything.
752 # Our exe is inside the virtualenv, don't need to do anything.
753 return
753 return
754
754
@@ -1190,7 +1190,7 b' class InteractiveShell(SingletonConfigurable):'
1190 -----
1190 -----
1191 All data structures here are only filled in, they are NOT reset by this
1191 All data structures here are only filled in, they are NOT reset by this
1192 method. If they were not empty before, data will simply be added to
1192 method. If they were not empty before, data will simply be added to
1193 therm.
1193 them.
1194 """
1194 """
1195 # This function works in two parts: first we put a few things in
1195 # This function works in two parts: first we put a few things in
1196 # user_ns, and we sync that contents into user_ns_hidden so that these
1196 # user_ns, and we sync that contents into user_ns_hidden so that these
@@ -2884,7 +2884,6 b' class InteractiveShell(SingletonConfigurable):'
2884 """
2884 """
2885 if not nodelist:
2885 if not nodelist:
2886 return
2886 return
2887
2888 if interactivity == 'last_expr_or_assign':
2887 if interactivity == 'last_expr_or_assign':
2889 if isinstance(nodelist[-1], _assign_nodes):
2888 if isinstance(nodelist[-1], _assign_nodes):
2890 asg = nodelist[-1]
2889 asg = nodelist[-1]
@@ -2914,7 +2913,6 b' class InteractiveShell(SingletonConfigurable):'
2914 to_run_exec, to_run_interactive = [], nodelist
2913 to_run_exec, to_run_interactive = [], nodelist
2915 else:
2914 else:
2916 raise ValueError("Interactivity was %r" % interactivity)
2915 raise ValueError("Interactivity was %r" % interactivity)
2917
2918 try:
2916 try:
2919 for i, node in enumerate(to_run_exec):
2917 for i, node in enumerate(to_run_exec):
2920 mod = ast.Module([node])
2918 mod = ast.Module([node])
@@ -302,21 +302,6 b' Currently the magic system has the following functions:""",'
302 print('Object `%s` not found' % oname)
302 print('Object `%s` not found' % oname)
303
303
304 @line_magic
304 @line_magic
305 def profile(self, parameter_s=''):
306 """DEPRECATED since IPython 2.0.
307
308 Raise `UsageError`. To profile code use the :magic:`prun` magic.
309
310
311 See Also
312 --------
313 prun : run code using the Python profiler (:magic:`prun`)
314 """
315 raise UsageError("The `%profile` magic has been deprecated since IPython 2.0. "
316 "and removed in IPython 6.0. Please use the value of `get_ipython().profile` instead "
317 "to see current profile in use. Perhaps you meant to use `%prun` to profile code?")
318
319 @line_magic
320 def pprint(self, parameter_s=''):
305 def pprint(self, parameter_s=''):
321 """Toggle pretty printing on/off."""
306 """Toggle pretty printing on/off."""
322 ptformatter = self.shell.display_formatter.formatters['text/plain']
307 ptformatter = self.shell.display_formatter.formatters['text/plain']
@@ -20,6 +20,8 b' import re'
20 import sys
20 import sys
21 import ast
21 import ast
22 from itertools import chain
22 from itertools import chain
23 from urllib.request import urlopen
24 from urllib.parse import urlencode
23
25
24 # Our own packages
26 # Our own packages
25 from IPython.core.error import TryNext, StdinNotImplementedError, UsageError
27 from IPython.core.error import TryNext, StdinNotImplementedError, UsageError
@@ -244,7 +246,7 b' class CodeMagics(Magics):'
244
246
245 @line_magic
247 @line_magic
246 def pastebin(self, parameter_s=''):
248 def pastebin(self, parameter_s=''):
247 """Upload code to Github's Gist paste bin, returning the URL.
249 """Upload code to dpaste's paste bin, returning the URL.
248
250
249 Usage:\\
251 Usage:\\
250 %pastebin [-d "Custom description"] 1-7
252 %pastebin [-d "Custom description"] 1-7
@@ -265,25 +267,14 b' class CodeMagics(Magics):'
265 print(e.args[0])
267 print(e.args[0])
266 return
268 return
267
269
268 # Deferred import
270 post_data = urlencode({
269 try:
271 "title": opts.get('d', "Pasted from IPython"),
270 from urllib.request import urlopen # Py 3
272 "syntax": "python3",
271 except ImportError:
273 "content": code
272 from urllib2 import urlopen
273 import json
274 post_data = json.dumps({
275 "description": opts.get('d', "Pasted from IPython"),
276 "public": True,
277 "files": {
278 "file1.py": {
279 "content": code
280 }
281 }
282 }).encode('utf-8')
274 }).encode('utf-8')
283
275
284 response = urlopen("https://api.github.com/gists", post_data)
276 response = urlopen("http://dpaste.com/api/v2/", post_data)
285 response_data = json.loads(response.read().decode('utf-8'))
277 return response.headers.get('Location')
286 return response_data['html_url']
287
278
288 @line_magic
279 @line_magic
289 def loadpy(self, arg_s):
280 def loadpy(self, arg_s):
@@ -110,7 +110,6 b' class TimeitResult(object):'
110 p.text(u'<TimeitResult : '+unic+u'>')
110 p.text(u'<TimeitResult : '+unic+u'>')
111
111
112
112
113
114 class TimeitTemplateFiller(ast.NodeTransformer):
113 class TimeitTemplateFiller(ast.NodeTransformer):
115 """Fill in the AST template for timing execution.
114 """Fill in the AST template for timing execution.
116
115
@@ -31,14 +31,14 b' def script_args(f):'
31 '--out', type=str,
31 '--out', type=str,
32 help="""The variable in which to store stdout from the script.
32 help="""The variable in which to store stdout from the script.
33 If the script is backgrounded, this will be the stdout *pipe*,
33 If the script is backgrounded, this will be the stdout *pipe*,
34 instead of the stderr text itself.
34 instead of the stderr text itself and will not be auto closed.
35 """
35 """
36 ),
36 ),
37 magic_arguments.argument(
37 magic_arguments.argument(
38 '--err', type=str,
38 '--err', type=str,
39 help="""The variable in which to store stderr from the script.
39 help="""The variable in which to store stderr from the script.
40 If the script is backgrounded, this will be the stderr *pipe*,
40 If the script is backgrounded, this will be the stderr *pipe*,
41 instead of the stderr text itself.
41 instead of the stderr text itself and will not be autoclosed.
42 """
42 """
43 ),
43 ),
44 magic_arguments.argument(
44 magic_arguments.argument(
@@ -187,11 +187,16 b' class ScriptMagics(Magics):'
187 if args.bg:
187 if args.bg:
188 self.bg_processes.append(p)
188 self.bg_processes.append(p)
189 self._gc_bg_processes()
189 self._gc_bg_processes()
190 to_close = []
190 if args.out:
191 if args.out:
191 self.shell.user_ns[args.out] = p.stdout
192 self.shell.user_ns[args.out] = p.stdout
193 else:
194 to_close.append(p.stdout)
192 if args.err:
195 if args.err:
193 self.shell.user_ns[args.err] = p.stderr
196 self.shell.user_ns[args.err] = p.stderr
194 self.job_manager.new(self._run_script, p, cell, daemon=True)
197 else:
198 to_close.append(p.stderr)
199 self.job_manager.new(self._run_script, p, cell, to_close, daemon=True)
195 if args.proc:
200 if args.proc:
196 self.shell.user_ns[args.proc] = p
201 self.shell.user_ns[args.proc] = p
197 return
202 return
@@ -231,10 +236,12 b' class ScriptMagics(Magics):'
231 sys.stderr.write(err)
236 sys.stderr.write(err)
232 sys.stderr.flush()
237 sys.stderr.flush()
233
238
234 def _run_script(self, p, cell):
239 def _run_script(self, p, cell, to_close):
235 """callback for running the script in the background"""
240 """callback for running the script in the background"""
236 p.stdin.write(cell)
241 p.stdin.write(cell)
237 p.stdin.close()
242 p.stdin.close()
243 for s in to_close:
244 s.close()
238 p.wait()
245 p.wait()
239
246
240 @line_magic("killbgscripts")
247 @line_magic("killbgscripts")
@@ -46,6 +46,9 b" backend2gui['CocoaAgg'] = 'osx'"
46 # And some backends that don't need GUI integration
46 # And some backends that don't need GUI integration
47 del backend2gui['nbAgg']
47 del backend2gui['nbAgg']
48 del backend2gui['agg']
48 del backend2gui['agg']
49 del backend2gui['svg']
50 del backend2gui['pdf']
51 del backend2gui['ps']
49 del backend2gui['module://ipykernel.pylab.backend_inline']
52 del backend2gui['module://ipykernel.pylab.backend_inline']
50
53
51 #-----------------------------------------------------------------------------
54 #-----------------------------------------------------------------------------
@@ -19,12 +19,12 b" name = 'ipython'"
19 # IPython version information. An empty _version_extra corresponds to a full
19 # IPython version information. An empty _version_extra corresponds to a full
20 # release. 'dev' as a _version_extra string means this is a development
20 # release. 'dev' as a _version_extra string means this is a development
21 # version
21 # version
22 _version_major = 6
22 _version_major = 7
23 _version_minor = 2
23 _version_minor = 0
24 _version_patch = 0
24 _version_patch = 0
25 _version_extra = '.dev'
25 _version_extra = '.dev'
26 # _version_extra = 'rc2'
26 # _version_extra = 'rc2'
27 #_version_extra = '' # Uncomment this for full releases
27 # _version_extra = '' # Uncomment this for full releases
28
28
29 # Construct full version string from these.
29 # Construct full version string from these.
30 _ver = [_version_major, _version_minor, _version_patch]
30 _ver = [_version_major, _version_minor, _version_patch]
@@ -14,7 +14,6 b' from IPython.testing.globalipapp import get_ipython'
14 ip = get_ipython()
14 ip = get_ipython()
15
15
16
16
17 @py3compat.doctest_refactor_print
18 def doctest_autocall():
17 def doctest_autocall():
19 """
18 """
20 In [1]: def f1(a,b,c):
19 In [1]: def f1(a,b,c):
@@ -39,7 +38,7 b' def doctest_autocall():'
39
38
40 In [7]: assert _ == 'abc'
39 In [7]: assert _ == 'abc'
41
40
42 In [8]: print _
41 In [8]: print(_)
43 abc
42 abc
44
43
45 In [9]: /f1 1,2,3
44 In [9]: /f1 1,2,3
@@ -316,13 +316,17 b' def test_jedi():'
316 start = start if start is not None else l
316 start = start if start is not None else l
317 end = end if end is not None else l
317 end = end if end is not None else l
318 with provisionalcompleter():
318 with provisionalcompleter():
319 ip.Completer.use_jedi = True
319 completions = set(ip.Completer.completions(s, l))
320 completions = set(ip.Completer.completions(s, l))
321 ip.Completer.use_jedi = False
320 assert_in(Completion(start, end, comp), completions, reason)
322 assert_in(Completion(start, end, comp), completions, reason)
321
323
322 def _test_not_complete(reason, s, comp):
324 def _test_not_complete(reason, s, comp):
323 l = len(s)
325 l = len(s)
324 with provisionalcompleter():
326 with provisionalcompleter():
327 ip.Completer.use_jedi = True
325 completions = set(ip.Completer.completions(s, l))
328 completions = set(ip.Completer.completions(s, l))
329 ip.Completer.use_jedi = False
326 assert_not_in(Completion(l, l, comp), completions, reason)
330 assert_not_in(Completion(l, l, comp), completions, reason)
327
331
328 import jedi
332 import jedi
@@ -341,8 +345,10 b' def test_completion_have_signature():'
341 """
345 """
342 ip = get_ipython()
346 ip = get_ipython()
343 with provisionalcompleter():
347 with provisionalcompleter():
348 ip.Completer.use_jedi = True
344 completions = ip.Completer.completions('ope', 3)
349 completions = ip.Completer.completions('ope', 3)
345 c = next(completions) # should be `open`
350 c = next(completions) # should be `open`
351 ip.Completer.use_jedi = False
346 assert 'file' in c.signature, "Signature of function was not found by completer"
352 assert 'file' in c.signature, "Signature of function was not found by completer"
347 assert 'encoding' in c.signature, "Signature of function was not found by completer"
353 assert 'encoding' in c.signature, "Signature of function was not found by completer"
348
354
@@ -357,7 +363,9 b' def test_deduplicate_completions():'
357 zoo = 1
363 zoo = 1
358 '''))
364 '''))
359 with provisionalcompleter():
365 with provisionalcompleter():
366 ip.Completer.use_jedi = True
360 l = list(_deduplicate_completions('Z.z', ip.Completer.completions('Z.z', 3)))
367 l = list(_deduplicate_completions('Z.z', ip.Completer.completions('Z.z', 3)))
368 ip.Completer.use_jedi = False
361
369
362 assert len(l) == 1, 'Completions (Z.z<tab>) correctly deduplicate: %s ' % l
370 assert len(l) == 1, 'Completions (Z.z<tab>) correctly deduplicate: %s ' % l
363 assert l[0].text == 'zoo' # and not `it.accumulate`
371 assert l[0].text == 'zoo' # and not `it.accumulate`
@@ -412,10 +420,10 b' def test_omit__names():'
412 nt.assert_in('ip.__str__', matches)
420 nt.assert_in('ip.__str__', matches)
413 nt.assert_in('ip._hidden_attr', matches)
421 nt.assert_in('ip._hidden_attr', matches)
414
422
415 c.use_jedi = True
423 # c.use_jedi = True
416 completions = set(c.completions('ip.', 3))
424 # completions = set(c.completions('ip.', 3))
417 nt.assert_in(Completion(3, 3, '__str__'), completions)
425 # nt.assert_in(Completion(3, 3, '__str__'), completions)
418 nt.assert_in(Completion(3,3, "_hidden_attr"), completions)
426 # nt.assert_in(Completion(3,3, "_hidden_attr"), completions)
419
427
420
428
421 cfg = Config()
429 cfg = Config()
@@ -427,10 +435,10 b' def test_omit__names():'
427 nt.assert_not_in('ip.__str__', matches)
435 nt.assert_not_in('ip.__str__', matches)
428 # nt.assert_in('ip._hidden_attr', matches)
436 # nt.assert_in('ip._hidden_attr', matches)
429
437
430 c.use_jedi = True
438 # c.use_jedi = True
431 completions = set(c.completions('ip.', 3))
439 # completions = set(c.completions('ip.', 3))
432 nt.assert_not_in(Completion(3,3,'__str__'), completions)
440 # nt.assert_not_in(Completion(3,3,'__str__'), completions)
433 nt.assert_in(Completion(3,3, "_hidden_attr"), completions)
441 # nt.assert_in(Completion(3,3, "_hidden_attr"), completions)
434
442
435 cfg = Config()
443 cfg = Config()
436 cfg.IPCompleter.omit__names = 2
444 cfg.IPCompleter.omit__names = 2
@@ -441,19 +449,19 b' def test_omit__names():'
441 nt.assert_not_in('ip.__str__', matches)
449 nt.assert_not_in('ip.__str__', matches)
442 nt.assert_not_in('ip._hidden_attr', matches)
450 nt.assert_not_in('ip._hidden_attr', matches)
443
451
444 c.use_jedi = True
452 # c.use_jedi = True
445 completions = set(c.completions('ip.', 3))
453 # completions = set(c.completions('ip.', 3))
446 nt.assert_not_in(Completion(3,3,'__str__'), completions)
454 # nt.assert_not_in(Completion(3,3,'__str__'), completions)
447 nt.assert_not_in(Completion(3,3, "_hidden_attr"), completions)
455 # nt.assert_not_in(Completion(3,3, "_hidden_attr"), completions)
448
456
449 with provisionalcompleter():
457 with provisionalcompleter():
450 c.use_jedi = False
458 c.use_jedi = False
451 s,matches = c.complete('ip._x.')
459 s,matches = c.complete('ip._x.')
452 nt.assert_in('ip._x.keys', matches)
460 nt.assert_in('ip._x.keys', matches)
453
461
454 c.use_jedi = True
462 # c.use_jedi = True
455 completions = set(c.completions('ip._x.', 6))
463 # completions = set(c.completions('ip._x.', 6))
456 nt.assert_in(Completion(6,6, "keys"), completions)
464 # nt.assert_in(Completion(6,6, "keys"), completions)
457
465
458 del ip._hidden_attr
466 del ip._hidden_attr
459 del ip._x
467 del ip._x
@@ -275,6 +275,10 b' def test_video_embedding():'
275 html = v._repr_html_()
275 html = v._repr_html_()
276 nt.assert_in('src="data:video/xyz;base64,YWJj"',html)
276 nt.assert_in('src="data:video/xyz;base64,YWJj"',html)
277
277
278 def test_html_metadata():
279 s = "<h1>Test</h1>"
280 h = display.HTML(s, metadata={"isolated": True})
281 nt.assert_equal(h._repr_html_(), (s, {"isolated": True}))
278
282
279 def test_display_id():
283 def test_display_id():
280 ip = get_ipython()
284 ip = get_ipython()
@@ -1,4 +1,7 b''
1 import sys
1 from IPython.testing.tools import AssertPrints, AssertNotPrints
2 from IPython.testing.tools import AssertPrints, AssertNotPrints
3 from IPython.core.displayhook import CapturingDisplayHook
4 from IPython.utils.capture import CapturedIO
2
5
3 ip = get_ipython()
6 ip = get_ipython()
4
7
@@ -101,3 +104,11 b' def test_interactivehooks_ast_modes_semi_supress():'
101
104
102 finally:
105 finally:
103 ip.ast_node_interactivity = saved_mode
106 ip.ast_node_interactivity = saved_mode
107
108 def test_capture_display_hook_format():
109 """Tests that the capture display hook conforms to the CapturedIO output format"""
110 hook = CapturingDisplayHook(ip)
111 hook({"foo": "bar"})
112 captured = CapturedIO(sys.stdout, sys.stderr, hook.outputs)
113 # Should not raise with RichOutput transformation error
114 captured.outputs
@@ -72,7 +72,7 b' In [4]: run simpleerr.py'
72 ---------------------------------------------------------------------------
72 ---------------------------------------------------------------------------
73 ZeroDivisionError Traceback (most recent call last)
73 ZeroDivisionError Traceback (most recent call last)
74 <BLANKLINE>
74 <BLANKLINE>
75 ... in <module>()
75 ... in <module>
76 30 mode = 'div'
76 30 mode = 'div'
77 31
77 31
78 ---> 32 bar(mode)
78 ---> 32 bar(mode)
@@ -104,7 +104,7 b' In [6]: run simpleerr.py'
104 ---------------------------------------------------------------------------
104 ---------------------------------------------------------------------------
105 ZeroDivisionError Traceback (most recent call last)
105 ZeroDivisionError Traceback (most recent call last)
106 <BLANKLINE>
106 <BLANKLINE>
107 ... in <module>()
107 ... in <module>
108 30 mode = 'div'
108 30 mode = 'div'
109 31
109 31
110 ---> 32 bar(mode)
110 ---> 32 bar(mode)
@@ -161,7 +161,7 b' In [22]: %tb'
161 ---------------------------------------------------------------------------
161 ---------------------------------------------------------------------------
162 SystemExit Traceback (most recent call last)
162 SystemExit Traceback (most recent call last)
163 <BLANKLINE>
163 <BLANKLINE>
164 ...<module>()
164 ...<module>
165 30 mode = 'div'
165 30 mode = 'div'
166 31
166 31
167 ---> 32 bar(mode)
167 ---> 32 bar(mode)
@@ -189,7 +189,7 b' In [24]: %tb'
189 ---------------------------------------------------------------------------
189 ---------------------------------------------------------------------------
190 SystemExit Traceback (most recent call last)
190 SystemExit Traceback (most recent call last)
191 <BLANKLINE>
191 <BLANKLINE>
192 ... in <module>()
192 ... in <module>
193 30 mode = 'div'
193 30 mode = 'div'
194 31
194 31
195 ---> 32 bar(mode)
195 ---> 32 bar(mode)
@@ -26,7 +26,6 b' from IPython.core.magic import (Magics, magics_class, line_magic,'
26 from IPython.core.magics import execution, script, code, logging
26 from IPython.core.magics import execution, script, code, logging
27 from IPython.testing import decorators as dec
27 from IPython.testing import decorators as dec
28 from IPython.testing import tools as tt
28 from IPython.testing import tools as tt
29 from IPython.utils import py3compat
30 from IPython.utils.io import capture_output
29 from IPython.utils.io import capture_output
31 from IPython.utils.tempdir import TemporaryDirectory
30 from IPython.utils.tempdir import TemporaryDirectory
32 from IPython.utils.process import find_cmd
31 from IPython.utils.process import find_cmd
@@ -304,12 +303,10 b' def test_macro_run():'
304 """Test that we can run a multi-line macro successfully."""
303 """Test that we can run a multi-line macro successfully."""
305 ip = get_ipython()
304 ip = get_ipython()
306 ip.history_manager.reset()
305 ip.history_manager.reset()
307 cmds = ["a=10", "a+=1", py3compat.doctest_refactor_print("print a"),
306 cmds = ["a=10", "a+=1", "print(a)", "%macro test 2-3"]
308 "%macro test 2-3"]
309 for cmd in cmds:
307 for cmd in cmds:
310 ip.run_cell(cmd, store_history=True)
308 ip.run_cell(cmd, store_history=True)
311 nt.assert_equal(ip.user_ns["test"].value,
309 nt.assert_equal(ip.user_ns["test"].value, "a+=1\nprint(a)\n")
312 py3compat.doctest_refactor_print("a+=1\nprint a\n"))
313 with tt.AssertPrints("12"):
310 with tt.AssertPrints("12"):
314 ip.run_cell("test")
311 ip.run_cell("test")
315 with tt.AssertPrints("13"):
312 with tt.AssertPrints("13"):
@@ -532,7 +529,6 b' def test_whos():'
532 _ip.user_ns['a'] = A()
529 _ip.user_ns['a'] = A()
533 _ip.magic("whos")
530 _ip.magic("whos")
534
531
535 @py3compat.u_format
536 def doctest_precision():
532 def doctest_precision():
537 """doctest for %precision
533 """doctest for %precision
538
534
@@ -566,11 +562,6 b' def test_timeit_shlex():'
566 _ip.magic('timeit -r1 -n1 f("a " + "b ")')
562 _ip.magic('timeit -r1 -n1 f("a " + "b ")')
567
563
568
564
569 def test_timeit_arguments():
570 "Test valid timeit arguments, should not cause SyntaxError (GH #1269)"
571 _ip.magic("timeit ('#')")
572
573
574 def test_timeit_special_syntax():
565 def test_timeit_special_syntax():
575 "Test %%timeit with IPython special syntax"
566 "Test %%timeit with IPython special syntax"
576 @register_line_magic
567 @register_line_magic
@@ -837,13 +828,16 b' def test_script_out_err():'
837 def test_script_bg_out():
828 def test_script_bg_out():
838 ip = get_ipython()
829 ip = get_ipython()
839 ip.run_cell_magic("script", "--bg --out output sh", "echo 'hi'")
830 ip.run_cell_magic("script", "--bg --out output sh", "echo 'hi'")
831
840 nt.assert_equal(ip.user_ns['output'].read(), b'hi\n')
832 nt.assert_equal(ip.user_ns['output'].read(), b'hi\n')
833 ip.user_ns['output'].close()
841
834
842 @dec.skip_win32
835 @dec.skip_win32
843 def test_script_bg_err():
836 def test_script_bg_err():
844 ip = get_ipython()
837 ip = get_ipython()
845 ip.run_cell_magic("script", "--bg --err error sh", "echo 'hello' >&2")
838 ip.run_cell_magic("script", "--bg --err error sh", "echo 'hello' >&2")
846 nt.assert_equal(ip.user_ns['error'].read(), b'hello\n')
839 nt.assert_equal(ip.user_ns['error'].read(), b'hello\n')
840 ip.user_ns['error'].close()
847
841
848 @dec.skip_win32
842 @dec.skip_win32
849 def test_script_bg_out_err():
843 def test_script_bg_out_err():
@@ -851,6 +845,8 b' def test_script_bg_out_err():'
851 ip.run_cell_magic("script", "--bg --out output --err error sh", "echo 'hi'\necho 'hello' >&2")
845 ip.run_cell_magic("script", "--bg --out output --err error sh", "echo 'hi'\necho 'hello' >&2")
852 nt.assert_equal(ip.user_ns['output'].read(), b'hi\n')
846 nt.assert_equal(ip.user_ns['output'].read(), b'hi\n')
853 nt.assert_equal(ip.user_ns['error'].read(), b'hello\n')
847 nt.assert_equal(ip.user_ns['error'].read(), b'hello\n')
848 ip.user_ns['output'].close()
849 ip.user_ns['error'].close()
854
850
855 def test_script_defaults():
851 def test_script_defaults():
856 ip = get_ipython()
852 ip = get_ipython()
@@ -1070,4 +1066,15 b' def test_logging_magic_not_quiet():'
1070 lm.logstart(os.path.join(td, "not_quiet.log"))
1066 lm.logstart(os.path.join(td, "not_quiet.log"))
1071 finally:
1067 finally:
1072 _ip.logger.logstop()
1068 _ip.logger.logstop()
1073
1069
1070 ##
1071 # this is slow, put at the end for local testing.
1072 ##
1073 def test_timeit_arguments():
1074 "Test valid timeit arguments, should not cause SyntaxError (GH #1269)"
1075 if sys.version_info < (3,7):
1076 _ip.magic("timeit ('#')")
1077 else:
1078 # 3.7 optimize no-op statement like above out, and complain there is
1079 # nothing in the for loop.
1080 _ip.magic("timeit a=('#')")
@@ -430,8 +430,5 b' def test_init_colors():'
430 def test_builtin_init():
430 def test_builtin_init():
431 info = inspector.info(list)
431 info = inspector.info(list)
432 init_def = info['init_definition']
432 init_def = info['init_definition']
433 # Python < 3.4 can't get init definition from builtins,
433 nt.assert_is_not_none(init_def)
434 # but still exercise the inspection in case of error-raising bugs.
435 if sys.version_info >= (3,4):
436 nt.assert_is_not_none(init_def)
437
434
@@ -34,7 +34,6 b' from IPython.core.profiledir import ProfileDir'
34
34
35 from IPython.testing import decorators as dec
35 from IPython.testing import decorators as dec
36 from IPython.testing import tools as tt
36 from IPython.testing import tools as tt
37 from IPython.utils import py3compat
38 from IPython.utils.process import getoutput
37 from IPython.utils.process import getoutput
39 from IPython.utils.tempdir import TemporaryDirectory
38 from IPython.utils.tempdir import TemporaryDirectory
40
39
@@ -100,15 +99,14 b' class ProfileStartupTest(TestCase):'
100 f.write(startup)
99 f.write(startup)
101 # write simple test file, to check that the startup file was run
100 # write simple test file, to check that the startup file was run
102 with open(self.fname, 'w') as f:
101 with open(self.fname, 'w') as f:
103 f.write(py3compat.doctest_refactor_print(test))
102 f.write(test)
104
103
105 def validate(self, output):
104 def validate(self, output):
106 tt.ipexec_validate(self.fname, output, '', options=self.options)
105 tt.ipexec_validate(self.fname, output, '', options=self.options)
107
106
108 @dec.skipif(win32_without_pywin32(), "Test requires pywin32 on Windows")
107 @dec.skipif(win32_without_pywin32(), "Test requires pywin32 on Windows")
109 def test_startup_py(self):
108 def test_startup_py(self):
110 self.init('00-start.py', 'zzz=123\n',
109 self.init('00-start.py', 'zzz=123\n', 'print(zzz)\n')
111 py3compat.doctest_refactor_print('print zzz\n'))
112 self.validate('123')
110 self.validate('123')
113
111
114 @dec.skipif(win32_without_pywin32(), "Test requires pywin32 on Windows")
112 @dec.skipif(win32_without_pywin32(), "Test requires pywin32 on Windows")
@@ -105,7 +105,7 b' def test_select_figure_formats_kwargs():'
105 f = formatter.lookup_by_type(Figure)
105 f = formatter.lookup_by_type(Figure)
106 cell = f.__closure__[0].cell_contents
106 cell = f.__closure__[0].cell_contents
107 nt.assert_equal(cell, kwargs)
107 nt.assert_equal(cell, kwargs)
108
108
109 # check that the formatter doesn't raise
109 # check that the formatter doesn't raise
110 fig = plt.figure()
110 fig = plt.figure()
111 ax = fig.add_subplot(1,1,1)
111 ax = fig.add_subplot(1,1,1)
@@ -150,7 +150,7 b' class TestPylabSwitch(object):'
150 class Shell(InteractiveShell):
150 class Shell(InteractiveShell):
151 def enable_gui(self, gui):
151 def enable_gui(self, gui):
152 pass
152 pass
153
153
154 def setup(self):
154 def setup(self):
155 import matplotlib
155 import matplotlib
156 def act_mpl(backend):
156 def act_mpl(backend):
@@ -244,3 +244,7 b' class TestPylabSwitch(object):'
244 nt.assert_equal(gui, 'qt')
244 nt.assert_equal(gui, 'qt')
245 nt.assert_equal(s.pylab_gui_select, 'qt')
245 nt.assert_equal(s.pylab_gui_select, 'qt')
246
246
247
248 def test_no_gui_backends():
249 for k in ['agg', 'svg', 'pdf', 'ps']:
250 assert k not in pt.backend2gui
@@ -31,7 +31,6 b' from nose import SkipTest'
31
31
32 from IPython.testing import decorators as dec
32 from IPython.testing import decorators as dec
33 from IPython.testing import tools as tt
33 from IPython.testing import tools as tt
34 from IPython.utils import py3compat
35 from IPython.utils.io import capture_output
34 from IPython.utils.io import capture_output
36 from IPython.utils.tempdir import TemporaryDirectory
35 from IPython.utils.tempdir import TemporaryDirectory
37 from IPython.core import debugger
36 from IPython.core import debugger
@@ -145,13 +144,12 b' def doctest_run_option_parser_for_windows():'
145 """
144 """
146
145
147
146
148 @py3compat.doctest_refactor_print
149 def doctest_reset_del():
147 def doctest_reset_del():
150 """Test that resetting doesn't cause errors in __del__ methods.
148 """Test that resetting doesn't cause errors in __del__ methods.
151
149
152 In [2]: class A(object):
150 In [2]: class A(object):
153 ...: def __del__(self):
151 ...: def __del__(self):
154 ...: print str("Hi")
152 ...: print(str("Hi"))
155 ...:
153 ...:
156
154
157 In [3]: a = A()
155 In [3]: a = A()
@@ -248,9 +246,9 b' class TestMagicRunSimple(tt.TempFileMixin):'
248 raise SkipTest("Test requires pywin32")
246 raise SkipTest("Test requires pywin32")
249 src = ("class A(object):\n"
247 src = ("class A(object):\n"
250 " def __del__(self):\n"
248 " def __del__(self):\n"
251 " print 'object A deleted'\n"
249 " print('object A deleted')\n"
252 "a = A()\n")
250 "a = A()\n")
253 self.mktmp(py3compat.doctest_refactor_print(src))
251 self.mktmp(src)
254 if dec.module_not_available('sqlite3'):
252 if dec.module_not_available('sqlite3'):
255 err = 'WARNING: IPython History requires SQLite, your history will not be saved\n'
253 err = 'WARNING: IPython History requires SQLite, your history will not be saved\n'
256 else:
254 else:
@@ -116,13 +116,15 b' from IPython.core import debugger'
116 from IPython.core.display_trap import DisplayTrap
116 from IPython.core.display_trap import DisplayTrap
117 from IPython.core.excolors import exception_colors
117 from IPython.core.excolors import exception_colors
118 from IPython.utils import PyColorize
118 from IPython.utils import PyColorize
119 from IPython.utils import openpy
120 from IPython.utils import path as util_path
119 from IPython.utils import path as util_path
121 from IPython.utils import py3compat
120 from IPython.utils import py3compat
122 from IPython.utils.data import uniq_stable
121 from IPython.utils.data import uniq_stable
123 from IPython.utils.terminal import get_terminal_size
122 from IPython.utils.terminal import get_terminal_size
123
124 from logging import info, error, debug
124 from logging import info, error, debug
125
125
126 from importlib.util import source_from_cache
127
126 import IPython.utils.colorable as colorable
128 import IPython.utils.colorable as colorable
127
129
128 # Globals
130 # Globals
@@ -374,16 +376,32 b' def _fixed_getinnerframes(etb, context=1, tb_offset=0):'
374 # (SyntaxErrors have to be treated specially because they have no traceback)
376 # (SyntaxErrors have to be treated specially because they have no traceback)
375
377
376
378
377 def _format_traceback_lines(lnum, index, lines, Colors, lvals=None, _line_format=(lambda x,_:x,None)):
379 def _format_traceback_lines(lnum, index, lines, Colors, lvals, _line_format):
380 """
381 Format tracebacks lines with pointing arrow, leading numbers...
382
383 Parameters
384 ==========
385
386 lnum: int
387 index: int
388 lines: list[string]
389 Colors:
390 ColorScheme used.
391 lvals: bytes
392 Values of local variables, already colored, to inject just after the error line.
393 _line_format: f (str) -> (str, bool)
394 return (colorized version of str, failure to do so)
395 """
378 numbers_width = INDENT_SIZE - 1
396 numbers_width = INDENT_SIZE - 1
379 res = []
397 res = []
380 i = lnum - index
381
398
382 for line in lines:
399 for i,line in enumerate(lines, lnum-index):
383 line = py3compat.cast_unicode(line)
400 line = py3compat.cast_unicode(line)
384
401
385 new_line, err = _line_format(line, 'str')
402 new_line, err = _line_format(line, 'str')
386 if not err: line = new_line
403 if not err:
404 line = new_line
387
405
388 if i == lnum:
406 if i == lnum:
389 # This is the line with the error
407 # This is the line with the error
@@ -399,7 +417,6 b' def _format_traceback_lines(lnum, index, lines, Colors, lvals=None, _line_forma'
399 res.append(line)
417 res.append(line)
400 if lvals and i == lnum:
418 if lvals and i == lnum:
401 res.append(lvals + '\n')
419 res.append(lvals + '\n')
402 i = i + 1
403 return res
420 return res
404
421
405 def is_recursion_error(etype, value, records):
422 def is_recursion_error(etype, value, records):
@@ -621,16 +638,6 b' class ListTB(TBTools):'
621 lines = ''.join(self._format_exception_only(etype, value))
638 lines = ''.join(self._format_exception_only(etype, value))
622 out_list.append(lines)
639 out_list.append(lines)
623
640
624 # Note: this code originally read:
625
626 ## for line in lines[:-1]:
627 ## out_list.append(" "+line)
628 ## out_list.append(lines[-1])
629
630 # This means it was indenting everything but the last line by a little
631 # bit. I've disabled this for now, but if we see ugliness somewhere we
632 # can restore it.
633
634 return out_list
641 return out_list
635
642
636 def _format_list(self, extracted_list):
643 def _format_list(self, extracted_list):
@@ -841,13 +848,6 b' class VerboseTB(TBTools):'
841 Colors.vName, ColorsNormal)
848 Colors.vName, ColorsNormal)
842 tpl_name_val = '%%s %s= %%s%s' % (Colors.valEm, ColorsNormal)
849 tpl_name_val = '%%s %s= %%s%s' % (Colors.valEm, ColorsNormal)
843
850
844 tpl_line = '%s%%s%s %%s' % (Colors.lineno, ColorsNormal)
845 tpl_line_em = '%s%%s%s %%s%s' % (Colors.linenoEm, Colors.line,
846 ColorsNormal)
847
848 abspath = os.path.abspath
849
850
851 if not file:
851 if not file:
852 file = '?'
852 file = '?'
853 elif file.startswith(str("<")) and file.endswith(str(">")):
853 elif file.startswith(str("<")) and file.endswith(str(">")):
@@ -869,17 +869,19 b' class VerboseTB(TBTools):'
869
869
870 file = py3compat.cast_unicode(file, util_path.fs_encoding)
870 file = py3compat.cast_unicode(file, util_path.fs_encoding)
871 link = tpl_link % util_path.compress_user(file)
871 link = tpl_link % util_path.compress_user(file)
872 args, varargs, varkw, locals = inspect.getargvalues(frame)
872 args, varargs, varkw, locals_ = inspect.getargvalues(frame)
873
873
874 if func == '?':
874 if func == '?':
875 call = ''
875 call = ''
876 elif func == '<module>':
877 call = tpl_call % (func, '')
876 else:
878 else:
877 # Decide whether to include variable details or not
879 # Decide whether to include variable details or not
878 var_repr = self.include_vars and eqrepr or nullrepr
880 var_repr = eqrepr if self.include_vars else nullrepr
879 try:
881 try:
880 call = tpl_call % (func, inspect.formatargvalues(args,
882 call = tpl_call % (func, inspect.formatargvalues(args,
881 varargs, varkw,
883 varargs, varkw,
882 locals, formatvalue=var_repr))
884 locals_, formatvalue=var_repr))
883 except KeyError:
885 except KeyError:
884 # This happens in situations like errors inside generator
886 # This happens in situations like errors inside generator
885 # expressions, where local variables are listed in the
887 # expressions, where local variables are listed in the
@@ -906,7 +908,7 b' class VerboseTB(TBTools):'
906 elif file.endswith(('.pyc', '.pyo')):
908 elif file.endswith(('.pyc', '.pyo')):
907 # Look up the corresponding source file.
909 # Look up the corresponding source file.
908 try:
910 try:
909 file = openpy.source_from_cache(file)
911 file = source_from_cache(file)
910 except ValueError:
912 except ValueError:
911 # Failed to get the source file for some reason
913 # Failed to get the source file for some reason
912 # E.g. https://github.com/ipython/ipython/issues/9486
914 # E.g. https://github.com/ipython/ipython/issues/9486
@@ -968,14 +970,15 b' class VerboseTB(TBTools):'
968 unique_names = uniq_stable(names)
970 unique_names = uniq_stable(names)
969
971
970 # Start loop over vars
972 # Start loop over vars
971 lvals = []
973 lvals = ''
974 lvals_list = []
972 if self.include_vars:
975 if self.include_vars:
973 for name_full in unique_names:
976 for name_full in unique_names:
974 name_base = name_full.split('.', 1)[0]
977 name_base = name_full.split('.', 1)[0]
975 if name_base in frame.f_code.co_varnames:
978 if name_base in frame.f_code.co_varnames:
976 if name_base in locals:
979 if name_base in locals_:
977 try:
980 try:
978 value = repr(eval(name_full, locals))
981 value = repr(eval(name_full, locals_))
979 except:
982 except:
980 value = undefined
983 value = undefined
981 else:
984 else:
@@ -990,11 +993,9 b' class VerboseTB(TBTools):'
990 else:
993 else:
991 value = undefined
994 value = undefined
992 name = tpl_global_var % name_full
995 name = tpl_global_var % name_full
993 lvals.append(tpl_name_val % (name, value))
996 lvals_list.append(tpl_name_val % (name, value))
994 if lvals:
997 if lvals_list:
995 lvals = '%s%s' % (indent, em_normal.join(lvals))
998 lvals = '%s%s' % (indent, em_normal.join(lvals_list))
996 else:
997 lvals = ''
998
999
999 level = '%s %s\n' % (link, call)
1000 level = '%s %s\n' % (link, call)
1000
1001
@@ -1041,7 +1042,6 b' class VerboseTB(TBTools):'
1041 def format_exception(self, etype, evalue):
1042 def format_exception(self, etype, evalue):
1042 colors = self.Colors # just a shorthand + quicker name lookup
1043 colors = self.Colors # just a shorthand + quicker name lookup
1043 colorsnormal = colors.Normal # used a lot
1044 colorsnormal = colors.Normal # used a lot
1044 indent = ' ' * INDENT_SIZE
1045 # Get (safely) a string form of the exception info
1045 # Get (safely) a string form of the exception info
1046 try:
1046 try:
1047 etype_str, evalue_str = map(str, (etype, evalue))
1047 etype_str, evalue_str = map(str, (etype, evalue))
@@ -339,10 +339,3 b' default_banner_parts = ["Python %s\\n"%sys.version.split("\\n")[0],'
339 ]
339 ]
340
340
341 default_banner = ''.join(default_banner_parts)
341 default_banner = ''.join(default_banner_parts)
342
343 # deprecated GUI banner
344
345 default_gui_banner = '\n'.join([
346 'DEPRECATED: IPython.core.usage.default_gui_banner is deprecated and will be removed',
347 default_banner,
348 ])
@@ -116,10 +116,9 b' import traceback'
116 import types
116 import types
117 import weakref
117 import weakref
118 from importlib import import_module
118 from importlib import import_module
119 from importlib.util import source_from_cache
119 from imp import reload
120 from imp import reload
120
121
121 from IPython.utils import openpy
122
123 #------------------------------------------------------------------------------
122 #------------------------------------------------------------------------------
124 # Autoreload functionality
123 # Autoreload functionality
125 #------------------------------------------------------------------------------
124 #------------------------------------------------------------------------------
@@ -195,7 +194,7 b' class ModuleReloader(object):'
195 py_filename = filename
194 py_filename = filename
196 else:
195 else:
197 try:
196 try:
198 py_filename = openpy.source_from_cache(filename)
197 py_filename = source_from_cache(filename)
199 except ValueError:
198 except ValueError:
200 return None, None
199 return None, None
201
200
@@ -109,47 +109,6 b' def loaded_api():'
109 def has_binding(api):
109 def has_binding(api):
110 """Safely check for PyQt4/5, PySide or PySide2, without importing submodules
110 """Safely check for PyQt4/5, PySide or PySide2, without importing submodules
111
111
112 Supports Python <= 3.3
113
114 Parameters
115 ----------
116 api : str [ 'pyqtv1' | 'pyqt' | 'pyqt5' | 'pyside' | 'pyside2' | 'pyqtdefault']
117 Which module to check for
118
119 Returns
120 -------
121 True if the relevant module appears to be importable
122 """
123 # we can't import an incomplete pyside and pyqt4
124 # this will cause a crash in sip (#1431)
125 # check for complete presence before importing
126 module_name = api_to_module[api]
127
128 import imp
129 try:
130 #importing top level PyQt4/PySide module is ok...
131 mod = import_module(module_name)
132 #...importing submodules is not
133 imp.find_module('QtCore', mod.__path__)
134 imp.find_module('QtGui', mod.__path__)
135 imp.find_module('QtSvg', mod.__path__)
136 if api in (QT_API_PYQT5, QT_API_PYSIDE2):
137 # QT5 requires QtWidgets too
138 imp.find_module('QtWidgets', mod.__path__)
139
140 #we can also safely check PySide version
141 if api == QT_API_PYSIDE:
142 return check_version(mod.__version__, '1.0.3')
143 else:
144 return True
145 except ImportError:
146 return False
147
148 def has_binding_new(api):
149 """Safely check for PyQt4/5, PySide or PySide2, without importing submodules
150
151 Supports Python >= 3.4
152
153 Parameters
112 Parameters
154 ----------
113 ----------
155 api : str [ 'pyqtv1' | 'pyqt' | 'pyqt5' | 'pyside' | 'pyside2' | 'pyqtdefault']
114 api : str [ 'pyqtv1' | 'pyqt' | 'pyqt5' | 'pyside' | 'pyside2' | 'pyqtdefault']
@@ -185,8 +144,6 b' def has_binding_new(api):'
185
144
186 return True
145 return True
187
146
188 if sys.version_info >= (3, 4):
189 has_binding = has_binding_new
190
147
191 def qtapi_version():
148 def qtapi_version():
192 """Return which QString API has been set, if any
149 """Return which QString API has been set, if any
@@ -2,13 +2,14 b''
2
2
3 Authors : MinRK, gregcaporaso, dannystaple
3 Authors : MinRK, gregcaporaso, dannystaple
4 """
4 """
5 from html import escape as html_escape
5 from os.path import exists, isfile, splitext, abspath, join, isdir
6 from os.path import exists, isfile, splitext, abspath, join, isdir
6 from os import walk, sep
7 from os import walk, sep, fsdecode
7
8
8 from IPython.core.display import DisplayObject
9 from IPython.core.display import DisplayObject, TextDisplayObject
9
10
10 __all__ = ['Audio', 'IFrame', 'YouTubeVideo', 'VimeoVideo', 'ScribdDocument',
11 __all__ = ['Audio', 'IFrame', 'YouTubeVideo', 'VimeoVideo', 'ScribdDocument',
11 'FileLink', 'FileLinks']
12 'FileLink', 'FileLinks', 'Code']
12
13
13
14
14 class Audio(DisplayObject):
15 class Audio(DisplayObject):
@@ -334,15 +335,16 b' class FileLink(object):'
334 if isdir(path):
335 if isdir(path):
335 raise ValueError("Cannot display a directory using FileLink. "
336 raise ValueError("Cannot display a directory using FileLink. "
336 "Use FileLinks to display '%s'." % path)
337 "Use FileLinks to display '%s'." % path)
337 self.path = path
338 self.path = fsdecode(path)
338 self.url_prefix = url_prefix
339 self.url_prefix = url_prefix
339 self.result_html_prefix = result_html_prefix
340 self.result_html_prefix = result_html_prefix
340 self.result_html_suffix = result_html_suffix
341 self.result_html_suffix = result_html_suffix
341
342
342 def _format_path(self):
343 def _format_path(self):
343 fp = ''.join([self.url_prefix,self.path])
344 fp = ''.join([self.url_prefix, html_escape(self.path)])
344 return ''.join([self.result_html_prefix,
345 return ''.join([self.result_html_prefix,
345 self.html_link_str % (fp, self.path),
346 self.html_link_str % \
347 (fp, html_escape(self.path, quote=False)),
346 self.result_html_suffix])
348 self.result_html_suffix])
347
349
348 def _repr_html_(self):
350 def _repr_html_(self):
@@ -555,3 +557,52 b' class FileLinks(FileLink):'
555 for dirname, subdirs, fnames in walked_dir:
557 for dirname, subdirs, fnames in walked_dir:
556 result_lines += self.terminal_display_formatter(dirname, fnames, self.included_suffixes)
558 result_lines += self.terminal_display_formatter(dirname, fnames, self.included_suffixes)
557 return '\n'.join(result_lines)
559 return '\n'.join(result_lines)
560
561
562 class Code(TextDisplayObject):
563 """Display syntax-highlighted source code.
564
565 This uses Pygments to highlight the code for HTML and Latex output.
566
567 Parameters
568 ----------
569 data : str
570 The code as a string
571 url : str
572 A URL to fetch the code from
573 filename : str
574 A local filename to load the code from
575 language : str
576 The short name of a Pygments lexer to use for highlighting.
577 If not specified, it will guess the lexer based on the filename
578 or the code. Available lexers: http://pygments.org/docs/lexers/
579 """
580 def __init__(self, data=None, url=None, filename=None, language=None):
581 self.language = language
582 super().__init__(data=data, url=url, filename=filename)
583
584 def _get_lexer(self):
585 if self.language:
586 from pygments.lexers import get_lexer_by_name
587 return get_lexer_by_name(self.language)
588 elif self.filename:
589 from pygments.lexers import get_lexer_for_filename
590 return get_lexer_for_filename(self.filename)
591 else:
592 from pygments.lexers import guess_lexer
593 return guess_lexer(self.data)
594
595 def __repr__(self):
596 return self.data
597
598 def _repr_html_(self):
599 from pygments import highlight
600 from pygments.formatters import HtmlFormatter
601 fmt = HtmlFormatter()
602 style = '<style>{}</style>'.format(fmt.get_style_defs('.output_html'))
603 return style + highlight(self.data, self._get_lexer(), fmt)
604
605 def _repr_latex_(self):
606 from pygments import highlight
607 from pygments.formatters import LatexFormatter
608 return highlight(self.data, self._get_lexer(), LatexFormatter())
@@ -2,7 +2,7 b''
2 """
2 """
3 Support for creating GUI apps and starting event loops.
3 Support for creating GUI apps and starting event loops.
4
4
5 IPython's GUI integration allows interative plotting and GUI usage in IPython
5 IPython's GUI integration allows interactive plotting and GUI usage in IPython
6 session. IPython has two different types of GUI integration:
6 session. IPython has two different types of GUI integration:
7
7
8 1. The terminal based IPython supports GUI event loops through Python's
8 1. The terminal based IPython supports GUI event loops through Python's
@@ -34,7 +34,9 b' This includes:'
34 import re
34 import re
35
35
36 # Third party
36 # Third party
37 from pygments.lexers import BashLexer, PythonLexer, Python3Lexer
37 from pygments.lexers import (
38 BashLexer, HtmlLexer, JavascriptLexer, RubyLexer, PerlLexer, PythonLexer,
39 Python3Lexer, TexLexer)
38 from pygments.lexer import (
40 from pygments.lexer import (
39 Lexer, DelegatingLexer, RegexLexer, do_insertions, bygroups, using,
41 Lexer, DelegatingLexer, RegexLexer, do_insertions, bygroups, using,
40 )
42 )
@@ -51,19 +53,6 b" __all__ = ['build_ipy_lexer', 'IPython3Lexer', 'IPythonLexer',"
51 'IPythonPartialTracebackLexer', 'IPythonTracebackLexer',
53 'IPythonPartialTracebackLexer', 'IPythonTracebackLexer',
52 'IPythonConsoleLexer', 'IPyLexer']
54 'IPythonConsoleLexer', 'IPyLexer']
53
55
54 ipython_tokens = [
55 (r"(?s)(\s*)(%%)(\w+)(.*)", bygroups(Text, Operator, Keyword, Text)),
56 (r'(?s)(^\s*)(%%!)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(BashLexer))),
57 (r"(%%?)(\w+)(\?\??)$", bygroups(Operator, Keyword, Operator)),
58 (r"\b(\?\??)(\s*)$", bygroups(Operator, Text)),
59 (r'(%)(sx|sc|system)(.*)(\n)', bygroups(Operator, Keyword,
60 using(BashLexer), Text)),
61 (r'(%)(\w+)(.*\n)', bygroups(Operator, Keyword, Text)),
62 (r'^(!!)(.+)(\n)', bygroups(Operator, using(BashLexer), Text)),
63 (r'(!)(?!=)(.+)(\n)', bygroups(Operator, using(BashLexer), Text)),
64 (r'^(\s*)(\?\??)(\s*%{0,2}[\w\.\*]*)', bygroups(Text, Operator, Text)),
65 (r'(\s*%{0,2}[\w\.\*]*)(\?\??)(\s*)$', bygroups(Text, Operator, Text)),
66 ]
67
56
68 def build_ipy_lexer(python3):
57 def build_ipy_lexer(python3):
69 """Builds IPython lexers depending on the value of `python3`.
58 """Builds IPython lexers depending on the value of `python3`.
@@ -92,6 +81,36 b' def build_ipy_lexer(python3):'
92 aliases = ['ipython2', 'ipython']
81 aliases = ['ipython2', 'ipython']
93 doc = """IPython Lexer"""
82 doc = """IPython Lexer"""
94
83
84 ipython_tokens = [
85 (r'(?s)(\s*)(%%capture)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
86 (r'(?s)(\s*)(%%debug)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
87 (r'(?is)(\s*)(%%html)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(HtmlLexer))),
88 (r'(?s)(\s*)(%%javascript)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(JavascriptLexer))),
89 (r'(?s)(\s*)(%%js)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(JavascriptLexer))),
90 (r'(?s)(\s*)(%%latex)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(TexLexer))),
91 (r'(?s)(\s*)(%%pypy)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PerlLexer))),
92 (r'(?s)(\s*)(%%prun)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
93 (r'(?s)(\s*)(%%pypy)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
94 (r'(?s)(\s*)(%%python)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
95 (r'(?s)(\s*)(%%python2)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PythonLexer))),
96 (r'(?s)(\s*)(%%python3)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(Python3Lexer))),
97 (r'(?s)(\s*)(%%ruby)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(RubyLexer))),
98 (r'(?s)(\s*)(%%time)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
99 (r'(?s)(\s*)(%%timeit)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
100 (r'(?s)(\s*)(%%writefile)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(PyLexer))),
101 (r"(?s)(\s*)(%%)(\w+)(.*)", bygroups(Text, Operator, Keyword, Text)),
102 (r'(?s)(^\s*)(%%!)([^\n]*\n)(.*)', bygroups(Text, Operator, Text, using(BashLexer))),
103 (r"(%%?)(\w+)(\?\??)$", bygroups(Operator, Keyword, Operator)),
104 (r"\b(\?\??)(\s*)$", bygroups(Operator, Text)),
105 (r'(%)(sx|sc|system)(.*)(\n)', bygroups(Operator, Keyword,
106 using(BashLexer), Text)),
107 (r'(%)(\w+)(.*\n)', bygroups(Operator, Keyword, Text)),
108 (r'^(!!)(.+)(\n)', bygroups(Operator, using(BashLexer), Text)),
109 (r'(!)(?!=)(.+)(\n)', bygroups(Operator, using(BashLexer), Text)),
110 (r'^(\s*)(\?\??)(\s*%{0,2}[\w\.\*]*)', bygroups(Text, Operator, Text)),
111 (r'(\s*%{0,2}[\w\.\*]*)(\?\??)(\s*)$', bygroups(Text, Operator, Text)),
112 ]
113
95 tokens = PyLexer.tokens.copy()
114 tokens = PyLexer.tokens.copy()
96 tokens['root'] = ipython_tokens + tokens['root']
115 tokens['root'] = ipython_tokens + tokens['root']
97
116
@@ -217,7 +236,7 b' class IPythonConsoleLexer(Lexer):'
217
236
218 ---------------------------------------------------------------------------
237 ---------------------------------------------------------------------------
219 Exception Traceback (most recent call last)
238 Exception Traceback (most recent call last)
220 <ipython-input-1-fca2ab0ca76b> in <module>()
239 <ipython-input-1-fca2ab0ca76b> in <module>
221 ----> 1 raise Exception
240 ----> 1 raise Exception
222
241
223 Exception:
242 Exception:
@@ -77,11 +77,13 b' Inheritance diagram:'
77 Portions (c) 2009 by Robert Kern.
77 Portions (c) 2009 by Robert Kern.
78 :license: BSD License.
78 :license: BSD License.
79 """
79 """
80
80 from contextlib import contextmanager
81 from contextlib import contextmanager
82 import datetime
83 import os
84 import re
81 import sys
85 import sys
82 import types
86 import types
83 import re
84 import datetime
85 from collections import deque
87 from collections import deque
86 from io import StringIO
88 from io import StringIO
87 from warnings import warn
89 from warnings import warn
@@ -742,7 +744,6 b' _type_pprinters = {'
742 tuple: _seq_pprinter_factory('(', ')'),
744 tuple: _seq_pprinter_factory('(', ')'),
743 list: _seq_pprinter_factory('[', ']'),
745 list: _seq_pprinter_factory('[', ']'),
744 dict: _dict_pprinter_factory('{', '}'),
746 dict: _dict_pprinter_factory('{', '}'),
745
746 set: _set_pprinter_factory('{', '}'),
747 set: _set_pprinter_factory('{', '}'),
747 frozenset: _set_pprinter_factory('frozenset({', '})'),
748 frozenset: _set_pprinter_factory('frozenset({', '})'),
748 super: _super_pprint,
749 super: _super_pprint,
@@ -751,12 +752,17 b' _type_pprinters = {'
751 types.FunctionType: _function_pprint,
752 types.FunctionType: _function_pprint,
752 types.BuiltinFunctionType: _function_pprint,
753 types.BuiltinFunctionType: _function_pprint,
753 types.MethodType: _repr_pprint,
754 types.MethodType: _repr_pprint,
754
755 datetime.datetime: _repr_pprint,
755 datetime.datetime: _repr_pprint,
756 datetime.timedelta: _repr_pprint,
756 datetime.timedelta: _repr_pprint,
757 _exception_base: _exception_pprint
757 _exception_base: _exception_pprint
758 }
758 }
759
759
760 # render os.environ like a dict
761 _env_type = type(os.environ)
762 # future-proof in case os.environ becomes a plain dict?
763 if _env_type is not dict:
764 _type_pprinters[_env_type] = _dict_pprinter_factory('environ{', '}')
765
760 try:
766 try:
761 # In PyPy, types.DictProxyType is dict, setting the dictproxy printer
767 # In PyPy, types.DictProxyType is dict, setting the dictproxy printer
762 # using dict.setdefault avoids overwritting the dict printer
768 # using dict.setdefault avoids overwritting the dict printer
@@ -768,7 +774,7 b' except AttributeError: # Python 3'
768 _type_pprinters[types.MappingProxyType] = \
774 _type_pprinters[types.MappingProxyType] = \
769 _dict_pprinter_factory('mappingproxy({', '})')
775 _dict_pprinter_factory('mappingproxy({', '})')
770 _type_pprinters[slice] = _repr_pprint
776 _type_pprinters[slice] = _repr_pprint
771
777
772 try:
778 try:
773 _type_pprinters[long] = _repr_pprint
779 _type_pprinters[long] = _repr_pprint
774 _type_pprinters[unicode] = _repr_pprint
780 _type_pprinters[unicode] = _repr_pprint
@@ -14,6 +14,11 b''
14 #-----------------------------------------------------------------------------
14 #-----------------------------------------------------------------------------
15 from tempfile import NamedTemporaryFile, mkdtemp
15 from tempfile import NamedTemporaryFile, mkdtemp
16 from os.path import split, join as pjoin, dirname
16 from os.path import split, join as pjoin, dirname
17 import sys
18 try:
19 import pathlib
20 except ImportError:
21 pass
17
22
18 # Third-party imports
23 # Third-party imports
19 import nose.tools as nt
24 import nose.tools as nt
@@ -33,6 +38,9 b' from IPython.testing.decorators import skipif_not_numpy'
33 def test_instantiation_FileLink():
38 def test_instantiation_FileLink():
34 """FileLink: Test class can be instantiated"""
39 """FileLink: Test class can be instantiated"""
35 fl = display.FileLink('example.txt')
40 fl = display.FileLink('example.txt')
41 # TODO: remove if when only Python >= 3.6 is supported
42 if sys.version_info >= (3, 6):
43 fl = display.FileLink(pathlib.PurePath('example.txt'))
36
44
37 def test_warning_on_non_existant_path_FileLink():
45 def test_warning_on_non_existant_path_FileLink():
38 """FileLink: Calling _repr_html_ on non-existant files returns a warning
46 """FileLink: Calling _repr_html_ on non-existant files returns a warning
@@ -175,3 +183,7 b' def test_recursive_FileLinks():'
175 def test_audio_from_file():
183 def test_audio_from_file():
176 path = pjoin(dirname(__file__), 'test.wav')
184 path = pjoin(dirname(__file__), 'test.wav')
177 display.Audio(filename=path)
185 display.Audio(filename=path)
186
187 def test_code_from_file():
188 c = display.Code(filename=__file__)
189 assert c._repr_html_().startswith('<style>')
@@ -127,3 +127,50 b' class TestLexers(TestCase):'
127 (Token.Text, '\n'),
127 (Token.Text, '\n'),
128 ]
128 ]
129 self.assertEqual(tokens, list(self.lexer.get_tokens(fragment)))
129 self.assertEqual(tokens, list(self.lexer.get_tokens(fragment)))
130
131 fragment = '%%writefile -a foo.py\nif a == b:\n pass'
132 tokens = [
133 (Token.Operator, '%%writefile'),
134 (Token.Text, ' -a foo.py\n'),
135 (Token.Keyword, 'if'),
136 (Token.Text, ' '),
137 (Token.Name, 'a'),
138 (Token.Text, ' '),
139 (Token.Operator, '=='),
140 (Token.Text, ' '),
141 (Token.Name, 'b'),
142 (Token.Punctuation, ':'),
143 (Token.Text, '\n'),
144 (Token.Text, ' '),
145 (Token.Keyword, 'pass'),
146 (Token.Text, '\n'),
147 ]
148 self.assertEqual(tokens, list(self.lexer.get_tokens(fragment)))
149
150 fragment = '%%timeit\nmath.sin(0)'
151 tokens = [
152 (Token.Operator, '%%timeit\n'),
153 (Token.Name, 'math'),
154 (Token.Operator, '.'),
155 (Token.Name, 'sin'),
156 (Token.Punctuation, '('),
157 (Token.Literal.Number.Integer, '0'),
158 (Token.Punctuation, ')'),
159 (Token.Text, '\n'),
160 ]
161
162 fragment = '%%HTML\n<div>foo</div>'
163 tokens = [
164 (Token.Operator, '%%HTML'),
165 (Token.Text, '\n'),
166 (Token.Punctuation, '<'),
167 (Token.Name.Tag, 'div'),
168 (Token.Punctuation, '>'),
169 (Token.Text, 'foo'),
170 (Token.Punctuation, '<'),
171 (Token.Punctuation, '/'),
172 (Token.Name.Tag, 'div'),
173 (Token.Punctuation, '>'),
174 (Token.Text, '\n'),
175 ]
176 self.assertEqual(tokens, list(self.lexer.get_tokens(fragment)))
@@ -6,6 +6,7 b''
6
6
7
7
8 from collections import Counter, defaultdict, deque, OrderedDict
8 from collections import Counter, defaultdict, deque, OrderedDict
9 import os
9 import types
10 import types
10 import string
11 import string
11 import unittest
12 import unittest
@@ -406,6 +407,15 b' def test_mappingproxy():'
406 for obj, expected in cases:
407 for obj, expected in cases:
407 nt.assert_equal(pretty.pretty(obj), expected)
408 nt.assert_equal(pretty.pretty(obj), expected)
408
409
410
411 def test_pretty_environ():
412 dict_repr = pretty.pretty(dict(os.environ))
413 # reindent to align with 'environ' prefix
414 dict_indented = dict_repr.replace('\n', '\n' + (' ' * len('environ')))
415 env_repr = pretty.pretty(os.environ)
416 nt.assert_equals(env_repr, 'environ' + dict_indented)
417
418
409 def test_function_pretty():
419 def test_function_pretty():
410 "Test pretty print of function"
420 "Test pretty print of function"
411 # posixpath is a pure python module, its interface is consistent
421 # posixpath is a pure python module, its interface is consistent
@@ -8,15 +8,14 b' from .ptutils import IPythonPTCompleter'
8 from .shortcuts import suspend_to_bg, cursor_in_leading_ws
8 from .shortcuts import suspend_to_bg, cursor_in_leading_ws
9
9
10 from prompt_toolkit.enums import DEFAULT_BUFFER
10 from prompt_toolkit.enums import DEFAULT_BUFFER
11 from prompt_toolkit.filters import (Condition, HasFocus, HasSelection,
11 from prompt_toolkit.filters import (Condition, has_focus, has_selection,
12 ViInsertMode, EmacsInsertMode)
12 vi_insert_mode, emacs_insert_mode)
13 from prompt_toolkit.keys import Keys
13 from prompt_toolkit.key_binding import KeyBindings
14 from prompt_toolkit.key_binding.manager import KeyBindingManager
15 from prompt_toolkit.key_binding.bindings.completion import display_completions_like_readline
14 from prompt_toolkit.key_binding.bindings.completion import display_completions_like_readline
16 from prompt_toolkit.token import Token
15 from pygments.token import Token
17 from prompt_toolkit.shortcuts import create_prompt_application
16 from prompt_toolkit.shortcuts.prompt import PromptSession
18 from prompt_toolkit.interface import CommandLineInterface
19 from prompt_toolkit.enums import EditingMode
17 from prompt_toolkit.enums import EditingMode
18 from prompt_toolkit.formatted_text import PygmentsTokens
20
19
21
20
22 class TerminalPdb(Pdb):
21 class TerminalPdb(Pdb):
@@ -26,46 +25,40 b' class TerminalPdb(Pdb):'
26 self.pt_init()
25 self.pt_init()
27
26
28 def pt_init(self):
27 def pt_init(self):
29 def get_prompt_tokens(cli):
28 def get_prompt_tokens():
30 return [(Token.Prompt, self.prompt)]
29 return [(Token.Prompt, self.prompt)]
31
30
32 def patch_stdout(**kwargs):
33 return self.pt_cli.patch_stdout_context(**kwargs)
34
35 if self._ptcomp is None:
31 if self._ptcomp is None:
36 compl = IPCompleter(shell=self.shell,
32 compl = IPCompleter(shell=self.shell,
37 namespace={},
33 namespace={},
38 global_namespace={},
34 global_namespace={},
39 parent=self.shell,
35 parent=self.shell,
40 )
36 )
41 self._ptcomp = IPythonPTCompleter(compl, patch_stdout=patch_stdout)
37 self._ptcomp = IPythonPTCompleter(compl)
42
38
43 kbmanager = KeyBindingManager.for_prompt()
39 kb = KeyBindings()
44 supports_suspend = Condition(lambda cli: hasattr(signal, 'SIGTSTP'))
40 supports_suspend = Condition(lambda: hasattr(signal, 'SIGTSTP'))
45 kbmanager.registry.add_binding(Keys.ControlZ, filter=supports_suspend
41 kb.add('c-z', filter=supports_suspend)(suspend_to_bg)
46 )(suspend_to_bg)
47
42
48 if self.shell.display_completions == 'readlinelike':
43 if self.shell.display_completions == 'readlinelike':
49 kbmanager.registry.add_binding(Keys.ControlI,
44 kb.add('tab', filter=(has_focus(DEFAULT_BUFFER)
50 filter=(HasFocus(DEFAULT_BUFFER)
45 & ~has_selection
51 & ~HasSelection()
46 & vi_insert_mode | emacs_insert_mode
52 & ViInsertMode() | EmacsInsertMode()
47 & ~cursor_in_leading_ws
53 & ~cursor_in_leading_ws
48 ))(display_completions_like_readline)
54 ))(display_completions_like_readline)
49
55 multicolumn = (self.shell.display_completions == 'multicolumn')
50 self.pt_app = PromptSession(
56
51 message=(lambda: PygmentsTokens(get_prompt_tokens())),
57 self._pt_app = create_prompt_application(
58 editing_mode=getattr(EditingMode, self.shell.editing_mode.upper()),
52 editing_mode=getattr(EditingMode, self.shell.editing_mode.upper()),
59 key_bindings_registry=kbmanager.registry,
53 key_bindings=kb,
60 history=self.shell.debugger_history,
54 history=self.shell.debugger_history,
61 completer= self._ptcomp,
55 completer=self._ptcomp,
62 enable_history_search=True,
56 enable_history_search=True,
63 mouse_support=self.shell.mouse_support,
57 mouse_support=self.shell.mouse_support,
64 get_prompt_tokens=get_prompt_tokens,
58 complete_style=self.shell.pt_complete_style,
65 display_completions_in_columns=multicolumn,
59 style=self.shell.style,
66 style=self.shell.style
60 inputhook=self.shell.inputhook,
67 )
61 )
68 self.pt_cli = CommandLineInterface(self._pt_app, eventloop=self.shell._eventloop)
69
62
70 def cmdloop(self, intro=None):
63 def cmdloop(self, intro=None):
71 """Repeatedly issue a prompt, accept input, parse an initial prefix
64 """Repeatedly issue a prompt, accept input, parse an initial prefix
@@ -92,7 +85,7 b' class TerminalPdb(Pdb):'
92 self._ptcomp.ipy_completer.namespace = self.curframe_locals
85 self._ptcomp.ipy_completer.namespace = self.curframe_locals
93 self._ptcomp.ipy_completer.global_namespace = self.curframe.f_globals
86 self._ptcomp.ipy_completer.global_namespace = self.curframe.f_globals
94 try:
87 try:
95 line = self.pt_cli.run(reset_current_buffer=True).text
88 line = self.pt_app.prompt() # reset_current_buffer=True)
96 except EOFError:
89 except EOFError:
97 line = 'EOF'
90 line = 'EOF'
98 line = self.precmd(line)
91 line = self.precmd(line)
@@ -15,15 +15,16 b' from traitlets import ('
15 Any,
15 Any,
16 )
16 )
17
17
18 from prompt_toolkit.document import Document
19 from prompt_toolkit.enums import DEFAULT_BUFFER, EditingMode
18 from prompt_toolkit.enums import DEFAULT_BUFFER, EditingMode
20 from prompt_toolkit.filters import (HasFocus, Condition, IsDone)
19 from prompt_toolkit.filters import (HasFocus, Condition, IsDone)
20 from prompt_toolkit.formatted_text import PygmentsTokens
21 from prompt_toolkit.history import InMemoryHistory
21 from prompt_toolkit.history import InMemoryHistory
22 from prompt_toolkit.shortcuts import create_prompt_application, create_eventloop, create_prompt_layout, create_output
23 from prompt_toolkit.interface import CommandLineInterface
24 from prompt_toolkit.key_binding.manager import KeyBindingManager
25 from prompt_toolkit.layout.processors import ConditionalProcessor, HighlightMatchingBracketProcessor
22 from prompt_toolkit.layout.processors import ConditionalProcessor, HighlightMatchingBracketProcessor
26 from prompt_toolkit.styles import PygmentsStyle, DynamicStyle
23 from prompt_toolkit.output import ColorDepth
24 from prompt_toolkit.patch_stdout import patch_stdout
25 from prompt_toolkit.shortcuts import PromptSession, CompleteStyle, print_formatted_text
26 from prompt_toolkit.styles import DynamicStyle, merge_styles
27 from prompt_toolkit.styles.pygments import style_from_pygments_cls, style_from_pygments_dict
27
28
28 from pygments.styles import get_style_by_name
29 from pygments.styles import get_style_by_name
29 from pygments.style import Style
30 from pygments.style import Style
@@ -34,7 +35,7 b' from .magics import TerminalMagics'
34 from .pt_inputhooks import get_inputhook_name_and_func
35 from .pt_inputhooks import get_inputhook_name_and_func
35 from .prompts import Prompts, ClassicPrompts, RichPromptDisplayHook
36 from .prompts import Prompts, ClassicPrompts, RichPromptDisplayHook
36 from .ptutils import IPythonPTCompleter, IPythonPTLexer
37 from .ptutils import IPythonPTCompleter, IPythonPTLexer
37 from .shortcuts import register_ipython_shortcuts
38 from .shortcuts import create_ipython_shortcuts
38
39
39 DISPLAY_BANNER_DEPRECATED = object()
40 DISPLAY_BANNER_DEPRECATED = object()
40
41
@@ -88,15 +89,11 b" _use_simple_prompt = ('IPY_TEST_SIMPLE_PROMPT' in os.environ) or (not _is_tty)"
88
89
89 class TerminalInteractiveShell(InteractiveShell):
90 class TerminalInteractiveShell(InteractiveShell):
90 space_for_menu = Integer(6, help='Number of line at the bottom of the screen '
91 space_for_menu = Integer(6, help='Number of line at the bottom of the screen '
91 'to reserve for the completion menu'
92 'to reserve for the completion menu'
92 ).tag(config=True)
93 ).tag(config=True)
93
94
94 def _space_for_menu_changed(self, old, new):
95 pt_app = None
95 self._update_layout()
96
97 pt_cli = None
98 debugger_history = None
96 debugger_history = None
99 _pt_app = None
100
97
101 simple_prompt = Bool(_use_simple_prompt,
98 simple_prompt = Bool(_use_simple_prompt,
102 help="""Use `raw_input` for the REPL, without completion and prompt colors.
99 help="""Use `raw_input` for the REPL, without completion and prompt colors.
@@ -167,9 +164,9 b' class TerminalInteractiveShell(InteractiveShell):'
167 def _prompts_default(self):
164 def _prompts_default(self):
168 return self.prompts_class(self)
165 return self.prompts_class(self)
169
166
170 @observe('prompts')
167 # @observe('prompts')
171 def _(self, change):
168 # def _(self, change):
172 self._update_layout()
169 # self._update_layout()
173
170
174 @default('displayhook_class')
171 @default('displayhook_class')
175 def _displayhook_class_default(self):
172 def _displayhook_class_default(self):
@@ -241,10 +238,7 b' class TerminalInteractiveShell(InteractiveShell):'
241 return
238 return
242
239
243 # Set up keyboard shortcuts
240 # Set up keyboard shortcuts
244 kbmanager = KeyBindingManager.for_prompt(
241 key_bindings = create_ipython_shortcuts(self)
245 enable_open_in_editor=self.extra_open_editor_shortcuts,
246 )
247 register_ipython_shortcuts(kbmanager.registry, self)
248
242
249 # Pre-populate history from IPython's history database
243 # Pre-populate history from IPython's history database
250 history = InMemoryHistory()
244 history = InMemoryHistory()
@@ -254,7 +248,7 b' class TerminalInteractiveShell(InteractiveShell):'
254 # Ignore blank lines and consecutive duplicates
248 # Ignore blank lines and consecutive duplicates
255 cell = cell.rstrip()
249 cell = cell.rstrip()
256 if cell and (cell != last_cell):
250 if cell and (cell != last_cell):
257 history.append(cell)
251 history.append_string(cell)
258 last_cell = cell
252 last_cell = cell
259
253
260 self._style = self._make_style_from_name_or_cls(self.highlighting_style)
254 self._style = self._make_style_from_name_or_cls(self.highlighting_style)
@@ -262,24 +256,18 b' class TerminalInteractiveShell(InteractiveShell):'
262
256
263 editing_mode = getattr(EditingMode, self.editing_mode.upper())
257 editing_mode = getattr(EditingMode, self.editing_mode.upper())
264
258
265 def patch_stdout(**kwargs):
259 self.pt_app = PromptSession(
266 return self.pt_cli.patch_stdout_context(**kwargs)
267
268 self._pt_app = create_prompt_application(
269 editing_mode=editing_mode,
260 editing_mode=editing_mode,
270 key_bindings_registry=kbmanager.registry,
261 key_bindings=key_bindings,
271 history=history,
262 history=history,
272 completer=IPythonPTCompleter(shell=self,
263 completer=IPythonPTCompleter(shell=self),
273 patch_stdout=patch_stdout),
264 enable_history_search = self.enable_history_search,
274 enable_history_search=self.enable_history_search,
275 style=self.style,
265 style=self.style,
266 include_default_pygments_style=False,
276 mouse_support=self.mouse_support,
267 mouse_support=self.mouse_support,
277 **self._layout_options()
268 enable_open_in_editor=self.extra_open_editor_shortcuts,
278 )
269 color_depth=(ColorDepth.TRUE_COLOR if self.true_color else None),
279 self._eventloop = create_eventloop(self.inputhook)
270 **self._extra_prompt_options())
280 self.pt_cli = CommandLineInterface(
281 self._pt_app, eventloop=self._eventloop,
282 output=create_output(true_color=self.true_color))
283
271
284 def _make_style_from_name_or_cls(self, name_or_cls):
272 def _make_style_from_name_or_cls(self, name_or_cls):
285 """
273 """
@@ -340,44 +328,60 b' class TerminalInteractiveShell(InteractiveShell):'
340 Token.OutPromptNum: '#ff0000 bold',
328 Token.OutPromptNum: '#ff0000 bold',
341 }
329 }
342 style_overrides.update(self.highlighting_style_overrides)
330 style_overrides.update(self.highlighting_style_overrides)
343 style = PygmentsStyle.from_defaults(pygments_style_cls=style_cls,
331 style = merge_styles([
344 style_dict=style_overrides)
332 style_from_pygments_cls(style_cls),
333 style_from_pygments_dict(style_overrides),
334 ])
345
335
346 return style
336 return style
347
337
348 def _layout_options(self):
338 @property
339 def pt_complete_style(self):
340 return {
341 'multicolumn': CompleteStyle.MULTI_COLUMN,
342 'column': CompleteStyle.COLUMN,
343 'readlinelike': CompleteStyle.READLINE_LIKE,
344 }[self.display_completions]
345
346 def _extra_prompt_options(self):
349 """
347 """
350 Return the current layout option for the current Terminal InteractiveShell
348 Return the current layout option for the current Terminal InteractiveShell
351 """
349 """
350 def get_message():
351 return PygmentsTokens(self.prompts.in_prompt_tokens())
352
352 return {
353 return {
354 'complete_in_thread': False,
353 'lexer':IPythonPTLexer(),
355 'lexer':IPythonPTLexer(),
354 'reserve_space_for_menu':self.space_for_menu,
356 'reserve_space_for_menu':self.space_for_menu,
355 'get_prompt_tokens':self.prompts.in_prompt_tokens,
357 'message': get_message,
356 'get_continuation_tokens':self.prompts.continuation_prompt_tokens,
358 'prompt_continuation': (
357 'multiline':True,
359 lambda width, lineno, is_soft_wrap:
358 'display_completions_in_columns': (self.display_completions == 'multicolumn'),
360 PygmentsTokens(self.prompts.continuation_prompt_tokens(width))),
361 'multiline': True,
362 'complete_style': self.pt_complete_style,
359
363
360 # Highlight matching brackets, but only when this setting is
364 # Highlight matching brackets, but only when this setting is
361 # enabled, and only when the DEFAULT_BUFFER has the focus.
365 # enabled, and only when the DEFAULT_BUFFER has the focus.
362 'extra_input_processors': [ConditionalProcessor(
366 'input_processors': [ConditionalProcessor(
363 processor=HighlightMatchingBracketProcessor(chars='[](){}'),
367 processor=HighlightMatchingBracketProcessor(chars='[](){}'),
364 filter=HasFocus(DEFAULT_BUFFER) & ~IsDone() &
368 filter=HasFocus(DEFAULT_BUFFER) & ~IsDone() &
365 Condition(lambda cli: self.highlight_matching_brackets))],
369 Condition(lambda: self.highlight_matching_brackets))],
366 }
370 }
367
371
368 def _update_layout(self):
369 """
370 Ask for a re computation of the application layout, if for example ,
371 some configuration options have changed.
372 """
373 if self._pt_app:
374 self._pt_app.layout = create_prompt_layout(**self._layout_options())
375
376 def prompt_for_code(self):
372 def prompt_for_code(self):
377 with self.pt_cli.patch_stdout_context(raw=True):
373 if self.rl_next_input:
378 document = self.pt_cli.run(
374 default = self.rl_next_input
379 pre_run=self.pre_prompt, reset_current_buffer=True)
375 self.rl_next_input = None
380 return document.text
376 else:
377 default = ''
378
379 with patch_stdout(raw=True):
380 text = self.pt_app.prompt(
381 default=default,
382 # pre_run=self.pre_prompt,# reset_current_buffer=True,
383 **self._extra_prompt_options())
384 return text
381
385
382 def enable_win_unicode_console(self):
386 def enable_win_unicode_console(self):
383 if sys.version_info >= (3, 6):
387 if sys.version_info >= (3, 6):
@@ -437,22 +441,6 b' class TerminalInteractiveShell(InteractiveShell):'
437
441
438 rl_next_input = None
442 rl_next_input = None
439
443
440 def pre_prompt(self):
441 if self.rl_next_input:
442 # We can't set the buffer here, because it will be reset just after
443 # this. Adding a callable to pre_run_callables does what we need
444 # after the buffer is reset.
445 s = self.rl_next_input
446 def set_doc():
447 self.pt_cli.application.buffer.document = Document(s)
448 if hasattr(self.pt_cli, 'pre_run_callables'):
449 self.pt_cli.pre_run_callables.append(set_doc)
450 else:
451 # Older version of prompt_toolkit; it's OK to set the document
452 # directly here.
453 set_doc()
454 self.rl_next_input = None
455
456 def interact(self, display_banner=DISPLAY_BANNER_DEPRECATED):
444 def interact(self, display_banner=DISPLAY_BANNER_DEPRECATED):
457
445
458 if display_banner is not DISPLAY_BANNER_DEPRECATED:
446 if display_banner is not DISPLAY_BANNER_DEPRECATED:
@@ -515,8 +503,9 b' class TerminalInteractiveShell(InteractiveShell):'
515 return
503 return
516
504
517 tokens = self.prompts.rewrite_prompt_tokens()
505 tokens = self.prompts.rewrite_prompt_tokens()
518 if self.pt_cli:
506 if self.pt_app:
519 self.pt_cli.print_tokens(tokens)
507 print_formatted_text(PygmentsTokens(tokens), end='',
508 style=self.pt_app.app.style)
520 print(cmd)
509 print(cmd)
521 else:
510 else:
522 prompt = ''.join(s for t, s in tokens)
511 prompt = ''.join(s for t, s in tokens)
@@ -531,7 +520,7 b' class TerminalInteractiveShell(InteractiveShell):'
531 elif self._prompts_before:
520 elif self._prompts_before:
532 self.prompts = self._prompts_before
521 self.prompts = self._prompts_before
533 self._prompts_before = None
522 self._prompts_before = None
534 self._update_layout()
523 # self._update_layout()
535
524
536
525
537 InteractiveShellABC.register(TerminalInteractiveShell)
526 InteractiveShellABC.register(TerminalInteractiveShell)
@@ -5,13 +5,15 b' import sys'
5
5
6 from IPython.core.displayhook import DisplayHook
6 from IPython.core.displayhook import DisplayHook
7
7
8 from prompt_toolkit.layout.utils import token_list_width
8 from prompt_toolkit.formatted_text import fragment_list_width, PygmentsTokens
9 from prompt_toolkit.shortcuts import print_formatted_text
10
9
11
10 class Prompts(object):
12 class Prompts(object):
11 def __init__(self, shell):
13 def __init__(self, shell):
12 self.shell = shell
14 self.shell = shell
13
15
14 def in_prompt_tokens(self, cli=None):
16 def in_prompt_tokens(self):
15 return [
17 return [
16 (Token.Prompt, 'In ['),
18 (Token.Prompt, 'In ['),
17 (Token.PromptNum, str(self.shell.execution_count)),
19 (Token.PromptNum, str(self.shell.execution_count)),
@@ -19,9 +21,9 b' class Prompts(object):'
19 ]
21 ]
20
22
21 def _width(self):
23 def _width(self):
22 return token_list_width(self.in_prompt_tokens())
24 return fragment_list_width(self.in_prompt_tokens())
23
25
24 def continuation_prompt_tokens(self, cli=None, width=None):
26 def continuation_prompt_tokens(self, width=None):
25 if width is None:
27 if width is None:
26 width = self._width()
28 width = self._width()
27 return [
29 return [
@@ -42,12 +44,12 b' class Prompts(object):'
42 ]
44 ]
43
45
44 class ClassicPrompts(Prompts):
46 class ClassicPrompts(Prompts):
45 def in_prompt_tokens(self, cli=None):
47 def in_prompt_tokens(self):
46 return [
48 return [
47 (Token.Prompt, '>>> '),
49 (Token.Prompt, '>>> '),
48 ]
50 ]
49
51
50 def continuation_prompt_tokens(self, cli=None, width=None):
52 def continuation_prompt_tokens(self, width=None):
51 return [
53 return [
52 (Token.Prompt, '... ')
54 (Token.Prompt, '... ')
53 ]
55 ]
@@ -73,7 +75,9 b' class RichPromptDisplayHook(DisplayHook):'
73 # Ask for a newline before multiline output
75 # Ask for a newline before multiline output
74 self.prompt_end_newline = False
76 self.prompt_end_newline = False
75
77
76 if self.shell.pt_cli:
78 if self.shell.pt_app:
77 self.shell.pt_cli.print_tokens(tokens)
79 print_formatted_text(PygmentsTokens(tokens),
80 style=self.shell.pt_app.app.style, end='',
81 )
78 else:
82 else:
79 sys.stdout.write(prompt_txt)
83 sys.stdout.write(prompt_txt)
@@ -14,8 +14,9 b' from IPython.core.completer import ('
14 provisionalcompleter, cursor_to_position,
14 provisionalcompleter, cursor_to_position,
15 _deduplicate_completions)
15 _deduplicate_completions)
16 from prompt_toolkit.completion import Completer, Completion
16 from prompt_toolkit.completion import Completer, Completion
17 from prompt_toolkit.layout.lexers import Lexer
17 from prompt_toolkit.lexers import Lexer
18 from prompt_toolkit.layout.lexers import PygmentsLexer
18 from prompt_toolkit.lexers import PygmentsLexer
19 from prompt_toolkit.patch_stdout import patch_stdout
19
20
20 import pygments.lexers as pygments_lexers
21 import pygments.lexers as pygments_lexers
21
22
@@ -52,14 +53,11 b' def _adjust_completion_text_based_on_context(text, body, offset):'
52
53
53 class IPythonPTCompleter(Completer):
54 class IPythonPTCompleter(Completer):
54 """Adaptor to provide IPython completions to prompt_toolkit"""
55 """Adaptor to provide IPython completions to prompt_toolkit"""
55 def __init__(self, ipy_completer=None, shell=None, patch_stdout=None):
56 def __init__(self, ipy_completer=None, shell=None):
56 if shell is None and ipy_completer is None:
57 if shell is None and ipy_completer is None:
57 raise TypeError("Please pass shell=an InteractiveShell instance.")
58 raise TypeError("Please pass shell=an InteractiveShell instance.")
58 self._ipy_completer = ipy_completer
59 self._ipy_completer = ipy_completer
59 self.shell = shell
60 self.shell = shell
60 if patch_stdout is None:
61 raise TypeError("Please pass patch_stdout")
62 self.patch_stdout = patch_stdout
63
61
64 @property
62 @property
65 def ipy_completer(self):
63 def ipy_completer(self):
@@ -75,7 +73,7 b' class IPythonPTCompleter(Completer):'
75 # is imported). This context manager ensures that doesn't interfere with
73 # is imported). This context manager ensures that doesn't interfere with
76 # the prompt.
74 # the prompt.
77
75
78 with self.patch_stdout(), provisionalcompleter():
76 with patch_stdout(), provisionalcompleter():
79 body = document.text
77 body = document.text
80 cursor_row = document.cursor_position_row
78 cursor_row = document.cursor_position_row
81 cursor_col = document.cursor_position_col
79 cursor_col = document.cursor_position_col
@@ -143,7 +141,7 b' class IPythonPTLexer(Lexer):'
143 'latex': PygmentsLexer(l.TexLexer),
141 'latex': PygmentsLexer(l.TexLexer),
144 }
142 }
145
143
146 def lex_document(self, cli, document):
144 def lex_document(self, document):
147 text = document.text.lstrip()
145 text = document.text.lstrip()
148
146
149 lexer = self.python_lexer
147 lexer = self.python_lexer
@@ -157,4 +155,4 b' class IPythonPTLexer(Lexer):'
157 lexer = l
155 lexer = l
158 break
156 break
159
157
160 return lexer.lex_document(cli, document)
158 return lexer.lex_document(document)
@@ -12,91 +12,78 b' import sys'
12 from typing import Callable
12 from typing import Callable
13
13
14
14
15 from prompt_toolkit.application.current import get_app
15 from prompt_toolkit.enums import DEFAULT_BUFFER, SEARCH_BUFFER
16 from prompt_toolkit.enums import DEFAULT_BUFFER, SEARCH_BUFFER
16 from prompt_toolkit.filters import (HasFocus, HasSelection, Condition,
17 from prompt_toolkit.filters import (has_focus, has_selection, Condition,
17 ViInsertMode, EmacsInsertMode, HasCompletions)
18 vi_insert_mode, emacs_insert_mode, has_completions, vi_mode)
18 from prompt_toolkit.filters.cli import ViMode, ViNavigationMode
19 from prompt_toolkit.keys import Keys
20 from prompt_toolkit.key_binding.bindings.completion import display_completions_like_readline
19 from prompt_toolkit.key_binding.bindings.completion import display_completions_like_readline
20 from prompt_toolkit.key_binding import KeyBindings
21
21
22 from IPython.utils.decorators import undoc
22 from IPython.utils.decorators import undoc
23
23
24 @undoc
24 @undoc
25 @Condition
25 @Condition
26 def cursor_in_leading_ws(cli):
26 def cursor_in_leading_ws():
27 before = cli.application.buffer.document.current_line_before_cursor
27 before = get_app().current_buffer.document.current_line_before_cursor
28 return (not before) or before.isspace()
28 return (not before) or before.isspace()
29
29
30 def register_ipython_shortcuts(registry, shell):
30
31 def create_ipython_shortcuts(shell):
31 """Set up the prompt_toolkit keyboard shortcuts for IPython"""
32 """Set up the prompt_toolkit keyboard shortcuts for IPython"""
32 insert_mode = ViInsertMode() | EmacsInsertMode()
33
34 kb = KeyBindings()
35 insert_mode = vi_insert_mode | emacs_insert_mode
33
36
34 if getattr(shell, 'handle_return', None):
37 if getattr(shell, 'handle_return', None):
35 return_handler = shell.handle_return(shell)
38 return_handler = shell.handle_return(shell)
36 else:
39 else:
37 return_handler = newline_or_execute_outer(shell)
40 return_handler = newline_or_execute_outer(shell)
38
41
39 # Ctrl+J == Enter, seemingly
42 kb.add('enter', filter=(has_focus(DEFAULT_BUFFER)
40 registry.add_binding(Keys.ControlJ,
43 & ~has_selection
41 filter=(HasFocus(DEFAULT_BUFFER)
44 & insert_mode
42 & ~HasSelection()
43 & insert_mode
44 ))(return_handler)
45 ))(return_handler)
45
46
46 registry.add_binding(Keys.ControlBackslash)(force_exit)
47 kb.add('c-\\')(force_exit)
47
48
48 registry.add_binding(Keys.ControlP,
49 kb.add('c-p', filter=(vi_insert_mode & has_focus(DEFAULT_BUFFER))
49 filter=(ViInsertMode() & HasFocus(DEFAULT_BUFFER)
50 )(previous_history_or_previous_completion)
50 ))(previous_history_or_previous_completion)
51
51
52 registry.add_binding(Keys.ControlN,
52 kb.add('c-n', filter=(vi_insert_mode & has_focus(DEFAULT_BUFFER))
53 filter=(ViInsertMode() & HasFocus(DEFAULT_BUFFER)
53 )(next_history_or_next_completion)
54 ))(next_history_or_next_completion)
55
54
56 registry.add_binding(Keys.ControlG,
55 kb.add('c-g', filter=(has_focus(DEFAULT_BUFFER) & has_completions)
57 filter=(HasFocus(DEFAULT_BUFFER) & HasCompletions()
56 )(dismiss_completion)
58 ))(dismiss_completion)
59
57
60 registry.add_binding(Keys.ControlC, filter=HasFocus(DEFAULT_BUFFER)
58 kb.add('c-c', filter=has_focus(DEFAULT_BUFFER))(reset_buffer)
61 )(reset_buffer)
62
59
63 registry.add_binding(Keys.ControlC, filter=HasFocus(SEARCH_BUFFER)
60 kb.add('c-c', filter=has_focus(SEARCH_BUFFER))(reset_search_buffer)
64 )(reset_search_buffer)
65
61
66 supports_suspend = Condition(lambda cli: hasattr(signal, 'SIGTSTP'))
62 supports_suspend = Condition(lambda: hasattr(signal, 'SIGTSTP'))
67 registry.add_binding(Keys.ControlZ, filter=supports_suspend
63 kb.add('c-z', filter=supports_suspend)(suspend_to_bg)
68 )(suspend_to_bg)
69
64
70 # Ctrl+I == Tab
65 # Ctrl+I == Tab
71 registry.add_binding(Keys.ControlI,
66 kb.add('tab', filter=(has_focus(DEFAULT_BUFFER)
72 filter=(HasFocus(DEFAULT_BUFFER)
67 & ~has_selection
73 & ~HasSelection()
68 & insert_mode
74 & insert_mode
69 & cursor_in_leading_ws
75 & cursor_in_leading_ws
76 ))(indent_buffer)
70 ))(indent_buffer)
71 kb.add('c-o', filter=(has_focus(DEFAULT_BUFFER)
72 & emacs_insert_mode))(newline_autoindent_outer(shell.input_transformer_manager))
77
73
78 registry.add_binding(Keys.ControlO,
74 kb.add('f2', filter=has_focus(DEFAULT_BUFFER))(open_input_in_editor)
79 filter=(HasFocus(DEFAULT_BUFFER)
80 & EmacsInsertMode()))(newline_autoindent_outer(shell.input_transformer_manager))
81
82 registry.add_binding(Keys.F2,
83 filter=HasFocus(DEFAULT_BUFFER)
84 )(open_input_in_editor)
85
75
86 if shell.display_completions == 'readlinelike':
76 if shell.display_completions == 'readlinelike':
87 registry.add_binding(Keys.ControlI,
77 kb.add('c-i', filter=(has_focus(DEFAULT_BUFFER)
88 filter=(HasFocus(DEFAULT_BUFFER)
78 & ~has_selection
89 & ~HasSelection()
79 & insert_mode
90 & insert_mode
80 & ~cursor_in_leading_ws
91 & ~cursor_in_leading_ws
81 ))(display_completions_like_readline)
92 ))(display_completions_like_readline)
93
82
94 if sys.platform == 'win32':
83 if sys.platform == 'win32':
95 registry.add_binding(Keys.ControlV,
84 kb.add('c-v', filter=(has_focus(DEFAULT_BUFFER) & ~vi_mode))(win_paste)
96 filter=(
85
97 HasFocus(
86 return kb
98 DEFAULT_BUFFER) & ~ViMode()
99 ))(win_paste)
100
87
101
88
102 def newline_or_execute_outer(shell):
89 def newline_or_execute_outer(shell):
@@ -127,8 +114,8 b' def newline_or_execute_outer(shell):'
127 b.insert_text('\n' + indent)
114 b.insert_text('\n' + indent)
128 return
115 return
129
116
130 if (status != 'incomplete') and b.accept_action.is_returnable:
117 if (status != 'incomplete') and b.accept_handler:
131 b.accept_action.validate_and_handle(event.cli, b)
118 b.validate_and_handle()
132 else:
119 else:
133 b.insert_text('\n' + indent)
120 b.insert_text('\n' + indent)
134 return newline_or_execute
121 return newline_or_execute
@@ -170,10 +157,10 b' def reset_search_buffer(event):'
170 if event.current_buffer.document.text:
157 if event.current_buffer.document.text:
171 event.current_buffer.reset()
158 event.current_buffer.reset()
172 else:
159 else:
173 event.cli.push_focus(DEFAULT_BUFFER)
160 event.app.layout.focus(DEFAULT_BUFFER)
174
161
175 def suspend_to_bg(event):
162 def suspend_to_bg(event):
176 event.cli.suspend_to_background()
163 event.app.suspend_to_background()
177
164
178 def force_exit(event):
165 def force_exit(event):
179 """
166 """
@@ -232,8 +219,8 b' def newline_autoindent_outer(inputsplitter) -> Callable[..., None]:'
232
219
233
220
234 def open_input_in_editor(event):
221 def open_input_in_editor(event):
235 event.cli.current_buffer.tempfile_suffix = ".py"
222 event.app.current_buffer.tempfile_suffix = ".py"
236 event.cli.current_buffer.open_in_editor(event.cli)
223 event.app.current_buffer.open_in_editor()
237
224
238
225
239 if sys.platform == 'win32':
226 if sys.platform == 'win32':
@@ -69,7 +69,7 b' if version_info < (6,):'
69 warnings.filterwarnings(
69 warnings.filterwarnings(
70 'ignore', message='.*Please use assertEqual instead', category=Warning, module='IPython.*')
70 'ignore', message='.*Please use assertEqual instead', category=Warning, module='IPython.*')
71
71
72 if version_info < (7,):
72 if version_info < (8,):
73 warnings.filterwarnings('ignore', message='.*Completer.complete.*',
73 warnings.filterwarnings('ignore', message='.*Completer.complete.*',
74 category=PendingDeprecationWarning, module='.*')
74 category=PendingDeprecationWarning, module='.*')
75 else:
75 else:
@@ -46,29 +46,26 b' Authors'
46 #-----------------------------------------------------------------------------
46 #-----------------------------------------------------------------------------
47
47
48 from IPython.testing.ipunittest import ipdoctest, ipdocstring
48 from IPython.testing.ipunittest import ipdoctest, ipdocstring
49 from IPython.utils.py3compat import doctest_refactor_print
50
49
51 #-----------------------------------------------------------------------------
50 #-----------------------------------------------------------------------------
52 # Test classes and functions
51 # Test classes and functions
53 #-----------------------------------------------------------------------------
52 #-----------------------------------------------------------------------------
54 @ipdoctest
53 @ipdoctest
55 @doctest_refactor_print
56 def simple_dt():
54 def simple_dt():
57 """
55 """
58 >>> print 1+1
56 >>> print(1+1)
59 2
57 2
60 """
58 """
61
59
62
60
63 @ipdoctest
61 @ipdoctest
64 @doctest_refactor_print
65 def ipdt_flush():
62 def ipdt_flush():
66 """
63 """
67 In [20]: print 1
64 In [20]: print(1)
68 1
65 1
69
66
70 In [26]: for i in range(4):
67 In [26]: for i in range(4):
71 ....: print i
68 ....: print(i)
72 ....:
69 ....:
73 ....:
70 ....:
74 0
71 0
@@ -82,14 +79,13 b' Out[27]: 7'
82
79
83
80
84 @ipdoctest
81 @ipdoctest
85 @doctest_refactor_print
86 def ipdt_indented_test():
82 def ipdt_indented_test():
87 """
83 """
88 In [20]: print 1
84 In [20]: print(1)
89 1
85 1
90
86
91 In [26]: for i in range(4):
87 In [26]: for i in range(4):
92 ....: print i
88 ....: print(i)
93 ....:
89 ....:
94 ....:
90 ....:
95 0
91 0
@@ -110,14 +106,13 b' class Foo(object):'
110 """
106 """
111
107
112 @ipdocstring
108 @ipdocstring
113 @doctest_refactor_print
114 def ipdt_method(self):
109 def ipdt_method(self):
115 """
110 """
116 In [20]: print 1
111 In [20]: print(1)
117 1
112 1
118
113
119 In [26]: for i in range(4):
114 In [26]: for i in range(4):
120 ....: print i
115 ....: print(i)
121 ....:
116 ....:
122 ....:
117 ....:
123 0
118 0
@@ -129,9 +124,8 b' class Foo(object):'
129 Out[27]: 7
124 Out[27]: 7
130 """
125 """
131
126
132 @doctest_refactor_print
133 def normaldt_method(self):
127 def normaldt_method(self):
134 """
128 """
135 >>> print 1+1
129 >>> print(1+1)
136 2
130 2
137 """
131 """
@@ -270,20 +270,25 b' class TempFileMixin(object):'
270 def mktmp(self, src, ext='.py'):
270 def mktmp(self, src, ext='.py'):
271 """Make a valid python temp file."""
271 """Make a valid python temp file."""
272 fname, f = temp_pyfile(src, ext)
272 fname, f = temp_pyfile(src, ext)
273 self.tmpfile = f
273 if not hasattr(self, 'tmps'):
274 self.tmps=[]
275 self.tmps.append((f, fname))
274 self.fname = fname
276 self.fname = fname
275
277
276 def tearDown(self):
278 def tearDown(self):
277 if hasattr(self, 'tmpfile'):
279 # If the tmpfile wasn't made because of skipped tests, like in
278 # If the tmpfile wasn't made because of skipped tests, like in
280 # win32, there's nothing to cleanup.
279 # win32, there's nothing to cleanup.
281 if hasattr(self, 'tmps'):
280 self.tmpfile.close()
282 for f,fname in self.tmps:
281 try:
283 # If the tmpfile wasn't made because of skipped tests, like in
282 os.unlink(self.fname)
284 # win32, there's nothing to cleanup.
283 except:
285 f.close()
284 # On Windows, even though we close the file, we still can't
286 try:
285 # delete it. I have no clue why
287 os.unlink(fname)
286 pass
288 except:
289 # On Windows, even though we close the file, we still can't
290 # delete it. I have no clue why
291 pass
287
292
288 def __enter__(self):
293 def __enter__(self):
289 return self
294 return self
@@ -29,7 +29,7 b' scan Python source code and re-emit it with no changes to its original'
29 formatting (which is the hard part).
29 formatting (which is the hard part).
30 """
30 """
31
31
32 __all__ = ['ANSICodeColors','Parser']
32 __all__ = ['ANSICodeColors', 'Parser']
33
33
34 _scheme_default = 'Linux'
34 _scheme_default = 'Linux'
35
35
@@ -43,7 +43,7 b' import tokenize'
43
43
44 generate_tokens = tokenize.generate_tokens
44 generate_tokens = tokenize.generate_tokens
45
45
46 from IPython.utils.coloransi import TermColors, InputTermColors ,ColorScheme, ColorSchemeTable
46 from IPython.utils.coloransi import TermColors, InputTermColors,ColorScheme, ColorSchemeTable
47 from .colorable import Colorable
47 from .colorable import Colorable
48 from io import StringIO
48 from io import StringIO
49
49
@@ -185,8 +185,11 b' class Parser(Colorable):'
185
185
186 super(Parser, self).__init__(parent=parent)
186 super(Parser, self).__init__(parent=parent)
187
187
188 self.color_table = color_table and color_table or ANSICodeColors
188 self.color_table = color_table if color_table else ANSICodeColors
189 self.out = out
189 self.out = out
190 self.pos = None
191 self.lines = None
192 self.raw = None
190 if not style:
193 if not style:
191 self.style = self.default_style
194 self.style = self.default_style
192 else:
195 else:
@@ -213,7 +216,7 b' class Parser(Colorable):'
213
216
214 string_output = 0
217 string_output = 0
215 if out == 'str' or self.out == 'str' or \
218 if out == 'str' or self.out == 'str' or \
216 isinstance(self.out,StringIO):
219 isinstance(self.out, StringIO):
217 # XXX - I don't really like this state handling logic, but at this
220 # XXX - I don't really like this state handling logic, but at this
218 # point I don't want to make major changes, so adding the
221 # point I don't want to make major changes, so adding the
219 # isinstance() check is the simplest I can do to ensure correct
222 # isinstance() check is the simplest I can do to ensure correct
@@ -223,15 +226,16 b' class Parser(Colorable):'
223 string_output = 1
226 string_output = 1
224 elif out is not None:
227 elif out is not None:
225 self.out = out
228 self.out = out
229 else:
230 raise ValueError('`out` or `self.out` should be file-like or the value `"str"`')
226
231
227 # Fast return of the unmodified input for NoColor scheme
232 # Fast return of the unmodified input for NoColor scheme
228 if self.style == 'NoColor':
233 if self.style == 'NoColor':
229 error = False
234 error = False
230 self.out.write(raw)
235 self.out.write(raw)
231 if string_output:
236 if string_output:
232 return raw,error
237 return raw, error
233 else:
238 return None, error
234 return None,error
235
239
236 # local shorthands
240 # local shorthands
237 colors = self.color_table[self.style].colors
241 colors = self.color_table[self.style].colors
@@ -245,9 +249,10 b' class Parser(Colorable):'
245 pos = 0
249 pos = 0
246 raw_find = self.raw.find
250 raw_find = self.raw.find
247 lines_append = self.lines.append
251 lines_append = self.lines.append
248 while 1:
252 while True:
249 pos = raw_find('\n', pos) + 1
253 pos = raw_find('\n', pos) + 1
250 if not pos: break
254 if not pos:
255 break
251 lines_append(pos)
256 lines_append(pos)
252 lines_append(len(self.raw))
257 lines_append(len(self.raw))
253
258
@@ -275,12 +280,13 b' class Parser(Colorable):'
275 return (output, error)
280 return (output, error)
276 return (None, error)
281 return (None, error)
277
282
278 def __call__(self, toktype, toktext, start_pos, end_pos, line):
283
279 """ Token handler, with syntax highlighting."""
284 def _inner_call_(self, toktype, toktext, start_pos):
280 (srow,scol) = start_pos
285 """like call but write to a temporary buffer"""
281 (erow,ecol) = end_pos
286 buff = StringIO()
287 srow, scol = start_pos
282 colors = self.colors
288 colors = self.colors
283 owrite = self.out.write
289 owrite = buff.write
284
290
285 # line separator, so this works across platforms
291 # line separator, so this works across platforms
286 linesep = os.linesep
292 linesep = os.linesep
@@ -297,7 +303,8 b' class Parser(Colorable):'
297 # skip indenting tokens
303 # skip indenting tokens
298 if toktype in [token.INDENT, token.DEDENT]:
304 if toktype in [token.INDENT, token.DEDENT]:
299 self.pos = newpos
305 self.pos = newpos
300 return
306 buff.seek(0)
307 return buff.read()
301
308
302 # map token type to a color group
309 # map token type to a color group
303 if token.LPAR <= toktype <= token.OP:
310 if token.LPAR <= toktype <= token.OP:
@@ -306,8 +313,6 b' class Parser(Colorable):'
306 toktype = _KEYWORD
313 toktype = _KEYWORD
307 color = colors.get(toktype, colors[_TEXT])
314 color = colors.get(toktype, colors[_TEXT])
308
315
309 #print '<%s>' % toktext, # dbg
310
311 # Triple quoted strings must be handled carefully so that backtracking
316 # Triple quoted strings must be handled carefully so that backtracking
312 # in pagers works correctly. We need color terminators on _each_ line.
317 # in pagers works correctly. We need color terminators on _each_ line.
313 if linesep in toktext:
318 if linesep in toktext:
@@ -316,3 +321,11 b' class Parser(Colorable):'
316
321
317 # send text
322 # send text
318 owrite('%s%s%s' % (color,toktext,colors.normal))
323 owrite('%s%s%s' % (color,toktext,colors.normal))
324 buff.seek(0)
325 return buff.read()
326
327
328 def __call__(self, toktype, toktext, start_pos, end_pos, line):
329 """ Token handler, with syntax highlighting."""
330 self.out.write(
331 self._inner_call_(toktype, toktext, start_pos))
@@ -23,12 +23,6 b' def uniq_stable(elems):'
23 return [x for x in elems if x not in seen and not seen.add(x)]
23 return [x for x in elems if x not in seen and not seen.add(x)]
24
24
25
25
26 def flatten(seq):
27 """Flatten a list of lists (NOT recursive, only works for 2d lists)."""
28
29 return [x for subseq in seq for x in subseq]
30
31
32 def chop(seq, size):
26 def chop(seq, size):
33 """Chop a sequence into chunks of the given size."""
27 """Chop a sequence into chunks of the given size."""
34 return [seq[i:i+size] for i in range(0,len(seq),size)]
28 return [seq[i:i+size] for i in range(0,len(seq),size)]
@@ -21,7 +21,6 b' from IPython.utils import py3compat'
21 # Code
21 # Code
22 #-----------------------------------------------------------------------------
22 #-----------------------------------------------------------------------------
23
23
24 @py3compat.doctest_refactor_print
25 def extract_vars(*names,**kw):
24 def extract_vars(*names,**kw):
26 """Extract a set of variables by name from another frame.
25 """Extract a set of variables by name from another frame.
27
26
@@ -17,7 +17,6 b' from warnings import warn'
17
17
18 from IPython.utils.decorators import undoc
18 from IPython.utils.decorators import undoc
19 from .capture import CapturedIO, capture_output
19 from .capture import CapturedIO, capture_output
20 from .py3compat import input
21
20
22 @undoc
21 @undoc
23 class IOStream:
22 class IOStream:
@@ -211,35 +210,34 b" def temp_pyfile(src, ext='.py'):"
211 f.flush()
210 f.flush()
212 return fname, f
211 return fname, f
213
212
213 @undoc
214 def atomic_writing(*args, **kwargs):
214 def atomic_writing(*args, **kwargs):
215 """DEPRECATED: moved to notebook.services.contents.fileio"""
215 """DEPRECATED: moved to notebook.services.contents.fileio"""
216 warn("IPython.utils.io.atomic_writing has moved to notebook.services.contents.fileio", stacklevel=2)
216 warn("IPython.utils.io.atomic_writing has moved to notebook.services.contents.fileio since IPython 4.0", DeprecationWarning, stacklevel=2)
217 from notebook.services.contents.fileio import atomic_writing
217 from notebook.services.contents.fileio import atomic_writing
218 return atomic_writing(*args, **kwargs)
218 return atomic_writing(*args, **kwargs)
219
219
220 @undoc
220 def raw_print(*args, **kw):
221 def raw_print(*args, **kw):
221 """Raw print to sys.__stdout__, otherwise identical interface to print()."""
222 """DEPRECATED: Raw print to sys.__stdout__, otherwise identical interface to print()."""
223 warn("IPython.utils.io.raw_print has been deprecated since IPython 7.0", DeprecationWarning, stacklevel=2)
222
224
223 print(*args, sep=kw.get('sep', ' '), end=kw.get('end', '\n'),
225 print(*args, sep=kw.get('sep', ' '), end=kw.get('end', '\n'),
224 file=sys.__stdout__)
226 file=sys.__stdout__)
225 sys.__stdout__.flush()
227 sys.__stdout__.flush()
226
228
227
229 @undoc
228 def raw_print_err(*args, **kw):
230 def raw_print_err(*args, **kw):
229 """Raw print to sys.__stderr__, otherwise identical interface to print()."""
231 """DEPRECATED: Raw print to sys.__stderr__, otherwise identical interface to print()."""
232 warn("IPython.utils.io.raw_print_err has been deprecated since IPython 7.0", DeprecationWarning, stacklevel=2)
230
233
231 print(*args, sep=kw.get('sep', ' '), end=kw.get('end', '\n'),
234 print(*args, sep=kw.get('sep', ' '), end=kw.get('end', '\n'),
232 file=sys.__stderr__)
235 file=sys.__stderr__)
233 sys.__stderr__.flush()
236 sys.__stderr__.flush()
234
237
235
238 @undoc
236 # Short aliases for quick debugging, do NOT use these in production code.
237 rprint = raw_print
238 rprinte = raw_print_err
239
240
241 def unicode_std_stream(stream='stdout'):
239 def unicode_std_stream(stream='stdout'):
242 """DEPRECATED, moved to nbconvert.utils.io"""
240 """DEPRECATED, moved to nbconvert.utils.io"""
243 warn("IPython.utils.io.unicode_std_stream has moved to nbconvert.utils.io", stacklevel=2)
241 warn("IPython.utils.io.unicode_std_stream has moved to nbconvert.utils.io since IPython 4.0", DeprecationWarning, stacklevel=2)
244 from nbconvert.utils.io import unicode_std_stream
242 from nbconvert.utils.io import unicode_std_stream
245 return unicode_std_stream(stream)
243 return unicode_std_stream(stream)
@@ -103,19 +103,3 b" def read_py_url(url, errors='replace', skip_encoding_cookie=True):"
103 response = urlopen(url)
103 response = urlopen(url)
104 buffer = io.BytesIO(response.read())
104 buffer = io.BytesIO(response.read())
105 return source_to_unicode(buffer, errors, skip_encoding_cookie)
105 return source_to_unicode(buffer, errors, skip_encoding_cookie)
106
107 def _list_readline(x):
108 """Given a list, returns a readline() function that returns the next element
109 with each call.
110 """
111 x = iter(x)
112 def readline():
113 return next(x)
114 return readline
115
116 # Code for going between .py files and cached .pyc files ----------------------
117 try:
118 from importlib.util import source_from_cache, cache_from_source
119 except ImportError :
120 ## deprecated since 3.4
121 from imp import source_from_cache, cache_from_source
@@ -21,7 +21,7 b' import sys'
21 import subprocess
21 import subprocess
22
22
23 from IPython.core import release
23 from IPython.core import release
24 from IPython.utils import py3compat, _sysinfo, encoding
24 from IPython.utils import _sysinfo, encoding
25
25
26 #-----------------------------------------------------------------------------
26 #-----------------------------------------------------------------------------
27 # Code
27 # Code
@@ -98,7 +98,6 b' def get_sys_info():'
98 path = p.realpath(p.dirname(p.abspath(p.join(__file__, '..'))))
98 path = p.realpath(p.dirname(p.abspath(p.join(__file__, '..'))))
99 return pkg_info(path)
99 return pkg_info(path)
100
100
101 @py3compat.doctest_refactor_print
102 def sys_info():
101 def sys_info():
103 """Return useful information about IPython and the system, as a string.
102 """Return useful information about IPython and the system, as a string.
104
103
@@ -106,7 +105,7 b' def sys_info():'
106 --------
105 --------
107 ::
106 ::
108
107
109 In [2]: print sys_info()
108 In [2]: print(sys_info())
110 {'commit_hash': '144fdae', # random
109 {'commit_hash': '144fdae', # random
111 'commit_source': 'repository',
110 'commit_source': 'repository',
112 'ipython_path': '/home/fperez/usr/lib/python2.6/site-packages/IPython',
111 'ipython_path': '/home/fperez/usr/lib/python2.6/site-packages/IPython',
@@ -18,7 +18,6 b' import nose.tools as nt'
18
18
19 from IPython.testing.decorators import skipif, skip_win32
19 from IPython.testing.decorators import skipif, skip_win32
20 from IPython.utils.io import IOStream, Tee, capture_output
20 from IPython.utils.io import IOStream, Tee, capture_output
21 from IPython.utils.py3compat import doctest_refactor_print
22 from IPython.utils.tempdir import TemporaryDirectory
21 from IPython.utils.tempdir import TemporaryDirectory
23
22
24
23
@@ -59,7 +58,7 b' class TeeTestCase(unittest.TestCase):'
59 def test_io_init():
58 def test_io_init():
60 """Test that io.stdin/out/err exist at startup"""
59 """Test that io.stdin/out/err exist at startup"""
61 for name in ('stdin', 'stdout', 'stderr'):
60 for name in ('stdin', 'stdout', 'stderr'):
62 cmd = doctest_refactor_print("from IPython.utils import io;print io.%s.__class__"%name)
61 cmd = "from IPython.utils import io;print(io.%s.__class__)"%name
63 p = Popen([sys.executable, '-c', cmd],
62 p = Popen([sys.executable, '-c', cmd],
64 stdout=PIPE)
63 stdout=PIPE)
65 p.wait()
64 p.wait()
@@ -29,11 +29,3 b' def test_source_to_unicode():'
29
29
30 source_no_cookie = openpy.source_to_unicode(source_bytes, skip_encoding_cookie=True)
30 source_no_cookie = openpy.source_to_unicode(source_bytes, skip_encoding_cookie=True)
31 nt.assert_not_in(u'coding: iso-8859-5', source_no_cookie)
31 nt.assert_not_in(u'coding: iso-8859-5', source_no_cookie)
32
33 def test_list_readline():
34 l = ['a', 'b']
35 readline = openpy._list_readline(l)
36 nt.assert_equal(readline(), 'a')
37 nt.assert_equal(readline(), 'b')
38 with nt.assert_raises(StopIteration):
39 readline() No newline at end of file
@@ -18,11 +18,7 b' import random'
18 import sys
18 import sys
19
19
20 import nose.tools as nt
20 import nose.tools as nt
21 try:
21 from pathlib import Path
22 from pathlib import Path
23 except ImportError:
24 # for Python 3.3
25 from pathlib2 import Path
26
22
27 from IPython.utils import text
23 from IPython.utils import text
28
24
@@ -137,13 +133,9 b' def eval_formatter_no_slicing_check(f):'
137
133
138 s = f.format('{stuff[slice(1,4)]}', **ns)
134 s = f.format('{stuff[slice(1,4)]}', **ns)
139 nt.assert_equal(s, 'ell')
135 nt.assert_equal(s, 'ell')
140
136
141 if sys.version_info >= (3, 4):
137 s = f.format("{a[:]}", a=[1, 2])
142 # String formatting has changed in Python 3.4, so this now works.
138 nt.assert_equal(s, "[1, 2]")
143 s = f.format("{a[:]}", a=[1, 2])
144 nt.assert_equal(s, "[1, 2]")
145 else:
146 nt.assert_raises(SyntaxError, f.format, "{a[:]}")
147
139
148 def test_eval_formatter():
140 def test_eval_formatter():
149 f = text.EvalFormatter()
141 f = text.EvalFormatter()
@@ -13,11 +13,7 b' import re'
13 import sys
13 import sys
14 import textwrap
14 import textwrap
15 from string import Formatter
15 from string import Formatter
16 try:
16 from pathlib import Path
17 from pathlib import Path
18 except ImportError:
19 # for Python 3.3
20 from pathlib2 import Path
21
17
22 from IPython.utils import py3compat
18 from IPython.utils import py3compat
23
19
@@ -665,7 +661,7 b' def compute_item_matrix(items, row_first=False, empty=None, *args, **kwargs) :'
665 empty : (default None)
661 empty : (default None)
666 default value to fill list if needed
662 default value to fill list if needed
667 separator_size : int (default=2)
663 separator_size : int (default=2)
668 How much caracters will be used as a separation between each columns.
664 How much characters will be used as a separation between each columns.
669 displaywidth : int (default=80)
665 displaywidth : int (default=80)
670 The width of the area onto which the columns should enter
666 The width of the area onto which the columns should enter
671
667
@@ -1,7 +1,16 b''
1 include README.rst
1 include README.rst
2 include COPYING.rst
2 include COPYING.rst
3 include LICENSE
3 include setupbase.py
4 include setupbase.py
4 include setupegg.py
5 include setupegg.py
6 include MANIFEST.in
7 include tox.ini
8 include .mailmap
9
10 recursive-exclude tools *
11 exclude tools
12 exclude CONTRIBUTING.md
13 exclude .editorconfig
5
14
6 graft setupext
15 graft setupext
7
16
@@ -29,6 +38,7 b' prune docs/dist'
29 # Patterns to exclude from any directory
38 # Patterns to exclude from any directory
30 global-exclude *~
39 global-exclude *~
31 global-exclude *.flc
40 global-exclude *.flc
41 global-exclude *.yml
32 global-exclude *.pyc
42 global-exclude *.pyc
33 global-exclude *.pyo
43 global-exclude *.pyo
34 global-exclude .dircopy.log
44 global-exclude .dircopy.log
@@ -23,7 +23,9 b' contribute to the project.'
23
23
24 **IPython versions and Python Support**
24 **IPython versions and Python Support**
25
25
26 **IPython 6** requires Python version 3.3 and above.
26 **IPython 7.0** requires Python version 3.4 and above.
27
28 **IPython 6.x** requires Python version 3.3 and above.
27
29
28 **IPython 5.x LTS** is the compatible release for Python 2.7.
30 **IPython 5.x LTS** is the compatible release for Python 2.7.
29 If you require Python 2 support, you **must** use IPython 5.x LTS. Please
31 If you require Python 2 support, you **must** use IPython 5.x LTS. Please
@@ -31,7 +33,7 b' update your project configurations and requirements as necessary.'
31
33
32
34
33 The Notebook, Qt console and a number of other pieces are now parts of *Jupyter*.
35 The Notebook, Qt console and a number of other pieces are now parts of *Jupyter*.
34 See the `Jupyter installation docs <http://jupyter.readthedocs.io/en/latest/install.html>`__
36 See the `Jupyter installation docs <https://jupyter.readthedocs.io/en/latest/install.html>`__
35 if you want to use these.
37 if you want to use these.
36
38
37
39
@@ -41,7 +43,7 b' Development and Instant running'
41 ===============================
43 ===============================
42
44
43 You can find the latest version of the development documentation on `readthedocs
45 You can find the latest version of the development documentation on `readthedocs
44 <http://ipython.readthedocs.io/en/latest/>`_.
46 <https://ipython.readthedocs.io/en/latest/>`_.
45
47
46 You can run IPython from this directory without even installing it system-wide
48 You can run IPython from this directory without even installing it system-wide
47 by typing at the terminal::
49 by typing at the terminal::
@@ -49,7 +51,7 b' by typing at the terminal::'
49 $ python -m IPython
51 $ python -m IPython
50
52
51 Or see the `development installation docs
53 Or see the `development installation docs
52 <http://ipython.readthedocs.io/en/latest/install/install.html#installing-the-development-version>`_
54 <https://ipython.readthedocs.io/en/latest/install/install.html#installing-the-development-version>`_
53 for the latest revision on read the docs.
55 for the latest revision on read the docs.
54
56
55 Documentation and installation instructions for older version of IPython can be
57 Documentation and installation instructions for older version of IPython can be
@@ -68,14 +70,14 b' Support version.'
68
70
69 If you are encountering this error message you are likely trying to install or
71 If you are encountering this error message you are likely trying to install or
70 use IPython from source. You need to checkout the remote 5.x branch. If you are
72 use IPython from source. You need to checkout the remote 5.x branch. If you are
71 using git the following should work:
73 using git the following should work::
72
74
73 $ git fetch origin
75 $ git fetch origin
74 $ git checkout 5.x
76 $ git checkout 5.x
75
77
76 If you encounter this error message with a regular install of IPython, then you
78 If you encounter this error message with a regular install of IPython, then you
77 likely need to update your package manager, for example if you are using `pip`
79 likely need to update your package manager, for example if you are using `pip`
78 check the version of pip with
80 check the version of pip with::
79
81
80 $ pip --version
82 $ pip --version
81
83
@@ -8,8 +8,8 b' environment:'
8 PYTHON_VERSION: "3.6.x"
8 PYTHON_VERSION: "3.6.x"
9 PYTHON_ARCH: "32"
9 PYTHON_ARCH: "32"
10
10
11 - PYTHON: "C:\\Python33-x64"
11 - PYTHON: "C:\\Python34-x64"
12 PYTHON_VERSION: "3.3.x"
12 PYTHON_VERSION: "3.4.x"
13 PYTHON_ARCH: "64"
13 PYTHON_ARCH: "64"
14
14
15 - PYTHON: "C:\\Python36-x64"
15 - PYTHON: "C:\\Python36-x64"
@@ -21,7 +21,7 b' init:'
21
21
22 install:
22 install:
23 - "SET PATH=%PYTHON%;%PYTHON%\\Scripts;%PATH%"
23 - "SET PATH=%PYTHON%;%PYTHON%\\Scripts;%PATH%"
24 - "%CMD_IN_ENV% pip install setuptools>=18.5 --upgrade"
24 - "%CMD_IN_ENV% python -m pip install --upgrade setuptools pip"
25 - "%CMD_IN_ENV% pip install nose coverage"
25 - "%CMD_IN_ENV% pip install nose coverage"
26 - "%CMD_IN_ENV% pip install .[test]"
26 - "%CMD_IN_ENV% pip install .[test]"
27 - "%CMD_IN_ENV% mkdir results"
27 - "%CMD_IN_ENV% mkdir results"
@@ -48,7 +48,7 b' API documentation. This build target skips that.'
48 You can run ``make help`` to see information on all possible make targets.
48 You can run ``make help`` to see information on all possible make targets.
49
49
50 To save time,
50 To save time,
51 the make targets above only proceess the files that have been changed since the
51 the make targets above only process the files that have been changed since the
52 previous docs build.
52 previous docs build.
53 To remove the previous docs build you can use ``make clean``.
53 To remove the previous docs build you can use ``make clean``.
54 You can also combine ``clean`` with other `make` commands;
54 You can also combine ``clean`` with other `make` commands;
@@ -1,7 +1,6 b''
1 from os.path import abspath, dirname, join
1 from os.path import abspath, dirname, join
2
2
3 from IPython.terminal.interactiveshell import KeyBindingManager
3 from IPython.terminal.shortcuts import create_ipython_shortcuts
4
5
4
6 def name(c):
5 def name(c):
7 s = c.__class__.__name__
6 s = c.__class__.__name__
@@ -42,8 +41,14 b' def multi_filter_str(flt):'
42 log_filters = {'_AndList': 'And', '_OrList': 'Or'}
41 log_filters = {'_AndList': 'And', '_OrList': 'Or'}
43 log_invert = {'_Invert'}
42 log_invert = {'_Invert'}
44
43
45 kbm = KeyBindingManager.for_prompt()
44 class _DummyTerminal(object):
46 ipy_bindings = kbm.registry.key_bindings
45 """Used as a buffer to get prompt_toolkit bindings
46 """
47 handle_return = None
48 input_splitter = None
49 display_completions = None
50
51 ipy_bindings = create_ipython_shortcuts(_DummyTerminal()).bindings
47
52
48 dummy_docs = [] # ignore bindings without proper documentation
53 dummy_docs = [] # ignore bindings without proper documentation
49
54
@@ -42,6 +42,13 b' For example::'
42 def _repr_html_(self):
42 def _repr_html_(self):
43 return "<h1>" + self.text + "</h1>"
43 return "<h1>" + self.text + "</h1>"
44
44
45 We often want to provide frontends with guidance on how to display the data. To
46 support this, ``_repr_*_()`` methods can also return a ``(data, metadata)``
47 tuple where ``metadata`` is a dictionary containing arbitrary key-value pairs for
48 the frontend to interpret. An example use case is ``_repr_jpeg_()``, which can
49 be set to return a jpeg image and a ``{'height': 400, 'width': 600}`` dictionary
50 to inform the frontend how to size the image.
51
45 There are also two more powerful display methods:
52 There are also two more powerful display methods:
46
53
47 .. class:: MyObject
54 .. class:: MyObject
@@ -11,7 +11,7 b' In order for this to be possible, you need to use the ``display()`` function,'
11 that should be available by default on IPython 5.4+ and 6.1+, or that you can
11 that should be available by default on IPython 5.4+ and 6.1+, or that you can
12 import with ``from IPython.display import display``. Then use ``display(<your
12 import with ``from IPython.display import display``. Then use ``display(<your
13 object>)`` instead of ``print()``, and if possible your object will be displayed
13 object>)`` instead of ``print()``, and if possible your object will be displayed
14 with a richer representation. In the terminal of course, there wont be much
14 with a richer representation. In the terminal of course, there won't be much
15 difference as object are most of the time represented by text, but in notebook
15 difference as object are most of the time represented by text, but in notebook
16 and similar interface you will get richer outputs.
16 and similar interface you will get richer outputs.
17
17
@@ -308,6 +308,9 b' one of (note that the modes are given unquoted):'
308 * [append:] well, that says it.
308 * [append:] well, that says it.
309 * [rotate:] create rotating logs log_name.1~, log_name.2~, etc.
309 * [rotate:] create rotating logs log_name.1~, log_name.2~, etc.
310
310
311 Adding the '-o' flag to '%logstart' magic (as in '%logstart -o [log_name [log_mode]]')
312 will also include output from iPython in the log file.
313
311 The :magic:`logoff` and :magic:`logon` functions allow you to temporarily stop and
314 The :magic:`logoff` and :magic:`logon` functions allow you to temporarily stop and
312 resume logging to a file which had previously been started with
315 resume logging to a file which had previously been started with
313 %logstart. They will fail (with an explanation) if you try to use them
316 %logstart. They will fail (with an explanation) if you try to use them
@@ -607,12 +610,66 b' startup files, and everything, just as if it were a normal IPython session.'
607 For information on setting configuration options when running IPython from
610 For information on setting configuration options when running IPython from
608 python, see :ref:`configure_start_ipython`.
611 python, see :ref:`configure_start_ipython`.
609
612
610 It is also possible to embed an IPython shell in a namespace in your Python code.
613 It is also possible to embed an IPython shell in a namespace in your Python
611 This allows you to evaluate dynamically the state of your code,
614 code. This allows you to evaluate dynamically the state of your code, operate
612 operate with your variables, analyze them, etc. Note however that
615 with your variables, analyze them, etc. For example, if you run the following
613 any changes you make to values while in the shell do not propagate back
616 code snippet::
614 to the running code, so it is safe to modify your values because you
617
615 won't break your code in bizarre ways by doing so.
618 import IPython
619
620 a = 42
621 IPython.embed()
622
623 and within the IPython shell, you reassign `a` to `23` to do further testing of
624 some sort, you can then exit::
625
626 >>> IPython.embed()
627 Python 3.6.2 (default, Jul 17 2017, 16:44:45)
628 Type 'copyright', 'credits' or 'license' for more information
629 IPython 6.2.0.dev -- An enhanced Interactive Python. Type '?' for help.
630
631 In [1]: a = 23
632
633 In [2]: exit()
634
635 Once you exit and print `a`, the value 23 will be shown::
636
637
638 In: print(a)
639 23
640
641 It's important to note that the code run in the embedded IPython shell will
642 *not* change the state of your code and variables, **unless** the shell is
643 contained within the global namespace. In the above example, `a` is changed
644 because this is true.
645
646 To further exemplify this, consider the following example::
647
648 import IPython
649 def do():
650 a = 42
651 print(a)
652 IPython.embed()
653 print(a)
654
655 Now if call the function and complete the state changes as we did above, the
656 value `42` will be printed. Again, this is because it's not in the global
657 namespace::
658
659 do()
660
661 Running a file with the above code can lead to the following session::
662
663 >>> do()
664 42
665 Python 3.6.2 (default, Jul 17 2017, 16:44:45)
666 Type 'copyright', 'credits' or 'license' for more information
667 IPython 6.2.0.dev -- An enhanced Interactive Python. Type '?' for help.
668
669 In [1]: a = 23
670
671 In [2]: exit()
672 42
616
673
617 .. note::
674 .. note::
618
675
@@ -711,7 +768,7 b' context line to show. This allows to a many line of context on shallow stack tra'
711 In[6]: foo(1)
768 In[6]: foo(1)
712 # ...
769 # ...
713 ipdb> where 8
770 ipdb> where 8
714 <ipython-input-6-9e45007b2b59>(1)<module>()
771 <ipython-input-6-9e45007b2b59>(1)<module>
715 ----> 1 foo(1)
772 ----> 1 foo(1)
716
773
717 <ipython-input-5-7baadc3d1465>(5)foo()
774 <ipython-input-5-7baadc3d1465>(5)foo()
@@ -740,7 +797,7 b' And less context on shallower Stack Trace:'
740 .. code::
797 .. code::
741
798
742 ipdb> where 1
799 ipdb> where 1
743 <ipython-input-13-afa180a57233>(1)<module>()
800 <ipython-input-13-afa180a57233>(1)<module>
744 ----> 1 foo(7)
801 ----> 1 foo(7)
745
802
746 <ipython-input-5-7baadc3d1465>(5)foo()
803 <ipython-input-5-7baadc3d1465>(5)foo()
@@ -217,29 +217,30 b' running, use the ``%connect_info`` magic to get the unique connection file,'
217 which will be something like ``--existing kernel-19732.json`` but with
217 which will be something like ``--existing kernel-19732.json`` but with
218 different numbers which correspond to the Process ID of the kernel.
218 different numbers which correspond to the Process ID of the kernel.
219
219
220 You can read more about using `jupyter qtconsole
220 You can read more about using `jupyter qtconsole
221 <http://jupyter.org/qtconsole/>`_, and
221 <http://jupyter.org/qtconsole/>`_, and
222 `jupyter notebook <http://jupyter-notebook.readthedocs.io/en/latest/>`_. There
222 `jupyter notebook <http://jupyter-notebook.readthedocs.io/en/latest/>`_. There
223 is also a :ref:`message spec <messaging>` which documents the protocol for
223 is also a :ref:`message spec <messaging>` which documents the protocol for
224 communication between kernels
224 communication between kernels
225 and clients.
225 and clients.
226
226
227 .. seealso::
227 .. seealso::
228
228
229 `Frontend/Kernel Model`_ example notebook
229 `Frontend/Kernel Model`_ example notebook
230
230
231
231
232 Interactive parallel computing
232 Interactive parallel computing
233 ==============================
233 ==============================
234
234
235
235
236 This functionality is optional and now part of the `ipyparallel
236 This functionality is optional and now part of the `ipyparallel
237 <http://ipyparallel.readthedocs.io/>`_ project.
237 <http://ipyparallel.readthedocs.io/>`_ project.
238
238
239 Portability and Python requirements
239 Portability and Python requirements
240 -----------------------------------
240 -----------------------------------
241
241
242 Version 6.0+ supports compatibility with Python 3.3 and higher.
242 Version 7.0+ supports Python 3.4 and higher.
243 Versions 6.x support Python 3.3 and higher.
243 Versions 2.0 to 5.x work with Python 2.7.x releases and Python 3.3 and higher.
244 Versions 2.0 to 5.x work with Python 2.7.x releases and Python 3.3 and higher.
244 Version 1.0 additionally worked with Python 2.6 and 3.2.
245 Version 1.0 additionally worked with Python 2.6 and 3.2.
245 Version 0.12 was the first version to fully support Python 3.
246 Version 0.12 was the first version to fully support Python 3.
@@ -384,7 +384,7 b' Regular issues (285):'
384 * `326 <https://github.com/ipython/ipython/issues/326>`_: Update docs and examples for parallel stuff to reflect movement away from Twisted
384 * `326 <https://github.com/ipython/ipython/issues/326>`_: Update docs and examples for parallel stuff to reflect movement away from Twisted
385 * `341 <https://github.com/ipython/ipython/issues/341>`_: FIx Parallel Magics for newparallel
385 * `341 <https://github.com/ipython/ipython/issues/341>`_: FIx Parallel Magics for newparallel
386 * `338 <https://github.com/ipython/ipython/issues/338>`_: Usability improvements to Qt console
386 * `338 <https://github.com/ipython/ipython/issues/338>`_: Usability improvements to Qt console
387 * `142 <https://github.com/ipython/ipython/issues/142>`_: unexpected auto-indenting when varibles names that start with 'pass'
387 * `142 <https://github.com/ipython/ipython/issues/142>`_: unexpected auto-indenting when variables names that start with 'pass'
388 * `296 <https://github.com/ipython/ipython/issues/296>`_: Automatic PDB via %pdb doesn't work
388 * `296 <https://github.com/ipython/ipython/issues/296>`_: Automatic PDB via %pdb doesn't work
389 * `337 <https://github.com/ipython/ipython/issues/337>`_: exit( and quit( in Qt console produces phantom signature/docstring popup, even though quit() or exit() raises NameError
389 * `337 <https://github.com/ipython/ipython/issues/337>`_: exit( and quit( in Qt console produces phantom signature/docstring popup, even though quit() or exit() raises NameError
390 * `318 <https://github.com/ipython/ipython/issues/318>`_: %debug broken in master: invokes missing save_history() method
390 * `318 <https://github.com/ipython/ipython/issues/318>`_: %debug broken in master: invokes missing save_history() method
@@ -580,7 +580,7 b' Pull Requests (793):'
580 * :ghpull:`3576`: Added support for markdown in heading cells when they are nbconverted.
580 * :ghpull:`3576`: Added support for markdown in heading cells when they are nbconverted.
581 * :ghpull:`3575`: tweak `run -d` message to 'continue execution'
581 * :ghpull:`3575`: tweak `run -d` message to 'continue execution'
582 * :ghpull:`3569`: add PYTHONSTARTUP to startup files
582 * :ghpull:`3569`: add PYTHONSTARTUP to startup files
583 * :ghpull:`3567`: Trigger a single event on js app initilized
583 * :ghpull:`3567`: Trigger a single event on js app initialized
584 * :ghpull:`3565`: style.min.css should always exist...
584 * :ghpull:`3565`: style.min.css should always exist...
585 * :ghpull:`3531`: allow markdown in heading cells
585 * :ghpull:`3531`: allow markdown in heading cells
586 * :ghpull:`3577`: Simplify codemirror ipython-mode
586 * :ghpull:`3577`: Simplify codemirror ipython-mode
@@ -1195,7 +1195,7 b' Issues (691):'
1195 * :ghissue:`3957`: Notebook help page broken in Firefox
1195 * :ghissue:`3957`: Notebook help page broken in Firefox
1196 * :ghissue:`3894`: nbconvert test failure
1196 * :ghissue:`3894`: nbconvert test failure
1197 * :ghissue:`3887`: 1.0.0a1 shows blank screen in both firefox and chrome (windows 7)
1197 * :ghissue:`3887`: 1.0.0a1 shows blank screen in both firefox and chrome (windows 7)
1198 * :ghissue:`3703`: `nbconvert`: Output options -- names and documentataion
1198 * :ghissue:`3703`: `nbconvert`: Output options -- names and documentation
1199 * :ghissue:`3931`: Tab completion not working during debugging in the notebook
1199 * :ghissue:`3931`: Tab completion not working during debugging in the notebook
1200 * :ghissue:`3936`: Ipcluster plugin is not working with Ipython 1.0dev
1200 * :ghissue:`3936`: Ipcluster plugin is not working with Ipython 1.0dev
1201 * :ghissue:`3941`: IPython Notebook kernel crash on Win7x64
1201 * :ghissue:`3941`: IPython Notebook kernel crash on Win7x64
@@ -1264,7 +1264,7 b' Issues (691):'
1264 * :ghissue:`3737`: ipython nbconvert crashes with ValueError: Invalid format string.
1264 * :ghissue:`3737`: ipython nbconvert crashes with ValueError: Invalid format string.
1265 * :ghissue:`3730`: nbconvert: unhelpful error when pandoc isn't installed
1265 * :ghissue:`3730`: nbconvert: unhelpful error when pandoc isn't installed
1266 * :ghissue:`3718`: markdown cell cursor misaligned in notebook
1266 * :ghissue:`3718`: markdown cell cursor misaligned in notebook
1267 * :ghissue:`3710`: mutiple input fields for %debug in the notebook after resetting the kernel
1267 * :ghissue:`3710`: multiple input fields for %debug in the notebook after resetting the kernel
1268 * :ghissue:`3713`: PyCharm has problems with IPython working inside PyPy created by virtualenv
1268 * :ghissue:`3713`: PyCharm has problems with IPython working inside PyPy created by virtualenv
1269 * :ghissue:`3712`: Code completion: Complete on dictionary keys
1269 * :ghissue:`3712`: Code completion: Complete on dictionary keys
1270 * :ghissue:`3680`: --pylab and --matplotlib flag
1270 * :ghissue:`3680`: --pylab and --matplotlib flag
@@ -1405,7 +1405,7 b' Issues (691):'
1405 * :ghissue:`3519`: IPython Parallel map mysteriously turns pandas Series into numpy ndarray
1405 * :ghissue:`3519`: IPython Parallel map mysteriously turns pandas Series into numpy ndarray
1406 * :ghissue:`3345`: IPython embedded shells ask if I want to exit, but I set confirm_exit = False
1406 * :ghissue:`3345`: IPython embedded shells ask if I want to exit, but I set confirm_exit = False
1407 * :ghissue:`3509`: IPython won't close without asking "Are you sure?" in Firefox
1407 * :ghissue:`3509`: IPython won't close without asking "Are you sure?" in Firefox
1408 * :ghissue:`3471`: Notebook jinja2/markupsafe depedencies in manual
1408 * :ghissue:`3471`: Notebook jinja2/markupsafe dependencies in manual
1409 * :ghissue:`3502`: Notebook broken in master
1409 * :ghissue:`3502`: Notebook broken in master
1410 * :ghissue:`3302`: autoreload does not work in ipython 0.13.x, python 3.3
1410 * :ghissue:`3302`: autoreload does not work in ipython 0.13.x, python 3.3
1411 * :ghissue:`3475`: no warning when leaving/closing notebook on master without saved changes
1411 * :ghissue:`3475`: no warning when leaving/closing notebook on master without saved changes
@@ -1477,7 +1477,7 b' Issues (691):'
1477 * :ghissue:`3380`: simple call to kernel
1477 * :ghissue:`3380`: simple call to kernel
1478 * :ghissue:`3379`: TaskRecord key 'started' not set
1478 * :ghissue:`3379`: TaskRecord key 'started' not set
1479 * :ghissue:`3241`: notebook connection time out
1479 * :ghissue:`3241`: notebook connection time out
1480 * :ghissue:`3334`: magic interpreter interpretes non magic commands?
1480 * :ghissue:`3334`: magic interpreter interprets non magic commands?
1481 * :ghissue:`3326`: python3.3: Type error when launching SGE cluster in IPython notebook
1481 * :ghissue:`3326`: python3.3: Type error when launching SGE cluster in IPython notebook
1482 * :ghissue:`3349`: pip3 doesn't run 2to3?
1482 * :ghissue:`3349`: pip3 doesn't run 2to3?
1483 * :ghissue:`3347`: Longlist support in ipdb
1483 * :ghissue:`3347`: Longlist support in ipdb
@@ -3,6 +3,28 b''
3 Issues closed in the 5.x development cycle
3 Issues closed in the 5.x development cycle
4 ==========================================
4 ==========================================
5
5
6 Issues closed in 5.6
7 --------------------
8
9 GitHub stats for 2017/09/15 - 2018/04/02 (tag: 5.5.0)
10
11 These lists are automatically generated, and may be incomplete or contain duplicates.
12
13 We closed 2 issues and merged 28 pull requests.
14 The full list can be seen `on GitHub <https://github.com/ipython/ipython/issues?q=milestone%3A5.6>`__
15
16 The following 10 authors contributed 47 commits.
17
18 * Benjamin Ragan-Kelley
19 * Henry Fredrick Schreiner
20 * Joris Van den Bossche
21 * Matthias Bussonnier
22 * Mradul Dubey
23 * Roshan Rao
24 * Samuel Lelièvre
25 * Teddy Rendahl
26 * Thomas A Caswell
27 * Thomas Kluyver
6
28
7 Issues closed in 5.4
29 Issues closed in 5.4
8 --------------------
30 --------------------
@@ -1,10 +1,58 b''
1 Issues closed in the 6.x development cycle
1 Issues closed in the 6.x development cycle
2 ==========================================
2 ==========================================
3
3
4 Issues closed in 6.2
4 Issues closed in 6.3
5 --------------------
5 --------------------
6
6
7
7
8 GitHub stats for 2017/09/15 - 2018/04/02 (tag: 6.2.0)
9
10 These lists are automatically generated, and may be incomplete or contain duplicates.
11
12 We closed 10 issues and merged 50 pull requests.
13 The full list can be seen `on GitHub <https://github.com/ipython/ipython/issues?q=milestone%3A6.3>`__
14
15 The following 35 authors contributed 253 commits.
16
17 * Anatoly Techtonik
18 * Antony Lee
19 * Benjamin Ragan-Kelley
20 * Corey McCandless
21 * Craig Citro
22 * Cristian Ciupitu
23 * David Cottrell
24 * David Straub
25 * Doug Latornell
26 * Fabio Niephaus
27 * Gergely Nagy
28 * Henry Fredrick Schreiner
29 * Hugo
30 * Ismael Venegas Castelló
31 * Ivan Gonzalez
32 * J Forde
33 * Jeremy Sikes
34 * Joris Van den Bossche
35 * Lesley Cordero
36 * luzpaz
37 * madhu94
38 * Matthew R. Scott
39 * Matthias Bussonnier
40 * Matthias Geier
41 * Olesya Baranova
42 * Peter Williams
43 * Rastislav Barlik
44 * Roshan Rao
45 * rs2
46 * Samuel Lelièvre
47 * Shailyn javier Ortiz jimenez
48 * Sjoerd de Vries
49 * Teddy Rendahl
50 * Thomas A Caswell
51 * Thomas Kluyver
52
53 Issues closed in 6.2
54 --------------------
55
8 GitHub stats for 2017/05/31 - 2017/09/15 (tag: 6.1.0)
56 GitHub stats for 2017/05/31 - 2017/09/15 (tag: 6.1.0)
9
57
10 These lists are automatically generated, and may be incomplete or contain duplicates.
58 These lists are automatically generated, and may be incomplete or contain duplicates.
@@ -43,5 +43,3 b' development work they do here in a user friendly format.'
43 version0.10
43 version0.10
44 version0.9
44 version0.9
45 version0.8
45 version0.8
46
47
@@ -293,7 +293,7 b' Backwards incompatible changes'
293 deprecated, but continue to work.
293 deprecated, but continue to work.
294
294
295 * For embedding a shell, note that the parameters ``user_global_ns`` and
295 * For embedding a shell, note that the parameters ``user_global_ns`` and
296 ``global_ns`` have been deprectated in favour of ``user_module`` and
296 ``global_ns`` have been deprecated in favour of ``user_module`` and
297 ``module`` respsectively. The new parameters expect a module-like object,
297 ``module`` respsectively. The new parameters expect a module-like object,
298 rather than a namespace dict. The old parameters remain for backwards
298 rather than a namespace dict. The old parameters remain for backwards
299 compatibility, although ``user_global_ns`` is now ignored. The ``user_ns``
299 compatibility, although ``user_global_ns`` is now ignored. The ``user_ns``
@@ -3,6 +3,33 b''
3 ============
3 ============
4
4
5
5
6 .. _whatsnew570:
7
8 IPython 5.7
9 ===========
10
11 * Fix IPython trying to import non-existing matplotlib backends :ghpull:`11087`
12 * fix for display hook not publishing object metadata :ghpull:`11101`
13
14 .. _whatsnew560:
15
16 IPython 5.6
17 ===========
18
19 * In Python 3.6 and above, dictionaries preserve the order items were added to
20 them. On these versions, IPython will display dictionaries in their native
21 order, rather than sorting by the keys (:ghpull:`10958`).
22 * :class:`~.IPython.display.ProgressBar` can now be used as an iterator
23 (:ghpull:`10813`).
24 * The shell object gains a :meth:`~.InteractiveShell.check_complete` method,
25 to allow a smoother transition to new input processing machinery planned for
26 IPython 7 (:ghpull:`11044`).
27 * IPython should start faster, as it no longer looks for all available pygments
28 styles on startup (:ghpull:`10859`).
29
30 You can see all the PR marked for the `5.6. milestone <https://github.com/ipython/ipython/pulls?utf8=%E2%9C%93&q=is%3Apr+milestone%3A5.6+is%3Aclosed+NOT+%22Backport+PR%22+>`_,
31 and all the `backport versions <https://github.com/ipython/ipython/pulls?utf8=%E2%9C%93&q=is%3Apr%20milestone%3A5.6%20is%3Aclosed%20%22Backport%20PR%22%20>`__.
32
6 .. _whatsnew550:
33 .. _whatsnew550:
7
34
8 IPython 5.5
35 IPython 5.5
@@ -2,6 +2,55 b''
2 6.x Series
2 6.x Series
3 ============
3 ============
4
4
5 .. _whatsnew640:
6
7 IPython 6.4.0
8 =============
9
10 Everything new in :ref:`IPython 5.7 <whatsnew570>`
11
12 * Fix display object not emitting metadata :ghpull:`11106`
13 * Comments failing Jedi test :ghpull:`11110`
14
15
16 .. _whatsnew631:
17
18 IPython 6.3.1
19 =============
20
21 This is a bugfix release to switch the default completions back to IPython's
22 own completion machinery. We discovered some problems with the completions
23 from Jedi, including completing column names on pandas data frames.
24
25 You can switch the completions source with the config option
26 :configtrait:`Completer.use_jedi`.
27
28 .. _whatsnew630:
29
30 IPython 6.3
31 ===========
32
33 IPython 6.3 contains all the bug fixes and features in
34 :ref:`IPython 5.6 <whatsnew560>`. In addition:
35
36 * A new display class :class:`IPython.display.Code` can be used to display
37 syntax highlighted code in a notebook (:ghpull:`10978`).
38 * The :cellmagic:`html` magic now takes a ``--isolated`` option to put the
39 content in an iframe (:ghpull:`10962`).
40 * The code to find completions using the Jedi library has had various
41 adjustments. This is still a work in progress, but we hope this version has
42 fewer annoyances (:ghpull:`10956`, :ghpull:`10969`, :ghpull:`10999`,
43 :ghpull:`11035`, :ghpull:`11063`, :ghpull:`11065`).
44 * The *post* event callbacks are now always called, even when the execution failed
45 (for example because of a ``SyntaxError``).
46 * The execution info and result objects are now made available in the
47 corresponding *pre* or *post* ``*_run_cell`` :doc:`event callbacks </config/callbacks>`
48 in a backward compatible manner (:ghissue:`10774` and :ghpull:`10795`).
49 * Performance with very long code cells (hundreds of lines) is greatly improved
50 (:ghpull:`10898`). Further improvements are planned for IPython 7.
51
52 You can see all `pull requests for the 6.3 milestone
53 <https://github.com/ipython/ipython/pulls?utf8=%E2%9C%93&q=is%3Apr+milestone%3A6.3+is%3Aclosed>`__.
5
54
6 .. _whatsnew620:
55 .. _whatsnew620:
7
56
@@ -436,7 +436,7 b''
436 "\n",
436 "\n",
437 " c.ScriptMagics.scripts = ['R', 'pypy', 'myprogram']\n",
437 " c.ScriptMagics.scripts = ['R', 'pypy', 'myprogram']\n",
438 "\n",
438 "\n",
439 "And if any of these programs do not apear on your default PATH, then you would also need to specify their location with:\n",
439 "And if any of these programs do not appear on your default PATH, then you would also need to specify their location with:\n",
440 "\n",
440 "\n",
441 " c.ScriptMagics.script_paths = {'myprogram': '/opt/path/to/myprogram'}"
441 " c.ScriptMagics.script_paths = {'myprogram': '/opt/path/to/myprogram'}"
442 ]
442 ]
@@ -1,4 +1,4 b''
1 #!/usr/bin/env python
1 #!/usr/bin/env python3
2 # -*- coding: utf-8 -*-
2 # -*- coding: utf-8 -*-
3 """Setup script for IPython.
3 """Setup script for IPython.
4
4
@@ -26,7 +26,7 b' import sys'
26 #
26 #
27 # This check is also made in IPython/__init__, don't forget to update both when
27 # This check is also made in IPython/__init__, don't forget to update both when
28 # changing Python version requirements.
28 # changing Python version requirements.
29 if sys.version_info < (3, 3):
29 if sys.version_info < (3, 4):
30 pip_message = 'This may be due to an out of date pip. Make sure you have pip >= 9.0.1.'
30 pip_message = 'This may be due to an out of date pip. Make sure you have pip >= 9.0.1.'
31 try:
31 try:
32 import pip
32 import pip
@@ -42,9 +42,9 b' if sys.version_info < (3, 3):'
42
42
43
43
44 error = """
44 error = """
45 IPython 6.0+ does not support Python 2.6, 2.7, 3.0, 3.1, or 3.2.
45 IPython 7.0+ supports Python 3.4 and above.
46 When using Python 2.7, please install IPython 5.x LTS Long Term Support version.
46 When using Python 2.7, please install IPython 5.x LTS Long Term Support version.
47 Beginning with IPython 6.0, Python 3.3 and above is required.
47 Python 3.3 was supported up to IPython 6.x.
48
48
49 See IPython `README.rst` file for more information:
49 See IPython `README.rst` file for more information:
50
50
@@ -175,7 +175,7 b' extras_require = dict('
175 parallel = ['ipyparallel'],
175 parallel = ['ipyparallel'],
176 qtconsole = ['qtconsole'],
176 qtconsole = ['qtconsole'],
177 doc = ['Sphinx>=1.3'],
177 doc = ['Sphinx>=1.3'],
178 test = ['nose>=0.10.1', 'requests', 'testpath', 'pygments', 'nbformat', 'ipykernel'],
178 test = ['nose>=0.10.1', 'requests', 'testpath', 'pygments', 'nbformat', 'ipykernel', 'numpy'],
179 terminal = [],
179 terminal = [],
180 kernel = ['ipykernel'],
180 kernel = ['ipykernel'],
181 nbformat = ['nbformat'],
181 nbformat = ['nbformat'],
@@ -190,7 +190,7 b' install_requires = ['
190 'pickleshare',
190 'pickleshare',
191 'simplegeneric>0.8',
191 'simplegeneric>0.8',
192 'traitlets>=4.2',
192 'traitlets>=4.2',
193 'prompt_toolkit>=1.0.15,<2.0.0',
193 'prompt_toolkit>=2.0.0,<2.1.0',
194 'pygments',
194 'pygments',
195 'backcall',
195 'backcall',
196 ]
196 ]
@@ -200,9 +200,7 b' install_requires = ['
200 # but requires pip >= 6. pip < 6 ignores these.
200 # but requires pip >= 6. pip < 6 ignores these.
201
201
202 extras_require.update({
202 extras_require.update({
203 'test:python_version >= "3.4"': ['numpy'],
203 ':python_version == "3.4"': ['typing'],
204 ':python_version == "3.3"': ['pathlib2'],
205 ':python_version <= "3.4"': ['typing'],
206 ':sys_platform != "win32"': ['pexpect'],
204 ':sys_platform != "win32"': ['pexpect'],
207 ':sys_platform == "darwin"': ['appnope'],
205 ':sys_platform == "darwin"': ['appnope'],
208 ':sys_platform == "win32"': ['colorama'],
206 ':sys_platform == "win32"': ['colorama'],
@@ -232,7 +230,7 b' for key, deps in extras_require.items():'
232 extras_require['all'] = everything
230 extras_require['all'] = everything
233
231
234 if 'setuptools' in sys.modules:
232 if 'setuptools' in sys.modules:
235 setuptools_extra_args['python_requires'] = '>=3.3'
233 setuptools_extra_args['python_requires'] = '>=3.4'
236 setuptools_extra_args['zip_safe'] = False
234 setuptools_extra_args['zip_safe'] = False
237 setuptools_extra_args['entry_points'] = {
235 setuptools_extra_args['entry_points'] = {
238 'console_scripts': find_entry_points(),
236 'console_scripts': find_entry_points(),
@@ -65,7 +65,7 b' class install_data_ext(install_data):'
65 files = lof[2]
65 files = lof[2]
66 if len(files) == 0:
66 if len(files) == 0:
67 # If there are no files listed, the user must be
67 # If there are no files listed, the user must be
68 # trying to create an empty directory, so add the the
68 # trying to create an empty directory, so add the
69 # directory to the list of output files.
69 # directory to the list of output files.
70 self.outfiles.append(dir)
70 self.outfiles.append(dir)
71 else:
71 else:
@@ -1,4 +1,4 b''
1 #!/usr/bin/env python
1 #!/usr/bin/env python3
2 """IPython release build script.
2 """IPython release build script.
3 """
3 """
4 import os
4 import os
@@ -58,7 +58,7 b' def merge_pr(num):'
58 cmd = "git pull "+repo+" "+branch
58 cmd = "git pull "+repo+" "+branch
59 not_merged[str(num)] = cmd
59 not_merged[str(num)] = cmd
60 print("==============================================================================")
60 print("==============================================================================")
61 print("Something went wrong merging this branch, you can try it manually by runngin :")
61 print("Something went wrong merging this branch, you can try it manually by running :")
62 print(cmd)
62 print(cmd)
63 print("==============================================================================")
63 print("==============================================================================")
64
64
@@ -118,7 +118,7 b' def main(*args):'
118
118
119 if not_merged :
119 if not_merged :
120 print('*************************************************************************************')
120 print('*************************************************************************************')
121 print('the following branch have not been merged automatically, considere doing it by hand :')
121 print('The following branch has not been merged automatically, consider doing it by hand :')
122 for num, cmd in not_merged.items() :
122 for num, cmd in not_merged.items() :
123 print( "PR {num}: {cmd}".format(num=num, cmd=cmd))
123 print( "PR {num}: {cmd}".format(num=num, cmd=cmd))
124 print('*************************************************************************************')
124 print('*************************************************************************************')
@@ -212,7 +212,7 b' if __name__ == "__main__":'
212
212
213 print("We closed %d issues and merged %d pull requests." % (n_issues, n_pulls))
213 print("We closed %d issues and merged %d pull requests." % (n_issues, n_pulls))
214 if milestone:
214 if milestone:
215 print("The full list can be seen `on GitHub <https://github.com/{project}/issues?q=milestone%3A{milestone}+>`__".format(project=project,milestone=milestone)
215 print("The full list can be seen `on GitHub <https://github.com/{project}/issues?q=milestone%3A{milestone}>`__".format(project=project,milestone=milestone)
216 )
216 )
217
217
218 print()
218 print()
@@ -1,4 +1,4 b''
1 #!/usr/bin/env python
1 #!/usr/bin/env python3
2 """IPython release script.
2 """IPython release script.
3
3
4 This should ONLY be run at real release time.
4 This should ONLY be run at real release time.
1 NO CONTENT: file was removed
NO CONTENT: file was removed
General Comments 0
You need to be logged in to leave comments. Login now