Show More
@@ -0,0 +1,11 b'' | |||
|
1 | c = get_config() | |
|
2 | ||
|
3 | # If the master config file uses syntax that's invalid in Python 3, we'll skip | |
|
4 | # it and just use the factory defaults. | |
|
5 | try: | |
|
6 | load_subconfig('ipython_config.py', profile='default') | |
|
7 | except Exception: | |
|
8 | pass | |
|
9 | else: | |
|
10 | # We reset exec_lines in case they're not compatible with Python 3. | |
|
11 | c.InteractiveShellApp.exec_lines = [] |
@@ -0,0 +1,32 b'' | |||
|
1 | # coding: utf-8 | |
|
2 | from IPython.core.splitinput import split_user_input | |
|
3 | from IPython.testing import tools as tt | |
|
4 | from IPython.utils import py3compat | |
|
5 | ||
|
6 | tests = [ | |
|
7 | ('x=1', ('', '', 'x', '=1')), | |
|
8 | ('?', ('', '?', '', '')), | |
|
9 | ('??', ('', '??', '', '')), | |
|
10 | (' ?', (' ', '?', '', '')), | |
|
11 | (' ??', (' ', '??', '', '')), | |
|
12 | ('??x', ('', '??', 'x', '')), | |
|
13 | ('?x=1', ('', '?', 'x', '=1')), | |
|
14 | ('!ls', ('', '!', 'ls', '')), | |
|
15 | (' !ls', (' ', '!', 'ls', '')), | |
|
16 | ('!!ls', ('', '!!', 'ls', '')), | |
|
17 | (' !!ls', (' ', '!!', 'ls', '')), | |
|
18 | (',ls', ('', ',', 'ls', '')), | |
|
19 | (';ls', ('', ';', 'ls', '')), | |
|
20 | (' ;ls', (' ', ';', 'ls', '')), | |
|
21 | ('f.g(x)', ('', '', 'f.g', '(x)')), | |
|
22 | ('f.g (x)', ('', '', 'f.g', '(x)')), | |
|
23 | ('?%hist', ('', '?', '%hist', '')), | |
|
24 | ('?x*', ('', '?', 'x*', '')), | |
|
25 | ] | |
|
26 | if py3compat.PY3: | |
|
27 | tests.append((u"PΓ©rez Fernando", (u'', u'', u'PΓ©rez', u'Fernando'))) | |
|
28 | else: | |
|
29 | tests.append((u"PΓ©rez Fernando", (u'', u'', u'P', u'Γ©rez Fernando'))) | |
|
30 | ||
|
31 | def test_split_user_input(): | |
|
32 | return tt.check_pairs(split_user_input, tests) |
@@ -0,0 +1,50 b'' | |||
|
1 | """Backwards compatibility - we use contextlib.nested to support Python 2.6, | |
|
2 | but it's removed in Python 3.2.""" | |
|
3 | ||
|
4 | # TODO : Remove this once we drop support for Python 2.6, and use | |
|
5 | # "with a, b:" instead. | |
|
6 | ||
|
7 | import sys | |
|
8 | ||
|
9 | from contextlib import contextmanager | |
|
10 | ||
|
11 | @contextmanager | |
|
12 | def nested(*managers): | |
|
13 | """Combine multiple context managers into a single nested context manager. | |
|
14 | ||
|
15 | This function has been deprecated in favour of the multiple manager form | |
|
16 | of the with statement. | |
|
17 | ||
|
18 | The one advantage of this function over the multiple manager form of the | |
|
19 | with statement is that argument unpacking allows it to be | |
|
20 | used with a variable number of context managers as follows: | |
|
21 | ||
|
22 | with nested(*managers): | |
|
23 | do_something() | |
|
24 | ||
|
25 | """ | |
|
26 | exits = [] | |
|
27 | vars = [] | |
|
28 | exc = (None, None, None) | |
|
29 | try: | |
|
30 | for mgr in managers: | |
|
31 | exit = mgr.__exit__ | |
|
32 | enter = mgr.__enter__ | |
|
33 | vars.append(enter()) | |
|
34 | exits.append(exit) | |
|
35 | yield vars | |
|
36 | except: | |
|
37 | exc = sys.exc_info() | |
|
38 | finally: | |
|
39 | while exits: | |
|
40 | exit = exits.pop() | |
|
41 | try: | |
|
42 | if exit(*exc): | |
|
43 | exc = (None, None, None) | |
|
44 | except: | |
|
45 | exc = sys.exc_info() | |
|
46 | if exc != (None, None, None): | |
|
47 | # Don't rely on sys.exc_info() still containing | |
|
48 | # the right information. Another exception may | |
|
49 | # have been raised and caught by an exit method | |
|
50 | raise exc[0], exc[1], exc[2] |
@@ -0,0 +1,95 b'' | |||
|
1 | # coding: utf-8 | |
|
2 | """Compatibility tricks for Python 3. Mainly to do with unicode.""" | |
|
3 | import sys | |
|
4 | import types | |
|
5 | ||
|
6 | orig_open = open | |
|
7 | ||
|
8 | def no_code(x, encoding=None): | |
|
9 | return x | |
|
10 | ||
|
11 | def decode(s, encoding=None): | |
|
12 | encoding = encoding or sys.stdin.encoding or sys.getdefaultencoding() | |
|
13 | return s.decode(encoding, "replace") | |
|
14 | ||
|
15 | def encode(u, encoding=None): | |
|
16 | encoding = encoding or sys.stdin.encoding or sys.getdefaultencoding() | |
|
17 | return u.encode(encoding, "replace") | |
|
18 | ||
|
19 | def cast_unicode(s, encoding=None): | |
|
20 | if isinstance(s, bytes): | |
|
21 | return decode(s, encoding) | |
|
22 | return s | |
|
23 | ||
|
24 | def cast_bytes(s, encoding=None): | |
|
25 | if not isinstance(s, bytes): | |
|
26 | return encode(s, encoding) | |
|
27 | return s | |
|
28 | ||
|
29 | if sys.version_info[0] >= 3: | |
|
30 | PY3 = True | |
|
31 | ||
|
32 | input = input | |
|
33 | builtin_mod_name = "builtins" | |
|
34 | ||
|
35 | str_to_unicode = no_code | |
|
36 | unicode_to_str = no_code | |
|
37 | str_to_bytes = encode | |
|
38 | bytes_to_str = decode | |
|
39 | cast_bytes_py2 = no_code | |
|
40 | ||
|
41 | def isidentifier(s, dotted=False): | |
|
42 | if dotted: | |
|
43 | return all(isidentifier(a) for a in s.split(".")) | |
|
44 | return s.isidentifier() | |
|
45 | ||
|
46 | open = orig_open | |
|
47 | ||
|
48 | MethodType = types.MethodType | |
|
49 | ||
|
50 | else: | |
|
51 | PY3 = False | |
|
52 | ||
|
53 | input = raw_input | |
|
54 | builtin_mod_name = "__builtin__" | |
|
55 | ||
|
56 | str_to_unicode = decode | |
|
57 | unicode_to_str = encode | |
|
58 | str_to_bytes = no_code | |
|
59 | bytes_to_str = no_code | |
|
60 | cast_bytes_py2 = cast_bytes | |
|
61 | ||
|
62 | import re | |
|
63 | _name_re = re.compile(r"[a-zA-Z_][a-zA-Z0-9_]*$") | |
|
64 | def isidentifier(s, dotted=False): | |
|
65 | if dotted: | |
|
66 | return all(isidentifier(a) for a in s.split(".")) | |
|
67 | return bool(_name_re.match(s)) | |
|
68 | ||
|
69 | class open(object): | |
|
70 | """Wrapper providing key part of Python 3 open() interface.""" | |
|
71 | def __init__(self, fname, mode="r", encoding="utf-8"): | |
|
72 | self.f = orig_open(fname, mode) | |
|
73 | self.enc = encoding | |
|
74 | ||
|
75 | def write(self, s): | |
|
76 | return self.f.write(s.encode(self.enc)) | |
|
77 | ||
|
78 | def read(self, size=-1): | |
|
79 | return self.f.read(size).decode(self.enc) | |
|
80 | ||
|
81 | def close(self): | |
|
82 | return self.f.close() | |
|
83 | ||
|
84 | def __enter__(self): | |
|
85 | return self | |
|
86 | ||
|
87 | def __exit__(self, etype, value, traceback): | |
|
88 | self.f.close() | |
|
89 | ||
|
90 | def MethodType(func, instance): | |
|
91 | return types.MethodType(func, instance, type(instance)) | |
|
92 | ||
|
93 | def execfile(fname, glob, loc=None): | |
|
94 | loc = loc if (loc is not None) else glob | |
|
95 | exec compile(open(fname).read(), fname, 'exec') in glob, loc |
@@ -0,0 +1,272 b'' | |||
|
1 | #!/usr/bin/env python | |
|
2 | # -*- coding: utf-8 -*- | |
|
3 | """Setup script for IPython. | |
|
4 | ||
|
5 | Under Posix environments it works like a typical setup.py script. | |
|
6 | Under Windows, the command sdist is not supported, since IPython | |
|
7 | requires utilities which are not available under Windows.""" | |
|
8 | ||
|
9 | #----------------------------------------------------------------------------- | |
|
10 | # Copyright (c) 2008-2011, IPython Development Team. | |
|
11 | # Copyright (c) 2001-2007, Fernando Perez <fernando.perez@colorado.edu> | |
|
12 | # Copyright (c) 2001, Janko Hauser <jhauser@zscout.de> | |
|
13 | # Copyright (c) 2001, Nathaniel Gray <n8gray@caltech.edu> | |
|
14 | # | |
|
15 | # Distributed under the terms of the Modified BSD License. | |
|
16 | # | |
|
17 | # The full license is in the file COPYING.txt, distributed with this software. | |
|
18 | #----------------------------------------------------------------------------- | |
|
19 | ||
|
20 | #----------------------------------------------------------------------------- | |
|
21 | # Minimal Python version sanity check | |
|
22 | #----------------------------------------------------------------------------- | |
|
23 | ||
|
24 | import sys | |
|
25 | ||
|
26 | # This check is also made in IPython/__init__, don't forget to update both when | |
|
27 | # changing Python version requirements. | |
|
28 | if sys.version[0:3] < '2.6': | |
|
29 | error = """\ | |
|
30 | ERROR: 'IPython requires Python Version 2.6 or above.' | |
|
31 | Exiting.""" | |
|
32 | print >> sys.stderr, error | |
|
33 | sys.exit(1) | |
|
34 | ||
|
35 | # At least we're on the python version we need, move on. | |
|
36 | ||
|
37 | #------------------------------------------------------------------------------- | |
|
38 | # Imports | |
|
39 | #------------------------------------------------------------------------------- | |
|
40 | ||
|
41 | # Stdlib imports | |
|
42 | import os | |
|
43 | import shutil | |
|
44 | ||
|
45 | from glob import glob | |
|
46 | ||
|
47 | # BEFORE importing distutils, remove MANIFEST. distutils doesn't properly | |
|
48 | # update it when the contents of directories change. | |
|
49 | if os.path.exists('MANIFEST'): os.remove('MANIFEST') | |
|
50 | ||
|
51 | from distutils.core import setup | |
|
52 | ||
|
53 | # Our own imports | |
|
54 | from IPython.utils.path import target_update | |
|
55 | ||
|
56 | from setupbase import ( | |
|
57 | setup_args, | |
|
58 | find_packages, | |
|
59 | find_package_data, | |
|
60 | find_scripts, | |
|
61 | find_data_files, | |
|
62 | check_for_dependencies, | |
|
63 | record_commit_info, | |
|
64 | ) | |
|
65 | from setupext import setupext | |
|
66 | ||
|
67 | isfile = os.path.isfile | |
|
68 | pjoin = os.path.join | |
|
69 | ||
|
70 | #----------------------------------------------------------------------------- | |
|
71 | # Function definitions | |
|
72 | #----------------------------------------------------------------------------- | |
|
73 | ||
|
74 | def cleanup(): | |
|
75 | """Clean up the junk left around by the build process""" | |
|
76 | if "develop" not in sys.argv: | |
|
77 | try: | |
|
78 | shutil.rmtree('ipython.egg-info') | |
|
79 | except: | |
|
80 | try: | |
|
81 | os.unlink('ipython.egg-info') | |
|
82 | except: | |
|
83 | pass | |
|
84 | ||
|
85 | #------------------------------------------------------------------------------- | |
|
86 | # Handle OS specific things | |
|
87 | #------------------------------------------------------------------------------- | |
|
88 | ||
|
89 | if os.name == 'posix': | |
|
90 | os_name = 'posix' | |
|
91 | elif os.name in ['nt','dos']: | |
|
92 | os_name = 'windows' | |
|
93 | else: | |
|
94 | print 'Unsupported operating system:',os.name | |
|
95 | sys.exit(1) | |
|
96 | ||
|
97 | # Under Windows, 'sdist' has not been supported. Now that the docs build with | |
|
98 | # Sphinx it might work, but let's not turn it on until someone confirms that it | |
|
99 | # actually works. | |
|
100 | if os_name == 'windows' and 'sdist' in sys.argv: | |
|
101 | print 'The sdist command is not available under Windows. Exiting.' | |
|
102 | sys.exit(1) | |
|
103 | ||
|
104 | #------------------------------------------------------------------------------- | |
|
105 | # Things related to the IPython documentation | |
|
106 | #------------------------------------------------------------------------------- | |
|
107 | ||
|
108 | # update the manuals when building a source dist | |
|
109 | if len(sys.argv) >= 2 and sys.argv[1] in ('sdist','bdist_rpm'): | |
|
110 | import textwrap | |
|
111 | ||
|
112 | # List of things to be updated. Each entry is a triplet of args for | |
|
113 | # target_update() | |
|
114 | to_update = [ | |
|
115 | # FIXME - Disabled for now: we need to redo an automatic way | |
|
116 | # of generating the magic info inside the rst. | |
|
117 | #('docs/magic.tex', | |
|
118 | #['IPython/Magic.py'], | |
|
119 | #"cd doc && ./update_magic.sh" ), | |
|
120 | ||
|
121 | ('docs/man/ipcluster.1.gz', | |
|
122 | ['docs/man/ipcluster.1'], | |
|
123 | 'cd docs/man && gzip -9c ipcluster.1 > ipcluster.1.gz'), | |
|
124 | ||
|
125 | ('docs/man/ipcontroller.1.gz', | |
|
126 | ['docs/man/ipcontroller.1'], | |
|
127 | 'cd docs/man && gzip -9c ipcontroller.1 > ipcontroller.1.gz'), | |
|
128 | ||
|
129 | ('docs/man/ipengine.1.gz', | |
|
130 | ['docs/man/ipengine.1'], | |
|
131 | 'cd docs/man && gzip -9c ipengine.1 > ipengine.1.gz'), | |
|
132 | ||
|
133 | ('docs/man/iplogger.1.gz', | |
|
134 | ['docs/man/iplogger.1'], | |
|
135 | 'cd docs/man && gzip -9c iplogger.1 > iplogger.1.gz'), | |
|
136 | ||
|
137 | ('docs/man/ipython.1.gz', | |
|
138 | ['docs/man/ipython.1'], | |
|
139 | 'cd docs/man && gzip -9c ipython.1 > ipython.1.gz'), | |
|
140 | ||
|
141 | ('docs/man/irunner.1.gz', | |
|
142 | ['docs/man/irunner.1'], | |
|
143 | 'cd docs/man && gzip -9c irunner.1 > irunner.1.gz'), | |
|
144 | ||
|
145 | ('docs/man/pycolor.1.gz', | |
|
146 | ['docs/man/pycolor.1'], | |
|
147 | 'cd docs/man && gzip -9c pycolor.1 > pycolor.1.gz'), | |
|
148 | ] | |
|
149 | ||
|
150 | # Only build the docs if sphinx is present | |
|
151 | try: | |
|
152 | import sphinx | |
|
153 | except ImportError: | |
|
154 | pass | |
|
155 | else: | |
|
156 | # The Makefile calls the do_sphinx scripts to build html and pdf, so | |
|
157 | # just one target is enough to cover all manual generation | |
|
158 | ||
|
159 | # First, compute all the dependencies that can force us to rebuild the | |
|
160 | # docs. Start with the main release file that contains metadata | |
|
161 | docdeps = ['IPython/core/release.py'] | |
|
162 | # Inculde all the reST sources | |
|
163 | pjoin = os.path.join | |
|
164 | for dirpath,dirnames,filenames in os.walk('docs/source'): | |
|
165 | if dirpath in ['_static','_templates']: | |
|
166 | continue | |
|
167 | docdeps += [ pjoin(dirpath,f) for f in filenames | |
|
168 | if f.endswith('.txt') ] | |
|
169 | # and the examples | |
|
170 | for dirpath,dirnames,filenames in os.walk('docs/example'): | |
|
171 | docdeps += [ pjoin(dirpath,f) for f in filenames | |
|
172 | if not f.endswith('~') ] | |
|
173 | # then, make them all dependencies for the main html docs | |
|
174 | to_update.append( | |
|
175 | ('docs/dist/index.html', | |
|
176 | docdeps, | |
|
177 | "cd docs && make dist") | |
|
178 | ) | |
|
179 | ||
|
180 | [ target_update(*t) for t in to_update ] | |
|
181 | ||
|
182 | #--------------------------------------------------------------------------- | |
|
183 | # Find all the packages, package data, and data_files | |
|
184 | #--------------------------------------------------------------------------- | |
|
185 | ||
|
186 | packages = find_packages() | |
|
187 | package_data = find_package_data() | |
|
188 | data_files = find_data_files() | |
|
189 | ||
|
190 | #--------------------------------------------------------------------------- | |
|
191 | # Handle scripts, dependencies, and setuptools specific things | |
|
192 | #--------------------------------------------------------------------------- | |
|
193 | ||
|
194 | # For some commands, use setuptools. Note that we do NOT list install here! | |
|
195 | # If you want a setuptools-enhanced install, just run 'setupegg.py install' | |
|
196 | needs_setuptools = set(('develop', 'sdist', 'release', 'bdist_egg', 'bdist_rpm', | |
|
197 | 'bdist', 'bdist_dumb', 'bdist_wininst', 'install_egg_info', | |
|
198 | 'build_sphinx', 'egg_info', 'easy_install', 'upload', | |
|
199 | )) | |
|
200 | if sys.platform == 'win32': | |
|
201 | # Depend on setuptools for install on *Windows only* | |
|
202 | # If we get script-installation working without setuptools, | |
|
203 | # then we can back off, but until then use it. | |
|
204 | # See Issue #369 on GitHub for more | |
|
205 | needs_setuptools.add('install') | |
|
206 | ||
|
207 | if len(needs_setuptools.intersection(sys.argv)) > 0: | |
|
208 | import setuptools | |
|
209 | ||
|
210 | # This dict is used for passing extra arguments that are setuptools | |
|
211 | # specific to setup | |
|
212 | setuptools_extra_args = {} | |
|
213 | ||
|
214 | if 'setuptools' in sys.modules: | |
|
215 | setuptools_extra_args['zip_safe'] = False | |
|
216 | setuptools_extra_args['entry_points'] = find_scripts(True) | |
|
217 | setup_args['extras_require'] = dict( | |
|
218 | parallel = 'pyzmq>=2.1.4', | |
|
219 | zmq = 'pyzmq>=2.1.4', | |
|
220 | doc = 'Sphinx>=0.3', | |
|
221 | test = 'nose>=0.10.1', | |
|
222 | notebook = 'tornado>=2.0' | |
|
223 | ) | |
|
224 | requires = setup_args.setdefault('install_requires', []) | |
|
225 | setupext.display_status = False | |
|
226 | if not setupext.check_for_readline(): | |
|
227 | if sys.platform == 'darwin': | |
|
228 | requires.append('readline') | |
|
229 | elif sys.platform.startswith('win') and sys.maxsize < 2**32: | |
|
230 | # only require pyreadline on 32b Windows, due to 64b bug in pyreadline: | |
|
231 | # https://bugs.launchpad.net/pyreadline/+bug/787574 | |
|
232 | requires.append('pyreadline') | |
|
233 | else: | |
|
234 | pass | |
|
235 | # do we want to install readline here? | |
|
236 | ||
|
237 | # Script to be run by the windows binary installer after the default setup | |
|
238 | # routine, to add shortcuts and similar windows-only things. Windows | |
|
239 | # post-install scripts MUST reside in the scripts/ dir, otherwise distutils | |
|
240 | # doesn't find them. | |
|
241 | if 'bdist_wininst' in sys.argv: | |
|
242 | if len(sys.argv) > 2 and \ | |
|
243 | ('sdist' in sys.argv or 'bdist_rpm' in sys.argv): | |
|
244 | print >> sys.stderr, "ERROR: bdist_wininst must be run alone. Exiting." | |
|
245 | sys.exit(1) | |
|
246 | setup_args['scripts'] = [pjoin('scripts','ipython_win_post_install.py')] | |
|
247 | setup_args['options'] = {"bdist_wininst": | |
|
248 | {"install_script": | |
|
249 | "ipython_win_post_install.py"}} | |
|
250 | else: | |
|
251 | # If we are running without setuptools, call this function which will | |
|
252 | # check for dependencies an inform the user what is needed. This is | |
|
253 | # just to make life easy for users. | |
|
254 | check_for_dependencies() | |
|
255 | setup_args['scripts'] = find_scripts(False) | |
|
256 | ||
|
257 | #--------------------------------------------------------------------------- | |
|
258 | # Do the actual setup now | |
|
259 | #--------------------------------------------------------------------------- | |
|
260 | ||
|
261 | setup_args['cmdclass'] = {'build_py': record_commit_info('IPython')} | |
|
262 | setup_args['packages'] = packages | |
|
263 | setup_args['package_data'] = package_data | |
|
264 | setup_args['data_files'] = data_files | |
|
265 | setup_args.update(setuptools_extra_args) | |
|
266 | ||
|
267 | def main(): | |
|
268 | setup(**setup_args) | |
|
269 | cleanup() | |
|
270 | ||
|
271 | if __name__ == '__main__': | |
|
272 | main() |
@@ -0,0 +1,13 b'' | |||
|
1 | import os.path | |
|
2 | from setuptools import setup | |
|
3 | ||
|
4 | from setupbase import (setup_args, find_scripts, find_packages) | |
|
5 | ||
|
6 | setup_args['entry_points'] = find_scripts(True, suffix='3') | |
|
7 | setup_args['packages'] = find_packages() | |
|
8 | ||
|
9 | def main(): | |
|
10 | setup(use_2to3 = True, **setup_args) | |
|
11 | ||
|
12 | if __name__ == "__main__": | |
|
13 | main() |
@@ -18,13 +18,13 b' Authors' | |||
|
18 | 18 | # Imports |
|
19 | 19 | #----------------------------------------------------------------------------- |
|
20 | 20 | |
|
21 | import __builtin__ | |
|
21 | import __builtin__ as builtin_mod | |
|
22 | 22 | import re |
|
23 | 23 | import sys |
|
24 | 24 | |
|
25 | 25 | from IPython.external import argparse |
|
26 | 26 | from IPython.utils.path import filefind, get_ipython_dir |
|
27 | from IPython.utils import warn | |
|
27 | from IPython.utils import py3compat, warn | |
|
28 | 28 | |
|
29 | 29 | #----------------------------------------------------------------------------- |
|
30 | 30 | # Exceptions |
@@ -131,7 +131,7 b' class Config(dict):' | |||
|
131 | 131 | # that you can't have section or attribute names that are |
|
132 | 132 | # builtins. |
|
133 | 133 | try: |
|
134 |
return getattr( |
|
|
134 | return getattr(builtin_mod, key) | |
|
135 | 135 | except AttributeError: |
|
136 | 136 | pass |
|
137 | 137 | if is_section_key(key): |
@@ -146,7 +146,7 b' class Config(dict):' | |||
|
146 | 146 | |
|
147 | 147 | def __setitem__(self, key, value): |
|
148 | 148 | # Don't allow names in __builtin__ to be modified. |
|
149 |
if hasattr( |
|
|
149 | if hasattr(builtin_mod, key): | |
|
150 | 150 | raise ConfigError('Config variable names cannot have the same name ' |
|
151 | 151 | 'as a Python builtin: %s' % key) |
|
152 | 152 | if self._is_section_key(key): |
@@ -312,7 +312,7 b' class PyFileConfigLoader(FileConfigLoader):' | |||
|
312 | 312 | namespace = dict(load_subconfig=load_subconfig, get_config=get_config) |
|
313 | 313 | fs_encoding = sys.getfilesystemencoding() or 'ascii' |
|
314 | 314 | conf_filename = self.full_filename.encode(fs_encoding) |
|
315 | execfile(conf_filename, namespace) | |
|
315 | py3compat.execfile(conf_filename, namespace) | |
|
316 | 316 | |
|
317 | 317 | def _convert_to_config(self): |
|
318 | 318 | if self.data is None: |
@@ -586,13 +586,7 b' class ArgParseConfigLoader(CommandLineConfigLoader):' | |||
|
586 | 586 | def _parse_args(self, args): |
|
587 | 587 | """self.parser->self.parsed_data""" |
|
588 | 588 | # decode sys.argv to support unicode command-line options |
|
589 | uargs = [] | |
|
590 | for a in args: | |
|
591 | if isinstance(a, str): | |
|
592 | # don't decode if we already got unicode | |
|
593 | a = a.decode(sys.stdin.encoding or | |
|
594 | sys.getdefaultencoding()) | |
|
595 | uargs.append(a) | |
|
589 | uargs = [py3compat.cast_unicode(a) for a in args] | |
|
596 | 590 | self.parsed_data, self.extra_args = self.parser.parse_known_args(uargs) |
|
597 | 591 | |
|
598 | 592 | def _convert_to_config(self): |
@@ -5,9 +5,9 b' app = c.InteractiveShellApp' | |||
|
5 | 5 | # and merge it into the current one. |
|
6 | 6 | load_subconfig('ipython_config.py', profile='default') |
|
7 | 7 | |
|
8 | c.InteractiveShell.prompt_in1 = '\C_LightGreen\u@\h\C_LightBlue[\C_LightCyan\Y1\C_LightBlue]\C_Green|\#> ' | |
|
9 | c.InteractiveShell.prompt_in2 = '\C_Green|\C_LightGreen\D\C_Green> ' | |
|
10 | c.InteractiveShell.prompt_out = '<\#> ' | |
|
8 | c.InteractiveShell.prompt_in1 = r'\C_LightGreen\u@\h\C_LightBlue[\C_LightCyan\Y1\C_LightBlue]\C_Green|\#> ' | |
|
9 | c.InteractiveShell.prompt_in2 = r'\C_Green|\C_LightGreen\D\C_Green> ' | |
|
10 | c.InteractiveShell.prompt_out = r'<\#> ' | |
|
11 | 11 | |
|
12 | 12 | c.InteractiveShell.prompts_pad_left = True |
|
13 | 13 | |
@@ -27,4 +27,4 b' lines = """' | |||
|
27 | 27 | if hasattr(app, 'exec_lines'): |
|
28 | 28 | app.exec_lines.append(lines) |
|
29 | 29 | else: |
|
30 | app.exec_lines = [lines] No newline at end of file | |
|
30 | app.exec_lines = [lines] |
@@ -48,7 +48,7 b' c = get_config()' | |||
|
48 | 48 | c.a=10 |
|
49 | 49 | c.b=20 |
|
50 | 50 | c.Foo.Bar.value=10 |
|
51 | c.Foo.Bam.value=range(10) | |
|
51 | c.Foo.Bam.value=list(range(10)) # list() is just so it's the same on Python 3 | |
|
52 | 52 | c.D.C.value='hi there' |
|
53 | 53 | """ |
|
54 | 54 |
@@ -38,7 +38,7 b' from IPython.utils.warn import warn, error' | |||
|
38 | 38 | #----------------------------------------------------------------------------- |
|
39 | 39 | |
|
40 | 40 | # This is used as the pattern for calls to split_user_input. |
|
41 |
shell_line_split = re.compile(r'^(\s*)(\S |
|
|
41 | shell_line_split = re.compile(r'^(\s*)()(\S+)(.*$)') | |
|
42 | 42 | |
|
43 | 43 | def default_aliases(): |
|
44 | 44 | """Return list of shell aliases to auto-define. |
@@ -222,7 +222,7 b' class AliasManager(Configurable):' | |||
|
222 | 222 | <16> 'q:/opt/np/notepad++.exe myfile.txt' |
|
223 | 223 | """ |
|
224 | 224 | |
|
225 | pre,fn,rest = split_user_input(line) | |
|
225 | pre,_,fn,rest = split_user_input(line) | |
|
226 | 226 | res = pre + self.expand_aliases(fn, rest) |
|
227 | 227 | return res |
|
228 | 228 | |
@@ -242,7 +242,7 b' class AliasManager(Configurable):' | |||
|
242 | 242 | |
|
243 | 243 | done = set() |
|
244 | 244 | while 1: |
|
245 | pre,fn,rest = split_user_input(line, shell_line_split) | |
|
245 | pre,_,fn,rest = split_user_input(line, shell_line_split) | |
|
246 | 246 | if fn in self.alias_table: |
|
247 | 247 | if fn in done: |
|
248 | 248 | warn("Cyclic alias definition, repeated '%s'" % fn) |
@@ -40,6 +40,7 b' from IPython.core import release, crashhandler' | |||
|
40 | 40 | from IPython.core.profiledir import ProfileDir, ProfileDirError |
|
41 | 41 | from IPython.utils.path import get_ipython_dir, get_ipython_package_dir |
|
42 | 42 | from IPython.utils.traitlets import List, Unicode, Type, Bool, Dict |
|
43 | from IPython.utils import py3compat | |
|
43 | 44 | |
|
44 | 45 | #----------------------------------------------------------------------------- |
|
45 | 46 | # Classes and functions |
@@ -102,9 +103,12 b' class BaseIPythonApplication(Application):' | |||
|
102 | 103 | def _config_file_paths_default(self): |
|
103 | 104 | return [os.getcwdu()] |
|
104 | 105 | |
|
105 |
profile = Unicode(u' |
|
|
106 | profile = Unicode(u'', config=True, | |
|
106 | 107 | help="""The IPython profile to use.""" |
|
107 | 108 | ) |
|
109 | def _profile_default(self): | |
|
110 | return "python3" if py3compat.PY3 else "default" | |
|
111 | ||
|
108 | 112 | def _profile_changed(self, name, old, new): |
|
109 | 113 | self.builtin_profile_dir = os.path.join( |
|
110 | 114 | get_ipython_package_dir(), u'config', u'profile', new |
@@ -222,7 +226,7 b' class BaseIPythonApplication(Application):' | |||
|
222 | 226 | p = ProfileDir.find_profile_dir_by_name(self.ipython_dir, self.profile, self.config) |
|
223 | 227 | except ProfileDirError: |
|
224 | 228 | # not found, maybe create it (always create default profile) |
|
225 |
if self.auto_create or self.profile== |
|
|
229 | if self.auto_create or self.profile==self._profile_default(): | |
|
226 | 230 | try: |
|
227 | 231 | p = ProfileDir.create_profile_dir_by_name(self.ipython_dir, self.profile, self.config) |
|
228 | 232 | except ProfileDirError: |
@@ -30,6 +30,7 b' from zipimport import zipimporter' | |||
|
30 | 30 | # Our own imports |
|
31 | 31 | from IPython.core.completer import expand_user, compress_user |
|
32 | 32 | from IPython.core.error import TryNext |
|
33 | from IPython.utils import py3compat | |
|
33 | 34 | |
|
34 | 35 | # FIXME: this should be pulled in with the right call via the component system |
|
35 | 36 | from IPython.core.ipapi import get as get_ipython |
@@ -66,10 +67,9 b' def shlex_split(x):' | |||
|
66 | 67 | # Example: |
|
67 | 68 | # %run "c:/python -> ['%run','"c:/python'] |
|
68 | 69 | |
|
69 | # shlex.split has unicode bugs, so encode first to str | |
|
70 | if isinstance(x, unicode): | |
|
71 | # don't raise errors on encoding: | |
|
72 | x = x.encode(sys.stdin.encoding or sys.getdefaultencoding(), 'replace') | |
|
70 | # shlex.split has unicode bugs in Python 2, so encode first to str | |
|
71 | if not py3compat.PY3: | |
|
72 | x = py3compat.cast_bytes(x) | |
|
73 | 73 | |
|
74 | 74 | endofline = [] |
|
75 | 75 | while x != '': |
@@ -29,6 +29,7 b' from StringIO import StringIO' | |||
|
29 | 29 | from IPython.config.configurable import Configurable |
|
30 | 30 | from IPython.lib import pretty |
|
31 | 31 | from IPython.utils.traitlets import Bool, Dict, Int, Unicode, CUnicode, ObjectName |
|
32 | from IPython.utils.py3compat import unicode_to_str | |
|
32 | 33 | |
|
33 | 34 | |
|
34 | 35 | #----------------------------------------------------------------------------- |
@@ -439,7 +440,7 b' class PlainTextFormatter(BaseFormatter):' | |||
|
439 | 440 | # ensure that stream does not get a mix of unicode and bytestrings, |
|
440 | 441 | # or it will cause trouble. |
|
441 | 442 | printer = pretty.RepresentationPrinter(stream, self.verbose, |
|
442 |
self.max_width, self.newline |
|
|
443 | self.max_width, unicode_to_str(self.newline), | |
|
443 | 444 | singleton_pprinters=self.singleton_printers, |
|
444 | 445 | type_pprinters=self.type_printers, |
|
445 | 446 | deferred_pprinters=self.deferred_printers) |
@@ -75,8 +75,10 b' class HistoryManager(Configurable):' | |||
|
75 | 75 | |
|
76 | 76 | # History saving in separate thread |
|
77 | 77 | save_thread = Instance('IPython.core.history.HistorySavingThread') |
|
78 |
|
|
|
79 | save_flag = Instance(threading._Event) | |
|
78 | try: # Event is a function returning an instance of _Event... | |
|
79 | save_flag = Instance(threading._Event) | |
|
80 | except AttributeError: # ...until Python 3.3, when it's a class. | |
|
81 | save_flag = Instance(threading.Event) | |
|
80 | 82 | |
|
81 | 83 | # Private interface |
|
82 | 84 | # Variables used to store the three last inputs from the user. On each new |
@@ -74,7 +74,9 b' import tokenize' | |||
|
74 | 74 | from StringIO import StringIO |
|
75 | 75 | |
|
76 | 76 | # IPython modules |
|
77 | from IPython.core.splitinput import split_user_input, LineInfo | |
|
77 | 78 | from IPython.utils.text import make_quoted_expr |
|
79 | from IPython.utils.py3compat import cast_unicode | |
|
78 | 80 | |
|
79 | 81 | #----------------------------------------------------------------------------- |
|
80 | 82 | # Globals |
@@ -481,132 +483,10 b' class InputSplitter(object):' | |||
|
481 | 483 | # Functions and classes for IPython-specific syntactic support |
|
482 | 484 | #----------------------------------------------------------------------------- |
|
483 | 485 | |
|
484 | # RegExp for splitting line contents into pre-char//first word-method//rest. | |
|
485 | # For clarity, each group in on one line. | |
|
486 | ||
|
487 | line_split = re.compile(""" | |
|
488 | ^(\s*) # any leading space | |
|
489 | ([,;/%]|!!?|\?\??) # escape character or characters | |
|
490 | \s*(%?[\w\.\*]*) # function/method, possibly with leading % | |
|
491 | # to correctly treat things like '?%magic' | |
|
492 | (\s+.*$|$) # rest of line | |
|
493 | """, re.VERBOSE) | |
|
494 | ||
|
495 | ||
|
496 | def split_user_input(line): | |
|
497 | """Split user input into early whitespace, esc-char, function part and rest. | |
|
498 | ||
|
499 | This is currently handles lines with '=' in them in a very inconsistent | |
|
500 | manner. | |
|
501 | ||
|
502 | Examples | |
|
503 | ======== | |
|
504 | >>> split_user_input('x=1') | |
|
505 | ('', '', 'x=1', '') | |
|
506 | >>> split_user_input('?') | |
|
507 | ('', '?', '', '') | |
|
508 | >>> split_user_input('??') | |
|
509 | ('', '??', '', '') | |
|
510 | >>> split_user_input(' ?') | |
|
511 | (' ', '?', '', '') | |
|
512 | >>> split_user_input(' ??') | |
|
513 | (' ', '??', '', '') | |
|
514 | >>> split_user_input('??x') | |
|
515 | ('', '??', 'x', '') | |
|
516 | >>> split_user_input('?x=1') | |
|
517 | ('', '', '?x=1', '') | |
|
518 | >>> split_user_input('!ls') | |
|
519 | ('', '!', 'ls', '') | |
|
520 | >>> split_user_input(' !ls') | |
|
521 | (' ', '!', 'ls', '') | |
|
522 | >>> split_user_input('!!ls') | |
|
523 | ('', '!!', 'ls', '') | |
|
524 | >>> split_user_input(' !!ls') | |
|
525 | (' ', '!!', 'ls', '') | |
|
526 | >>> split_user_input(',ls') | |
|
527 | ('', ',', 'ls', '') | |
|
528 | >>> split_user_input(';ls') | |
|
529 | ('', ';', 'ls', '') | |
|
530 | >>> split_user_input(' ;ls') | |
|
531 | (' ', ';', 'ls', '') | |
|
532 | >>> split_user_input('f.g(x)') | |
|
533 | ('', '', 'f.g(x)', '') | |
|
534 | >>> split_user_input('f.g (x)') | |
|
535 | ('', '', 'f.g', '(x)') | |
|
536 | >>> split_user_input('?%hist') | |
|
537 | ('', '?', '%hist', '') | |
|
538 | >>> split_user_input('?x*') | |
|
539 | ('', '?', 'x*', '') | |
|
540 | """ | |
|
541 | match = line_split.match(line) | |
|
542 | if match: | |
|
543 | lspace, esc, fpart, rest = match.groups() | |
|
544 | else: | |
|
545 | # print "match failed for line '%s'" % line | |
|
546 | try: | |
|
547 | fpart, rest = line.split(None, 1) | |
|
548 | except ValueError: | |
|
549 | # print "split failed for line '%s'" % line | |
|
550 | fpart, rest = line,'' | |
|
551 | lspace = re.match('^(\s*)(.*)', line).groups()[0] | |
|
552 | esc = '' | |
|
553 | ||
|
554 | # fpart has to be a valid python identifier, so it better be only pure | |
|
555 | # ascii, no unicode: | |
|
556 | try: | |
|
557 | fpart = fpart.encode('ascii') | |
|
558 | except UnicodeEncodeError: | |
|
559 | lspace = unicode(lspace) | |
|
560 | rest = fpart + u' ' + rest | |
|
561 | fpart = u'' | |
|
562 | ||
|
563 | #print 'line:<%s>' % line # dbg | |
|
564 | #print 'esc <%s> fpart <%s> rest <%s>' % (esc,fpart.strip(),rest) # dbg | |
|
565 | return lspace, esc, fpart.strip(), rest.lstrip() | |
|
566 | ||
|
567 | ||
|
568 | 486 | # The escaped translators ALL receive a line where their own escape has been |
|
569 | 487 | # stripped. Only '?' is valid at the end of the line, all others can only be |
|
570 | 488 | # placed at the start. |
|
571 | 489 | |
|
572 | class LineInfo(object): | |
|
573 | """A single line of input and associated info. | |
|
574 | ||
|
575 | This is a utility class that mostly wraps the output of | |
|
576 | :func:`split_user_input` into a convenient object to be passed around | |
|
577 | during input transformations. | |
|
578 | ||
|
579 | Includes the following as properties: | |
|
580 | ||
|
581 | line | |
|
582 | The original, raw line | |
|
583 | ||
|
584 | lspace | |
|
585 | Any early whitespace before actual text starts. | |
|
586 | ||
|
587 | esc | |
|
588 | The initial esc character (or characters, for double-char escapes like | |
|
589 | '??' or '!!'). | |
|
590 | ||
|
591 | fpart | |
|
592 | The 'function part', which is basically the maximal initial sequence | |
|
593 | of valid python identifiers and the '.' character. This is what is | |
|
594 | checked for alias and magic transformations, used for auto-calling, | |
|
595 | etc. | |
|
596 | ||
|
597 | rest | |
|
598 | Everything else on the line. | |
|
599 | """ | |
|
600 | def __init__(self, line): | |
|
601 | self.line = line | |
|
602 | self.lspace, self.esc, self.fpart, self.rest = \ | |
|
603 | split_user_input(line) | |
|
604 | ||
|
605 | def __str__(self): | |
|
606 | return "LineInfo [%s|%s|%s|%s]" % (self.lspace, self.esc, | |
|
607 | self.fpart, self.rest) | |
|
608 | ||
|
609 | ||
|
610 | 490 | # Transformations of the special syntaxes that don't rely on an explicit escape |
|
611 | 491 | # character but instead on patterns on the input line |
|
612 | 492 | |
@@ -680,19 +560,20 b' def _make_help_call(target, esc, lspace, next_input=None):' | |||
|
680 | 560 | method = 'pinfo2' if esc == '??' \ |
|
681 | 561 | else 'psearch' if '*' in target \ |
|
682 | 562 | else 'pinfo' |
|
683 | ||
|
563 | arg = make_quoted_expr(" ".join([method, target])) | |
|
564 | ||
|
684 | 565 | if next_input: |
|
685 |
tpl = '%sget_ipython().magic( |
|
|
686 |
return tpl % (lspace, |
|
|
566 | tpl = '%sget_ipython().magic(%s, next_input=%s)' | |
|
567 | return tpl % (lspace, arg, make_quoted_expr(next_input)) | |
|
687 | 568 | else: |
|
688 |
return '%sget_ipython().magic( |
|
|
569 | return '%sget_ipython().magic(%s)' % (lspace, arg) | |
|
689 | 570 | |
|
690 | 571 | _initial_space_re = re.compile(r'\s*') |
|
691 | 572 | _help_end_re = re.compile(r"""(%? |
|
692 |
[a-zA-Z_*][ |
|
|
693 |
(\.[a-zA-Z_*][ |
|
|
573 | [a-zA-Z_*][\w*]* # Variable name | |
|
574 | (\.[a-zA-Z_*][\w*]*)* # .etc.etc | |
|
694 | 575 | ) |
|
695 |
(\?\??)$ |
|
|
576 | (\?\??)$ # ? or ??""", | |
|
696 | 577 | re.VERBOSE) |
|
697 | 578 | def transform_help_end(line): |
|
698 | 579 | """Translate lines with ?/?? at the end""" |
@@ -702,7 +583,6 b' def transform_help_end(line):' | |||
|
702 | 583 | target = m.group(1) |
|
703 | 584 | esc = m.group(3) |
|
704 | 585 | lspace = _initial_space_re.match(line).group(0) |
|
705 | newline = _make_help_call(target, esc, lspace) | |
|
706 | 586 | |
|
707 | 587 | # If we're mid-command, put it back on the next prompt for the user. |
|
708 | 588 | next_input = line.rstrip('?') if line.strip() != m.group(0) else None |
@@ -730,14 +610,14 b' class EscapedTransformer(object):' | |||
|
730 | 610 | def _tr_system(line_info): |
|
731 | 611 | "Translate lines escaped with: !" |
|
732 | 612 | cmd = line_info.line.lstrip().lstrip(ESC_SHELL) |
|
733 |
return '%sget_ipython().system(%s)' % (line_info. |
|
|
613 | return '%sget_ipython().system(%s)' % (line_info.pre, | |
|
734 | 614 | make_quoted_expr(cmd)) |
|
735 | 615 | |
|
736 | 616 | @staticmethod |
|
737 | 617 | def _tr_system2(line_info): |
|
738 | 618 | "Translate lines escaped with: !!" |
|
739 | 619 | cmd = line_info.line.lstrip()[2:] |
|
740 |
return '%sget_ipython().getoutput(%s)' % (line_info. |
|
|
620 | return '%sget_ipython().getoutput(%s)' % (line_info.pre, | |
|
741 | 621 | make_quoted_expr(cmd)) |
|
742 | 622 | |
|
743 | 623 | @staticmethod |
@@ -747,33 +627,33 b' class EscapedTransformer(object):' | |||
|
747 | 627 | if not line_info.line[1:]: |
|
748 | 628 | return 'get_ipython().show_usage()' |
|
749 | 629 | |
|
750 |
return _make_help_call(line_info. |
|
|
630 | return _make_help_call(line_info.ifun, line_info.esc, line_info.pre) | |
|
751 | 631 | |
|
752 | 632 | @staticmethod |
|
753 | 633 | def _tr_magic(line_info): |
|
754 | 634 | "Translate lines escaped with: %" |
|
755 | 635 | tpl = '%sget_ipython().magic(%s)' |
|
756 |
cmd = make_quoted_expr(' '.join([line_info. |
|
|
757 |
|
|
|
758 |
return tpl % (line_info. |
|
|
636 | cmd = make_quoted_expr(' '.join([line_info.ifun, | |
|
637 | line_info.the_rest]).strip()) | |
|
638 | return tpl % (line_info.pre, cmd) | |
|
759 | 639 | |
|
760 | 640 | @staticmethod |
|
761 | 641 | def _tr_quote(line_info): |
|
762 | 642 | "Translate lines escaped with: ," |
|
763 |
return '%s%s("%s")' % (line_info. |
|
|
764 | '", "'.join(line_info.rest.split()) ) | |
|
643 | return '%s%s("%s")' % (line_info.pre, line_info.ifun, | |
|
644 | '", "'.join(line_info.the_rest.split()) ) | |
|
765 | 645 | |
|
766 | 646 | @staticmethod |
|
767 | 647 | def _tr_quote2(line_info): |
|
768 | 648 | "Translate lines escaped with: ;" |
|
769 |
return '%s%s("%s")' % (line_info. |
|
|
770 | line_info.rest) | |
|
649 | return '%s%s("%s")' % (line_info.pre, line_info.ifun, | |
|
650 | line_info.the_rest) | |
|
771 | 651 | |
|
772 | 652 | @staticmethod |
|
773 | 653 | def _tr_paren(line_info): |
|
774 | 654 | "Translate lines escaped with: /" |
|
775 |
return '%s%s(%s)' % (line_info. |
|
|
776 | ", ".join(line_info.rest.split())) | |
|
655 | return '%s%s(%s)' % (line_info.pre, line_info.ifun, | |
|
656 | ", ".join(line_info.the_rest.split())) | |
|
777 | 657 | |
|
778 | 658 | def __call__(self, line): |
|
779 | 659 | """Class to transform lines that are explicitly escaped out. |
@@ -837,13 +717,12 b' class IPythonInputSplitter(InputSplitter):' | |||
|
837 | 717 | return super(IPythonInputSplitter, self).push(lines) |
|
838 | 718 | |
|
839 | 719 | # We must ensure all input is pure unicode |
|
840 | if type(lines)==str: | |
|
841 | lines = lines.decode(self.encoding) | |
|
720 | lines = cast_unicode(lines, self.encoding) | |
|
842 | 721 | |
|
843 | 722 | lines_list = lines.splitlines() |
|
844 | 723 | |
|
845 | 724 | transforms = [transform_ipy_prompt, transform_classic_prompt, |
|
846 |
transform_escaped, |
|
|
725 | transform_help_end, transform_escaped, | |
|
847 | 726 | transform_assign_system, transform_assign_magic] |
|
848 | 727 | |
|
849 | 728 | # Transform logic |
@@ -17,7 +17,7 b'' | |||
|
17 | 17 | from __future__ import with_statement |
|
18 | 18 | from __future__ import absolute_import |
|
19 | 19 | |
|
20 | import __builtin__ | |
|
20 | import __builtin__ as builtin_mod | |
|
21 | 21 | import __future__ |
|
22 | 22 | import abc |
|
23 | 23 | import ast |
@@ -29,7 +29,10 b' import re' | |||
|
29 | 29 | import sys |
|
30 | 30 | import tempfile |
|
31 | 31 | import types |
|
32 | from contextlib import nested | |
|
32 | try: | |
|
33 | from contextlib import nested | |
|
34 | except: | |
|
35 | from IPython.utils.nested_context import nested | |
|
33 | 36 | |
|
34 | 37 | from IPython.config.configurable import SingletonConfigurable |
|
35 | 38 | from IPython.core import debugger, oinspect |
@@ -61,6 +64,7 b' from IPython.core.profiledir import ProfileDir' | |||
|
61 | 64 | from IPython.external.Itpl import ItplNS |
|
62 | 65 | from IPython.utils import PyColorize |
|
63 | 66 | from IPython.utils import io |
|
67 | from IPython.utils import py3compat | |
|
64 | 68 | from IPython.utils.doctestreload import doctest_reload |
|
65 | 69 | from IPython.utils.io import ask_yes_no, rprint |
|
66 | 70 | from IPython.utils.ipstruct import Struct |
@@ -410,7 +414,10 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
410 | 414 | # We save this here in case user code replaces raw_input, but it needs |
|
411 | 415 | # to be after init_readline(), because PyPy's readline works by replacing |
|
412 | 416 | # raw_input. |
|
413 | self.raw_input_original = raw_input | |
|
417 | if py3compat.PY3: | |
|
418 | self.raw_input_original = input | |
|
419 | else: | |
|
420 | self.raw_input_original = raw_input | |
|
414 | 421 | # init_completer must come after init_readline, because it needs to |
|
415 | 422 | # know whether readline is present or not system-wide to configure the |
|
416 | 423 | # completers, since the completion machinery can now operate |
@@ -925,7 +932,7 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
925 | 932 | self.ns_table = {'user':user_ns, |
|
926 | 933 | 'user_global':user_global_ns, |
|
927 | 934 | 'internal':self.internal_ns, |
|
928 |
'builtin': |
|
|
935 | 'builtin':builtin_mod.__dict__ | |
|
929 | 936 | } |
|
930 | 937 | |
|
931 | 938 | # Similarly, track all namespaces where references can be held and that |
@@ -979,13 +986,13 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
979 | 986 | # Set __name__ to __main__ to better match the behavior of the |
|
980 | 987 | # normal interpreter. |
|
981 | 988 | user_ns = {'__name__' :'__main__', |
|
982 |
|
|
|
983 |
'__builtins__' : |
|
|
989 | py3compat.builtin_mod_name: builtin_mod, | |
|
990 | '__builtins__' : builtin_mod, | |
|
984 | 991 | } |
|
985 | 992 | else: |
|
986 | 993 | user_ns.setdefault('__name__','__main__') |
|
987 |
user_ns.setdefault( |
|
|
988 |
user_ns.setdefault('__builtins__', |
|
|
994 | user_ns.setdefault(py3compat.builtin_mod_name,builtin_mod) | |
|
995 | user_ns.setdefault('__builtins__',builtin_mod) | |
|
989 | 996 | |
|
990 | 997 | if user_global_ns is None: |
|
991 | 998 | user_global_ns = user_ns |
@@ -1049,7 +1056,7 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1049 | 1056 | |
|
1050 | 1057 | # For more details: |
|
1051 | 1058 | # http://mail.python.org/pipermail/python-dev/2001-April/014068.html |
|
1052 |
ns = dict(__builtin__ = |
|
|
1059 | ns = dict(__builtin__ = builtin_mod) | |
|
1053 | 1060 | |
|
1054 | 1061 | # Put 'help' in the user namespace |
|
1055 | 1062 | try: |
@@ -1255,13 +1262,9 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1255 | 1262 | |
|
1256 | 1263 | Has special code to detect magic functions. |
|
1257 | 1264 | """ |
|
1258 |
|
|
|
1265 | oname = oname.strip() | |
|
1259 | 1266 | #print '1- oname: <%r>' % oname # dbg |
|
1260 | try: | |
|
1261 | oname = oname.strip().encode('ascii') | |
|
1262 | #print '2- oname: <%r>' % oname # dbg | |
|
1263 | except UnicodeEncodeError: | |
|
1264 | print 'Python identifiers can only contain ascii characters.' | |
|
1267 | if not py3compat.isidentifier(oname.lstrip(ESC_MAGIC), dotted=True): | |
|
1265 | 1268 | return dict(found=False) |
|
1266 | 1269 | |
|
1267 | 1270 | alias_ns = None |
@@ -1271,7 +1274,7 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1271 | 1274 | # find things in the same order that Python finds them. |
|
1272 | 1275 | namespaces = [ ('Interactive', self.user_ns), |
|
1273 | 1276 | ('IPython internal', self.internal_ns), |
|
1274 |
('Python builtin', |
|
|
1277 | ('Python builtin', builtin_mod.__dict__), | |
|
1275 | 1278 | ('Alias', self.alias_manager.alias_table), |
|
1276 | 1279 | ] |
|
1277 | 1280 | alias_ns = self.alias_manager.alias_table |
@@ -1283,8 +1286,8 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1283 | 1286 | # We need to special-case 'print', which as of python2.6 registers as a |
|
1284 | 1287 | # function but should only be treated as one if print_function was |
|
1285 | 1288 | # loaded with a future import. In this case, just bail. |
|
1286 |
if (oname == 'print' and not |
|
|
1287 |
|
|
|
1289 | if (oname == 'print' and not py3compat.PY3 and not \ | |
|
1290 | (self.compile.compiler_flags & __future__.CO_FUTURE_PRINT_FUNCTION)): | |
|
1288 | 1291 | return {'found':found, 'obj':obj, 'namespace':ospace, |
|
1289 | 1292 | 'ismagic':ismagic, 'isalias':isalias, 'parent':parent} |
|
1290 | 1293 | |
@@ -1526,7 +1529,7 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1526 | 1529 | |
|
1527 | 1530 | if etype is SyntaxError: |
|
1528 | 1531 | # Though this won't be called by syntax errors in the input |
|
1529 |
# line, there may be SyntaxError cases w |
|
|
1532 | # line, there may be SyntaxError cases with imported code. | |
|
1530 | 1533 | self.showsyntaxerror(filename) |
|
1531 | 1534 | elif etype is UsageError: |
|
1532 | 1535 | print "UsageError:", value |
@@ -1679,7 +1682,9 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1679 | 1682 | |
|
1680 | 1683 | # Remove some chars from the delimiters list. If we encounter |
|
1681 | 1684 | # unicode chars, discard them. |
|
1682 |
delims = readline.get_completer_delims() |
|
|
1685 | delims = readline.get_completer_delims() | |
|
1686 | if not py3compat.PY3: | |
|
1687 | delims = delims.encode("ascii", "ignore") | |
|
1683 | 1688 | for d in self.readline_remove_delims: |
|
1684 | 1689 | delims = delims.replace(d, "") |
|
1685 | 1690 | delims = delims.replace(ESC_MAGIC, '') |
@@ -1701,7 +1706,8 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1701 | 1706 | include_latest=True): |
|
1702 | 1707 | if cell.strip(): # Ignore blank lines |
|
1703 | 1708 | for line in cell.splitlines(): |
|
1704 |
self.readline.add_history(line |
|
|
1709 | self.readline.add_history(py3compat.unicode_to_str(line, | |
|
1710 | stdin_encoding)) | |
|
1705 | 1711 | |
|
1706 | 1712 | def set_next_input(self, s): |
|
1707 | 1713 | """ Sets the 'default' input string for the next command line. |
@@ -1907,8 +1913,6 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
1907 | 1913 | |
|
1908 | 1914 | self.define_magic('foo',foo_impl) |
|
1909 | 1915 | """ |
|
1910 | ||
|
1911 | import new | |
|
1912 | 1916 | im = types.MethodType(func,self) |
|
1913 | 1917 | old = getattr(self, "magic_" + magicname, None) |
|
1914 | 1918 | setattr(self, "magic_" + magicname, im) |
@@ -2175,15 +2179,10 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
2175 | 2179 | # behavior of running a script from the system command line, where |
|
2176 | 2180 | # Python inserts the script's directory into sys.path |
|
2177 | 2181 | dname = os.path.dirname(fname) |
|
2178 | ||
|
2179 | if isinstance(fname, unicode): | |
|
2180 | # execfile uses default encoding instead of filesystem encoding | |
|
2181 | # so unicode filenames will fail | |
|
2182 | fname = fname.encode(sys.getfilesystemencoding() or sys.getdefaultencoding()) | |
|
2183 | 2182 | |
|
2184 | 2183 | with prepended_to_syspath(dname): |
|
2185 | 2184 | try: |
|
2186 | execfile(fname,*where) | |
|
2185 | py3compat.execfile(fname,*where) | |
|
2187 | 2186 | except SystemExit, status: |
|
2188 | 2187 | # If the call was made with 0 or None exit status (sys.exit(0) |
|
2189 | 2188 | # or sys.exit() ), don't bother showing a traceback, as both of |
@@ -2455,7 +2454,7 b' class InteractiveShell(SingletonConfigurable, Magic):' | |||
|
2455 | 2454 | # Skip our own frame in searching for locals: |
|
2456 | 2455 | sys._getframe(depth+1).f_locals # locals |
|
2457 | 2456 | ) |
|
2458 |
return str(res) |
|
|
2457 | return py3compat.str_to_unicode(str(res), res.codec) | |
|
2459 | 2458 | |
|
2460 | 2459 | def mktempfile(self, data=None, prefix='ipython_edit_'): |
|
2461 | 2460 | """Make a new tempfile and return its filename. |
@@ -10,6 +10,8 b'' | |||
|
10 | 10 | import re |
|
11 | 11 | import sys |
|
12 | 12 | |
|
13 | from IPython.utils import py3compat | |
|
14 | ||
|
13 | 15 | coding_declaration = re.compile(r"#\s*coding[:=]\s*([-\w.]+)") |
|
14 | 16 | |
|
15 | 17 | class Macro(object): |
@@ -37,8 +39,7 b' class Macro(object):' | |||
|
37 | 39 | self.value = code + '\n' |
|
38 | 40 | |
|
39 | 41 | def __str__(self): |
|
40 | enc = sys.stdin.encoding or sys.getdefaultencoding() | |
|
41 | return self.value.encode(enc, "replace") | |
|
42 | return py3compat.unicode_to_str(self.value) | |
|
42 | 43 | |
|
43 | 44 | def __unicode__(self): |
|
44 | 45 | return self.value |
@@ -15,7 +15,7 b'' | |||
|
15 | 15 | # Imports |
|
16 | 16 | #----------------------------------------------------------------------------- |
|
17 | 17 | |
|
18 | import __builtin__ | |
|
18 | import __builtin__ as builtin_mod | |
|
19 | 19 | import __future__ |
|
20 | 20 | import bdb |
|
21 | 21 | import inspect |
@@ -52,6 +52,7 b' from IPython.core import magic_arguments, page' | |||
|
52 | 52 | from IPython.core.prefilter import ESC_MAGIC |
|
53 | 53 | from IPython.lib.pylabtools import mpl_runner |
|
54 | 54 | from IPython.testing.skipdoctest import skip_doctest |
|
55 | from IPython.utils import py3compat | |
|
55 | 56 | from IPython.utils.io import file_read, nlprint |
|
56 | 57 | from IPython.utils.path import get_py_filename, unquote_filename |
|
57 | 58 | from IPython.utils.process import arg_split, abbrev_cwd |
@@ -60,7 +61,6 b' from IPython.utils.text import LSString, SList, format_screen' | |||
|
60 | 61 | from IPython.utils.timing import clock, clock2 |
|
61 | 62 | from IPython.utils.warn import warn, error |
|
62 | 63 | from IPython.utils.ipstruct import Struct |
|
63 | import IPython.utils.generics | |
|
64 | 64 | |
|
65 | 65 | #----------------------------------------------------------------------------- |
|
66 | 66 | # Utility functions |
@@ -676,7 +676,7 b' Currently the magic system has the following functions:\\n"""' | |||
|
676 | 676 | |
|
677 | 677 | %psearch -a _* list objects beginning with a single underscore""" |
|
678 | 678 | try: |
|
679 |
|
|
|
679 | parameter_s.encode('ascii') | |
|
680 | 680 | except UnicodeEncodeError: |
|
681 | 681 | print 'Python identifiers can only contain ascii characters.' |
|
682 | 682 | return |
@@ -1729,7 +1729,7 b' Currently the magic system has the following functions:\\n"""' | |||
|
1729 | 1729 | # Since this seems to be done by the interpreter itself, the best |
|
1730 | 1730 | # we can do is to at least restore __builtins__ for the user on |
|
1731 | 1731 | # exit. |
|
1732 |
self.shell.user_ns['__builtins__'] = |
|
|
1732 | self.shell.user_ns['__builtins__'] = builtin_mod | |
|
1733 | 1733 | |
|
1734 | 1734 | # Ensure key global structures are restored |
|
1735 | 1735 | sys.argv = save_argv |
@@ -2085,11 +2085,9 b' Currently the magic system has the following functions:\\n"""' | |||
|
2085 | 2085 | except (TypeError, ValueError) as e: |
|
2086 | 2086 | print e.args[0] |
|
2087 | 2087 | return |
|
2088 | if isinstance(cmds, unicode): | |
|
2089 | cmds = cmds.encode("utf-8") | |
|
2090 | with open(fname,'w') as f: | |
|
2091 | f.write("# coding: utf-8\n") | |
|
2092 | f.write(cmds) | |
|
2088 | with py3compat.open(fname,'w', encoding="utf-8") as f: | |
|
2089 | f.write(u"# coding: utf-8\n") | |
|
2090 | f.write(py3compat.cast_unicode(cmds)) | |
|
2093 | 2091 | print 'The following commands were written to file `%s`:' % fname |
|
2094 | 2092 | print cmds |
|
2095 | 2093 |
@@ -24,12 +24,16 b' import os' | |||
|
24 | 24 | import sys |
|
25 | 25 | import types |
|
26 | 26 | from collections import namedtuple |
|
27 | from itertools import izip_longest | |
|
27 | try: | |
|
28 | from itertools import izip_longest | |
|
29 | except ImportError: | |
|
30 | from itertools import zip_longest as izip_longest | |
|
28 | 31 | |
|
29 | 32 | # IPython's own |
|
30 | 33 | from IPython.core import page |
|
31 | 34 | from IPython.utils import PyColorize |
|
32 | 35 | from IPython.utils import io |
|
36 | from IPython.utils import py3compat | |
|
33 | 37 | from IPython.utils.text import indent |
|
34 | 38 | from IPython.utils.wildcard import list_namespace |
|
35 | 39 | from IPython.utils.coloransi import * |
@@ -249,7 +253,7 b' class Inspector:' | |||
|
249 | 253 | try: |
|
250 | 254 | # We need a plain string here, NOT unicode! |
|
251 | 255 | hdef = oname + inspect.formatargspec(*getargspec(obj)) |
|
252 |
return hdef |
|
|
256 | return py3compat.unicode_to_str(hdef, 'ascii') | |
|
253 | 257 | except: |
|
254 | 258 | return None |
|
255 | 259 | |
@@ -362,7 +366,7 b' class Inspector:' | |||
|
362 | 366 | except: |
|
363 | 367 | self.noinfo('source',oname) |
|
364 | 368 | else: |
|
365 | page.page(self.format(src)) | |
|
369 | page.page(self.format(py3compat.unicode_to_str(src))) | |
|
366 | 370 | |
|
367 | 371 | def pfile(self,obj,oname=''): |
|
368 | 372 | """Show the whole file where an object was defined.""" |
@@ -455,7 +459,7 b' class Inspector:' | |||
|
455 | 459 | # Source or docstring, depending on detail level and whether |
|
456 | 460 | # source found. |
|
457 | 461 | if detail_level > 0 and info['source'] is not None: |
|
458 | displayfields.append(("Source", info['source'])) | |
|
462 | displayfields.append(("Source", self.format(py3compat.unicode_to_str(info['source'])))) | |
|
459 | 463 | elif info['docstring'] is not None: |
|
460 | 464 | displayfields.append(("Docstring", info["docstring"])) |
|
461 | 465 | |
@@ -604,12 +608,11 b' class Inspector:' | |||
|
604 | 608 | source = None |
|
605 | 609 | try: |
|
606 | 610 | try: |
|
607 | src = getsource(obj,binary_file) | |
|
611 | source = getsource(obj,binary_file) | |
|
608 | 612 | except TypeError: |
|
609 | 613 | if hasattr(obj,'__class__'): |
|
610 | src = getsource(obj.__class__,binary_file) | |
|
611 | if src is not None: | |
|
612 | source = self.format(src) | |
|
614 | source = getsource(obj.__class__,binary_file) | |
|
615 | if source is not None: | |
|
613 | 616 | out['source'] = source.rstrip() |
|
614 | 617 | except Exception: |
|
615 | 618 | pass |
@@ -32,7 +32,7 b' from IPython.core.alias import AliasManager' | |||
|
32 | 32 | from IPython.core.autocall import IPyAutocall |
|
33 | 33 | from IPython.config.configurable import Configurable |
|
34 | 34 | from IPython.core.macro import Macro |
|
35 | from IPython.core.splitinput import split_user_input | |
|
35 | from IPython.core.splitinput import split_user_input, LineInfo | |
|
36 | 36 | from IPython.core import page |
|
37 | 37 | |
|
38 | 38 | from IPython.utils.traitlets import List, Int, Any, Unicode, CBool, Bool, Instance |
@@ -92,78 +92,6 b' def is_shadowed(identifier, ip):' | |||
|
92 | 92 | |
|
93 | 93 | |
|
94 | 94 | #----------------------------------------------------------------------------- |
|
95 | # The LineInfo class used throughout | |
|
96 | #----------------------------------------------------------------------------- | |
|
97 | ||
|
98 | ||
|
99 | class LineInfo(object): | |
|
100 | """A single line of input and associated info. | |
|
101 | ||
|
102 | Includes the following as properties: | |
|
103 | ||
|
104 | line | |
|
105 | The original, raw line | |
|
106 | ||
|
107 | continue_prompt | |
|
108 | Is this line a continuation in a sequence of multiline input? | |
|
109 | ||
|
110 | pre | |
|
111 | The initial esc character or whitespace. | |
|
112 | ||
|
113 | pre_char | |
|
114 | The escape character(s) in pre or the empty string if there isn't one. | |
|
115 | Note that '!!' is a possible value for pre_char. Otherwise it will | |
|
116 | always be a single character. | |
|
117 | ||
|
118 | pre_whitespace | |
|
119 | The leading whitespace from pre if it exists. If there is a pre_char, | |
|
120 | this is just ''. | |
|
121 | ||
|
122 | ifun | |
|
123 | The 'function part', which is basically the maximal initial sequence | |
|
124 | of valid python identifiers and the '.' character. This is what is | |
|
125 | checked for alias and magic transformations, used for auto-calling, | |
|
126 | etc. | |
|
127 | ||
|
128 | the_rest | |
|
129 | Everything else on the line. | |
|
130 | """ | |
|
131 | def __init__(self, line, continue_prompt): | |
|
132 | self.line = line | |
|
133 | self.continue_prompt = continue_prompt | |
|
134 | self.pre, self.ifun, self.the_rest = split_user_input(line) | |
|
135 | ||
|
136 | self.pre_char = self.pre.strip() | |
|
137 | if self.pre_char: | |
|
138 | self.pre_whitespace = '' # No whitespace allowd before esc chars | |
|
139 | else: | |
|
140 | self.pre_whitespace = self.pre | |
|
141 | ||
|
142 | self._oinfo = None | |
|
143 | ||
|
144 | def ofind(self, ip): | |
|
145 | """Do a full, attribute-walking lookup of the ifun in the various | |
|
146 | namespaces for the given IPython InteractiveShell instance. | |
|
147 | ||
|
148 | Return a dict with keys: found,obj,ospace,ismagic | |
|
149 | ||
|
150 | Note: can cause state changes because of calling getattr, but should | |
|
151 | only be run if autocall is on and if the line hasn't matched any | |
|
152 | other, less dangerous handlers. | |
|
153 | ||
|
154 | Does cache the results of the call, so can be called multiple times | |
|
155 | without worrying about *further* damaging state. | |
|
156 | """ | |
|
157 | if not self._oinfo: | |
|
158 | # ip.shell._ofind is actually on the Magic class! | |
|
159 | self._oinfo = ip.shell._ofind(self.ifun) | |
|
160 | return self._oinfo | |
|
161 | ||
|
162 | def __str__(self): | |
|
163 | return "Lineinfo [%s|%s|%s]" %(self.pre, self.ifun, self.the_rest) | |
|
164 | ||
|
165 | ||
|
166 | #----------------------------------------------------------------------------- | |
|
167 | 95 | # Main Prefilter manager |
|
168 | 96 | #----------------------------------------------------------------------------- |
|
169 | 97 | |
@@ -630,7 +558,7 b' class MultiLineMagicChecker(PrefilterChecker):' | |||
|
630 | 558 | # both ! and !!. |
|
631 | 559 | if line_info.continue_prompt \ |
|
632 | 560 | and self.prefilter_manager.multi_line_specials: |
|
633 |
if line_info. |
|
|
561 | if line_info.esc == ESC_MAGIC: | |
|
634 | 562 | return self.prefilter_manager.get_handler_by_name('magic') |
|
635 | 563 | else: |
|
636 | 564 | return None |
@@ -644,14 +572,16 b' class EscCharsChecker(PrefilterChecker):' | |||
|
644 | 572 | """Check for escape character and return either a handler to handle it, |
|
645 | 573 | or None if there is no escape char.""" |
|
646 | 574 | if line_info.line[-1] == ESC_HELP \ |
|
647 |
and line_info. |
|
|
648 |
and line_info. |
|
|
575 | and line_info.esc != ESC_SHELL \ | |
|
576 | and line_info.esc != ESC_SH_CAP: | |
|
649 | 577 | # the ? can be at the end, but *not* for either kind of shell escape, |
|
650 | 578 | # because a ? can be a vaild final char in a shell cmd |
|
651 | 579 | return self.prefilter_manager.get_handler_by_name('help') |
|
652 | 580 | else: |
|
581 | if line_info.pre: | |
|
582 | return None | |
|
653 | 583 | # This returns None like it should if no handler exists |
|
654 |
return self.prefilter_manager.get_handler_by_esc(line_info. |
|
|
584 | return self.prefilter_manager.get_handler_by_esc(line_info.esc) | |
|
655 | 585 | |
|
656 | 586 | |
|
657 | 587 | class AssignmentChecker(PrefilterChecker): |
@@ -872,6 +802,7 b' class AutoHandler(PrefilterHandler):' | |||
|
872 | 802 | ifun = line_info.ifun |
|
873 | 803 | the_rest = line_info.the_rest |
|
874 | 804 | pre = line_info.pre |
|
805 | esc = line_info.esc | |
|
875 | 806 | continue_prompt = line_info.continue_prompt |
|
876 | 807 | obj = line_info.ofind(self)['obj'] |
|
877 | 808 | #print 'pre <%s> ifun <%s> rest <%s>' % (pre,ifun,the_rest) # dbg |
@@ -883,13 +814,13 b' class AutoHandler(PrefilterHandler):' | |||
|
883 | 814 | force_auto = isinstance(obj, IPyAutocall) |
|
884 | 815 | auto_rewrite = getattr(obj, 'rewrite', True) |
|
885 | 816 | |
|
886 |
if |
|
|
817 | if esc == ESC_QUOTE: | |
|
887 | 818 | # Auto-quote splitting on whitespace |
|
888 | 819 | newcmd = '%s("%s")' % (ifun,'", "'.join(the_rest.split()) ) |
|
889 |
elif |
|
|
820 | elif esc == ESC_QUOTE2: | |
|
890 | 821 | # Auto-quote whole string |
|
891 | 822 | newcmd = '%s("%s")' % (ifun,the_rest) |
|
892 |
elif |
|
|
823 | elif esc == ESC_PAREN: | |
|
893 | 824 | newcmd = '%s(%s)' % (ifun,",".join(the_rest.split())) |
|
894 | 825 | else: |
|
895 | 826 | # Auto-paren. |
@@ -946,7 +877,7 b' class HelpHandler(PrefilterHandler):' | |||
|
946 | 877 | line = line[:-1] |
|
947 | 878 | if line: |
|
948 | 879 | #print 'line:<%r>' % line # dbg |
|
949 | self.shell.magic_pinfo(line) | |
|
880 | self.shell.magic_pinfo(line_info.ifun) | |
|
950 | 881 | else: |
|
951 | 882 | self.shell.show_usage() |
|
952 | 883 | return '' # Empty string is needed here! |
@@ -123,3 +123,18 b" download_url = 'http://archive.ipython.org/release/%s' % version" | |||
|
123 | 123 | platforms = ['Linux','Mac OSX','Windows XP/2000/NT'] |
|
124 | 124 | |
|
125 | 125 | keywords = ['Interactive','Interpreter','Shell','Parallel','Distributed'] |
|
126 | ||
|
127 | classifiers = [ | |
|
128 | 'Intended Audience :: Developers', | |
|
129 | 'Intended Audience :: Science/Research' | |
|
130 | 'License :: OSI Approved :: BSD License', | |
|
131 | 'Programming Language :: Python', | |
|
132 | 'Programming Language :: Python :: 2', | |
|
133 | 'Programming Language :: Python :: 2.6', | |
|
134 | 'Programming Language :: Python :: 2.7', | |
|
135 | 'Programming Language :: Python :: 3', | |
|
136 | 'Programming Language :: Python :: 3.1', | |
|
137 | 'Programming Language :: Python :: 3.2', | |
|
138 | 'Topic :: System :: Distributed Computing', | |
|
139 | 'Topic :: System :: Shells' | |
|
140 | ] |
@@ -1,6 +1,7 b'' | |||
|
1 | 1 | # encoding: utf-8 |
|
2 | 2 | """ |
|
3 | Simple utility for splitting user input. | |
|
3 | Simple utility for splitting user input. This is used by both inputsplitter and | |
|
4 | prefilter. | |
|
4 | 5 | |
|
5 | 6 | Authors: |
|
6 | 7 | |
@@ -22,45 +23,37 b' Authors:' | |||
|
22 | 23 | import re |
|
23 | 24 | import sys |
|
24 | 25 | |
|
26 | from IPython.utils import py3compat | |
|
27 | ||
|
25 | 28 | #----------------------------------------------------------------------------- |
|
26 | 29 | # Main function |
|
27 | 30 | #----------------------------------------------------------------------------- |
|
28 | 31 | |
|
29 | ||
|
30 | 32 | # RegExp for splitting line contents into pre-char//first word-method//rest. |
|
31 | 33 | # For clarity, each group in on one line. |
|
32 | 34 | |
|
33 |
# WARNING: update the regexp if the escapes in interactiveshell are changed, as |
|
|
34 | # are hardwired in. | |
|
35 | # WARNING: update the regexp if the escapes in interactiveshell are changed, as | |
|
36 | # they are hardwired in. | |
|
35 | 37 | |
|
36 | 38 | # Although it's not solely driven by the regex, note that: |
|
37 | 39 | # ,;/% only trigger if they are the first character on the line |
|
38 | 40 | # ! and !! trigger if they are first char(s) *or* follow an indent |
|
39 | 41 | # ? triggers as first or last char. |
|
40 | 42 | |
|
41 | # The three parts of the regex are: | |
|
42 | # 1) pre: pre_char *or* initial whitespace | |
|
43 | # 2) ifun: first word/method (mix of \w and '.') | |
|
44 | # 3) the_rest: rest of line (separated from ifun by space if non-empty) | |
|
45 | line_split = re.compile(r'^([,;/%?]|!!?|\s*)' | |
|
46 | r'\s*([\w\.]+)' | |
|
47 | r'(\s+.*$|$)') | |
|
48 | ||
|
49 | # r'[\w\.]+' | |
|
50 | # r'\s*=\s*%.*' | |
|
43 | line_split = re.compile(""" | |
|
44 | ^(\s*) # any leading space | |
|
45 | ([,;/%]|!!?|\?\??)? # escape character or characters | |
|
46 | \s*(%?[\w\.\*]*) # function/method, possibly with leading % | |
|
47 | # to correctly treat things like '?%magic' | |
|
48 | (.*?$|$) # rest of line | |
|
49 | """, re.VERBOSE) | |
|
51 | 50 | |
|
52 | 51 | def split_user_input(line, pattern=None): |
|
53 |
"""Split user input into |
|
|
54 | ||
|
55 | This is currently handles lines with '=' in them in a very inconsistent | |
|
56 | manner. | |
|
52 | """Split user input into initial whitespace, escape character, function part | |
|
53 | and the rest. | |
|
57 | 54 | """ |
|
58 | 55 | # We need to ensure that the rest of this routine deals only with unicode |
|
59 | if type(line)==str: | |
|
60 | codec = sys.stdin.encoding | |
|
61 | if codec is None: | |
|
62 | codec = 'utf-8' | |
|
63 | line = line.decode(codec) | |
|
56 | line = py3compat.cast_unicode(line, sys.stdin.encoding or 'utf-8') | |
|
64 | 57 | |
|
65 | 58 | if pattern is None: |
|
66 | 59 | pattern = line_split |
@@ -73,18 +66,73 b' def split_user_input(line, pattern=None):' | |||
|
73 | 66 | # print "split failed for line '%s'" % line |
|
74 | 67 | ifun, the_rest = line, u'' |
|
75 | 68 | pre = re.match('^(\s*)(.*)',line).groups()[0] |
|
69 | esc = "" | |
|
76 | 70 | else: |
|
77 | pre,ifun,the_rest = match.groups() | |
|
78 | ||
|
79 | # ifun has to be a valid python identifier, so it better encode into | |
|
80 | # ascii. We do still make it a unicode string so that we consistently | |
|
81 | # return unicode, but it will be one that is guaranteed to be pure ascii | |
|
82 | try: | |
|
83 | ifun = unicode(ifun.encode('ascii')) | |
|
84 | except UnicodeEncodeError: | |
|
85 | the_rest = ifun + u' ' + the_rest | |
|
86 | ifun = u'' | |
|
71 | pre, esc, ifun, the_rest = match.groups() | |
|
87 | 72 | |
|
88 | 73 | #print 'line:<%s>' % line # dbg |
|
89 | 74 | #print 'pre <%s> ifun <%s> rest <%s>' % (pre,ifun.strip(),the_rest) # dbg |
|
90 | return pre, ifun.strip(), the_rest.lstrip() | |
|
75 | return pre, esc or '', ifun.strip(), the_rest.lstrip() | |
|
76 | ||
|
77 | class LineInfo(object): | |
|
78 | """A single line of input and associated info. | |
|
79 | ||
|
80 | Includes the following as properties: | |
|
81 | ||
|
82 | line | |
|
83 | The original, raw line | |
|
84 | ||
|
85 | continue_prompt | |
|
86 | Is this line a continuation in a sequence of multiline input? | |
|
87 | ||
|
88 | pre | |
|
89 | Any leading whitespace. | |
|
90 | ||
|
91 | esc | |
|
92 | The escape character(s) in pre or the empty string if there isn't one. | |
|
93 | Note that '!!' and '??' are possible values for esc. Otherwise it will | |
|
94 | always be a single character. | |
|
95 | ||
|
96 | ifun | |
|
97 | The 'function part', which is basically the maximal initial sequence | |
|
98 | of valid python identifiers and the '.' character. This is what is | |
|
99 | checked for alias and magic transformations, used for auto-calling, | |
|
100 | etc. In contrast to Python identifiers, it may start with "%" and contain | |
|
101 | "*". | |
|
102 | ||
|
103 | the_rest | |
|
104 | Everything else on the line. | |
|
105 | """ | |
|
106 | def __init__(self, line, continue_prompt=False): | |
|
107 | self.line = line | |
|
108 | self.continue_prompt = continue_prompt | |
|
109 | self.pre, self.esc, self.ifun, self.the_rest = split_user_input(line) | |
|
110 | ||
|
111 | self.pre_char = self.pre.strip() | |
|
112 | if self.pre_char: | |
|
113 | self.pre_whitespace = '' # No whitespace allowd before esc chars | |
|
114 | else: | |
|
115 | self.pre_whitespace = self.pre | |
|
116 | ||
|
117 | self._oinfo = None | |
|
118 | ||
|
119 | def ofind(self, ip): | |
|
120 | """Do a full, attribute-walking lookup of the ifun in the various | |
|
121 | namespaces for the given IPython InteractiveShell instance. | |
|
122 | ||
|
123 | Return a dict with keys: found,obj,ospace,ismagic | |
|
124 | ||
|
125 | Note: can cause state changes because of calling getattr, but should | |
|
126 | only be run if autocall is on and if the line hasn't matched any | |
|
127 | other, less dangerous handlers. | |
|
128 | ||
|
129 | Does cache the results of the call, so can be called multiple times | |
|
130 | without worrying about *further* damaging state. | |
|
131 | """ | |
|
132 | if not self._oinfo: | |
|
133 | # ip.shell._ofind is actually on the Magic class! | |
|
134 | self._oinfo = ip.shell._ofind(self.ifun) | |
|
135 | return self._oinfo | |
|
136 | ||
|
137 | def __str__(self): | |
|
138 | return "LineInfo [%s|%s|%s|%s]" %(self.pre, self.esc, self.ifun, self.the_rest) |
@@ -2,6 +2,8 b'' | |||
|
2 | 2 | |
|
3 | 3 | See test_run for details.""" |
|
4 | 4 | |
|
5 | from __future__ import print_function | |
|
6 | ||
|
5 | 7 | import sys |
|
6 | 8 | |
|
7 | 9 | # We want to ensure that while objects remain available for immediate access, |
@@ -10,10 +12,11 b' import sys' | |||
|
10 | 12 | class C(object): |
|
11 | 13 | def __init__(self,name): |
|
12 | 14 | self.name = name |
|
15 | self.p = print | |
|
13 | 16 | self.flush_stdout = sys.stdout.flush |
|
14 | 17 | |
|
15 | 18 | def __del__(self): |
|
16 |
|
|
|
19 | self.p('tclass.py: deleting object:',self.name) | |
|
17 | 20 | self.flush_stdout() |
|
18 | 21 | |
|
19 | 22 | try: |
@@ -28,5 +31,5 b' else:' | |||
|
28 | 31 | |
|
29 | 32 | # This next print statement is NOT debugging, we're making the check on a |
|
30 | 33 | # completely separate process so we verify by capturing stdout: |
|
31 |
print |
|
|
34 | print('ARGV 1-:', sys.argv[1:]) | |
|
32 | 35 | sys.stdout.flush() |
@@ -6,6 +6,7 b' import tempfile' | |||
|
6 | 6 | |
|
7 | 7 | from IPython.core.application import BaseIPythonApplication |
|
8 | 8 | from IPython.testing import decorators as testdec |
|
9 | from IPython.utils import py3compat | |
|
9 | 10 | |
|
10 | 11 | @testdec.onlyif_unicode_paths |
|
11 | 12 | def test_unicode_cwd(): |
@@ -35,7 +36,7 b' def test_unicode_ipdir():' | |||
|
35 | 36 | |
|
36 | 37 | old_ipdir1 = os.environ.pop("IPYTHONDIR", None) |
|
37 | 38 | old_ipdir2 = os.environ.pop("IPYTHON_DIR", None) |
|
38 |
os.environ["IPYTHONDIR"] = ipdir |
|
|
39 | os.environ["IPYTHONDIR"] = py3compat.unicode_to_str(ipdir, "utf-8") | |
|
39 | 40 | try: |
|
40 | 41 | app = BaseIPythonApplication() |
|
41 | 42 | # The lines below are copied from Application.initialize() |
@@ -23,6 +23,7 b' import nose.tools as nt' | |||
|
23 | 23 | |
|
24 | 24 | # Our own imports |
|
25 | 25 | from IPython.core import compilerop |
|
26 | from IPython.utils import py3compat | |
|
26 | 27 | |
|
27 | 28 | #----------------------------------------------------------------------------- |
|
28 | 29 | # Test functions |
@@ -51,7 +52,7 b' def test_cache():' | |||
|
51 | 52 | def setUp(): |
|
52 | 53 | # Check we're in a proper Python 2 environment (some imports, such |
|
53 | 54 | # as GTK, can change the default encoding, which can hide bugs.) |
|
54 | nt.assert_equal(sys.getdefaultencoding(), "ascii") | |
|
55 | nt.assert_equal(sys.getdefaultencoding(), "utf-8" if py3compat.PY3 else "ascii") | |
|
55 | 56 | |
|
56 | 57 | def test_cache_unicode(): |
|
57 | 58 | cp = compilerop.CachingCompiler() |
@@ -10,6 +10,7 b' import nose.tools as nt' | |||
|
10 | 10 | # our own packages |
|
11 | 11 | from IPython.core import autocall |
|
12 | 12 | from IPython.testing import decorators as dec |
|
13 | from IPython.testing import tools as tt | |
|
13 | 14 | from IPython.testing.globalipapp import get_ipython |
|
14 | 15 | |
|
15 | 16 | #----------------------------------------------------------------------------- |
@@ -40,15 +41,7 b' def run(tests):' | |||
|
40 | 41 | """Loop through a list of (pre, post) inputs, where pre is the string |
|
41 | 42 | handed to ipython, and post is how that string looks after it's been |
|
42 | 43 | transformed (i.e. ipython's notion of _i)""" |
|
43 | for pre, post in tests: | |
|
44 | global num_tests | |
|
45 | num_tests += 1 | |
|
46 | actual = ip.prefilter_manager.prefilter_lines(pre) | |
|
47 | if actual != None: | |
|
48 | actual = actual.rstrip('\n') | |
|
49 | if actual != post: | |
|
50 | failures.append('Expected %r to become %r, found %r' % ( | |
|
51 | pre, post, actual)) | |
|
44 | tt.check_pairs(ip.prefilter_manager.prefilter_lines, tests) | |
|
52 | 45 | |
|
53 | 46 | |
|
54 | 47 | def test_handlers(): |
@@ -16,9 +16,10 b' import nose.tools as nt' | |||
|
16 | 16 | # our own packages |
|
17 | 17 | from IPython.utils.tempdir import TemporaryDirectory |
|
18 | 18 | from IPython.core.history import HistoryManager, extract_hist_ranges |
|
19 | from IPython.utils import py3compat | |
|
19 | 20 | |
|
20 | 21 | def setUp(): |
|
21 | nt.assert_equal(sys.getdefaultencoding(), "ascii") | |
|
22 | nt.assert_equal(sys.getdefaultencoding(), "utf-8" if py3compat.PY3 else "ascii") | |
|
22 | 23 | |
|
23 | 24 | def test_history(): |
|
24 | 25 | ip = get_ipython() |
@@ -125,7 +125,7 b' def test_get_input_encoding():' | |||
|
125 | 125 | nt.assert_true(isinstance(encoding, basestring)) |
|
126 | 126 | # simple-minded check that at least encoding a simple string works with the |
|
127 | 127 | # encoding we got. |
|
128 | nt.assert_equal('test'.encode(encoding), 'test') | |
|
128 | nt.assert_equal(u'test'.encode(encoding), b'test') | |
|
129 | 129 | |
|
130 | 130 | |
|
131 | 131 | class NoInputEncodingTestCase(unittest.TestCase): |
@@ -390,15 +390,6 b' def test_LineInfo():' | |||
|
390 | 390 | linfo = isp.LineInfo(' %cd /home') |
|
391 | 391 | nt.assert_equals(str(linfo), 'LineInfo [ |%|cd|/home]') |
|
392 | 392 | |
|
393 | ||
|
394 | def test_split_user_input(): | |
|
395 | """Unicode test - split_user_input already has good doctests""" | |
|
396 | line = u"PΓ©rez Fernando" | |
|
397 | parts = isp.split_user_input(line) | |
|
398 | parts_expected = (u'', u'', u'', line) | |
|
399 | nt.assert_equal(parts, parts_expected) | |
|
400 | ||
|
401 | ||
|
402 | 393 | # Transformer tests |
|
403 | 394 | def transform_checker(tests, func): |
|
404 | 395 | """Utility to loop over test inputs""" |
@@ -611,7 +602,8 b' class IPythonInputTestCase(InputSplitterTestCase):' | |||
|
611 | 602 | |
|
612 | 603 | isp.push(raw) |
|
613 | 604 | out, out_raw = isp.source_raw_reset() |
|
614 |
self.assertEqual(out.rstrip(), out_t |
|
|
605 | self.assertEqual(out.rstrip(), out_t, | |
|
606 | tt.pair_fail_msg.format("inputsplitter",raw, out_t, out)) | |
|
615 | 607 | self.assertEqual(out_raw.rstrip(), raw.rstrip()) |
|
616 | 608 | |
|
617 | 609 | def test_syntax_multiline(self): |
@@ -75,7 +75,7 b' Traceback (most recent call last):' | |||
|
75 | 75 | div0() |
|
76 | 76 | ...line 8, in div0 |
|
77 | 77 | x/y |
|
78 | ZeroDivisionError: integer division or modulo by zero | |
|
78 | ZeroDivisionError: ... | |
|
79 | 79 | """ |
|
80 | 80 | |
|
81 | 81 | |
@@ -107,7 +107,7 b' ZeroDivisionError Traceback (most recent call last)' | |||
|
107 | 107 | 9 |
|
108 | 108 | 10 def sysexit(stat, mode): |
|
109 | 109 | <BLANKLINE> |
|
110 | ZeroDivisionError: integer division or modulo by zero | |
|
110 | ZeroDivisionError: ... | |
|
111 | 111 | """ |
|
112 | 112 | |
|
113 | 113 | |
@@ -144,7 +144,7 b' ZeroDivisionError Traceback (most recent call last)' | |||
|
144 | 144 | 9 |
|
145 | 145 | 10 def sysexit(stat, mode): |
|
146 | 146 | <BLANKLINE> |
|
147 | ZeroDivisionError: integer division or modulo by zero | |
|
147 | ZeroDivisionError: ... | |
|
148 | 148 | """ |
|
149 | 149 | |
|
150 | 150 |
@@ -20,6 +20,7 b' import nose.tools as nt' | |||
|
20 | 20 | |
|
21 | 21 | # Our own imports |
|
22 | 22 | from .. import oinspect |
|
23 | from IPython.utils import py3compat | |
|
23 | 24 | |
|
24 | 25 | #----------------------------------------------------------------------------- |
|
25 | 26 | # Globals and constants |
@@ -96,7 +97,8 b' def test_info():' | |||
|
96 | 97 | "Check that Inspector.info fills out various fields as expected." |
|
97 | 98 | i = inspector.info(Call, oname='Call') |
|
98 | 99 | nt.assert_equal(i['type_name'], 'type') |
|
99 | nt.assert_equal(i['base_class'], "<type 'type'>") | |
|
100 | expted_class = str(type(type)) # <class 'type'> (Python 3) or <type 'type'> | |
|
101 | nt.assert_equal(i['base_class'], expted_class) | |
|
100 | 102 | nt.assert_equal(i['string_form'], "<class 'IPython.core.tests.test_oinspect.Call'>") |
|
101 | 103 | fname = __file__ |
|
102 | 104 | if fname.endswith(".pyc"): |
@@ -125,9 +127,10 b' def test_info():' | |||
|
125 | 127 | nt.assert_equal(i['call_docstring'], c.__call__.__doc__) |
|
126 | 128 | |
|
127 | 129 | # Test old-style classes, which for example may not have an __init__ method. |
|
128 | i = inspector.info(OldStyle) | |
|
129 | nt.assert_equal(i['type_name'], 'classobj') | |
|
130 | ||
|
131 | i = inspector.info(OldStyle()) | |
|
132 | nt.assert_equal(i['type_name'], 'instance') | |
|
133 |
nt.assert_equal(i[' |
|
|
130 | if not py3compat.PY3: | |
|
131 | i = inspector.info(OldStyle) | |
|
132 | nt.assert_equal(i['type_name'], 'classobj') | |
|
133 | ||
|
134 | i = inspector.info(OldStyle()) | |
|
135 | nt.assert_equal(i['type_name'], 'instance') | |
|
136 | nt.assert_equal(i['docstring'], OldStyle.__doc__) |
@@ -83,6 +83,11 b' import tokenize' | |||
|
83 | 83 | import traceback |
|
84 | 84 | import types |
|
85 | 85 | |
|
86 | try: # Python 2 | |
|
87 | generate_tokens = tokenize.generate_tokens | |
|
88 | except AttributeError: # Python 3 | |
|
89 | generate_tokens = tokenize.tokenize | |
|
90 | ||
|
86 | 91 | # For purposes of monkeypatching inspect to fix a bug in it. |
|
87 | 92 | from inspect import getsourcefile, getfile, getmodule,\ |
|
88 | 93 | ismodule, isclass, ismethod, isfunction, istraceback, isframe, iscode |
@@ -94,6 +99,7 b' from IPython.core.display_trap import DisplayTrap' | |||
|
94 | 99 | from IPython.core.excolors import exception_colors |
|
95 | 100 | from IPython.utils import PyColorize |
|
96 | 101 | from IPython.utils import io |
|
102 | from IPython.utils import py3compat | |
|
97 | 103 | from IPython.utils.data import uniq_stable |
|
98 | 104 | from IPython.utils.warn import info, error |
|
99 | 105 | |
@@ -278,8 +284,7 b' def _format_traceback_lines(lnum, index, lines, Colors, lvals=None,scheme=None):' | |||
|
278 | 284 | # serious refactoring, so that all of the ultratb and PyColorize code |
|
279 | 285 | # is unicode-safe. So for now this is rather an ugly hack, but |
|
280 | 286 | # necessary to at least have readable tracebacks. Improvements welcome! |
|
281 | if type(line)==unicode: | |
|
282 | line = line.encode('utf-8', 'replace') | |
|
287 | line = py3compat.cast_bytes_py2(line, 'utf-8') | |
|
283 | 288 | |
|
284 | 289 | new_line, err = _line_format(line, 'str', scheme) |
|
285 | 290 | if not err: line = new_line |
@@ -872,7 +877,8 b' class VerboseTB(TBTools):' | |||
|
872 | 877 | try: |
|
873 | 878 | # This builds the names list in-place by capturing it from the |
|
874 | 879 | # enclosing scope. |
|
875 |
|
|
|
880 | for token in generate_tokens(linereader): | |
|
881 | tokeneater(*token) | |
|
876 | 882 | except IndexError: |
|
877 | 883 | # signals exit of tokenizer |
|
878 | 884 | pass |
@@ -933,7 +939,7 b' class VerboseTB(TBTools):' | |||
|
933 | 939 | # ... and format it |
|
934 | 940 | exception = ['%s%s%s: %s' % (Colors.excName, etype_str, |
|
935 | 941 | ColorsNormal, evalue_str)] |
|
936 | if type(evalue) is types.InstanceType: | |
|
942 | if (not py3compat.PY3) and type(evalue) is types.InstanceType: | |
|
937 | 943 | try: |
|
938 | 944 | names = [w for w in dir(evalue) if isinstance(w, basestring)] |
|
939 | 945 | except: |
@@ -1,20 +1,24 b'' | |||
|
1 | """This is version 0.7 of Philip J. Eby's simplegeneric module | |
|
2 | (http://pypi.python.org/pypi/simplegeneric), patched to work with Python 3, | |
|
3 | which doesn't support old-style classes. | |
|
4 | """ | |
|
5 | ||
|
1 | 6 | #Name: simplegeneric |
|
2 |
#Version: 0. |
|
|
7 | #Version: 0.7 | |
|
3 | 8 | #Summary: Simple generic functions (similar to Python's own len(), pickle.dump(), etc.) |
|
4 |
#Home-page: http:// |
|
|
9 | #Home-page: http://pypi.python.org/pypi/simplegeneric | |
|
5 | 10 | #Author: Phillip J. Eby |
|
6 | 11 | #Author-email: peak@eby-sarna.com |
|
7 | 12 | #License: PSF or ZPL |
|
8 | 13 | |
|
9 | # This is version 0.6 of Philip J. Eby's simplegeneric module | |
|
10 | # (http://cheeseshop.python.org/pypi/simplegeneric) patched to work | |
|
11 | # with Python 2.3 (which doesn't support assigning to __name__) | |
|
12 | ||
|
13 | 14 | __all__ = ["generic"] |
|
14 | 15 | |
|
15 | ||
|
16 | from types import ClassType, InstanceType | |
|
17 | classtypes = type, ClassType | |
|
16 | try: | |
|
17 | from types import ClassType, InstanceType | |
|
18 | except ImportError: | |
|
19 | classtypes = type | |
|
20 | else: | |
|
21 | classtypes = type, ClassType | |
|
18 | 22 | |
|
19 | 23 | def generic(func): |
|
20 | 24 | """Create a simple generic function""" |
@@ -30,38 +34,44 b' def generic(func):' | |||
|
30 | 34 | else: |
|
31 | 35 | return func(*args, **kw) |
|
32 | 36 | |
|
33 |
_by_type = {object: func |
|
|
37 | _by_type = {object: func} | |
|
38 | try: | |
|
39 | _by_type[InstanceType] = _by_class | |
|
40 | except NameError: # Python 3 | |
|
41 | pass | |
|
42 | ||
|
34 | 43 | _gbt = _by_type.get |
|
35 | 44 | |
|
36 | def when_type(t): | |
|
37 |
"""Decorator to add a method that will be called for t |
|
|
38 |
|
|
|
39 | raise TypeError( | |
|
40 | "%r is not a type or class" % (t,) | |
|
41 | ) | |
|
42 | def decorate(f): | |
|
43 | if _by_type.setdefault(t,f) is not f: | |
|
45 | def when_type(*types): | |
|
46 | """Decorator to add a method that will be called for the given types""" | |
|
47 | for t in types: | |
|
48 | if not isinstance(t, classtypes): | |
|
44 | 49 | raise TypeError( |
|
45 |
"%r |
|
|
50 | "%r is not a type or class" % (t,) | |
|
46 | 51 | ) |
|
52 | def decorate(f): | |
|
53 | for t in types: | |
|
54 | if _by_type.setdefault(t,f) is not f: | |
|
55 | raise TypeError( | |
|
56 | "%r already has method for type %r" % (func, t) | |
|
57 | ) | |
|
47 | 58 | return f |
|
48 | 59 | return decorate |
|
49 | 60 | |
|
50 | 61 | |
|
51 | 62 | |
|
52 | 63 | |
|
53 | ||
|
54 | ||
|
55 | 64 | _by_object = {} |
|
56 | 65 | _gbo = _by_object.get |
|
57 | 66 | |
|
58 | def when_object(o): | |
|
59 |
"""Decorator to add a method t |
|
|
67 | def when_object(*obs): | |
|
68 | """Decorator to add a method to be called for the given object(s)""" | |
|
60 | 69 | def decorate(f): |
|
61 | if _by_object.setdefault(id(o), (o,f))[1] is not f: | |
|
62 | raise TypeError( | |
|
63 | "%r already has method for object %r" % (func, o) | |
|
64 | ) | |
|
70 | for o in obs: | |
|
71 | if _by_object.setdefault(id(o), (o,f))[1] is not f: | |
|
72 | raise TypeError( | |
|
73 | "%r already has method for object %r" % (func, o) | |
|
74 | ) | |
|
65 | 75 | return f |
|
66 | 76 | return decorate |
|
67 | 77 | |
@@ -78,10 +88,7 b' def generic(func):' | |||
|
78 | 88 | else: |
|
79 | 89 | return f[1](*args, **kw) |
|
80 | 90 | |
|
81 | try: | |
|
82 | dispatch.__name__ = func.__name__ | |
|
83 | except TypeError: | |
|
84 | pass | |
|
91 | dispatch.__name__ = func.__name__ | |
|
85 | 92 | dispatch.__dict__ = func.__dict__.copy() |
|
86 | 93 | dispatch.__doc__ = func.__doc__ |
|
87 | 94 | dispatch.__module__ = func.__module__ |
@@ -94,46 +101,9 b' def generic(func):' | |||
|
94 | 101 | return dispatch |
|
95 | 102 | |
|
96 | 103 | |
|
97 | ||
|
98 | ||
|
99 | 104 | def test_suite(): |
|
100 | 105 | import doctest |
|
101 | 106 | return doctest.DocFileSuite( |
|
102 | 107 | 'README.txt', |
|
103 | 108 | optionflags=doctest.ELLIPSIS|doctest.REPORT_ONLY_FIRST_FAILURE, |
|
104 | 109 | ) |
|
105 | ||
|
106 | ||
|
107 | ||
|
108 | ||
|
109 | ||
|
110 | ||
|
111 | ||
|
112 | ||
|
113 | ||
|
114 | ||
|
115 | ||
|
116 | ||
|
117 | ||
|
118 | ||
|
119 | ||
|
120 | ||
|
121 | ||
|
122 | ||
|
123 | ||
|
124 | ||
|
125 | ||
|
126 | ||
|
127 | ||
|
128 | ||
|
129 | ||
|
130 | ||
|
131 | ||
|
132 | ||
|
133 | ||
|
134 | ||
|
135 | ||
|
136 | ||
|
137 | ||
|
138 | ||
|
139 |
@@ -83,7 +83,7 b' class RichIPythonWidget(IPythonWidget):' | |||
|
83 | 83 | self._append_html(self._make_out_prompt(prompt_number), True) |
|
84 | 84 | # This helps the output to look nice. |
|
85 | 85 | self._append_plain_text('\n', True) |
|
86 | self._append_png(decodestring(data['image/png']), True) | |
|
86 | self._append_png(decodestring(data['image/png'].encode('ascii')), True) | |
|
87 | 87 | self._append_html(self.output_sep2, True) |
|
88 | 88 | else: |
|
89 | 89 | # Default back to the plain text representation. |
@@ -104,7 +104,7 b' class RichIPythonWidget(IPythonWidget):' | |||
|
104 | 104 | elif data.has_key('image/png'): |
|
105 | 105 | # PNG data is base64 encoded as it passes over the network |
|
106 | 106 | # in a JSON structure so we decode it. |
|
107 | png = decodestring(data['image/png']) | |
|
107 | png = decodestring(data['image/png'].encode('ascii')) | |
|
108 | 108 | self._append_png(png, True) |
|
109 | 109 | else: |
|
110 | 110 | # Default back to the plain text representation. |
@@ -26,7 +26,10 b' from __future__ import with_statement' | |||
|
26 | 26 | import __main__ |
|
27 | 27 | |
|
28 | 28 | import sys |
|
29 | from contextlib import nested | |
|
29 | try: | |
|
30 | from contextlib import nested | |
|
31 | except: | |
|
32 | from IPython.utils.nested_context import nested | |
|
30 | 33 | |
|
31 | 34 | from IPython.core import ultratb |
|
32 | 35 | from IPython.frontend.terminal.interactiveshell import TerminalInteractiveShell |
@@ -16,17 +16,22 b'' | |||
|
16 | 16 | |
|
17 | 17 | import __builtin__ |
|
18 | 18 | import bdb |
|
19 | from contextlib import nested | |
|
20 | 19 | import os |
|
21 | 20 | import re |
|
22 | 21 | import sys |
|
23 | 22 | |
|
23 | try: | |
|
24 | from contextlib import nested | |
|
25 | except: | |
|
26 | from IPython.utils.nested_context import nested | |
|
27 | ||
|
24 | 28 | from IPython.core.error import TryNext |
|
25 | 29 | from IPython.core.usage import interactive_usage, default_banner |
|
26 | 30 | from IPython.core.interactiveshell import InteractiveShell, InteractiveShellABC |
|
27 | 31 | from IPython.lib.inputhook import enable_gui |
|
28 | 32 | from IPython.lib.pylabtools import pylab_activate |
|
29 | 33 | from IPython.testing.skipdoctest import skip_doctest |
|
34 | from IPython.utils import py3compat | |
|
30 | 35 | from IPython.utils.terminal import toggle_set_term_title, set_term_title |
|
31 | 36 | from IPython.utils.process import abbrev_cwd |
|
32 | 37 | from IPython.utils.warn import warn |
@@ -332,7 +337,7 b' class TerminalInteractiveShell(InteractiveShell):' | |||
|
332 | 337 | self.set_readline_completer() |
|
333 | 338 | |
|
334 | 339 | try: |
|
335 |
line = self.raw_input_original(prompt) |
|
|
340 | line = py3compat.str_to_unicode(self.raw_input_original(prompt)) | |
|
336 | 341 | except ValueError: |
|
337 | 342 | warn("\n********\nYou or a %run:ed script called sys.stdin.close()" |
|
338 | 343 | " or sys.stdout.close()!\nExiting IPython!") |
@@ -159,7 +159,10 b' def deep_reload_hook(module):' | |||
|
159 | 159 | return import_module(name[i+1:], name, parent) |
|
160 | 160 | |
|
161 | 161 | # Save the original hooks |
|
162 | original_reload = __builtin__.reload | |
|
162 | try: | |
|
163 | original_reload = __builtin__.reload | |
|
164 | except AttributeError: | |
|
165 | original_reload = imp.reload # Python 3 | |
|
163 | 166 | |
|
164 | 167 | # Replacement for reload() |
|
165 | 168 | def reload(module, exclude=['sys', '__builtin__', '__main__']): |
@@ -169,7 +169,6 b" print 'bye!'" | |||
|
169 | 169 | # |
|
170 | 170 | #***************************************************************************** |
|
171 | 171 | |
|
172 | import exceptions | |
|
173 | 172 | import os |
|
174 | 173 | import re |
|
175 | 174 | import shlex |
@@ -182,7 +181,7 b' from IPython.utils.text import marquee' | |||
|
182 | 181 | |
|
183 | 182 | __all__ = ['Demo','IPythonDemo','LineDemo','IPythonLineDemo','DemoError'] |
|
184 | 183 | |
|
185 |
class DemoError( |
|
|
184 | class DemoError(Exception): pass | |
|
186 | 185 | |
|
187 | 186 | def re_mark(mark): |
|
188 | 187 | return re.compile(r'^\s*#\s+<demo>\s+%s\s*$' % mark,re.MULTILINE) |
@@ -454,8 +454,10 b' class GroupQueue(object):' | |||
|
454 | 454 | except ValueError: |
|
455 | 455 | pass |
|
456 | 456 | |
|
457 | ||
|
458 | _baseclass_reprs = (object.__repr__, types.InstanceType.__repr__) | |
|
457 | try: | |
|
458 | _baseclass_reprs = (object.__repr__, types.InstanceType.__repr__) | |
|
459 | except AttributeError: # Python 3 | |
|
460 | _baseclass_reprs = (object.__repr__,) | |
|
459 | 461 | |
|
460 | 462 | |
|
461 | 463 | def _default_pprint(obj, p, cycle): |
@@ -648,23 +650,33 b' _type_pprinters = {' | |||
|
648 | 650 | tuple: _seq_pprinter_factory('(', ')', tuple), |
|
649 | 651 | list: _seq_pprinter_factory('[', ']', list), |
|
650 | 652 | dict: _dict_pprinter_factory('{', '}', dict), |
|
651 | types.DictProxyType: _dict_pprinter_factory('<dictproxy {', '}>'), | |
|
653 | ||
|
652 | 654 | set: _seq_pprinter_factory('set([', '])', set), |
|
653 | 655 | frozenset: _seq_pprinter_factory('frozenset([', '])', frozenset), |
|
654 | 656 | super: _super_pprint, |
|
655 | 657 | _re_pattern_type: _re_pattern_pprint, |
|
656 | 658 | type: _type_pprint, |
|
657 | types.ClassType: _type_pprint, | |
|
658 | 659 | types.FunctionType: _function_pprint, |
|
659 | 660 | types.BuiltinFunctionType: _function_pprint, |
|
660 | 661 | types.SliceType: _repr_pprint, |
|
661 | 662 | types.MethodType: _repr_pprint, |
|
662 | xrange: _repr_pprint, | |
|
663 | ||
|
663 | 664 | datetime.datetime: _repr_pprint, |
|
664 | 665 | datetime.timedelta: _repr_pprint, |
|
665 | 666 | _exception_base: _exception_pprint |
|
666 | 667 | } |
|
667 | 668 | |
|
669 | try: | |
|
670 | _type_pprinters[types.DictProxyType] = _dict_pprinter_factory('<dictproxy {', '}>') | |
|
671 | _type_pprinters[types.ClassType] = _type_pprint, | |
|
672 | except AttributeError: # Python 3 | |
|
673 | pass | |
|
674 | ||
|
675 | try: | |
|
676 | _type_pprinters[xrange] = _repr_pprint | |
|
677 | except NameError: | |
|
678 | _type_pprinters[range] = _repr_pprint | |
|
679 | ||
|
668 | 680 | #: printers for types specified by name |
|
669 | 681 | _deferred_type_pprinters = { |
|
670 | 682 | } |
@@ -19,7 +19,7 b' Authors' | |||
|
19 | 19 | # Imports |
|
20 | 20 | #----------------------------------------------------------------------------- |
|
21 | 21 | |
|
22 |
from |
|
|
22 | from io import BytesIO | |
|
23 | 23 | |
|
24 | 24 | from IPython.utils.decorators import flag_calls |
|
25 | 25 | |
@@ -99,11 +99,11 b" def print_figure(fig, fmt='png'):" | |||
|
99 | 99 | fig.set_facecolor('white') |
|
100 | 100 | fig.set_edgecolor('white') |
|
101 | 101 | try: |
|
102 |
s |
|
|
102 | bytes_io = BytesIO() | |
|
103 | 103 | # use 72 dpi to match QTConsole's dpi |
|
104 |
fig.canvas.print_figure(s |
|
|
104 | fig.canvas.print_figure(bytes_io, format=fmt, dpi=72, | |
|
105 | 105 | bbox_inches='tight') |
|
106 |
data = s |
|
|
106 | data = bytes_io.getvalue() | |
|
107 | 107 | finally: |
|
108 | 108 | fig.set_facecolor(fc) |
|
109 | 109 | fig.set_edgecolor(ec) |
@@ -370,7 +370,7 b' class Client(HasTraits):' | |||
|
370 | 370 | self.session = Session(**extra_args) |
|
371 | 371 | |
|
372 | 372 | self._query_socket = self._context.socket(zmq.DEALER) |
|
373 |
self._query_socket.setsockopt(zmq.IDENTITY, |
|
|
373 | self._query_socket.setsockopt(zmq.IDENTITY, self.session.bsession) | |
|
374 | 374 | if self._ssh: |
|
375 | 375 | tunnel.tunnel_connection(self._query_socket, url, sshserver, **ssh_kwargs) |
|
376 | 376 | else: |
@@ -496,7 +496,7 b' class Client(HasTraits):' | |||
|
496 | 496 | content = msg.content |
|
497 | 497 | self._config['registration'] = dict(content) |
|
498 | 498 | if content.status == 'ok': |
|
499 |
ident = |
|
|
499 | ident = self.session.bsession | |
|
500 | 500 | if content.mux: |
|
501 | 501 | self._mux_socket = self._context.socket(zmq.DEALER) |
|
502 | 502 | self._mux_socket.setsockopt(zmq.IDENTITY, ident) |
@@ -512,7 +512,7 b' class Client(HasTraits):' | |||
|
512 | 512 | self._notification_socket.setsockopt(zmq.SUBSCRIBE, b'') |
|
513 | 513 | # if content.query: |
|
514 | 514 | # self._query_socket = self._context.socket(zmq.DEALER) |
|
515 | # self._query_socket.setsockopt(zmq.IDENTITY, self.session.session) | |
|
515 | # self._query_socket.setsockopt(zmq.IDENTITY, self.session.bsession) | |
|
516 | 516 | # connect_socket(self._query_socket, content.query) |
|
517 | 517 | if content.control: |
|
518 | 518 | self._control_socket = self._context.socket(zmq.DEALER) |
@@ -16,6 +16,7 b' from types import ModuleType' | |||
|
16 | 16 | from IPython.parallel.client.asyncresult import AsyncResult |
|
17 | 17 | from IPython.parallel.error import UnmetDependency |
|
18 | 18 | from IPython.parallel.util import interactive |
|
19 | from IPython.utils import py3compat | |
|
19 | 20 | |
|
20 | 21 | class depend(object): |
|
21 | 22 | """Dependency decorator, for use with tasks. |
@@ -65,9 +66,10 b' class dependent(object):' | |||
|
65 | 66 | raise UnmetDependency() |
|
66 | 67 | return self.f(*args, **kwargs) |
|
67 | 68 | |
|
68 | @property | |
|
69 | def __name__(self): | |
|
70 | return self.func_name | |
|
69 | if not py3compat.PY3: | |
|
70 | @property | |
|
71 | def __name__(self): | |
|
72 | return self.func_name | |
|
71 | 73 | |
|
72 | 74 | @interactive |
|
73 | 75 | def _require(*names): |
@@ -288,7 +288,7 b' class HubFactory(RegistrationFactory):' | |||
|
288 | 288 | # resubmit stream |
|
289 | 289 | r = ZMQStream(ctx.socket(zmq.DEALER), loop) |
|
290 | 290 | url = util.disambiguate_url(self.client_info['task'][-1]) |
|
291 |
r.setsockopt(zmq.IDENTITY, |
|
|
291 | r.setsockopt(zmq.IDENTITY, self.session.bsession) | |
|
292 | 292 | r.connect(url) |
|
293 | 293 | |
|
294 | 294 | self.hub = Hub(loop=loop, session=self.session, monitor=sub, heartmonitor=self.heartmonitor, |
@@ -177,7 +177,7 b' class TaskScheduler(SessionFactory):' | |||
|
177 | 177 | ident = CBytes() # ZMQ identity. This should just be self.session.session |
|
178 | 178 | # but ensure Bytes |
|
179 | 179 | def _ident_default(self): |
|
180 |
return |
|
|
180 | return self.session.bsession | |
|
181 | 181 | |
|
182 | 182 | def start(self): |
|
183 | 183 | self.engine_stream.on_recv(self.dispatch_result, copy=False) |
@@ -20,15 +20,15 b' from __future__ import print_function' | |||
|
20 | 20 | #----------------------------------------------------------------------------- |
|
21 | 21 | |
|
22 | 22 | # stdlib |
|
23 | import __builtin__ | |
|
23 | import __builtin__ as builtin_mod | |
|
24 | 24 | import os |
|
25 | 25 | import sys |
|
26 | from types import MethodType | |
|
27 | 26 | |
|
28 | 27 | # our own |
|
29 | 28 | from . import tools |
|
30 | 29 | |
|
31 | 30 | from IPython.utils import io |
|
31 | from IPython.utils import py3compat | |
|
32 | 32 | from IPython.frontend.terminal.interactiveshell import TerminalInteractiveShell |
|
33 | 33 | |
|
34 | 34 | #----------------------------------------------------------------------------- |
@@ -131,7 +131,7 b' class ipnsdict(dict):' | |||
|
131 | 131 | # aggressive low-level cleaning of the execution namespace, we need to |
|
132 | 132 | # correct for that ourselves, to ensure consitency with the 'real' |
|
133 | 133 | # ipython. |
|
134 |
self['__builtins__'] = |
|
|
134 | self['__builtins__'] = builtin_mod | |
|
135 | 135 | |
|
136 | 136 | def __delitem__(self, key): |
|
137 | 137 | """Part of the test suite checks that we can release all |
@@ -204,11 +204,10 b' def start_ipython():' | |||
|
204 | 204 | # Modify the IPython system call with one that uses getoutput, so that we |
|
205 | 205 | # can capture subcommands and print them to Python's stdout, otherwise the |
|
206 | 206 | # doctest machinery would miss them. |
|
207 |
shell.system = MethodType(xsys, shell |
|
|
207 | shell.system = py3compat.MethodType(xsys, shell) | |
|
208 | 208 | |
|
209 | 209 | |
|
210 |
shell._showtraceback = MethodType(_showtraceback, shell |
|
|
211 | TerminalInteractiveShell) | |
|
210 | shell._showtraceback = py3compat.MethodType(_showtraceback, shell) | |
|
212 | 211 | |
|
213 | 212 | # IPython is ready, now clean up some global state... |
|
214 | 213 | |
@@ -223,8 +222,8 b' def start_ipython():' | |||
|
223 | 222 | # now return this without recursively calling here again. |
|
224 | 223 | _ip = shell |
|
225 | 224 | get_ipython = _ip.get_ipython |
|
226 |
|
|
|
227 |
|
|
|
225 | builtin_mod._ip = _ip | |
|
226 | builtin_mod.get_ipython = get_ipython | |
|
228 | 227 | |
|
229 | 228 | # To avoid extra IPython messages during testing, suppress io.stdout/stderr |
|
230 | 229 | io.stdout = StreamProxy('stdout') |
@@ -17,6 +17,7 b' Note: merely importing this module causes the monkeypatch to be applied."""' | |||
|
17 | 17 | #----------------------------------------------------------------------------- |
|
18 | 18 | |
|
19 | 19 | import unittest |
|
20 | import sys | |
|
20 | 21 | import nose.loader |
|
21 | 22 | from inspect import ismethod, isfunction |
|
22 | 23 | |
@@ -64,5 +65,7 b' def getTestCaseNames(self, testCaseClass):' | |||
|
64 | 65 | |
|
65 | 66 | ########################################################################## |
|
66 | 67 | # Apply monkeypatch here |
|
67 | nose.loader.TestLoader.getTestCaseNames = getTestCaseNames | |
|
68 | # Python 3 must be running with newer version of Nose, so don't touch anything. | |
|
69 | if sys.version_info[0] < 3: | |
|
70 | nose.loader.TestLoader.getTestCaseNames = getTestCaseNames | |
|
68 | 71 | ########################################################################## |
@@ -295,7 +295,7 b' class TempFileMixin(object):' | |||
|
295 | 295 | # delete it. I have no clue why |
|
296 | 296 | pass |
|
297 | 297 | |
|
298 |
pair_fail_msg = ("Testing |
|
|
298 | pair_fail_msg = ("Testing {0}\n\n" | |
|
299 | 299 | "In:\n" |
|
300 | 300 | " {1!r}\n" |
|
301 | 301 | "Expected:\n" |
@@ -318,9 +318,10 b' def check_pairs(func, pairs):' | |||
|
318 | 318 | None. Raises an AssertionError if any output does not match the expected |
|
319 | 319 | value. |
|
320 | 320 | """ |
|
321 | name = getattr(func, "func_name", getattr(func, "__name__", "<unknown>")) | |
|
321 | 322 | for inp, expected in pairs: |
|
322 | 323 | out = func(inp) |
|
323 |
assert out == expected, pair_fail_msg.format( |
|
|
324 | assert out == expected, pair_fail_msg.format(name, inp, expected, out) | |
|
324 | 325 | |
|
325 | 326 | @contextmanager |
|
326 | 327 | def mute_warn(): |
@@ -342,4 +343,3 b' def make_tempfile(name):' | |||
|
342 | 343 | yield |
|
343 | 344 | finally: |
|
344 | 345 | os.unlink(name) |
|
345 |
@@ -42,6 +42,13 b' import sys' | |||
|
42 | 42 | import token |
|
43 | 43 | import tokenize |
|
44 | 44 | |
|
45 | try: | |
|
46 | generate_tokens = tokenize.generate_tokens | |
|
47 | except AttributeError: | |
|
48 | # Python 3. Note that we use the undocumented _tokenize because it expects | |
|
49 | # strings, not bytes. See also Python issue #9969. | |
|
50 | generate_tokens = tokenize._tokenize | |
|
51 | ||
|
45 | 52 | from IPython.utils.coloransi import * |
|
46 | 53 | |
|
47 | 54 | ############################################################################# |
@@ -177,10 +184,11 b' class Parser:' | |||
|
177 | 184 | |
|
178 | 185 | error = False |
|
179 | 186 | try: |
|
180 |
|
|
|
181 | except tokenize.TokenError, ex: | |
|
182 | msg = ex[0] | |
|
183 |
|
|
|
187 | for atoken in generate_tokens(text.readline): | |
|
188 | self(*atoken) | |
|
189 | except tokenize.TokenError as ex: | |
|
190 | msg = ex.args[0] | |
|
191 | line = ex.args[1][0] | |
|
184 | 192 | self.out.write("%s\n\n*** ERROR: %s%s%s\n" % |
|
185 | 193 | (colors[token.ERRORTOKEN], |
|
186 | 194 | msg, self.raw[self.lines[line]:], |
@@ -17,6 +17,8 b' of subprocess utilities, and it contains tools that are common to all of them.' | |||
|
17 | 17 | import subprocess |
|
18 | 18 | import sys |
|
19 | 19 | |
|
20 | from IPython.utils import py3compat | |
|
21 | ||
|
20 | 22 | #----------------------------------------------------------------------------- |
|
21 | 23 | # Function definitions |
|
22 | 24 | #----------------------------------------------------------------------------- |
@@ -116,8 +118,8 b' def getoutput(cmd):' | |||
|
116 | 118 | |
|
117 | 119 | out = process_handler(cmd, lambda p: p.communicate()[0], subprocess.STDOUT) |
|
118 | 120 | if out is None: |
|
119 |
|
|
|
120 | return out | |
|
121 | return '' | |
|
122 | return py3compat.bytes_to_str(out) | |
|
121 | 123 | |
|
122 | 124 | |
|
123 | 125 | def getoutputerror(cmd): |
@@ -138,5 +140,6 b' def getoutputerror(cmd):' | |||
|
138 | 140 | |
|
139 | 141 | out_err = process_handler(cmd, lambda p: p.communicate()) |
|
140 | 142 | if out_err is None: |
|
141 |
|
|
|
142 |
|
|
|
143 | return '', '' | |
|
144 | out, err = out_err | |
|
145 | return py3compat.bytes_to_str(out), py3compat.bytes_to_str(err) |
@@ -103,7 +103,7 b' class Tee(object):' | |||
|
103 | 103 | # Inspired by: |
|
104 | 104 | # http://mail.python.org/pipermail/python-list/2007-May/442737.html |
|
105 | 105 | |
|
106 |
def __init__(self, file_or_name, mode= |
|
|
106 | def __init__(self, file_or_name, mode="w", channel='stdout'): | |
|
107 | 107 | """Construct a new Tee object. |
|
108 | 108 | |
|
109 | 109 | Parameters |
@@ -119,7 +119,7 b' class Tee(object):' | |||
|
119 | 119 | if channel not in ['stdout', 'stderr']: |
|
120 | 120 | raise ValueError('Invalid channel spec %s' % channel) |
|
121 | 121 | |
|
122 | if hasattr(file, 'write') and hasattr(file, 'seek'): | |
|
122 | if hasattr(file_or_name, 'write') and hasattr(file_or_name, 'seek'): | |
|
123 | 123 | self.file = file_or_name |
|
124 | 124 | else: |
|
125 | 125 | self.file = open(file_or_name, mode) |
@@ -16,6 +16,9 b' import sys' | |||
|
16 | 16 | import types |
|
17 | 17 | from datetime import datetime |
|
18 | 18 | |
|
19 | from IPython.utils import py3compat | |
|
20 | next_attr_name = '__next__' if py3compat.PY3 else 'next' | |
|
21 | ||
|
19 | 22 | #----------------------------------------------------------------------------- |
|
20 | 23 | # Globals and constants |
|
21 | 24 | #----------------------------------------------------------------------------- |
@@ -134,7 +137,7 b' def json_clean(obj):' | |||
|
134 | 137 | return obj.decode(sys.getdefaultencoding(), 'replace') |
|
135 | 138 | |
|
136 | 139 | if isinstance(obj, container_to_list) or ( |
|
137 |
hasattr(obj, '__iter__') and hasattr(obj, |
|
|
140 | hasattr(obj, '__iter__') and hasattr(obj, next_attr_name)): | |
|
138 | 141 | obj = list(obj) |
|
139 | 142 | |
|
140 | 143 | if isinstance(obj, list): |
@@ -23,6 +23,7 b' import IPython' | |||
|
23 | 23 | from IPython.utils import warn |
|
24 | 24 | from IPython.utils.process import system |
|
25 | 25 | from IPython.utils.importstring import import_item |
|
26 | from IPython.utils import py3compat | |
|
26 | 27 | |
|
27 | 28 | #----------------------------------------------------------------------------- |
|
28 | 29 | # Code |
@@ -30,14 +31,6 b' from IPython.utils.importstring import import_item' | |||
|
30 | 31 | |
|
31 | 32 | fs_encoding = sys.getfilesystemencoding() |
|
32 | 33 | |
|
33 | def _cast_unicode(s, enc=None): | |
|
34 | """Turn 8-bit strings into unicode.""" | |
|
35 | if isinstance(s, bytes): | |
|
36 | enc = enc or sys.getdefaultencoding() | |
|
37 | return s.decode(enc) | |
|
38 | return s | |
|
39 | ||
|
40 | ||
|
41 | 34 | def _get_long_path_name(path): |
|
42 | 35 | """Dummy no-op.""" |
|
43 | 36 | return path |
@@ -203,7 +196,7 b' def get_home_dir():' | |||
|
203 | 196 | root=os.path.abspath(root).rstrip('\\') |
|
204 | 197 | if _writable_dir(os.path.join(root, '_ipython')): |
|
205 | 198 | os.environ["IPYKITROOT"] = root |
|
206 |
return |
|
|
199 | return py3compat.cast_unicode(root, fs_encoding) | |
|
207 | 200 | |
|
208 | 201 | if os.name == 'posix': |
|
209 | 202 | # Linux, Unix, AIX, OS X |
@@ -218,11 +211,11 b' def get_home_dir():' | |||
|
218 | 211 | homedir = Popen('echo $HOME', shell=True, |
|
219 | 212 | stdout=PIPE).communicate()[0].strip() |
|
220 | 213 | if homedir: |
|
221 |
return |
|
|
214 | return py3compat.cast_unicode(homedir, fs_encoding) | |
|
222 | 215 | else: |
|
223 | 216 | raise HomeDirError('Undefined $HOME, IPython cannot proceed.') |
|
224 | 217 | else: |
|
225 |
return |
|
|
218 | return py3compat.cast_unicode(homedir, fs_encoding) | |
|
226 | 219 | elif os.name == 'nt': |
|
227 | 220 | # Now for win9x, XP, Vista, 7? |
|
228 | 221 | # For some strange reason all of these return 'nt' for os.name. |
@@ -236,7 +229,7 b' def get_home_dir():' | |||
|
236 | 229 | pass |
|
237 | 230 | else: |
|
238 | 231 | if _writable_dir(homedir): |
|
239 |
return |
|
|
232 | return py3compat.cast_unicode(homedir, fs_encoding) | |
|
240 | 233 | |
|
241 | 234 | # Now look for a local home directory |
|
242 | 235 | try: |
@@ -245,7 +238,7 b' def get_home_dir():' | |||
|
245 | 238 | pass |
|
246 | 239 | else: |
|
247 | 240 | if _writable_dir(homedir): |
|
248 |
return |
|
|
241 | return py3compat.cast_unicode(homedir, fs_encoding) | |
|
249 | 242 | |
|
250 | 243 | # Now the users profile directory |
|
251 | 244 | try: |
@@ -254,7 +247,7 b' def get_home_dir():' | |||
|
254 | 247 | pass |
|
255 | 248 | else: |
|
256 | 249 | if _writable_dir(homedir): |
|
257 |
return |
|
|
250 | return py3compat.cast_unicode(homedir, fs_encoding) | |
|
258 | 251 | |
|
259 | 252 | # Use the registry to get the 'My Documents' folder. |
|
260 | 253 | try: |
@@ -269,7 +262,7 b' def get_home_dir():' | |||
|
269 | 262 | pass |
|
270 | 263 | else: |
|
271 | 264 | if _writable_dir(homedir): |
|
272 |
return |
|
|
265 | return py3compat.cast_unicode(homedir, fs_encoding) | |
|
273 | 266 | |
|
274 | 267 | # A user with a lot of unix tools in win32 may have defined $HOME. |
|
275 | 268 | # Try this as a last ditch option. |
@@ -279,7 +272,7 b' def get_home_dir():' | |||
|
279 | 272 | pass |
|
280 | 273 | else: |
|
281 | 274 | if _writable_dir(homedir): |
|
282 |
return |
|
|
275 | return py3compat.cast_unicode(homedir, fs_encoding) | |
|
283 | 276 | |
|
284 | 277 | # If all else fails, raise HomeDirError |
|
285 | 278 | raise HomeDirError('No valid home directory could be found') |
@@ -302,7 +295,7 b' def get_xdg_dir():' | |||
|
302 | 295 | # use ~/.config if not set OR empty |
|
303 | 296 | xdg = env.get("XDG_CONFIG_HOME", None) or os.path.join(get_home_dir(), '.config') |
|
304 | 297 | if xdg and _writable_dir(xdg): |
|
305 |
return |
|
|
298 | return py3compat.cast_unicode(xdg, fs_encoding) | |
|
306 | 299 | |
|
307 | 300 | return None |
|
308 | 301 | |
@@ -311,7 +304,7 b' def get_ipython_dir():' | |||
|
311 | 304 | """Get the IPython directory for this platform and user. |
|
312 | 305 | |
|
313 | 306 | This uses the logic in `get_home_dir` to find the home directory |
|
314 | and the adds .ipython to the end of the path. | |
|
307 | and then adds .ipython to the end of the path. | |
|
315 | 308 | """ |
|
316 | 309 | |
|
317 | 310 | env = os.environ |
@@ -356,13 +349,13 b' def get_ipython_dir():' | |||
|
356 | 349 | " using a temp directory."%parent) |
|
357 | 350 | ipdir = tempfile.mkdtemp() |
|
358 | 351 | |
|
359 |
return |
|
|
352 | return py3compat.cast_unicode(ipdir, fs_encoding) | |
|
360 | 353 | |
|
361 | 354 | |
|
362 | 355 | def get_ipython_package_dir(): |
|
363 | 356 | """Get the base directory where IPython itself is installed.""" |
|
364 | 357 | ipdir = os.path.dirname(IPython.__file__) |
|
365 |
return |
|
|
358 | return py3compat.cast_unicode(ipdir, fs_encoding) | |
|
366 | 359 | |
|
367 | 360 | |
|
368 | 361 | def get_ipython_module_path(module_str): |
@@ -377,7 +370,7 b' def get_ipython_module_path(module_str):' | |||
|
377 | 370 | mod = import_item(module_str) |
|
378 | 371 | the_path = mod.__file__.replace('.pyc', '.py') |
|
379 | 372 | the_path = the_path.replace('.pyo', '.py') |
|
380 |
return |
|
|
373 | return py3compat.cast_unicode(the_path, fs_encoding) | |
|
381 | 374 | |
|
382 | 375 | |
|
383 | 376 | def expand_path(s): |
@@ -442,7 +435,7 b' def filehash(path):' | |||
|
442 | 435 | """Make an MD5 hash of a file, ignoring any differences in line |
|
443 | 436 | ending characters.""" |
|
444 | 437 | with open(path, "rU") as f: |
|
445 | return md5(f.read()).hexdigest() | |
|
438 | return md5(py3compat.str_to_bytes(f.read())).hexdigest() | |
|
446 | 439 | |
|
447 | 440 | # If the config is unmodified from the default, we'll just delete it. |
|
448 | 441 | # These are consistent for 0.10.x, thankfully. We're not going to worry about |
@@ -35,8 +35,8 b' License: MIT open source license.' | |||
|
35 | 35 | |
|
36 | 36 | from IPython.external.path import path as Path |
|
37 | 37 | import os,stat,time |
|
38 | import collections | |
|
38 | 39 | import cPickle as pickle |
|
39 | import UserDict | |
|
40 | 40 | import glob |
|
41 | 41 | |
|
42 | 42 | def gethashfile(key): |
@@ -44,7 +44,7 b' def gethashfile(key):' | |||
|
44 | 44 | |
|
45 | 45 | _sentinel = object() |
|
46 | 46 | |
|
47 |
class PickleShareDB( |
|
|
47 | class PickleShareDB(collections.MutableMapping): | |
|
48 | 48 | """ The main 'connection' object for PickleShare database """ |
|
49 | 49 | def __init__(self,root): |
|
50 | 50 | """ Return a db object that will manage the specied directory""" |
@@ -187,6 +187,12 b' class PickleShareDB(UserDict.DictMixin):' | |||
|
187 | 187 | else: |
|
188 | 188 | files = [Path(p) for p in glob.glob(self.root/globpat)] |
|
189 | 189 | return [self._normalized(p) for p in files if p.isfile()] |
|
190 | ||
|
191 | def __iter__(self): | |
|
192 | return iter(keys) | |
|
193 | ||
|
194 | def __len__(self): | |
|
195 | return len(keys) | |
|
190 | 196 | |
|
191 | 197 | def uncache(self,*items): |
|
192 | 198 | """ Removes all, or specified items from cache |
@@ -27,6 +27,7 b' else:' | |||
|
27 | 27 | from ._process_posix import _find_cmd, system, getoutput |
|
28 | 28 | |
|
29 | 29 | from ._process_common import getoutputerror |
|
30 | from IPython.utils import py3compat | |
|
30 | 31 | |
|
31 | 32 | #----------------------------------------------------------------------------- |
|
32 | 33 | # Code |
@@ -65,7 +66,7 b' def find_cmd(cmd):' | |||
|
65 | 66 | except OSError: |
|
66 | 67 | raise FindCmdError('command could not be found: %s' % cmd) |
|
67 | 68 | # which returns empty if not found |
|
68 | if path == '': | |
|
69 | if path == b'': | |
|
69 | 70 | raise FindCmdError('command could not be found: %s' % cmd) |
|
70 | 71 | return os.path.abspath(path) |
|
71 | 72 | |
@@ -115,7 +116,7 b' def arg_split(s, posix=False):' | |||
|
115 | 116 | # At least encoding the input when it's unicode seems to help, but there |
|
116 | 117 | # may be more problems lurking. Apparently this is fixed in python3. |
|
117 | 118 | is_unicode = False |
|
118 | if isinstance(s, unicode): | |
|
119 | if (not py3compat.PY3) and isinstance(s, unicode): | |
|
119 | 120 | is_unicode = True |
|
120 | 121 | s = s.encode('utf-8') |
|
121 | 122 | lex = shlex.shlex(s, posix=posix) |
@@ -31,17 +31,24 b' from IPython.testing import decorators as dec' | |||
|
31 | 31 | from IPython.testing.decorators import skip_if_not_win32, skip_win32 |
|
32 | 32 | from IPython.testing.tools import make_tempfile |
|
33 | 33 | from IPython.utils import path, io |
|
34 | from IPython.utils import py3compat | |
|
34 | 35 | |
|
35 | 36 | # Platform-dependent imports |
|
36 | 37 | try: |
|
37 | 38 | import _winreg as wreg |
|
38 | 39 | except ImportError: |
|
39 | 40 | #Fake _winreg module on none windows platforms |
|
40 |
import |
|
|
41 | sys.modules["_winreg"] = new.module("_winreg") | |
|
41 | import types | |
|
42 | wr_name = "winreg" if py3compat.PY3 else "_winreg" | |
|
43 | sys.modules[wr_name] = types.ModuleType(wr_name) | |
|
42 | 44 | import _winreg as wreg |
|
43 | 45 | #Add entries that needs to be stubbed by the testing code |
|
44 | 46 | (wreg.OpenKey, wreg.QueryValueEx,) = (None, None) |
|
47 | ||
|
48 | try: | |
|
49 | reload | |
|
50 | except NameError: # Python 3 | |
|
51 | from imp import reload | |
|
45 | 52 | |
|
46 | 53 | #----------------------------------------------------------------------------- |
|
47 | 54 | # Globals |
@@ -37,7 +37,7 b' def test_find_cmd_python():' | |||
|
37 | 37 | def test_find_cmd_ls(): |
|
38 | 38 | """Make sure we can find the full path to ls.""" |
|
39 | 39 | path = find_cmd('ls') |
|
40 | nt.assert_true(path.endswith('ls')) | |
|
40 | nt.assert_true(path.endswith(b'ls')) | |
|
41 | 41 | |
|
42 | 42 | |
|
43 | 43 | def has_pywin32(): |
@@ -23,7 +23,7 b' import textwrap' | |||
|
23 | 23 | from string import Formatter |
|
24 | 24 | |
|
25 | 25 | from IPython.external.path import path |
|
26 | ||
|
26 | from IPython.utils import py3compat | |
|
27 | 27 | from IPython.utils.io import nlprint |
|
28 | 28 | from IPython.utils.data import flatten |
|
29 | 29 | |
@@ -284,7 +284,7 b' def make_quoted_expr(s):' | |||
|
284 | 284 | tail = '' |
|
285 | 285 | tailpadding = '' |
|
286 | 286 | raw = '' |
|
287 | ucode = 'u' | |
|
287 | ucode = '' if py3compat.PY3 else 'u' | |
|
288 | 288 | if "\\" in s: |
|
289 | 289 | raw = 'r' |
|
290 | 290 | if s.endswith('\\'): |
@@ -494,7 +494,7 b" def marquee(txt='',width=78,mark='*'):" | |||
|
494 | 494 | """ |
|
495 | 495 | if not txt: |
|
496 | 496 | return (mark*width)[:width] |
|
497 | nmark = (width-len(txt)-2)/len(mark)/2 | |
|
497 | nmark = (width-len(txt)-2)//len(mark)//2 | |
|
498 | 498 | if nmark < 0: nmark =0 |
|
499 | 499 | marks = mark*nmark |
|
500 | 500 | return '%s %s %s' % (marks,txt,marks) |
@@ -587,10 +587,10 b' class EvalFormatter(Formatter):' | |||
|
587 | 587 | -------- |
|
588 | 588 | |
|
589 | 589 | In [1]: f = EvalFormatter() |
|
590 | In [2]: f.format('{n/4}', n=8) | |
|
590 | In [2]: f.format('{n//4}', n=8) | |
|
591 | 591 | Out[2]: '2' |
|
592 | 592 | |
|
593 | In [3]: f.format('{range(3)}') | |
|
593 | In [3]: f.format('{list(range(3))}') | |
|
594 | 594 | Out[3]: '[0, 1, 2]' |
|
595 | 595 | |
|
596 | 596 | In [4]: f.format('{3*2}') |
@@ -52,15 +52,17 b' import inspect' | |||
|
52 | 52 | import re |
|
53 | 53 | import sys |
|
54 | 54 | import types |
|
55 |
from types import |
|
|
56 | InstanceType, ClassType, FunctionType, | |
|
57 | ListType, TupleType | |
|
58 | ) | |
|
55 | from types import FunctionType | |
|
56 | try: | |
|
57 | from types import ClassType, InstanceType | |
|
58 | ClassTypes = (ClassType, type) | |
|
59 | except: | |
|
60 | ClassTypes = (type,) | |
|
61 | ||
|
59 | 62 | from .importstring import import_item |
|
63 | from IPython.utils import py3compat | |
|
60 | 64 | |
|
61 | ClassTypes = (ClassType, type) | |
|
62 | ||
|
63 | SequenceTypes = (ListType, TupleType, set, frozenset) | |
|
65 | SequenceTypes = (list, tuple, set, frozenset) | |
|
64 | 66 | |
|
65 | 67 | #----------------------------------------------------------------------------- |
|
66 | 68 | # Basic classes |
@@ -108,7 +110,7 b' def repr_type(obj):' | |||
|
108 | 110 | error messages. |
|
109 | 111 | """ |
|
110 | 112 | the_type = type(obj) |
|
111 | if the_type is InstanceType: | |
|
113 | if (not py3compat.PY3) and the_type is InstanceType: | |
|
112 | 114 | # Old-style class. |
|
113 | 115 | the_type = obj.__class__ |
|
114 | 116 | msg = '%r %r' % (obj, the_type) |
@@ -616,7 +618,7 b' class ClassBasedTraitType(TraitType):' | |||
|
616 | 618 | |
|
617 | 619 | def error(self, obj, value): |
|
618 | 620 | kind = type(value) |
|
619 | if kind is InstanceType: | |
|
621 | if (not py3compat.PY3) and kind is InstanceType: | |
|
620 | 622 | msg = 'class %s' % value.__class__.__name__ |
|
621 | 623 | else: |
|
622 | 624 | msg = '%s (i.e. %s)' % ( str( kind )[1:-1], repr( value ) ) |
@@ -880,29 +882,31 b' class CInt(Int):' | |||
|
880 | 882 | except: |
|
881 | 883 | self.error(obj, value) |
|
882 | 884 | |
|
885 | if py3compat.PY3: | |
|
886 | Long, CLong = Int, CInt | |
|
887 | else: | |
|
888 | class Long(TraitType): | |
|
889 | """A long integer trait.""" | |
|
883 | 890 | |
|
884 | class Long(TraitType): | |
|
885 | """A long integer trait.""" | |
|
886 | ||
|
887 | default_value = 0L | |
|
888 | info_text = 'a long' | |
|
891 | default_value = 0L | |
|
892 | info_text = 'a long' | |
|
889 | 893 | |
|
890 | def validate(self, obj, value): | |
|
891 | if isinstance(value, long): | |
|
892 | return value | |
|
893 | if isinstance(value, int): | |
|
894 | return long(value) | |
|
895 | self.error(obj, value) | |
|
894 | def validate(self, obj, value): | |
|
895 | if isinstance(value, long): | |
|
896 | return value | |
|
897 | if isinstance(value, int): | |
|
898 | return long(value) | |
|
899 | self.error(obj, value) | |
|
896 | 900 | |
|
897 | 901 | |
|
898 | class CLong(Long): | |
|
899 | """A casting version of the long integer trait.""" | |
|
902 | class CLong(Long): | |
|
903 | """A casting version of the long integer trait.""" | |
|
900 | 904 | |
|
901 | def validate(self, obj, value): | |
|
902 | try: | |
|
903 | return long(value) | |
|
904 | except: | |
|
905 | self.error(obj, value) | |
|
905 | def validate(self, obj, value): | |
|
906 | try: | |
|
907 | return long(value) | |
|
908 | except: | |
|
909 | self.error(obj, value) | |
|
906 | 910 | |
|
907 | 911 | |
|
908 | 912 | class Float(TraitType): |
@@ -955,7 +959,7 b' class CComplex(Complex):' | |||
|
955 | 959 | # for Python 3 conversion and for reliable unicode behaviour on Python 2. So |
|
956 | 960 | # we don't have a Str type. |
|
957 | 961 | class Bytes(TraitType): |
|
958 | """A trait for strings.""" | |
|
962 | """A trait for byte strings.""" | |
|
959 | 963 | |
|
960 | 964 | default_value = '' |
|
961 | 965 | info_text = 'a string' |
@@ -967,7 +971,7 b' class Bytes(TraitType):' | |||
|
967 | 971 | |
|
968 | 972 | |
|
969 | 973 | class CBytes(Bytes): |
|
970 | """A casting version of the string trait.""" | |
|
974 | """A casting version of the byte string trait.""" | |
|
971 | 975 | |
|
972 | 976 | def validate(self, obj, value): |
|
973 | 977 | try: |
@@ -1006,12 +1010,12 b' class ObjectName(TraitType):' | |||
|
1006 | 1010 | This does not check that the name exists in any scope.""" |
|
1007 | 1011 | info_text = "a valid object identifier in Python" |
|
1008 | 1012 | |
|
1009 | if sys.version_info[0] < 3: | |
|
1013 | if py3compat.PY3: | |
|
1014 | # Python 3: | |
|
1015 | coerce_str = staticmethod(lambda _,s: s) | |
|
1016 | ||
|
1017 | else: | |
|
1010 | 1018 | # Python 2: |
|
1011 | _name_re = re.compile(r"[a-zA-Z_][a-zA-Z0-9_]*$") | |
|
1012 | def isidentifier(self, s): | |
|
1013 | return bool(self._name_re.match(s)) | |
|
1014 | ||
|
1015 | 1019 | def coerce_str(self, obj, value): |
|
1016 | 1020 | "In Python 2, coerce ascii-only unicode to str" |
|
1017 | 1021 | if isinstance(value, unicode): |
@@ -1021,15 +1025,10 b' class ObjectName(TraitType):' | |||
|
1021 | 1025 | self.error(obj, value) |
|
1022 | 1026 | return value |
|
1023 | 1027 | |
|
1024 | else: | |
|
1025 | # Python 3: | |
|
1026 | isidentifier = staticmethod(lambda s: s.isidentifier()) | |
|
1027 | coerce_str = staticmethod(lambda _,s: s) | |
|
1028 | ||
|
1029 | 1028 | def validate(self, obj, value): |
|
1030 | 1029 | value = self.coerce_str(obj, value) |
|
1031 | 1030 | |
|
1032 |
if isinstance(value, str) and |
|
|
1031 | if isinstance(value, str) and py3compat.isidentifier(value): | |
|
1033 | 1032 | return value |
|
1034 | 1033 | self.error(obj, value) |
|
1035 | 1034 | |
@@ -1038,8 +1037,7 b' class DottedObjectName(ObjectName):' | |||
|
1038 | 1037 | def validate(self, obj, value): |
|
1039 | 1038 | value = self.coerce_str(obj, value) |
|
1040 | 1039 | |
|
1041 |
if isinstance(value, str) and |
|
|
1042 | for x in value.split('.')): | |
|
1040 | if isinstance(value, str) and py3compat.isidentifier(value, dotted=True): | |
|
1043 | 1041 | return value |
|
1044 | 1042 | self.error(obj, value) |
|
1045 | 1043 |
@@ -30,10 +30,10 b' class ZMQDisplayHook(object):' | |||
|
30 | 30 | def _encode_binary(format_dict): |
|
31 | 31 | pngdata = format_dict.get('image/png') |
|
32 | 32 | if pngdata is not None: |
|
33 | format_dict['image/png'] = encodestring(pngdata) | |
|
33 | format_dict['image/png'] = encodestring(pngdata).decode('ascii') | |
|
34 | 34 | jpegdata = format_dict.get('image/jpeg') |
|
35 | 35 | if jpegdata is not None: |
|
36 | format_dict['image/jpeg'] = encodestring(jpegdata) | |
|
36 | format_dict['image/jpeg'] = encodestring(jpegdata).decode('ascii') | |
|
37 | 37 | |
|
38 | 38 | |
|
39 | 39 | class ZMQShellDisplayHook(DisplayHook): |
@@ -33,6 +33,7 b' from IPython.core.shellapp import (' | |||
|
33 | 33 | InteractiveShellApp, shell_flags, shell_aliases |
|
34 | 34 | ) |
|
35 | 35 | from IPython.utils import io |
|
36 | from IPython.utils import py3compat | |
|
36 | 37 | from IPython.utils.jsonutil import json_clean |
|
37 | 38 | from IPython.lib import pylabtools |
|
38 | 39 | from IPython.utils.traitlets import ( |
@@ -219,7 +220,10 b' class Kernel(Configurable):' | |||
|
219 | 220 | # Replace raw_input. Note that is not sufficient to replace |
|
220 | 221 | # raw_input in the user namespace. |
|
221 | 222 | raw_input = lambda prompt='': self._raw_input(prompt, ident, parent) |
|
222 | __builtin__.raw_input = raw_input | |
|
223 | if py3compat.PY3: | |
|
224 | __builtin__.input = raw_input | |
|
225 | else: | |
|
226 | __builtin__.raw_input = raw_input | |
|
223 | 227 | |
|
224 | 228 | # Set the parent message of the display hook and out streams. |
|
225 | 229 | shell.displayhook.set_parent(parent) |
@@ -188,7 +188,7 b' class ShellSocketChannel(ZMQSocketChannel):' | |||
|
188 | 188 | def run(self): |
|
189 | 189 | """The thread's main activity. Call start() instead.""" |
|
190 | 190 | self.socket = self.context.socket(zmq.DEALER) |
|
191 | self.socket.setsockopt(zmq.IDENTITY, self.session.session) | |
|
191 | self.socket.setsockopt(zmq.IDENTITY, self.session.bsession) | |
|
192 | 192 | self.socket.connect('tcp://%s:%i' % self.address) |
|
193 | 193 | self.iostate = POLLERR|POLLIN |
|
194 | 194 | self.ioloop.add_handler(self.socket, self._handle_events, |
@@ -394,8 +394,8 b' class SubSocketChannel(ZMQSocketChannel):' | |||
|
394 | 394 | def run(self): |
|
395 | 395 | """The thread's main activity. Call start() instead.""" |
|
396 | 396 | self.socket = self.context.socket(zmq.SUB) |
|
397 | self.socket.setsockopt(zmq.SUBSCRIBE,'') | |
|
398 | self.socket.setsockopt(zmq.IDENTITY, self.session.session) | |
|
397 | self.socket.setsockopt(zmq.SUBSCRIBE,b'') | |
|
398 | self.socket.setsockopt(zmq.IDENTITY, self.session.bsession) | |
|
399 | 399 | self.socket.connect('tcp://%s:%i' % self.address) |
|
400 | 400 | self.iostate = POLLIN|POLLERR |
|
401 | 401 | self.ioloop.add_handler(self.socket, self._handle_events, |
@@ -483,7 +483,7 b' class StdInSocketChannel(ZMQSocketChannel):' | |||
|
483 | 483 | def run(self): |
|
484 | 484 | """The thread's main activity. Call start() instead.""" |
|
485 | 485 | self.socket = self.context.socket(zmq.DEALER) |
|
486 | self.socket.setsockopt(zmq.IDENTITY, self.session.session) | |
|
486 | self.socket.setsockopt(zmq.IDENTITY, self.session.bsession) | |
|
487 | 487 | self.socket.connect('tcp://%s:%i' % self.address) |
|
488 | 488 | self.iostate = POLLERR|POLLIN |
|
489 | 489 | self.ioloop.add_handler(self.socket, self._handle_events, |
@@ -562,7 +562,7 b' class HBSocketChannel(ZMQSocketChannel):' | |||
|
562 | 562 | |
|
563 | 563 | def _create_socket(self): |
|
564 | 564 | self.socket = self.context.socket(zmq.REQ) |
|
565 | self.socket.setsockopt(zmq.IDENTITY, self.session.session) | |
|
565 | self.socket.setsockopt(zmq.IDENTITY, self.session.bsession) | |
|
566 | 566 | self.socket.connect('tcp://%s:%i' % self.address) |
|
567 | 567 | self.poller = zmq.Poller() |
|
568 | 568 | self.poller.register(self.socket, zmq.POLLIN) |
@@ -25,6 +25,7 b' import traceback' | |||
|
25 | 25 | import zmq |
|
26 | 26 | |
|
27 | 27 | # Local imports. |
|
28 | from IPython.utils import py3compat | |
|
28 | 29 | from IPython.utils.traitlets import HasTraits, Instance, Dict, Float |
|
29 | 30 | from completer import KernelCompleter |
|
30 | 31 | from entry_point import base_launch_kernel |
@@ -116,7 +117,10 b' class Kernel(HasTraits):' | |||
|
116 | 117 | # Replace raw_input. Note that is not sufficient to replace |
|
117 | 118 | # raw_input in the user namespace. |
|
118 | 119 | raw_input = lambda prompt='': self._raw_input(prompt, ident, parent) |
|
119 | __builtin__.raw_input = raw_input | |
|
120 | if py3compat.PY3: | |
|
121 | __builtin__.input = raw_input | |
|
122 | else: | |
|
123 | __builtin__.raw_input = raw_input | |
|
120 | 124 | |
|
121 | 125 | # Set the parent message of the display hook and out streams. |
|
122 | 126 | sys.displayhook.set_parent(parent) |
@@ -46,8 +46,9 b' from zmq.eventloop.zmqstream import ZMQStream' | |||
|
46 | 46 | from IPython.config.configurable import Configurable, LoggingConfigurable |
|
47 | 47 | from IPython.utils.importstring import import_item |
|
48 | 48 | from IPython.utils.jsonutil import extract_dates, squash_dates, date_default |
|
49 | from IPython.utils.py3compat import str_to_bytes | |
|
49 | 50 | from IPython.utils.traitlets import (CBytes, Unicode, Bool, Any, Instance, Set, |
|
50 | DottedObjectName) | |
|
51 | DottedObjectName, CUnicode) | |
|
51 | 52 | |
|
52 | 53 | #----------------------------------------------------------------------------- |
|
53 | 54 | # utility functions |
@@ -238,10 +239,18 b' class Session(Configurable):' | |||
|
238 | 239 | else: |
|
239 | 240 | self.unpack = import_item(str(new)) |
|
240 | 241 | |
|
241 |
session = C |
|
|
242 | session = CUnicode(u'', config=True, | |
|
242 | 243 | help="""The UUID identifying this session.""") |
|
243 | 244 | def _session_default(self): |
|
244 |
|
|
|
245 | u = unicode(uuid.uuid4()) | |
|
246 | self.bsession = u.encode('ascii') | |
|
247 | return u | |
|
248 | ||
|
249 | def _session_changed(self, name, old, new): | |
|
250 | self.bsession = self.session.encode('ascii') | |
|
251 | ||
|
252 | # bsession is the session as bytes | |
|
253 | bsession = CBytes(b'') | |
|
245 | 254 | |
|
246 | 255 | username = Unicode(os.environ.get('USER',u'username'), config=True, |
|
247 | 256 | help="""Username for the Session. Default is your system username.""") |
@@ -295,9 +304,11 b' class Session(Configurable):' | |||
|
295 | 304 | pack/unpack : callables |
|
296 | 305 | You can also set the pack/unpack callables for serialization |
|
297 | 306 | directly. |
|
298 |
session : |
|
|
307 | session : unicode (must be ascii) | |
|
299 | 308 | the ID of this Session object. The default is to generate a new |
|
300 | 309 | UUID. |
|
310 | bsession : bytes | |
|
311 | The session as bytes | |
|
301 | 312 | username : unicode |
|
302 | 313 | username added to message headers. The default is to ask the OS. |
|
303 | 314 | key : bytes |
@@ -310,6 +321,8 b' class Session(Configurable):' | |||
|
310 | 321 | super(Session, self).__init__(**kwargs) |
|
311 | 322 | self._check_packers() |
|
312 | 323 | self.none = self.pack({}) |
|
324 | # ensure self._session_default() if necessary, so bsession is defined: | |
|
325 | self.session | |
|
313 | 326 | |
|
314 | 327 | @property |
|
315 | 328 | def msg_id(self): |
@@ -380,7 +393,7 b' class Session(Configurable):' | |||
|
380 | 393 | h = self.auth.copy() |
|
381 | 394 | for m in msg_list: |
|
382 | 395 | h.update(m) |
|
383 | return h.hexdigest() | |
|
396 | return str_to_bytes(h.hexdigest()) | |
|
384 | 397 | |
|
385 | 398 | def serialize(self, msg, ident=None): |
|
386 | 399 | """Serialize the message components to bytes. |
@@ -401,7 +414,7 b' class Session(Configurable):' | |||
|
401 | 414 | [ident1,ident2,...,DELIM,HMAC,p_header,p_parent,p_content, |
|
402 | 415 | buffer1,buffer2,...]. In this list, the p_* entities are |
|
403 | 416 | the packed or serialized versions, so if JSON is used, these |
|
404 |
are u |
|
|
417 | are utf8 encoded JSON strings. | |
|
405 | 418 | """ |
|
406 | 419 | content = msg.get('content', {}) |
|
407 | 420 | if content is None: |
@@ -185,4 +185,26 b' class TestSession(SessionTestCase):' | |||
|
185 | 185 | content = dict(code='whoda',stuff=object()) |
|
186 | 186 | themsg = self.session.msg('execute',content=content) |
|
187 | 187 | pmsg = theids |
|
188 | ||
|
189 | def test_session_id(self): | |
|
190 | session = ss.Session() | |
|
191 | # get bs before us | |
|
192 | bs = session.bsession | |
|
193 | us = session.session | |
|
194 | self.assertEquals(us.encode('ascii'), bs) | |
|
195 | session = ss.Session() | |
|
196 | # get us before bs | |
|
197 | us = session.session | |
|
198 | bs = session.bsession | |
|
199 | self.assertEquals(us.encode('ascii'), bs) | |
|
200 | # change propagates: | |
|
201 | session.session = 'something else' | |
|
202 | bs = session.bsession | |
|
203 | us = session.session | |
|
204 | self.assertEquals(us.encode('ascii'), bs) | |
|
205 | session = ss.Session(session='stuff') | |
|
206 | # get us before bs | |
|
207 | self.assertEquals(session.bsession, session.session.encode('ascii')) | |
|
208 | self.assertEquals(b'stuff', session.bsession) | |
|
209 | ||
|
188 | 210 |
@@ -1,270 +1,10 b'' | |||
|
1 | #!/usr/bin/env python | |
|
2 | # -*- coding: utf-8 -*- | |
|
3 | """Setup script for IPython. | |
|
4 | ||
|
5 | Under Posix environments it works like a typical setup.py script. | |
|
6 | Under Windows, the command sdist is not supported, since IPython | |
|
7 | requires utilities which are not available under Windows.""" | |
|
8 | ||
|
9 | #----------------------------------------------------------------------------- | |
|
10 | # Copyright (c) 2008-2011, IPython Development Team. | |
|
11 | # Copyright (c) 2001-2007, Fernando Perez <fernando.perez@colorado.edu> | |
|
12 | # Copyright (c) 2001, Janko Hauser <jhauser@zscout.de> | |
|
13 | # Copyright (c) 2001, Nathaniel Gray <n8gray@caltech.edu> | |
|
14 | # | |
|
15 | # Distributed under the terms of the Modified BSD License. | |
|
16 | # | |
|
17 | # The full license is in the file COPYING.txt, distributed with this software. | |
|
18 | #----------------------------------------------------------------------------- | |
|
19 | ||
|
20 | #----------------------------------------------------------------------------- | |
|
21 | # Minimal Python version sanity check | |
|
22 | #----------------------------------------------------------------------------- | |
|
1 | """This calls the setup routine for Python 2 or 3 as required.""" | |
|
23 | 2 | |
|
24 | 3 | import sys |
|
25 | 4 | |
|
26 | # This check is also made in IPython/__init__, don't forget to update both when | |
|
27 | # changing Python version requirements. | |
|
28 | if sys.version[0:3] < '2.6': | |
|
29 | error = """\ | |
|
30 | ERROR: 'IPython requires Python Version 2.6 or above.' | |
|
31 | Exiting.""" | |
|
32 | print >> sys.stderr, error | |
|
33 | sys.exit(1) | |
|
34 | ||
|
35 | # At least we're on the python version we need, move on. | |
|
36 | ||
|
37 | #------------------------------------------------------------------------------- | |
|
38 | # Imports | |
|
39 | #------------------------------------------------------------------------------- | |
|
40 | ||
|
41 | # Stdlib imports | |
|
42 | import os | |
|
43 | import shutil | |
|
44 | ||
|
45 | from glob import glob | |
|
46 | ||
|
47 | # BEFORE importing distutils, remove MANIFEST. distutils doesn't properly | |
|
48 | # update it when the contents of directories change. | |
|
49 | if os.path.exists('MANIFEST'): os.remove('MANIFEST') | |
|
50 | ||
|
51 | from distutils.core import setup | |
|
52 | ||
|
53 | # Our own imports | |
|
54 | from IPython.utils.path import target_update | |
|
55 | ||
|
56 | from setupbase import ( | |
|
57 | setup_args, | |
|
58 | find_packages, | |
|
59 | find_package_data, | |
|
60 | find_scripts, | |
|
61 | find_data_files, | |
|
62 | check_for_dependencies, | |
|
63 | record_commit_info, | |
|
64 | ) | |
|
65 | from setupext import setupext | |
|
66 | ||
|
67 | isfile = os.path.isfile | |
|
68 | pjoin = os.path.join | |
|
69 | ||
|
70 | #----------------------------------------------------------------------------- | |
|
71 | # Function definitions | |
|
72 | #----------------------------------------------------------------------------- | |
|
73 | ||
|
74 | def cleanup(): | |
|
75 | """Clean up the junk left around by the build process""" | |
|
76 | if "develop" not in sys.argv: | |
|
77 | try: | |
|
78 | shutil.rmtree('ipython.egg-info') | |
|
79 | except: | |
|
80 | try: | |
|
81 | os.unlink('ipython.egg-info') | |
|
82 | except: | |
|
83 | pass | |
|
84 | ||
|
85 | #------------------------------------------------------------------------------- | |
|
86 | # Handle OS specific things | |
|
87 | #------------------------------------------------------------------------------- | |
|
88 | ||
|
89 | if os.name == 'posix': | |
|
90 | os_name = 'posix' | |
|
91 | elif os.name in ['nt','dos']: | |
|
92 | os_name = 'windows' | |
|
5 | if sys.version_info[0] >= 3: | |
|
6 | from setup3 import main | |
|
93 | 7 | else: |
|
94 | print 'Unsupported operating system:',os.name | |
|
95 | sys.exit(1) | |
|
96 | ||
|
97 | # Under Windows, 'sdist' has not been supported. Now that the docs build with | |
|
98 | # Sphinx it might work, but let's not turn it on until someone confirms that it | |
|
99 | # actually works. | |
|
100 | if os_name == 'windows' and 'sdist' in sys.argv: | |
|
101 | print 'The sdist command is not available under Windows. Exiting.' | |
|
102 | sys.exit(1) | |
|
103 | ||
|
104 | #------------------------------------------------------------------------------- | |
|
105 | # Things related to the IPython documentation | |
|
106 | #------------------------------------------------------------------------------- | |
|
107 | ||
|
108 | # update the manuals when building a source dist | |
|
109 | if len(sys.argv) >= 2 and sys.argv[1] in ('sdist','bdist_rpm'): | |
|
110 | import textwrap | |
|
111 | ||
|
112 | # List of things to be updated. Each entry is a triplet of args for | |
|
113 | # target_update() | |
|
114 | to_update = [ | |
|
115 | # FIXME - Disabled for now: we need to redo an automatic way | |
|
116 | # of generating the magic info inside the rst. | |
|
117 | #('docs/magic.tex', | |
|
118 | #['IPython/Magic.py'], | |
|
119 | #"cd doc && ./update_magic.sh" ), | |
|
120 | ||
|
121 | ('docs/man/ipcluster.1.gz', | |
|
122 | ['docs/man/ipcluster.1'], | |
|
123 | 'cd docs/man && gzip -9c ipcluster.1 > ipcluster.1.gz'), | |
|
124 | ||
|
125 | ('docs/man/ipcontroller.1.gz', | |
|
126 | ['docs/man/ipcontroller.1'], | |
|
127 | 'cd docs/man && gzip -9c ipcontroller.1 > ipcontroller.1.gz'), | |
|
128 | ||
|
129 | ('docs/man/ipengine.1.gz', | |
|
130 | ['docs/man/ipengine.1'], | |
|
131 | 'cd docs/man && gzip -9c ipengine.1 > ipengine.1.gz'), | |
|
132 | ||
|
133 | ('docs/man/iplogger.1.gz', | |
|
134 | ['docs/man/iplogger.1'], | |
|
135 | 'cd docs/man && gzip -9c iplogger.1 > iplogger.1.gz'), | |
|
136 | ||
|
137 | ('docs/man/ipython.1.gz', | |
|
138 | ['docs/man/ipython.1'], | |
|
139 | 'cd docs/man && gzip -9c ipython.1 > ipython.1.gz'), | |
|
140 | ||
|
141 | ('docs/man/irunner.1.gz', | |
|
142 | ['docs/man/irunner.1'], | |
|
143 | 'cd docs/man && gzip -9c irunner.1 > irunner.1.gz'), | |
|
144 | ||
|
145 | ('docs/man/pycolor.1.gz', | |
|
146 | ['docs/man/pycolor.1'], | |
|
147 | 'cd docs/man && gzip -9c pycolor.1 > pycolor.1.gz'), | |
|
148 | ] | |
|
149 | ||
|
150 | # Only build the docs if sphinx is present | |
|
151 | try: | |
|
152 | import sphinx | |
|
153 | except ImportError: | |
|
154 | pass | |
|
155 | else: | |
|
156 | # The Makefile calls the do_sphinx scripts to build html and pdf, so | |
|
157 | # just one target is enough to cover all manual generation | |
|
158 | ||
|
159 | # First, compute all the dependencies that can force us to rebuild the | |
|
160 | # docs. Start with the main release file that contains metadata | |
|
161 | docdeps = ['IPython/core/release.py'] | |
|
162 | # Inculde all the reST sources | |
|
163 | pjoin = os.path.join | |
|
164 | for dirpath,dirnames,filenames in os.walk('docs/source'): | |
|
165 | if dirpath in ['_static','_templates']: | |
|
166 | continue | |
|
167 | docdeps += [ pjoin(dirpath,f) for f in filenames | |
|
168 | if f.endswith('.txt') ] | |
|
169 | # and the examples | |
|
170 | for dirpath,dirnames,filenames in os.walk('docs/example'): | |
|
171 | docdeps += [ pjoin(dirpath,f) for f in filenames | |
|
172 | if not f.endswith('~') ] | |
|
173 | # then, make them all dependencies for the main html docs | |
|
174 | to_update.append( | |
|
175 | ('docs/dist/index.html', | |
|
176 | docdeps, | |
|
177 | "cd docs && make dist") | |
|
178 | ) | |
|
179 | ||
|
180 | [ target_update(*t) for t in to_update ] | |
|
181 | ||
|
182 | #--------------------------------------------------------------------------- | |
|
183 | # Find all the packages, package data, and data_files | |
|
184 | #--------------------------------------------------------------------------- | |
|
185 | ||
|
186 | packages = find_packages() | |
|
187 | package_data = find_package_data() | |
|
188 | data_files = find_data_files() | |
|
189 | ||
|
190 | #--------------------------------------------------------------------------- | |
|
191 | # Handle scripts, dependencies, and setuptools specific things | |
|
192 | #--------------------------------------------------------------------------- | |
|
193 | ||
|
194 | # For some commands, use setuptools. Note that we do NOT list install here! | |
|
195 | # If you want a setuptools-enhanced install, just run 'setupegg.py install' | |
|
196 | needs_setuptools = set(('develop', 'sdist', 'release', 'bdist_egg', 'bdist_rpm', | |
|
197 | 'bdist', 'bdist_dumb', 'bdist_wininst', 'install_egg_info', | |
|
198 | 'build_sphinx', 'egg_info', 'easy_install', 'upload', | |
|
199 | )) | |
|
200 | if sys.platform == 'win32': | |
|
201 | # Depend on setuptools for install on *Windows only* | |
|
202 | # If we get script-installation working without setuptools, | |
|
203 | # then we can back off, but until then use it. | |
|
204 | # See Issue #369 on GitHub for more | |
|
205 | needs_setuptools.add('install') | |
|
206 | ||
|
207 | if len(needs_setuptools.intersection(sys.argv)) > 0: | |
|
208 | import setuptools | |
|
209 | ||
|
210 | # This dict is used for passing extra arguments that are setuptools | |
|
211 | # specific to setup | |
|
212 | setuptools_extra_args = {} | |
|
213 | ||
|
214 | if 'setuptools' in sys.modules: | |
|
215 | setuptools_extra_args['zip_safe'] = False | |
|
216 | setuptools_extra_args['entry_points'] = find_scripts(True) | |
|
217 | setup_args['extras_require'] = dict( | |
|
218 | parallel = 'pyzmq>=2.1.4', | |
|
219 | zmq = 'pyzmq>=2.1.4', | |
|
220 | doc = 'Sphinx>=0.3', | |
|
221 | test = 'nose>=0.10.1', | |
|
222 | notebook = 'tornado>=2.0' | |
|
223 | ) | |
|
224 | requires = setup_args.setdefault('install_requires', []) | |
|
225 | setupext.display_status = False | |
|
226 | if not setupext.check_for_readline(): | |
|
227 | if sys.platform == 'darwin': | |
|
228 | requires.append('readline') | |
|
229 | elif sys.platform.startswith('win') and sys.maxsize < 2**32: | |
|
230 | # only require pyreadline on 32b Windows, due to 64b bug in pyreadline: | |
|
231 | # https://bugs.launchpad.net/pyreadline/+bug/787574 | |
|
232 | requires.append('pyreadline') | |
|
233 | else: | |
|
234 | pass | |
|
235 | # do we want to install readline here? | |
|
236 | ||
|
237 | # Script to be run by the windows binary installer after the default setup | |
|
238 | # routine, to add shortcuts and similar windows-only things. Windows | |
|
239 | # post-install scripts MUST reside in the scripts/ dir, otherwise distutils | |
|
240 | # doesn't find them. | |
|
241 | if 'bdist_wininst' in sys.argv: | |
|
242 | if len(sys.argv) > 2 and \ | |
|
243 | ('sdist' in sys.argv or 'bdist_rpm' in sys.argv): | |
|
244 | print >> sys.stderr, "ERROR: bdist_wininst must be run alone. Exiting." | |
|
245 | sys.exit(1) | |
|
246 | setup_args['scripts'] = [pjoin('scripts','ipython_win_post_install.py')] | |
|
247 | setup_args['options'] = {"bdist_wininst": | |
|
248 | {"install_script": | |
|
249 | "ipython_win_post_install.py"}} | |
|
250 | else: | |
|
251 | # If we are running without setuptools, call this function which will | |
|
252 | # check for dependencies an inform the user what is needed. This is | |
|
253 | # just to make life easy for users. | |
|
254 | check_for_dependencies() | |
|
255 | setup_args['scripts'] = find_scripts(False) | |
|
256 | ||
|
257 | #--------------------------------------------------------------------------- | |
|
258 | # Do the actual setup now | |
|
259 | #--------------------------------------------------------------------------- | |
|
260 | ||
|
261 | setup_args['cmdclass'] = {'build_py': record_commit_info('IPython')} | |
|
262 | setup_args['packages'] = packages | |
|
263 | setup_args['package_data'] = package_data | |
|
264 | setup_args['data_files'] = data_files | |
|
265 | setup_args.update(setuptools_extra_args) | |
|
266 | ||
|
8 | from setup2 import main | |
|
267 | 9 | |
|
268 | if __name__ == '__main__': | |
|
269 | setup(**setup_args) | |
|
270 | cleanup() | |
|
10 | main() |
@@ -23,7 +23,10 b' from __future__ import print_function' | |||
|
23 | 23 | import os |
|
24 | 24 | import sys |
|
25 | 25 | |
|
26 | from ConfigParser import ConfigParser | |
|
26 | try: | |
|
27 | from configparser import ConfigParser | |
|
28 | except: | |
|
29 | from ConfigParser import ConfigParser | |
|
27 | 30 | from distutils.command.build_py import build_py |
|
28 | 31 | from glob import glob |
|
29 | 32 | |
@@ -40,6 +43,13 b' pjoin = os.path.join' | |||
|
40 | 43 | def oscmd(s): |
|
41 | 44 | print(">", s) |
|
42 | 45 | os.system(s) |
|
46 | ||
|
47 | try: | |
|
48 | execfile | |
|
49 | except NameError: | |
|
50 | def execfile(fname, globs, locs=None): | |
|
51 | locs = locs or globs | |
|
52 | exec(compile(open(fname).read(), fname, "exec"), globs, locs) | |
|
43 | 53 | |
|
44 | 54 | # A little utility we'll need below, since glob() does NOT allow you to do |
|
45 | 55 | # exclusion on multiple endings! |
@@ -58,7 +68,7 b' def file_doesnt_endwith(test,endings):' | |||
|
58 | 68 | #--------------------------------------------------------------------------- |
|
59 | 69 | |
|
60 | 70 | # release.py contains version, authors, license, url, keywords, etc. |
|
61 | execfile(pjoin('IPython','core','release.py')) | |
|
71 | execfile(pjoin('IPython','core','release.py'), globals()) | |
|
62 | 72 | |
|
63 | 73 | # Create a dict with the basic information |
|
64 | 74 | # This dict is eventually passed to setup after additional keys are added. |
@@ -74,6 +84,7 b' setup_args = dict(' | |||
|
74 | 84 | license = license, |
|
75 | 85 | platforms = platforms, |
|
76 | 86 | keywords = keywords, |
|
87 | classifiers = classifiers, | |
|
77 | 88 | cmdclass = {'install_data': install_data_ext}, |
|
78 | 89 | ) |
|
79 | 90 | |
@@ -235,28 +246,31 b' def make_man_update_target(manpage):' | |||
|
235 | 246 | # Find scripts |
|
236 | 247 | #--------------------------------------------------------------------------- |
|
237 | 248 | |
|
238 | def find_scripts(entry_points=False): | |
|
249 | def find_scripts(entry_points=False, suffix=''): | |
|
239 | 250 | """Find IPython's scripts. |
|
240 | 251 | |
|
241 | 252 | if entry_points is True: |
|
242 | 253 | return setuptools entry_point-style definitions |
|
243 | 254 | else: |
|
244 | 255 | return file paths of plain scripts [default] |
|
256 | ||
|
257 | suffix is appended to script names if entry_points is True, so that the | |
|
258 | Python 3 scripts get named "ipython3" etc. | |
|
245 | 259 | """ |
|
246 | 260 | if entry_points: |
|
247 | console_scripts = [ | |
|
248 | 'ipython = IPython.frontend.terminal.ipapp:launch_new_instance', | |
|
249 | 'pycolor = IPython.utils.PyColorize:main', | |
|
250 | 'ipcontroller = IPython.parallel.apps.ipcontrollerapp:launch_new_instance', | |
|
251 | 'ipengine = IPython.parallel.apps.ipengineapp:launch_new_instance', | |
|
252 | 'iplogger = IPython.parallel.apps.iploggerapp:launch_new_instance', | |
|
253 | 'ipcluster = IPython.parallel.apps.ipclusterapp:launch_new_instance', | |
|
254 | 'iptest = IPython.testing.iptest:main', | |
|
255 | 'irunner = IPython.lib.irunner:main' | |
|
256 | ] | |
|
257 | gui_scripts = [ | |
|
258 | 'ipython-qtconsole = IPython.frontend.qt.console.qtconsoleapp:main', | |
|
259 | ] | |
|
261 | console_scripts = [s % suffix for s in [ | |
|
262 | 'ipython%s = IPython.frontend.terminal.ipapp:launch_new_instance', | |
|
263 | 'pycolor%s = IPython.utils.PyColorize:main', | |
|
264 | 'ipcontroller%s = IPython.parallel.apps.ipcontrollerapp:launch_new_instance', | |
|
265 | 'ipengine%s = IPython.parallel.apps.ipengineapp:launch_new_instance', | |
|
266 | 'iplogger%s = IPython.parallel.apps.iploggerapp:launch_new_instance', | |
|
267 | 'ipcluster%s = IPython.parallel.apps.ipclusterapp:launch_new_instance', | |
|
268 | 'iptest%s = IPython.testing.iptest:main', | |
|
269 | 'irunner%s = IPython.lib.irunner:main' | |
|
270 | ]] | |
|
271 | gui_scripts = [s % suffix for s in [ | |
|
272 | 'ipython%s-qtconsole = IPython.frontend.qt.console.qtconsoleapp:main', | |
|
273 | ]] | |
|
260 | 274 | scripts = dict(console_scripts=console_scripts, gui_scripts=gui_scripts) |
|
261 | 275 | else: |
|
262 | 276 | parallel_scripts = pjoin('IPython','parallel','scripts') |
General Comments 0
You need to be logged in to leave comments.
Login now