##// END OF EJS Templates
Massive refactoring of of the core....
Brian Granger -
Show More
@@ -1,81 +1,66 b''
1 1 #-----------------------------------------------------------------------------
2 # IPython Shell Configuration Defaults
2 # Global options
3 3 #-----------------------------------------------------------------------------
4 4
5 Global.classic = False
6 Global.nosep = False
7
5 8 #-----------------------------------------------------------------------------
6 # Startup
9 # InteractiveShell options
7 10 #-----------------------------------------------------------------------------
8 11
9 AUTOCALL = True
10
11 AUTOEDIT_SYNTAX = False
12
13 AUTOINDENT = True
14
15 AUTOMAGIC = True
16
17 CACHE_SIZE = 1000
18 12
19 CLASSIC = False
13 InteractiveShell.autocall = 1
20 14
21 COLORS = 'Linux'
15 InteractiveShell.autoedit_syntax = False
22 16
23 COLOR_INFO = True
17 InteractiveShell.autoindent = True
24 18
25 CONFIRM_EXIT = True
19 InteractiveShell.automagic = False
26 20
27 DEEP_RELOAD = False
21 InteractiveShell.banner1 = 'This if for overriding the default IPython banner'
22
23 InteractiveShell.banner2 = "This is for extra banner text"
28 24
29 EDITOR = 0
25 InteractiveShell.cache_size = 1000
30 26
31 LOG = True
27 InteractiveShell.colors = 'LightBG'
32 28
33 LOGFILE = ''
29 InteractiveShell.color_info = True
34 30
35 BANNER = True
31 InteractiveShell.confirm_exit = True
36 32
37 MESSAGES = True
33 InteractiveShell.deep_reload = False
38 34
39 PDB = False
35 InteractiveShell.display_banner = True
40 36
41 PPRINT = True
37 InteractiveShell.editor = 'nano'
42 38
43 PROMPT_IN1 = 'In [\#]: '
39 InteractiveShell.logstart = True
44 40
45 PROMPT_IN2 = ' .\D.: '
41 InteractiveShell.logfile = 'ipython_log.py'
46 42
47 PROMPT_OUT = 'Out[\#]: '
43 InteractiveShell.logplay = 'mylog.py'
48 44
49 PROMPTS_PAD_LEFT = True
45 InteractiveShell.object_info_string_level = 0
50 46
51 QUICK = False
47 InteractiveShell.pager = 'less'
52 48
53 SCREEN_LENGTH = 0
49 InteractiveShell.pdb = False
54 50
55 SEPARATE_IN = '\n'
56 SEPARATE_OUT = ''
57 SEPARATE_OUT2 = ''
58 NOSEP = False
51 InteractiveShell.pprint = True
59 52
60 WILDCARDS_CASE_SENSITIVE = True
53 InteractiveShell.prompt_in1 = 'In [\#]: '
54 InteractiveShell.prompt_in2 = ' .\D.: '
55 InteractiveShell.prompt_out = 'Out[\#]: '
56 InteractiveShell.prompts_pad_left = True
61 57
62 OBJECT_INFO_STRING_LEVEL = 0
58 InteractiveShell.quiet = False
63 59
64 XMODE = 'Context'
60 # Readline
61 InteractiveShell.readline_use = False
65 62
66 MULTI_LINE_SPECIALS = True
67
68 SYSTEM_HEADER = "IPython system call: "
69
70 SYSTEM_VERBOSE = True
71
72 #-----------------------------------------------------------------------------
73 # Readline
74 #-----------------------------------------------------------------------------
75
76 READLINE = True
77
78 READLINE_PARSE_AND_BIND = [
63 InteractiveShell.readline_parse_and_bind = [
79 64 'tab: complete',
80 65 '"\C-l": possible-completions',
81 66 'set show-all-if-ambiguous on',
@@ -92,29 +77,39 b' READLINE_PARSE_AND_BIND = ['
92 77 '"\C-k": kill-line',
93 78 '"\C-u": unix-line-discard',
94 79 ]
80 InteractiveShell.readline_remove_delims = '-/~'
81 InteractiveShell.readline_merge_completions = True
82 InteractiveShell.readline_omit_names = 0
83
84 InteractiveShell.screen_length = 0
85
86 InteractiveShell.separate_in = '\n'
87 InteractiveShell.separate_out = ''
88 InteractiveShell.separate_out2 = ''
89
90 InteractiveShell.system_header = "IPython system call: "
95 91
96 READLINE_REMOVE_DELIMS = '-/~'
92 InteractiveShell.system_verbose = True
97 93
98 READLINE_MERGE_COMPLETIONS = True
94 InteractiveShell.term_title = False
99 95
100 READLINE_OMIT_NAMES = 0
96 InteractiveShell.wildcards_case_sensitive = True
97
98 InteractiveShell.xmode = 'Context'
101 99
102 100 #-----------------------------------------------------------------------------
103 # Code to execute
101 # PrefilterManager options
104 102 #-----------------------------------------------------------------------------
105 103
106 EXECUTE = [
107 'import numpy as np',
108 'import sympy',
109 'a = 10'
110 ]
111
112 EXECFILE = []
104 PrefilterManager.multi_line_specials = True
113 105
114 106 #-----------------------------------------------------------------------------
115 # Alias
107 # AliasManager options
116 108 #-----------------------------------------------------------------------------
117 109
118 ALIAS = [
119 ('myls', 'ls -la')
110 # Do this to enable all defaults
111 # AliasManager.default_aliases = []
112
113 AliasManger.user_aliases = [
114 ('foo', 'echo Hi')
120 115 ] No newline at end of file
@@ -1,6 +1,10 b''
1 1 #!/usr/bin/env python
2 2 # encoding: utf-8
3 """A factory for creating configuration objects.
3 """A simple configuration system.
4
5 Authors:
6
7 * Brian Granger
4 8 """
5 9
6 10 #-----------------------------------------------------------------------------
@@ -14,22 +18,138 b''
14 18 # Imports
15 19 #-----------------------------------------------------------------------------
16 20
21 import __builtin__
17 22 import os
18 23 import sys
19 24
20 25 from IPython.external import argparse
21 from IPython.utils.ipstruct import Struct
22 26 from IPython.utils.genutils import filefind
23 27
24 28 #-----------------------------------------------------------------------------
25 # Code
29 # Exceptions
26 30 #-----------------------------------------------------------------------------
27 31
28 32
29 class ConfigLoaderError(Exception):
33 class ConfigError(Exception):
30 34 pass
31 35
32 36
37 class ConfigLoaderError(ConfigError):
38 pass
39
40
41 #-----------------------------------------------------------------------------
42 # Config class for holding config information
43 #-----------------------------------------------------------------------------
44
45
46 class Config(dict):
47 """An attribute based dict that can do smart merges."""
48
49 def __init__(self, *args, **kwds):
50 dict.__init__(self, *args, **kwds)
51 # This sets self.__dict__ = self, but it has to be done this way
52 # because we are also overriding __setattr__.
53 dict.__setattr__(self, '__dict__', self)
54
55 def _merge(self, other):
56 to_update = {}
57 for k, v in other.items():
58 if not self.has_key(k):
59 to_update[k] = v
60 else: # I have this key
61 if isinstance(v, Config):
62 # Recursively merge common sub Configs
63 self[k]._merge(v)
64 else:
65 # Plain updates for non-Configs
66 to_update[k] = v
67
68 self.update(to_update)
69
70 def _is_section_key(self, key):
71 if key[0].upper()==key[0] and not key.startswith('_'):
72 return True
73 else:
74 return False
75
76 def has_key(self, key):
77 if self._is_section_key(key):
78 return True
79 else:
80 return dict.has_key(self, key)
81
82 def _has_section(self, key):
83 if self._is_section_key(key):
84 if dict.has_key(self, key):
85 return True
86 return False
87
88 def copy(self):
89 return type(self)(dict.copy(self))
90
91 def __copy__(self):
92 return self.copy()
93
94 def __deepcopy__(self, memo):
95 import copy
96 return type(self)(copy.deepcopy(self.items()))
97
98 def __getitem__(self, key):
99 # Because we use this for an exec namespace, we need to delegate
100 # the lookup of names in __builtin__ to itself. This means
101 # that you can't have section or attribute names that are
102 # builtins.
103 try:
104 return getattr(__builtin__, key)
105 except AttributeError:
106 pass
107 if self._is_section_key(key):
108 try:
109 return dict.__getitem__(self, key)
110 except KeyError:
111 c = Config()
112 dict.__setitem__(self, key, c)
113 return c
114 else:
115 return dict.__getitem__(self, key)
116
117 def __setitem__(self, key, value):
118 # Don't allow names in __builtin__ to be modified.
119 if hasattr(__builtin__, key):
120 raise ConfigError('Config variable names cannot have the same name '
121 'as a Python builtin: %s' % key)
122 if self._is_section_key(key):
123 if not isinstance(value, Config):
124 raise ValueError('values whose keys begin with an uppercase '
125 'char must be Config instances: %r, %r' % (key, value))
126 else:
127 dict.__setitem__(self, key, value)
128
129 def __getattr__(self, key):
130 try:
131 return self.__getitem__(key)
132 except KeyError, e:
133 raise AttributeError(e)
134
135 def __setattr__(self, key, value):
136 try:
137 self.__setitem__(key, value)
138 except KeyError, e:
139 raise AttributeError(e)
140
141 def __delattr__(self, key):
142 try:
143 dict.__delitem__(self, key)
144 except KeyError, e:
145 raise AttributeError(e)
146
147
148 #-----------------------------------------------------------------------------
149 # Config loading classes
150 #-----------------------------------------------------------------------------
151
152
33 153 class ConfigLoader(object):
34 154 """A object for loading configurations from just about anywhere.
35 155
@@ -59,7 +179,7 b' class ConfigLoader(object):'
59 179 self.clear()
60 180
61 181 def clear(self):
62 self.config = Struct()
182 self.config = Config()
63 183
64 184 def load_config(self):
65 185 """Load a config from somewhere, return a Struct.
@@ -106,7 +226,7 b' class PyFileConfigLoader(FileConfigLoader):'
106 226 """Load the config from a file and return it as a Struct."""
107 227 self._find_file()
108 228 self._read_file_as_dict()
109 self._convert_to_struct()
229 self._convert_to_config()
110 230 return self.config
111 231
112 232 def _find_file(self):
@@ -114,15 +234,12 b' class PyFileConfigLoader(FileConfigLoader):'
114 234 self.full_filename = filefind(self.filename, self.path)
115 235
116 236 def _read_file_as_dict(self):
117 self.data = {}
118 execfile(self.full_filename, self.data)
237 execfile(self.full_filename, self.config)
119 238
120 def _convert_to_struct(self):
239 def _convert_to_config(self):
121 240 if self.data is None:
122 241 ConfigLoaderError('self.data does not exist')
123 for k, v in self.data.iteritems():
124 if k == k.upper():
125 self.config[k] = v
242 del self.config['__builtins__']
126 243
127 244
128 245 class CommandLineConfigLoader(ConfigLoader):
@@ -133,8 +250,8 b' class CommandLineConfigLoader(ConfigLoader):'
133 250 """
134 251
135 252
136 class NoDefault(object): pass
137 NoDefault = NoDefault()
253 class NoConfigDefault(object): pass
254 NoConfigDefault = NoConfigDefault()
138 255
139 256 class ArgParseConfigLoader(CommandLineConfigLoader):
140 257
@@ -155,7 +272,7 b' class ArgParseConfigLoader(CommandLineConfigLoader):'
155 272 """Parse command line arguments and return as a Struct."""
156 273 self._create_parser()
157 274 self._parse_args(args)
158 self._convert_to_struct()
275 self._convert_to_config()
159 276 return self.config
160 277
161 278 def _create_parser(self):
@@ -169,7 +286,7 b' class ArgParseConfigLoader(CommandLineConfigLoader):'
169 286 def _add_arguments(self):
170 287 for argument in self.arguments:
171 288 if not argument[1].has_key('default'):
172 argument[1]['default'] = NoDefault
289 argument[1]['default'] = NoConfigDefault
173 290 self.parser.add_argument(*argument[0],**argument[1])
174 291
175 292 def _parse_args(self, args=None):
@@ -179,25 +296,10 b' class ArgParseConfigLoader(CommandLineConfigLoader):'
179 296 else:
180 297 self.parsed_data = self.parser.parse_args(args)
181 298
182 def _convert_to_struct(self):
299 def _convert_to_config(self):
183 300 """self.parsed_data->self.config"""
184 self.config = Struct()
185 301 for k, v in vars(self.parsed_data).items():
186 if v is not NoDefault:
187 setattr(self.config, k, v)
188
189 class IPythonArgParseConfigLoader(ArgParseConfigLoader):
302 if v is not NoConfigDefault:
303 exec_str = 'self.config.' + k + '= v'
304 exec exec_str in locals(), globals()
190 305
191 def _add_other_arguments(self):
192 self.parser.add_argument('-ipythondir',dest='IPYTHONDIR',type=str,
193 help='Set to override default location of IPYTHONDIR.',
194 default=NoDefault)
195 self.parser.add_argument('-p','-profile',dest='PROFILE',type=str,
196 help='The string name of the ipython profile to be used.',
197 default=NoDefault)
198 self.parser.add_argument('-debug',dest="DEBUG",action='store_true',
199 help='Debug the application startup process.',
200 default=NoDefault)
201 self.parser.add_argument('-config_file',dest='CONFIG_FILE',type=str,
202 help='Set the config file name to override default.',
203 default=NoDefault)
@@ -24,7 +24,12 b' import os'
24 24 from tempfile import mkstemp
25 25 from unittest import TestCase
26 26
27 from IPython.config.loader import PyFileConfigLoader, ArgParseConfigLoader
27 from IPython.config.loader import (
28 Config,
29 PyFileConfigLoader,
30 ArgParseConfigLoader,
31 ConfigError
32 )
28 33
29 34 #-----------------------------------------------------------------------------
30 35 # Actual tests
@@ -32,10 +37,11 b' from IPython.config.loader import PyFileConfigLoader, ArgParseConfigLoader'
32 37
33 38
34 39 pyfile = """
35 A = 10
36 B = range(10)
37 C = True
38 D = 'hi there'
40 a = 10
41 b = 20
42 Foo.Bar.value = 10
43 Foo.Bam.value = range(10)
44 D.C.value = 'hi there'
39 45 """
40 46
41 47 class TestPyFileCL(TestCase):
@@ -48,10 +54,11 b' class TestPyFileCL(TestCase):'
48 54 # Unlink the file
49 55 cl = PyFileConfigLoader(fname)
50 56 config = cl.load_config()
51 self.assertEquals(config.A, 10)
52 self.assertEquals(config.B, range(10))
53 self.assertEquals(config.C, True)
54 self.assertEquals(config.D, 'hi there')
57 self.assertEquals(config.a, 10)
58 self.assertEquals(config.b, 20)
59 self.assertEquals(config.Foo.Bar.value, 10)
60 self.assertEquals(config.Foo.Bam.value, range(10))
61 self.assertEquals(config.D.C.value, 'hi there')
55 62
56 63
57 64 class TestArgParseCL(TestCase):
@@ -60,18 +67,18 b' class TestArgParseCL(TestCase):'
60 67
61 68 class MyLoader(ArgParseConfigLoader):
62 69 arguments = (
63 (('-f','--foo'), dict(dest='FOO', type=str)),
64 (('-b',), dict(dest='BAR', type=int)),
65 (('-n',), dict(dest='N', action='store_true')),
66 (('BAM',), dict(type=str))
70 (('-f','--foo'), dict(dest='Global.foo', type=str)),
71 (('-b',), dict(dest='MyClass.bar', type=int)),
72 (('-n',), dict(dest='n', action='store_true')),
73 (('Global.bam',), dict(type=str))
67 74 )
68 75
69 76 cl = MyLoader()
70 77 config = cl.load_config('-f hi -b 10 -n wow'.split())
71 self.assertEquals(config.FOO, 'hi')
72 self.assertEquals(config.BAR, 10)
73 self.assertEquals(config.N, True)
74 self.assertEquals(config.BAM, 'wow')
78 self.assertEquals(config.Global.foo, 'hi')
79 self.assertEquals(config.MyClass.bar, 10)
80 self.assertEquals(config.n, True)
81 self.assertEquals(config.Global.bam, 'wow')
75 82
76 83 def test_add_arguments(self):
77 84
@@ -79,7 +86,7 b' class TestArgParseCL(TestCase):'
79 86 def _add_arguments(self):
80 87 subparsers = self.parser.add_subparsers(dest='subparser_name')
81 88 subparser1 = subparsers.add_parser('1')
82 subparser1.add_argument('-x')
89 subparser1.add_argument('-x',dest='Global.x')
83 90 subparser2 = subparsers.add_parser('2')
84 91 subparser2.add_argument('y')
85 92
@@ -89,5 +96,68 b' class TestArgParseCL(TestCase):'
89 96 self.assertEquals(config.y, 'frobble')
90 97 config = cl.load_config('1 -x frobble'.split())
91 98 self.assertEquals(config.subparser_name, '1')
92 self.assertEquals(config.x, 'frobble')
93
99 self.assertEquals(config.Global.x, 'frobble')
100
101 class TestConfig(TestCase):
102
103 def test_setget(self):
104 c = Config()
105 c.a = 10
106 self.assertEquals(c.a, 10)
107 self.assertEquals(c.has_key('b'), False)
108
109 def test_auto_section(self):
110 c = Config()
111 self.assertEquals(c.has_key('A'), True)
112 self.assertEquals(c._has_section('A'), False)
113 A = c.A
114 A.foo = 'hi there'
115 self.assertEquals(c._has_section('A'), True)
116 self.assertEquals(c.A.foo, 'hi there')
117 del c.A
118 self.assertEquals(len(c.A.keys()),0)
119
120 def test_merge_doesnt_exist(self):
121 c1 = Config()
122 c2 = Config()
123 c2.bar = 10
124 c2.Foo.bar = 10
125 c1._merge(c2)
126 self.assertEquals(c1.Foo.bar, 10)
127 self.assertEquals(c1.bar, 10)
128 c2.Bar.bar = 10
129 c1._merge(c2)
130 self.assertEquals(c1.Bar.bar, 10)
131
132 def test_merge_exists(self):
133 c1 = Config()
134 c2 = Config()
135 c1.Foo.bar = 10
136 c1.Foo.bam = 30
137 c2.Foo.bar = 20
138 c2.Foo.wow = 40
139 c1._merge(c2)
140 self.assertEquals(c1.Foo.bam, 30)
141 self.assertEquals(c1.Foo.bar, 20)
142 self.assertEquals(c1.Foo.wow, 40)
143 c2.Foo.Bam.bam = 10
144 c1._merge(c2)
145 self.assertEquals(c1.Foo.Bam.bam, 10)
146
147 def test_deepcopy(self):
148 c1 = Config()
149 c1.Foo.bar = 10
150 c1.Foo.bam = 30
151 c1.a = 'asdf'
152 c1.b = range(10)
153 import copy
154 c2 = copy.deepcopy(c1)
155 self.assertEquals(c1, c2)
156 self.assert_(c1 is not c2)
157 self.assert_(c1.Foo is not c2.Foo)
158
159 def test_builtin(self):
160 c1 = Config()
161 exec 'foo = True' in c1
162 self.assertEquals(c1.foo, True)
163 self.assertRaises(ConfigError, setattr, c1, 'ValueError', 10)
@@ -43,7 +43,7 b' def default_aliases():'
43 43 # Make some aliases automatically
44 44 # Prepare list of shell aliases to auto-define
45 45 if os.name == 'posix':
46 auto_alias = ('mkdir mkdir', 'rmdir rmdir',
46 default_aliases = ('mkdir mkdir', 'rmdir rmdir',
47 47 'mv mv -i','rm rm -i','cp cp -i',
48 48 'cat cat','less less','clear clear',
49 49 # a better ls
@@ -75,15 +75,15 b' def default_aliases():'
75 75 # things which are executable
76 76 'lx ls -lF | grep ^-..x',
77 77 )
78 auto_alias = auto_alias + ls_extra
78 default_aliases = default_aliases + ls_extra
79 79 elif os.name in ['nt','dos']:
80 auto_alias = ('ls dir /on',
80 default_aliases = ('ls dir /on',
81 81 'ddir dir /ad /on', 'ldir dir /ad /on',
82 82 'mkdir mkdir','rmdir rmdir','echo echo',
83 83 'ren ren','cls cls','copy copy')
84 84 else:
85 auto_alias = ()
86 return [s.split(None,1) for s in auto_alias]
85 default_aliases = ()
86 return [s.split(None,1) for s in default_aliases]
87 87
88 88
89 89 class AliasError(Exception):
@@ -101,8 +101,8 b' class InvalidAliasError(AliasError):'
101 101
102 102 class AliasManager(Component):
103 103
104 auto_alias = List(default_aliases())
105 user_alias = List(default_value=[], config_key='USER_ALIAS')
104 default_aliases = List(default_aliases(), config=True)
105 user_aliases = List(default_value=[], config=True)
106 106
107 107 def __init__(self, parent, config=None):
108 108 super(AliasManager, self).__init__(parent, config=config)
@@ -137,13 +137,16 b' class AliasManager(Component):'
137 137
138 138 def init_aliases(self):
139 139 # Load default aliases
140 for name, cmd in self.auto_alias:
140 for name, cmd in self.default_aliases:
141 141 self.soft_define_alias(name, cmd)
142 142
143 143 # Load user aliases
144 for name, cmd in self.user_alias:
144 for name, cmd in self.user_aliases:
145 145 self.soft_define_alias(name, cmd)
146 146
147 def clear_aliases(self):
148 self.alias_table.clear()
149
147 150 def soft_define_alias(self, name, cmd):
148 151 """Define an alias, but don't raise on an AliasError."""
149 152 try:
@@ -160,6 +163,10 b' class AliasManager(Component):'
160 163 nargs = self.validate_alias(name, cmd)
161 164 self.alias_table[name] = (nargs, cmd)
162 165
166 def undefine_alias(self, name):
167 if self.alias_table.has_key(name):
168 del self.alias_table[name]
169
163 170 def validate_alias(self, name, cmd):
164 171 """Validate an alias and return the its number of arguments."""
165 172 if name in self.no_alias:
@@ -26,13 +26,14 b' Notes'
26 26 import os
27 27 import sys
28 28 import traceback
29
30 29 from copy import deepcopy
31 from IPython.utils.ipstruct import Struct
30
32 31 from IPython.utils.genutils import get_ipython_dir, filefind
33 32 from IPython.config.loader import (
34 IPythonArgParseConfigLoader,
35 PyFileConfigLoader
33 PyFileConfigLoader,
34 ArgParseConfigLoader,
35 Config,
36 NoConfigDefault
36 37 )
37 38
38 39 #-----------------------------------------------------------------------------
@@ -40,6 +41,27 b' from IPython.config.loader import ('
40 41 #-----------------------------------------------------------------------------
41 42
42 43
44 class IPythonArgParseConfigLoader(ArgParseConfigLoader):
45 """Default command line options for IPython based applications."""
46
47 def _add_other_arguments(self):
48 self.parser.add_argument('-ipythondir',dest='Global.ipythondir',type=str,
49 help='Set to override default location of Global.ipythondir.',
50 default=NoConfigDefault,
51 metavar='Global.ipythondir')
52 self.parser.add_argument('-p','-profile',dest='Global.profile',type=str,
53 help='The string name of the ipython profile to be used.',
54 default=NoConfigDefault,
55 metavar='Global.profile')
56 self.parser.add_argument('-debug',dest="Global.debug",action='store_true',
57 help='Debug the application startup process.',
58 default=NoConfigDefault)
59 self.parser.add_argument('-config_file',dest='Global.config_file',type=str,
60 help='Set the config file name to override default.',
61 default=NoConfigDefault,
62 metavar='Global.config_file')
63
64
43 65 class ApplicationError(Exception):
44 66 pass
45 67
@@ -79,8 +101,8 b' class Application(object):'
79 101
80 102 def create_default_config(self):
81 103 """Create defaults that can't be set elsewhere."""
82 self.default_config = Struct()
83 self.default_config.IPYTHONDIR = get_ipython_dir()
104 self.default_config = Config()
105 self.default_config.Global.ipythondir = get_ipython_dir()
84 106
85 107 def create_command_line_config(self):
86 108 """Create and return a command line config loader."""
@@ -99,7 +121,7 b' class Application(object):'
99 121 loader = self.create_command_line_config()
100 122 self.command_line_config = loader.load_config()
101 123 try:
102 self.debug = self.command_line_config.DEBUG
124 self.debug = self.command_line_config.Global.debug
103 125 except AttributeError:
104 126 pass # use class default
105 127 self.log("Default config loaded:", self.default_config)
@@ -120,9 +142,9 b' class Application(object):'
120 142 """
121 143
122 144 try:
123 self.ipythondir = self.command_line_config.IPYTHONDIR
145 self.ipythondir = self.command_line_config.Global.ipythondir
124 146 except AttributeError:
125 self.ipythondir = self.default_config.IPYTHONDIR
147 self.ipythondir = self.default_config.Global.ipythondir
126 148 sys.path.append(os.path.abspath(self.ipythondir))
127 149 if not os.path.isdir(self.ipythondir):
128 150 os.makedirs(self.ipythondir, mode = 0777)
@@ -138,12 +160,12 b' class Application(object):'
138 160 """
139 161
140 162 try:
141 self.config_file_name = self.command_line_config.CONFIG_FILE
163 self.config_file_name = self.command_line_config.Global.config_file
142 164 except AttributeError:
143 165 pass
144 166
145 167 try:
146 self.profile_name = self.command_line_config.PROFILE
168 self.profile_name = self.command_line_config.Global.profile
147 169 name_parts = self.config_file_name.split('.')
148 170 name_parts.insert(1, '_' + self.profile_name + '.')
149 171 self.config_file_name = ''.join(name_parts)
@@ -165,15 +187,15 b' class Application(object):'
165 187 ``CONFIG_FILE`` config variable is set to the resolved config file
166 188 location. If not successful, an empty config is used.
167 189 """
168 loader = PyFileConfigLoader(self.config_file_name,
169 self.config_file_paths)
190 loader = PyFileConfigLoader(self.config_file_name,
191 path=self.config_file_paths)
170 192 try:
171 193 self.file_config = loader.load_config()
172 self.file_config.CONFIG_FILE = loader.full_filename
194 self.file_config.Global.config_file = loader.full_filename
173 195 except IOError:
174 196 self.log("Config file not found, skipping: %s" % \
175 197 self.config_file_name)
176 self.file_config = Struct()
198 self.file_config = Config()
177 199 else:
178 200 self.log("Config file loaded: %s" % loader.full_filename,
179 201 self.file_config)
@@ -184,10 +206,10 b' class Application(object):'
184 206
185 207 def merge_configs(self):
186 208 """Merge the default, command line and file config objects."""
187 config = Struct()
188 config.update(self.default_config)
189 config.update(self.file_config)
190 config.update(self.command_line_config)
209 config = Config()
210 config._merge(self.default_config)
211 config._merge(self.file_config)
212 config._merge(self.command_line_config)
191 213 self.master_config = config
192 214 self.log("Master config created:", self.master_config)
193 215
@@ -223,12 +245,13 b' class Application(object):'
223 245 def attempt(self, func, action='abort'):
224 246 try:
225 247 func()
248 except SystemExit:
249 self.exit()
226 250 except:
227 251 if action == 'abort':
228 252 self.print_traceback()
229 253 self.abort()
230 254 elif action == 'exit':
231 self.print_traceback()
232 255 self.exit()
233 256
234 257 def print_traceback(self):
@@ -40,6 +40,9 b' class BuiltinTrap(Component):'
40 40 def __init__(self, parent):
41 41 super(BuiltinTrap, self).__init__(parent, None, None)
42 42 self._orig_builtins = {}
43 # We define this to track if a single BuiltinTrap is nested.
44 # Only turn off the trap when the outermost call to __exit__ is made.
45 self._nested_level = 0
43 46
44 47 @auto_attr
45 48 def shell(self):
@@ -50,12 +53,16 b' class BuiltinTrap(Component):'
50 53 return shell
51 54
52 55 def __enter__(self):
53 self.set()
56 if self._nested_level == 0:
57 self.set()
58 self._nested_level += 1
54 59 # I return self, so callers can use add_builtin in a with clause.
55 60 return self
56 61
57 62 def __exit__(self, type, value, traceback):
58 self.unset()
63 if self._nested_level == 1:
64 self.unset()
65 self._nested_level -= 1
59 66 return True
60 67
61 68 def add_builtin(self, key, value):
@@ -108,4 +115,4 b' class BuiltinTrap(Component):'
108 115 try:
109 116 del __builtin__.__dict__['__IPYTHON__active']
110 117 except KeyError:
111 pass No newline at end of file
118 pass
@@ -25,7 +25,7 b' import datetime'
25 25 from weakref import WeakValueDictionary
26 26
27 27 from IPython.utils.importstring import import_item
28 from IPython.utils.ipstruct import Struct
28 from IPython.config.loader import Config
29 29 from IPython.utils.traitlets import (
30 30 HasTraitlets, TraitletError, MetaHasTraitlets, Instance, This
31 31 )
@@ -187,7 +187,7 b' class Component(HasTraitlets):'
187 187 __metaclass__ = MetaComponent
188 188
189 189 # Traitlets are fun!
190 config = Instance(Struct,(),{})
190 config = Instance(Config,(),{})
191 191 parent = This()
192 192 root = This()
193 193 created = None
@@ -203,7 +203,7 b' class Component(HasTraitlets):'
203 203 name : str
204 204 The unique name of the component. If empty, then a unique
205 205 one will be autogenerated.
206 config : Struct
206 config : Config
207 207 If this is empty, self.config = parent.config, otherwise
208 208 self.config = config and root.config is ignored. This argument
209 209 should only be used to *override* the automatic inheritance of
@@ -232,7 +232,7 b' class Component(HasTraitlets):'
232 232 else:
233 233 self.name = name
234 234 self.root = self # This is the default, it is set when parent is set
235 self.parent = parent
235 self.parent = parent
236 236 if config is not None:
237 237 self.config = deepcopy(config)
238 238 else:
@@ -274,15 +274,20 b' class Component(HasTraitlets):'
274 274 In the future, we might want to do a pop here so stale config info
275 275 is not passed onto children.
276 276 """
277 # Get all traitlets with a config_key metadata entry
278 traitlets = self.traitlets('config_key')
279 for k, v in traitlets.items():
280 try:
281 config_value = new[v.get_metadata('config_key')]
282 except KeyError:
283 pass
284 else:
285 setattr(self, k, config_value)
277 # Get all traitlets with a config metadata entry that is True
278 traitlets = self.traitlets(config=True)
279
280 # Don't do a blind getattr as that would cause the config to
281 # dynamically create the section with name self.__class__.__name__.
282 if new._has_section(self.__class__.__name__):
283 my_config = new[self.__class__.__name__]
284 for k, v in traitlets.items():
285 try:
286 config_value = my_config[k]
287 except KeyError:
288 pass
289 else:
290 setattr(self, k, config_value)
286 291
287 292 @property
288 293 def children(self):
@@ -40,9 +40,11 b' class DisplayTrap(Component):'
40 40
41 41 def __init__(self, parent, hook):
42 42 super(DisplayTrap, self).__init__(parent, None, None)
43
44 43 self.hook = hook
45 44 self.old_hook = None
45 # We define this to track if a single BuiltinTrap is nested.
46 # Only turn off the trap when the outermost call to __exit__ is made.
47 self._nested_level = 0
46 48
47 49 @auto_attr
48 50 def shell(self):
@@ -53,11 +55,15 b' class DisplayTrap(Component):'
53 55 return shell
54 56
55 57 def __enter__(self):
56 self.set()
58 if self._nested_level == 0:
59 self.set()
60 self._nested_level += 1
57 61 return self
58 62
59 63 def __exit__(self, type, value, traceback):
60 self.unset()
64 if self._nested_level == 1:
65 self.unset()
66 self._nested_level -= 1
61 67 return True
62 68
63 69 def set(self):
@@ -30,10 +30,12 b' from contextlib import nested'
30 30
31 31 from IPython.core import ultratb
32 32 from IPython.core.iplib import InteractiveShell
33 from IPython.core.ipapp import load_default_config
33 34
34 35 from IPython.utils.traitlets import Bool, Str, CBool
35 36 from IPython.utils.genutils import ask_yes_no
36 37
38
37 39 #-----------------------------------------------------------------------------
38 40 # Classes and functions
39 41 #-----------------------------------------------------------------------------
@@ -260,6 +262,8 b" def embed(header='', config=None, usage=None, banner1=None, banner2=None,"
260 262 Full customization can be done by passing a :class:`Struct` in as the
261 263 config argument.
262 264 """
265 if config is None:
266 config = load_default_config()
263 267 global _embedded_shell
264 268 if _embedded_shell is None:
265 269 _embedded_shell = InteractiveShellEmbed(config=config,
@@ -27,13 +27,17 b' import os'
27 27 import sys
28 28 import warnings
29 29
30 from IPython.core.application import Application
30 from IPython.core.application import Application, IPythonArgParseConfigLoader
31 31 from IPython.core import release
32 32 from IPython.core.iplib import InteractiveShell
33 from IPython.config.loader import IPythonArgParseConfigLoader, NoDefault
33 from IPython.config.loader import (
34 NoConfigDefault,
35 Config,
36 PyFileConfigLoader
37 )
34 38
35 39 from IPython.utils.ipstruct import Struct
36
40 from IPython.utils.genutils import get_ipython_dir
37 41
38 42 #-----------------------------------------------------------------------------
39 43 # Utilities and helpers
@@ -62,172 +66,187 b' deprecated. See the %gui magic for information on the new interface.'
62 66
63 67 cl_args = (
64 68 (('-autocall',), dict(
65 type=int, dest='AUTOCALL', default=NoDefault,
66 help='Set the autocall value (0,1,2).')
69 type=int, dest='InteractiveShell.autocall', default=NoConfigDefault,
70 help='Set the autocall value (0,1,2).',
71 metavar='InteractiveShell.autocall')
67 72 ),
68 73 (('-autoindent',), dict(
69 action='store_true', dest='AUTOINDENT', default=NoDefault,
74 action='store_true', dest='InteractiveShell.autoindent', default=NoConfigDefault,
70 75 help='Turn on autoindenting.')
71 76 ),
72 77 (('-noautoindent',), dict(
73 action='store_false', dest='AUTOINDENT', default=NoDefault,
78 action='store_false', dest='InteractiveShell.autoindent', default=NoConfigDefault,
74 79 help='Turn off autoindenting.')
75 80 ),
76 81 (('-automagic',), dict(
77 action='store_true', dest='AUTOMAGIC', default=NoDefault,
82 action='store_true', dest='InteractiveShell.automagic', default=NoConfigDefault,
78 83 help='Turn on the auto calling of magic commands.')
79 84 ),
80 85 (('-noautomagic',), dict(
81 action='store_false', dest='AUTOMAGIC', default=NoDefault,
86 action='store_false', dest='InteractiveShell.automagic', default=NoConfigDefault,
82 87 help='Turn off the auto calling of magic commands.')
83 88 ),
84 89 (('-autoedit_syntax',), dict(
85 action='store_true', dest='AUTOEDIT_SYNTAX', default=NoDefault,
90 action='store_true', dest='InteractiveShell.autoedit_syntax', default=NoConfigDefault,
86 91 help='Turn on auto editing of files with syntax errors.')
87 92 ),
88 93 (('-noautoedit_syntax',), dict(
89 action='store_false', dest='AUTOEDIT_SYNTAX', default=NoDefault,
94 action='store_false', dest='InteractiveShell.autoedit_syntax', default=NoConfigDefault,
90 95 help='Turn off auto editing of files with syntax errors.')
91 96 ),
92 97 (('-banner',), dict(
93 action='store_true', dest='DISPLAY_BANNER', default=NoDefault,
98 action='store_true', dest='InteractiveShell.display_banner', default=NoConfigDefault,
94 99 help='Display a banner upon starting IPython.')
95 100 ),
96 101 (('-nobanner',), dict(
97 action='store_false', dest='DISPLAY_BANNER', default=NoDefault,
102 action='store_false', dest='InteractiveShell.display_banner', default=NoConfigDefault,
98 103 help="Don't display a banner upon starting IPython.")
99 104 ),
100 105 (('-c',), dict(
101 type=str, dest='C', default=NoDefault,
102 help="Execute the given command string.")
106 type=str, dest='InteractiveShell.c', default=NoConfigDefault,
107 help="Execute the given command string.",
108 metavar='InteractiveShell.c')
103 109 ),
104 110 (('-cache_size',), dict(
105 type=int, dest='CACHE_SIZE', default=NoDefault,
106 help="Set the size of the output cache.")
111 type=int, dest='InteractiveShell.cache_size', default=NoConfigDefault,
112 help="Set the size of the output cache.",
113 metavar='InteractiveShell.cache_size')
107 114 ),
108 115 (('-classic',), dict(
109 action='store_true', dest='CLASSIC', default=NoDefault,
116 action='store_true', dest='Global.classic', default=NoConfigDefault,
110 117 help="Gives IPython a similar feel to the classic Python prompt.")
111 118 ),
112 119 (('-colors',), dict(
113 type=str, dest='COLORS', default=NoDefault,
114 help="Set the color scheme (NoColor, Linux, and LightBG).")
120 type=str, dest='InteractiveShell.colors', default=NoConfigDefault,
121 help="Set the color scheme (NoColor, Linux, and LightBG).",
122 metavar='InteractiveShell.colors')
115 123 ),
116 124 (('-color_info',), dict(
117 action='store_true', dest='COLOR_INFO', default=NoDefault,
125 action='store_true', dest='InteractiveShell.color_info', default=NoConfigDefault,
118 126 help="Enable using colors for info related things.")
119 127 ),
120 128 (('-nocolor_info',), dict(
121 action='store_false', dest='COLOR_INFO', default=NoDefault,
129 action='store_false', dest='InteractiveShell.color_info', default=NoConfigDefault,
122 130 help="Disable using colors for info related things.")
123 131 ),
124 132 (('-confirm_exit',), dict(
125 action='store_true', dest='CONFIRM_EXIT', default=NoDefault,
133 action='store_true', dest='InteractiveShell.confirm_exit', default=NoConfigDefault,
126 134 help="Prompt the user when existing.")
127 135 ),
128 136 (('-noconfirm_exit',), dict(
129 action='store_false', dest='CONFIRM_EXIT', default=NoDefault,
137 action='store_false', dest='InteractiveShell.confirm_exit', default=NoConfigDefault,
130 138 help="Don't prompt the user when existing.")
131 139 ),
132 140 (('-deep_reload',), dict(
133 action='store_true', dest='DEEP_RELOAD', default=NoDefault,
141 action='store_true', dest='InteractiveShell.deep_reload', default=NoConfigDefault,
134 142 help="Enable deep (recursive) reloading by default.")
135 143 ),
136 144 (('-nodeep_reload',), dict(
137 action='store_false', dest='DEEP_RELOAD', default=NoDefault,
145 action='store_false', dest='InteractiveShell.deep_reload', default=NoConfigDefault,
138 146 help="Disable deep (recursive) reloading by default.")
139 147 ),
140 148 (('-editor',), dict(
141 type=str, dest='EDITOR', default=NoDefault,
142 help="Set the editor used by IPython (default to $EDITOR/vi/notepad).")
149 type=str, dest='InteractiveShell.editor', default=NoConfigDefault,
150 help="Set the editor used by IPython (default to $EDITOR/vi/notepad).",
151 metavar='InteractiveShell.editor')
143 152 ),
144 153 (('-log','-l'), dict(
145 action='store_true', dest='LOGSTART', default=NoDefault,
154 action='store_true', dest='InteractiveShell.logstart', default=NoConfigDefault,
146 155 help="Start logging to the default file (./ipython_log.py).")
147 156 ),
148 157 (('-logfile','-lf'), dict(
149 type=str, dest='LOGFILE', default=NoDefault,
150 help="Specify the name of your logfile.")
158 type=str, dest='InteractiveShell.logfile', default=NoConfigDefault,
159 help="Specify the name of your logfile.",
160 metavar='InteractiveShell.logfile')
151 161 ),
152 162 (('-logplay','-lp'), dict(
153 type=str, dest='LOGPLAY', default=NoDefault,
154 help="Re-play a log file and then append to it.")
163 type=str, dest='InteractiveShell.logplay', default=NoConfigDefault,
164 help="Re-play a log file and then append to it.",
165 metavar='InteractiveShell.logplay')
155 166 ),
156 167 (('-pdb',), dict(
157 action='store_true', dest='PDB', default=NoDefault,
168 action='store_true', dest='InteractiveShell.pdb', default=NoConfigDefault,
158 169 help="Enable auto calling the pdb debugger after every exception.")
159 170 ),
160 171 (('-nopdb',), dict(
161 action='store_false', dest='PDB', default=NoDefault,
172 action='store_false', dest='InteractiveShell.pdb', default=NoConfigDefault,
162 173 help="Disable auto calling the pdb debugger after every exception.")
163 174 ),
164 175 (('-pprint',), dict(
165 action='store_true', dest='PPRINT', default=NoDefault,
176 action='store_true', dest='InteractiveShell.pprint', default=NoConfigDefault,
166 177 help="Enable auto pretty printing of results.")
167 178 ),
168 179 (('-nopprint',), dict(
169 action='store_false', dest='PPRINT', default=NoDefault,
180 action='store_false', dest='InteractiveShell.pprint', default=NoConfigDefault,
170 181 help="Disable auto auto pretty printing of results.")
171 182 ),
172 183 (('-prompt_in1','-pi1'), dict(
173 type=str, dest='PROMPT_IN1', default=NoDefault,
174 help="Set the main input prompt ('In [\#]: ')")
184 type=str, dest='InteractiveShell.prompt_in1', default=NoConfigDefault,
185 help="Set the main input prompt ('In [\#]: ')",
186 metavar='InteractiveShell.prompt_in1')
175 187 ),
176 188 (('-prompt_in2','-pi2'), dict(
177 type=str, dest='PROMPT_IN2', default=NoDefault,
178 help="Set the secondary input prompt (' .\D.: ')")
189 type=str, dest='InteractiveShell.prompt_in2', default=NoConfigDefault,
190 help="Set the secondary input prompt (' .\D.: ')",
191 metavar='InteractiveShell.prompt_in2')
179 192 ),
180 193 (('-prompt_out','-po'), dict(
181 type=str, dest='PROMPT_OUT', default=NoDefault,
182 help="Set the output prompt ('Out[\#]:')")
194 type=str, dest='InteractiveShell.prompt_out', default=NoConfigDefault,
195 help="Set the output prompt ('Out[\#]:')",
196 metavar='InteractiveShell.prompt_out')
183 197 ),
184 198 (('-quick',), dict(
185 action='store_true', dest='QUICK', default=NoDefault,
199 action='store_true', dest='Global.quick', default=NoConfigDefault,
186 200 help="Enable quick startup with no config files.")
187 201 ),
188 202 (('-readline',), dict(
189 action='store_true', dest='READLINE_USE', default=NoDefault,
203 action='store_true', dest='InteractiveShell.readline_use', default=NoConfigDefault,
190 204 help="Enable readline for command line usage.")
191 205 ),
192 206 (('-noreadline',), dict(
193 action='store_false', dest='READLINE_USE', default=NoDefault,
207 action='store_false', dest='InteractiveShell.readline_use', default=NoConfigDefault,
194 208 help="Disable readline for command line usage.")
195 209 ),
196 210 (('-screen_length','-sl'), dict(
197 type=int, dest='SCREEN_LENGTH', default=NoDefault,
198 help='Number of lines on screen, used to control printing of long strings.')
211 type=int, dest='InteractiveShell.screen_length', default=NoConfigDefault,
212 help='Number of lines on screen, used to control printing of long strings.',
213 metavar='InteractiveShell.screen_length')
199 214 ),
200 215 (('-separate_in','-si'), dict(
201 type=str, dest='SEPARATE_IN', default=NoDefault,
202 help="Separator before input prompts. Default '\n'.")
216 type=str, dest='InteractiveShell.separate_in', default=NoConfigDefault,
217 help="Separator before input prompts. Default '\n'.",
218 metavar='InteractiveShell.separate_in')
203 219 ),
204 220 (('-separate_out','-so'), dict(
205 type=str, dest='SEPARATE_OUT', default=NoDefault,
206 help="Separator before output prompts. Default 0 (nothing).")
221 type=str, dest='InteractiveShell.separate_out', default=NoConfigDefault,
222 help="Separator before output prompts. Default 0 (nothing).",
223 metavar='InteractiveShell.separate_out')
207 224 ),
208 225 (('-separate_out2','-so2'), dict(
209 type=str, dest='SEPARATE_OUT2', default=NoDefault,
210 help="Separator after output prompts. Default 0 (nonight).")
226 type=str, dest='InteractiveShell.separate_out2', default=NoConfigDefault,
227 help="Separator after output prompts. Default 0 (nonight).",
228 metavar='InteractiveShell.separate_out2')
211 229 ),
212 230 (('-nosep',), dict(
213 action='store_true', dest='NOSEP', default=NoDefault,
231 action='store_true', dest='Global.nosep', default=NoConfigDefault,
214 232 help="Eliminate all spacing between prompts.")
215 233 ),
216 234 (('-term_title',), dict(
217 action='store_true', dest='TERM_TITLE', default=NoDefault,
235 action='store_true', dest='InteractiveShell.term_title', default=NoConfigDefault,
218 236 help="Enable auto setting the terminal title.")
219 237 ),
220 238 (('-noterm_title',), dict(
221 action='store_false', dest='TERM_TITLE', default=NoDefault,
239 action='store_false', dest='InteractiveShell.term_title', default=NoConfigDefault,
222 240 help="Disable auto setting the terminal title.")
223 241 ),
224 242 (('-xmode',), dict(
225 type=str, dest='XMODE', default=NoDefault,
226 help="Exception mode ('Plain','Context','Verbose')")
243 type=str, dest='InteractiveShell.xmode', default=NoConfigDefault,
244 help="Exception mode ('Plain','Context','Verbose')",
245 metavar='InteractiveShell.xmode')
227 246 ),
228 247 # These are only here to get the proper deprecation warnings
229 248 (('-pylab','-wthread','-qthread','-q4thread','-gthread'), dict(
230 action='store_true', dest='THREADED_SHELL', default=NoDefault,
249 action='store_true', dest='Global.threaded_shell', default=NoConfigDefault,
231 250 help="These command line flags are deprecated, see the 'gui' magic.")
232 251 ),
233 252 )
@@ -238,9 +257,11 b' class IPythonAppCLConfigLoader(IPythonArgParseConfigLoader):'
238 257 arguments = cl_args
239 258
240 259
260 _default_config_file_name = 'ipython_config.py'
261
241 262 class IPythonApp(Application):
242 263 name = 'ipython'
243 config_file_name = 'ipython_config.py'
264 config_file_name = _default_config_file_name
244 265
245 266 def create_command_line_config(self):
246 267 """Create and return a command line config loader."""
@@ -252,19 +273,15 b' class IPythonApp(Application):'
252 273 """Do actions after loading cl config."""
253 274 clc = self.command_line_config
254 275
255 # This needs to be set here, the rest are set in pre_construct.
256 if hasattr(clc, 'CLASSIC'):
257 if clc.CLASSIC: clc.QUICK = 1
258
259 276 # Display the deprecation warnings about threaded shells
260 if hasattr(clc, 'THREADED_SHELL'):
277 if hasattr(clc.Global, 'threaded_shell'):
261 278 threaded_shell_warning()
262 del clc['THREADED_SHELL']
279 del clc.Global['threaded_shell']
263 280
264 281 def load_file_config(self):
265 if hasattr(self.command_line_config, 'QUICK'):
266 if self.command_line_config.QUICK:
267 self.file_config = Struct()
282 if hasattr(self.command_line_config.Global, 'quick'):
283 if self.command_line_config.Global.quick:
284 self.file_config = Config()
268 285 return
269 286 super(IPythonApp, self).load_file_config()
270 287
@@ -274,25 +291,28 b' class IPythonApp(Application):'
274 291 def pre_construct(self):
275 292 config = self.master_config
276 293
277 if hasattr(config, 'CLASSIC'):
278 if config.CLASSIC:
279 config.QUICK = 1
280 config.CACHE_SIZE = 0
281 config.PPRINT = 0
282 config.PROMPT_IN1 = '>>> '
283 config.PROMPT_IN2 = '... '
284 config.PROMPT_OUT = ''
285 config.SEPARATE_IN = config.SEPARATE_OUT = config.SEPARATE_OUT2 = ''
286 config.COLORS = 'NoColor'
287 config.XMODE = 'Plain'
294 if hasattr(config.Global, 'classic'):
295 if config.Global.classic:
296 config.InteractiveShell.cache_size = 0
297 config.InteractiveShell.pprint = 0
298 config.InteractiveShell.prompt_in1 = '>>> '
299 config.InteractiveShell.prompt_in2 = '... '
300 config.InteractiveShell.prompt_out = ''
301 config.InteractiveShell.separate_in = \
302 config.InteractiveShell.separate_out = \
303 config.InteractiveShell.separate_out2 = ''
304 config.InteractiveShell.colors = 'NoColor'
305 config.InteractiveShell.xmode = 'Plain'
288 306
289 307 # All this should be moved to traitlet handlers in InteractiveShell
290 308 # But, currently InteractiveShell doesn't have support for changing
291 309 # these values at runtime. Once we support that, this should
292 310 # be moved there!!!
293 if hasattr(config, 'NOSEP'):
294 if config.NOSEP:
295 config.SEPARATE_IN = config.SEPARATE_OUT = config.SEPARATE_OUT2 = '0'
311 if hasattr(config.Global, 'nosep'):
312 if config.Global.nosep:
313 config.InteractiveShell.separate_in = \
314 config.InteractiveShell.separate_out = \
315 config.InteractiveShell.separate_out2 = '0'
296 316
297 317 def construct(self):
298 318 # I am a little hesitant to put these into InteractiveShell itself.
@@ -307,12 +327,23 b' class IPythonApp(Application):'
307 327 parent=None,
308 328 config=self.master_config
309 329 )
310 print self.shell
311 330
312 331 def start_app(self):
313 332 self.shell.mainloop()
314 333
315 334
335 def load_default_config(ipythondir=None):
336 """Load the default config file from the default ipythondir.
337
338 This is useful for embedded shells.
339 """
340 if ipythondir is None:
341 ipythondir = get_ipython_dir()
342 cl = PyFileConfigLoader(_default_config_file_name, ipythondir)
343 config = cl.load_config()
344 return config
345
346
316 347 if __name__ == '__main__':
317 348 app = IPythonApp()
318 349 app.start() No newline at end of file
@@ -62,6 +62,7 b' from IPython.lib.backgroundjobs import BackgroundJobManager'
62 62 from IPython.utils.ipstruct import Struct
63 63 from IPython.utils import PyColorize
64 64 from IPython.utils.genutils import *
65 from IPython.utils.genutils import get_ipython_dir
65 66 from IPython.utils.strdispatch import StrDispatch
66 67 from IPython.utils.platutils import toggle_set_term_title, set_term_title
67 68
@@ -188,50 +189,47 b' class SeparateStr(Str):'
188 189 class InteractiveShell(Component, Magic):
189 190 """An enhanced, interactive shell for Python."""
190 191
191 autocall = Enum((0,1,2), config_key='AUTOCALL')
192 autoedit_syntax = CBool(False, config_key='AUTOEDIT_SYNTAX')
193 autoindent = CBool(True, config_key='AUTOINDENT')
194 automagic = CBool(True, config_key='AUTOMAGIC')
195 display_banner = CBool(True, config_key='DISPLAY_BANNER')
192 autocall = Enum((0,1,2), config=True)
193 autoedit_syntax = CBool(False, config=True)
194 autoindent = CBool(True, config=True)
195 automagic = CBool(True, config=True)
196 display_banner = CBool(True, config=True)
196 197 banner = Str('')
197 banner1 = Str(default_banner, config_key='BANNER1')
198 banner2 = Str('', config_key='BANNER2')
199 c = Str('', config_key='C')
200 cache_size = Int(1000, config_key='CACHE_SIZE')
201 classic = CBool(False, config_key='CLASSIC')
202 color_info = CBool(True, config_key='COLOR_INFO')
198 banner1 = Str(default_banner, config=True)
199 banner2 = Str('', config=True)
200 c = Str('', config=True)
201 cache_size = Int(1000, config=True)
202 color_info = CBool(True, config=True)
203 203 colors = CaselessStrEnum(('NoColor','LightBG','Linux'),
204 default_value='LightBG', config_key='COLORS')
205 confirm_exit = CBool(True, config_key='CONFIRM_EXIT')
206 debug = CBool(False, config_key='DEBUG')
207 deep_reload = CBool(False, config_key='DEEP_RELOAD')
204 default_value='LightBG', config=True)
205 confirm_exit = CBool(True, config=True)
206 debug = CBool(False, config=True)
207 deep_reload = CBool(False, config=True)
208 208 embedded = CBool(False)
209 209 embedded_active = CBool(False)
210 editor = Str(get_default_editor(), config_key='EDITOR')
210 editor = Str(get_default_editor(), config=True)
211 211 filename = Str("<ipython console>")
212 interactive = CBool(False, config_key='INTERACTIVE')
213 ipythondir= Unicode('', config_key='IPYTHONDIR') # Set to os.getcwd() in __init__
214 logstart = CBool(False, config_key='LOGSTART')
215 logfile = Str('', config_key='LOGFILE')
216 logplay = Str('', config_key='LOGPLAY')
212 interactive = CBool(False, config=True)
213 ipythondir= Unicode('', config=True) # Set to get_ipython_dir() in __init__
214 logstart = CBool(False, config=True)
215 logfile = Str('', config=True)
216 logplay = Str('', config=True)
217 217 object_info_string_level = Enum((0,1,2), default_value=0,
218 config_keys='OBJECT_INFO_STRING_LEVEL')
219 pager = Str('less', config_key='PAGER')
220 pdb = CBool(False, config_key='PDB')
221 pprint = CBool(True, config_key='PPRINT')
222 profile = Str('', config_key='PROFILE')
223 prompt_in1 = Str('In [\\#]: ', config_key='PROMPT_IN1')
224 prompt_in2 = Str(' .\\D.: ', config_key='PROMPT_IN2')
225 prompt_out = Str('Out[\\#]: ', config_key='PROMPT_OUT1')
226 prompts_pad_left = CBool(True, config_key='PROMPTS_PAD_LEFT')
227 quiet = CBool(False, config_key='QUIET')
228
229 readline_use = CBool(True, config_key='READLINE_USE')
230 readline_merge_completions = CBool(True,
231 config_key='READLINE_MERGE_COMPLETIONS')
232 readline_omit__names = Enum((0,1,2), default_value=0,
233 config_key='READLINE_OMIT_NAMES')
234 readline_remove_delims = Str('-/~', config_key='READLINE_REMOVE_DELIMS')
218 config=True)
219 pager = Str('less', config=True)
220 pdb = CBool(False, config=True)
221 pprint = CBool(True, config=True)
222 profile = Str('', config=True)
223 prompt_in1 = Str('In [\\#]: ', config=True)
224 prompt_in2 = Str(' .\\D.: ', config=True)
225 prompt_out = Str('Out[\\#]: ', config=True)
226 prompts_pad_left = CBool(True, config=True)
227 quiet = CBool(False, config=True)
228
229 readline_use = CBool(True, config=True)
230 readline_merge_completions = CBool(True, config=True)
231 readline_omit__names = Enum((0,1,2), default_value=0, config=True)
232 readline_remove_delims = Str('-/~', config=True)
235 233 readline_parse_and_bind = List([
236 234 'tab: complete',
237 235 '"\C-l": possible-completions',
@@ -248,24 +246,22 b' class InteractiveShell(Component, Magic):'
248 246 '"\e[B": history-search-forward',
249 247 '"\C-k": kill-line',
250 248 '"\C-u": unix-line-discard',
251 ], allow_none=False, config_key='READLINE_PARSE_AND_BIND'
252 )
249 ], allow_none=False, config=True)
253 250
254 screen_length = Int(0, config_key='SCREEN_LENGTH')
251 screen_length = Int(0, config=True)
255 252
256 253 # Use custom TraitletTypes that convert '0'->'' and '\\n'->'\n'
257 separate_in = SeparateStr('\n', config_key='SEPARATE_IN')
258 separate_out = SeparateStr('', config_key='SEPARATE_OUT')
259 separate_out2 = SeparateStr('', config_key='SEPARATE_OUT2')
260
261 system_header = Str('IPython system call: ', config_key='SYSTEM_HEADER')
262 system_verbose = CBool(False, config_key='SYSTEM_VERBOSE')
263 term_title = CBool(False, config_key='TERM_TITLE')
264 wildcards_case_sensitive = CBool(True, config_key='WILDCARDS_CASE_SENSITIVE')
254 separate_in = SeparateStr('\n', config=True)
255 separate_out = SeparateStr('', config=True)
256 separate_out2 = SeparateStr('', config=True)
257
258 system_header = Str('IPython system call: ', config=True)
259 system_verbose = CBool(False, config=True)
260 term_title = CBool(False, config=True)
261 wildcards_case_sensitive = CBool(True, config=True)
265 262 xmode = CaselessStrEnum(('Context','Plain', 'Verbose'),
266 default_value='Context', config_key='XMODE')
263 default_value='Context', config=True)
267 264
268 alias = List(allow_none=False, config_key='ALIAS')
269 265 autoexec = List(allow_none=False)
270 266
271 267 # class attribute to indicate whether the class supports threads or not.
@@ -279,7 +275,7 b' class InteractiveShell(Component, Magic):'
279 275
280 276 # This is where traitlets with a config_key argument are updated
281 277 # from the values on config.
282 super(InteractiveShell, self).__init__(parent, config=config, name='__IP')
278 super(InteractiveShell, self).__init__(parent, config=config)
283 279
284 280 # These are relatively independent and stateless
285 281 self.init_ipythondir(ipythondir)
@@ -288,7 +284,7 b' class InteractiveShell(Component, Magic):'
288 284 self.init_usage(usage)
289 285 self.init_banner(banner1, banner2)
290 286
291 # Create namespaces (user_ns, user_global_ns, alias_table, etc.)
287 # Create namespaces (user_ns, user_global_ns, etc.)
292 288 self.init_create_namespaces(user_ns, user_global_ns)
293 289 # This has to be done after init_create_namespaces because it uses
294 290 # something in self.user_ns, but before init_sys_modules, which
@@ -327,6 +323,9 b' class InteractiveShell(Component, Magic):'
327 323 self.init_pdb()
328 324 self.hooks.late_startup_hook()
329 325
326 def get_ipython(self):
327 return self
328
330 329 #-------------------------------------------------------------------------
331 330 # Traitlet changed handlers
332 331 #-------------------------------------------------------------------------
@@ -337,6 +336,10 b' class InteractiveShell(Component, Magic):'
337 336 def _banner2_changed(self):
338 337 self.compute_banner()
339 338
339 def _ipythondir_changed(self, name, new):
340 if not os.path.isdir(new):
341 os.makedirs(new, mode = 0777)
342
340 343 @property
341 344 def usable_screen_length(self):
342 345 if self.screen_length == 0:
@@ -370,22 +373,16 b' class InteractiveShell(Component, Magic):'
370 373 def init_ipythondir(self, ipythondir):
371 374 if ipythondir is not None:
372 375 self.ipythondir = ipythondir
373 self.config.IPYTHONDIR = self.ipythondir
376 self.config.Global.ipythondir = self.ipythondir
374 377 return
375 378
376 if hasattr(self.config, 'IPYTHONDIR'):
377 self.ipythondir = self.config.IPYTHONDIR
378 if not hasattr(self.config, 'IPYTHONDIR'):
379 # cdw is always defined
380 self.ipythondir = os.getcwd()
381
382 # The caller must make sure that ipythondir exists. We should
383 # probably handle this using a Dir traitlet.
384 if not os.path.isdir(self.ipythondir):
385 raise IOError('IPython dir does not exist: %s' % self.ipythondir)
379 if hasattr(self.config.Global, 'ipythondir'):
380 self.ipythondir = self.config.Global.ipythondir
381 else:
382 self.ipythondir = get_ipython_dir()
386 383
387 384 # All children can just read this
388 self.config.IPYTHONDIR = self.ipythondir
385 self.config.Global.ipythondir = self.ipythondir
389 386
390 387 def init_instance_attrs(self):
391 388 self.jobs = BackgroundJobManager()
@@ -825,11 +822,6 b' class InteractiveShell(Component, Magic):'
825 822 # them from cluttering user-visible stuff. Will be updated later
826 823 self.internal_ns = {}
827 824
828 # Namespace of system aliases. Each entry in the alias
829 # table must be a 2-tuple of the form (N,name), where N is the number
830 # of positional arguments of the alias.
831 self.alias_table = {}
832
833 825 # Now that FakeModule produces a real module, we've run into a nasty
834 826 # problem: after script execution (via %run), the module where the user
835 827 # code ran is deleted. Now that this object is a true module (needed
@@ -863,7 +855,6 b' class InteractiveShell(Component, Magic):'
863 855 # introspection facilities can search easily.
864 856 self.ns_table = {'user':user_ns,
865 857 'user_global':user_global_ns,
866 'alias':self.alias_table,
867 858 'internal':self.internal_ns,
868 859 'builtin':__builtin__.__dict__
869 860 }
@@ -872,8 +863,7 b' class InteractiveShell(Component, Magic):'
872 863 # we can safely clear (so it can NOT include builtin). This one can be
873 864 # a simple list.
874 865 self.ns_refs_table = [ user_ns, user_global_ns, self.user_config_ns,
875 self.alias_table, self.internal_ns,
876 self._main_ns_cache ]
866 self.internal_ns, self._main_ns_cache ]
877 867
878 868 def init_sys_modules(self):
879 869 # We need to insert into sys.modules something that looks like a
@@ -961,11 +951,8 b' class InteractiveShell(Component, Magic):'
961 951 method. If they were not empty before, data will simply be added to
962 952 therm.
963 953 """
964 # The user namespace MUST have a pointer to the shell itself.
965 self.user_ns[self.name] = self
966
967 954 # Store myself as the public api!!!
968 self.user_ns['_ip'] = self
955 self.user_ns['get_ipython'] = self.get_ipython
969 956
970 957 # make global variables for user access to the histories
971 958 self.user_ns['_ih'] = self.input_hist
@@ -994,13 +981,19 b' class InteractiveShell(Component, Magic):'
994 981 for ns in self.ns_refs_table:
995 982 ns.clear()
996 983
984 self.alias_manager.clear_aliases()
985
997 986 # Clear input and output histories
998 987 self.input_hist[:] = []
999 988 self.input_hist_raw[:] = []
1000 989 self.output_hist.clear()
990
1001 991 # Restore the user namespaces to minimal usability
1002 992 self.init_user_ns()
1003 993
994 # Restore the default and user aliases
995 self.alias_manager.init_aliases()
996
1004 997 def push(self, variables, interactive=True):
1005 998 """Inject a group of variables into the IPython user namespace.
1006 999
@@ -1076,7 +1069,7 b' class InteractiveShell(Component, Magic):'
1076 1069 histfname = 'history-%s' % self.profile
1077 1070 except AttributeError:
1078 1071 histfname = 'history'
1079 self.histfile = os.path.join(self.config.IPYTHONDIR, histfname)
1072 self.histfile = os.path.join(self.ipythondir, histfname)
1080 1073
1081 1074 # Fill the history zero entry, user counter starts at 1
1082 1075 self.input_hist.append('\n')
@@ -1084,12 +1077,12 b' class InteractiveShell(Component, Magic):'
1084 1077
1085 1078 def init_shadow_hist(self):
1086 1079 try:
1087 self.db = pickleshare.PickleShareDB(self.config.IPYTHONDIR + "/db")
1080 self.db = pickleshare.PickleShareDB(self.ipythondir + "/db")
1088 1081 except exceptions.UnicodeDecodeError:
1089 1082 print "Your ipythondir can't be decoded to unicode!"
1090 1083 print "Please set HOME environment variable to something that"
1091 1084 print r"only has ASCII characters, e.g. c:\home"
1092 print "Now it is", self.config.IPYTHONDIR
1085 print "Now it is", self.ipythondir
1093 1086 sys.exit()
1094 1087 self.shadowhist = ipcorehist.ShadowHist(self.db)
1095 1088
@@ -1472,10 +1465,10 b' class InteractiveShell(Component, Magic):'
1472 1465 import atexit
1473 1466 from IPython.core.completer import IPCompleter
1474 1467 self.Completer = IPCompleter(self,
1475 self.user_ns,
1476 self.user_global_ns,
1477 self.readline_omit__names,
1478 self.alias_table)
1468 self.user_ns,
1469 self.user_global_ns,
1470 self.readline_omit__names,
1471 self.alias_manager.alias_table)
1479 1472 sdisp = self.strdispatchers.get('complete_command', StrDispatch())
1480 1473 self.strdispatchers['complete_command'] = sdisp
1481 1474 self.Completer.custom_completers = sdisp
@@ -1607,8 +1600,11 b' class InteractiveShell(Component, Magic):'
1607 1600 error("Magic function `%s` not found." % magic_name)
1608 1601 else:
1609 1602 magic_args = self.var_expand(magic_args,1)
1610 with nested(self.builtin_trap, self.display_trap):
1611 return fn(magic_args)
1603 with nested(self.builtin_trap,):
1604 result = fn(magic_args)
1605 # Unfortunately, the return statement is what will trigger
1606 # the displayhook, but it is no longer set!
1607 return result
1612 1608
1613 1609 def define_magic(self, magicname, func):
1614 1610 """Expose own function as magic function for ipython
@@ -1666,6 +1662,7 b' class InteractiveShell(Component, Magic):'
1666 1662
1667 1663 def init_alias(self):
1668 1664 self.alias_manager = AliasManager(self, config=self.config)
1665 self.ns_table['alias'] = self.alias_manager.alias_table,
1669 1666
1670 1667 #-------------------------------------------------------------------------
1671 1668 # Things related to the running of code
@@ -1673,7 +1670,7 b' class InteractiveShell(Component, Magic):'
1673 1670
1674 1671 def ex(self, cmd):
1675 1672 """Execute a normal python statement in user namespace."""
1676 with nested(self.builtin_trap, self.display_trap):
1673 with nested(self.builtin_trap,):
1677 1674 exec cmd in self.user_global_ns, self.user_ns
1678 1675
1679 1676 def ev(self, expr):
@@ -1681,7 +1678,7 b' class InteractiveShell(Component, Magic):'
1681 1678
1682 1679 Returns the result of evaluation
1683 1680 """
1684 with nested(self.builtin_trap, self.display_trap):
1681 with nested(self.builtin_trap,):
1685 1682 return eval(expr, self.user_global_ns, self.user_ns)
1686 1683
1687 1684 def mainloop(self, banner=None):
@@ -47,6 +47,7 b' from IPython.utils import wildcard'
47 47 from IPython.core import debugger, oinspect
48 48 from IPython.core.error import TryNext
49 49 from IPython.core.fakemodule import FakeModule
50 from IPython.core.prefilter import ESC_MAGIC
50 51 from IPython.external.Itpl import Itpl, itpl, printpl,itplns
51 52 from IPython.utils.PyColorize import Parser
52 53 from IPython.utils.ipstruct import Struct
@@ -205,9 +206,9 b' python-profiler package from non-free.""")'
205 206 namespaces = [ ('Interactive', self.shell.user_ns),
206 207 ('IPython internal', self.shell.internal_ns),
207 208 ('Python builtin', __builtin__.__dict__),
208 ('Alias', self.shell.alias_table),
209 ('Alias', self.shell.alias_manager.alias_table),
209 210 ]
210 alias_ns = self.shell.alias_table
211 alias_ns = self.shell.alias_manager.alias_table
211 212
212 213 # initialize results to 'null'
213 214 found = 0; obj = None; ospace = None; ds = None;
@@ -244,7 +245,7 b' python-profiler package from non-free.""")'
244 245
245 246 # Try to see if it's magic
246 247 if not found:
247 if oname.startswith(self.shell.ESC_MAGIC):
248 if oname.startswith(ESC_MAGIC):
248 249 oname = oname[1:]
249 250 obj = getattr(self,'magic_'+oname,None)
250 251 if obj is not None:
@@ -272,10 +273,10 b' python-profiler package from non-free.""")'
272 273 # Characters that need to be escaped for latex:
273 274 escape_re = re.compile(r'(%|_|\$|#|&)',re.MULTILINE)
274 275 # Magic command names as headers:
275 cmd_name_re = re.compile(r'^(%s.*?):' % self.shell.ESC_MAGIC,
276 cmd_name_re = re.compile(r'^(%s.*?):' % ESC_MAGIC,
276 277 re.MULTILINE)
277 278 # Magic commands
278 cmd_re = re.compile(r'(?P<cmd>%s.+?\b)(?!\}\}:)' % self.shell.ESC_MAGIC,
279 cmd_re = re.compile(r'(?P<cmd>%s.+?\b)(?!\}\}:)' % ESC_MAGIC,
279 280 re.MULTILINE)
280 281 # Paragraph continue
281 282 par_re = re.compile(r'\\$',re.MULTILINE)
@@ -376,7 +377,7 b' python-profiler package from non-free.""")'
376 377 # Functions for IPython shell work (vars,funcs, config, etc)
377 378 def magic_lsmagic(self, parameter_s = ''):
378 379 """List currently available magic functions."""
379 mesc = self.shell.ESC_MAGIC
380 mesc = ESC_MAGIC
380 381 print 'Available magic functions:\n'+mesc+\
381 382 (' '+mesc).join(self.lsmagic())
382 383 print '\n' + Magic.auto_status[self.shell.automagic]
@@ -424,11 +425,11 b' python-profiler package from non-free.""")'
424 425
425 426
426 427 if mode == 'rest':
427 rest_docs.append('**%s%s**::\n\n\t%s\n\n' %(self.shell.ESC_MAGIC,
428 rest_docs.append('**%s%s**::\n\n\t%s\n\n' %(ESC_MAGIC,
428 429 fname,fndoc))
429 430
430 431 else:
431 magic_docs.append('%s%s:\n\t%s\n' %(self.shell.ESC_MAGIC,
432 magic_docs.append('%s%s:\n\t%s\n' %(ESC_MAGIC,
432 433 fname,fndoc))
433 434
434 435 magic_docs = ''.join(magic_docs)
@@ -479,7 +480,7 b" of any of them, type %magic_name?, e.g. '%cd?'."
479 480
480 481 Currently the magic system has the following functions:\n"""
481 482
482 mesc = self.shell.ESC_MAGIC
483 mesc = ESC_MAGIC
483 484 outmsg = ("%s\n%s\n\nSummary of magic functions (from %slsmagic):"
484 485 "\n\n%s%s\n\n%s" % (outmsg,
485 486 magic_docs,mesc,mesc,
@@ -2620,52 +2621,27 b' Defaulting color scheme to \'NoColor\'"""'
2620 2621 par = parameter_s.strip()
2621 2622 if not par:
2622 2623 stored = self.db.get('stored_aliases', {} )
2623 atab = self.shell.alias_table
2624 aliases = atab.keys()
2625 aliases.sort()
2626 res = []
2627 showlast = []
2628 for alias in aliases:
2629 special = False
2630 try:
2631 tgt = atab[alias][1]
2632 except (TypeError, AttributeError):
2633 # unsubscriptable? probably a callable
2634 tgt = atab[alias]
2635 special = True
2636 # 'interesting' aliases
2637 if (alias in stored or
2638 special or
2639 alias.lower() != os.path.splitext(tgt)[0].lower() or
2640 ' ' in tgt):
2641 showlast.append((alias, tgt))
2642 else:
2643 res.append((alias, tgt ))
2644
2645 # show most interesting aliases last
2646 res.extend(showlast)
2647 print "Total number of aliases:",len(aliases)
2648 return res
2624 aliases = sorted(self.shell.alias_manager.aliases)
2625 # for k, v in stored:
2626 # atab.append(k, v[0])
2627
2628 print "Total number of aliases:", len(aliases)
2629 return aliases
2630
2631 # Now try to define a new one
2649 2632 try:
2650 alias,cmd = par.split(None,1)
2633 alias,cmd = par.split(None, 1)
2651 2634 except:
2652 2635 print oinspect.getdoc(self.magic_alias)
2653 2636 else:
2654 nargs = cmd.count('%s')
2655 if nargs>0 and cmd.find('%l')>=0:
2656 error('The %s and %l specifiers are mutually exclusive '
2657 'in alias definitions.')
2658 else: # all looks OK
2659 self.shell.alias_table[alias] = (nargs,cmd)
2660 self.shell.alias_table_validate(verbose=0)
2637 self.shell.alias_manager.soft_define_alias(alias, cmd)
2661 2638 # end magic_alias
2662 2639
2663 2640 def magic_unalias(self, parameter_s = ''):
2664 2641 """Remove an alias"""
2665 2642
2666 2643 aname = parameter_s.strip()
2667 if aname in self.shell.alias_table:
2668 del self.shell.alias_table[aname]
2644 self.shell.alias_manager.undefine_alias(aname)
2669 2645 stored = self.db.get('stored_aliases', {} )
2670 2646 if aname in stored:
2671 2647 print "Removing %stored alias",aname
@@ -2686,6 +2662,7 b' Defaulting color scheme to \'NoColor\'"""'
2686 2662 This function also resets the root module cache of module completer,
2687 2663 used on slow filesystems.
2688 2664 """
2665 from IPython.core.alias import InvalidAliasError
2689 2666
2690 2667 # for the benefit of module completer in ipy_completers.py
2691 2668 del self.db['rootmodules']
@@ -2693,14 +2670,13 b' Defaulting color scheme to \'NoColor\'"""'
2693 2670 path = [os.path.abspath(os.path.expanduser(p)) for p in
2694 2671 os.environ.get('PATH','').split(os.pathsep)]
2695 2672 path = filter(os.path.isdir,path)
2696
2697 alias_table = self.shell.alias_table
2673
2698 2674 syscmdlist = []
2675 # Now define isexec in a cross platform manner.
2699 2676 if os.name == 'posix':
2700 2677 isexec = lambda fname:os.path.isfile(fname) and \
2701 2678 os.access(fname,os.X_OK)
2702 2679 else:
2703
2704 2680 try:
2705 2681 winext = os.environ['pathext'].replace(';','|').replace('.','')
2706 2682 except KeyError:
@@ -2710,6 +2686,8 b' Defaulting color scheme to \'NoColor\'"""'
2710 2686 execre = re.compile(r'(.*)\.(%s)$' % winext,re.IGNORECASE)
2711 2687 isexec = lambda fname:os.path.isfile(fname) and execre.match(fname)
2712 2688 savedir = os.getcwd()
2689
2690 # Now walk the paths looking for executables to alias.
2713 2691 try:
2714 2692 # write the whole loop for posix/Windows so we don't have an if in
2715 2693 # the innermost part
@@ -2717,14 +2695,16 b' Defaulting color scheme to \'NoColor\'"""'
2717 2695 for pdir in path:
2718 2696 os.chdir(pdir)
2719 2697 for ff in os.listdir(pdir):
2720 if isexec(ff) and ff not in self.shell.no_alias:
2721 # each entry in the alias table must be (N,name),
2722 # where N is the number of positional arguments of the
2723 # alias.
2724 # Dots will be removed from alias names, since ipython
2725 # assumes names with dots to be python code
2726 alias_table[ff.replace('.','')] = (0,ff)
2727 syscmdlist.append(ff)
2698 if isexec(ff):
2699 try:
2700 # Removes dots from the name since ipython
2701 # will assume names with dots to be python.
2702 self.shell.alias_manager.define_alias(
2703 ff.replace('.',''), ff)
2704 except InvalidAliasError:
2705 pass
2706 else:
2707 syscmdlist.append(ff)
2728 2708 else:
2729 2709 for pdir in path:
2730 2710 os.chdir(pdir)
@@ -2733,16 +2713,14 b' Defaulting color scheme to \'NoColor\'"""'
2733 2713 if isexec(ff) and base.lower() not in self.shell.no_alias:
2734 2714 if ext.lower() == '.exe':
2735 2715 ff = base
2736 alias_table[base.lower().replace('.','')] = (0,ff)
2737 syscmdlist.append(ff)
2738 # Make sure the alias table doesn't contain keywords or builtins
2739 self.shell.alias_table_validate()
2740 # Call again init_auto_alias() so we get 'rm -i' and other
2741 # modified aliases since %rehashx will probably clobber them
2742
2743 # no, we don't want them. if %rehashx clobbers them, good,
2744 # we'll probably get better versions
2745 # self.shell.init_auto_alias()
2716 try:
2717 # Removes dots from the name since ipython
2718 # will assume names with dots to be python.
2719 self.shell.alias_manager.define_alias(
2720 base.lower().replace('.',''), ff)
2721 except InvalidAliasError:
2722 pass
2723 syscmdlist.append(ff)
2746 2724 db = self.db
2747 2725 db['syscmdlist'] = syscmdlist
2748 2726 finally:
@@ -3167,7 +3145,7 b' Defaulting color scheme to \'NoColor\'"""'
3167 3145 """
3168 3146
3169 3147 start = parameter_s.strip()
3170 esc_magic = self.shell.ESC_MAGIC
3148 esc_magic = ESC_MAGIC
3171 3149 # Identify magic commands even if automagic is on (which means
3172 3150 # the in-memory version is different from that typed by the user).
3173 3151 if self.shell.automagic:
@@ -174,7 +174,7 b' class PrefilterManager(Component):'
174 174 to transform the input line.
175 175 """
176 176
177 multi_line_specials = CBool(True, config_key='MULTI_LINE_SPECIALS')
177 multi_line_specials = CBool(True, config=True)
178 178
179 179 def __init__(self, parent, config=None):
180 180 super(PrefilterManager, self).__init__(parent, config=config)
@@ -274,16 +274,16 b' class PrefilterManager(Component):'
274 274 # the input history needs to track even empty lines
275 275 stripped = line.strip()
276 276
277 handle_normal = self.get_handler_by_name('normal')
277 normal_handler = self.get_handler_by_name('normal')
278 278 if not stripped:
279 279 if not continue_prompt:
280 280 self.shell.outputcache.prompt_count -= 1
281 281
282 return handle_normal(line_info)
282 return normal_handler.handle(line_info)
283 283
284 284 # special handlers are only allowed for single line statements
285 285 if continue_prompt and not self.multi_line_specials:
286 return handle_normal(line_info)
286 return normal_handler.handle(line_info)
287 287
288 288 return self.prefilter_line_info(line_info)
289 289
@@ -310,7 +310,7 b' class PrefilterManager(Component):'
310 310 class PrefilterChecker(Component):
311 311 """Inspect an input line and return a handler for that line."""
312 312
313 priority = Int(100)
313 priority = Int(100, config=True)
314 314 shell = Any
315 315 prefilter_manager = Any
316 316
@@ -336,7 +336,7 b' class PrefilterChecker(Component):'
336 336
337 337 class EmacsChecker(PrefilterChecker):
338 338
339 priority = Int(100)
339 priority = Int(100, config=True)
340 340
341 341 def check(self, line_info):
342 342 "Emacs ipython-mode tags certain input lines."
@@ -348,7 +348,7 b' class EmacsChecker(PrefilterChecker):'
348 348
349 349 class ShellEscapeChecker(PrefilterChecker):
350 350
351 priority = Int(200)
351 priority = Int(200, config=True)
352 352
353 353 def check(self, line_info):
354 354 if line_info.line.lstrip().startswith(ESC_SHELL):
@@ -357,7 +357,7 b' class ShellEscapeChecker(PrefilterChecker):'
357 357
358 358 class IPyAutocallChecker(PrefilterChecker):
359 359
360 priority = Int(300)
360 priority = Int(300, config=True)
361 361
362 362 def check(self, line_info):
363 363 "Instances of IPyAutocall in user_ns get autocalled immediately"
@@ -371,7 +371,7 b' class IPyAutocallChecker(PrefilterChecker):'
371 371
372 372 class MultiLineMagicChecker(PrefilterChecker):
373 373
374 priority = Int(400)
374 priority = Int(400, config=True)
375 375
376 376 def check(self, line_info):
377 377 "Allow ! and !! in multi-line statements if multi_line_specials is on"
@@ -388,7 +388,7 b' class MultiLineMagicChecker(PrefilterChecker):'
388 388
389 389 class EscCharsChecker(PrefilterChecker):
390 390
391 priority = Int(500)
391 priority = Int(500, config=True)
392 392
393 393 def check(self, line_info):
394 394 """Check for escape character and return either a handler to handle it,
@@ -406,7 +406,7 b' class EscCharsChecker(PrefilterChecker):'
406 406
407 407 class AssignmentChecker(PrefilterChecker):
408 408
409 priority = Int(600)
409 priority = Int(600, config=True)
410 410
411 411 def check(self, line_info):
412 412 """Check to see if user is assigning to a var for the first time, in
@@ -423,7 +423,7 b' class AssignmentChecker(PrefilterChecker):'
423 423
424 424 class AutoMagicChecker(PrefilterChecker):
425 425
426 priority = Int(700)
426 priority = Int(700, config=True)
427 427
428 428 def check(self, line_info):
429 429 """If the ifun is magic, and automagic is on, run it. Note: normal,
@@ -447,7 +447,7 b' class AutoMagicChecker(PrefilterChecker):'
447 447
448 448 class AliasChecker(PrefilterChecker):
449 449
450 priority = Int(800)
450 priority = Int(800, config=True)
451 451
452 452 @auto_attr
453 453 def alias_manager(self):
@@ -467,7 +467,7 b' class AliasChecker(PrefilterChecker):'
467 467
468 468 class PythonOpsChecker(PrefilterChecker):
469 469
470 priority = Int(900)
470 priority = Int(900, config=True)
471 471
472 472 def check(self, line_info):
473 473 """If the 'rest' of the line begins with a function call or pretty much
@@ -482,7 +482,7 b' class PythonOpsChecker(PrefilterChecker):'
482 482
483 483 class AutocallChecker(PrefilterChecker):
484 484
485 priority = Int(1000)
485 priority = Int(1000, config=True)
486 486
487 487 def check(self, line_info):
488 488 "Check if the initial word/function is callable and autocall is on."
@@ -567,7 +567,7 b' class AliasHandler(PrefilterHandler):'
567 567 transformed = self.alias_manager.expand_aliases(line_info.ifun,line_info.the_rest)
568 568 # pre is needed, because it carries the leading whitespace. Otherwise
569 569 # aliases won't work in indented sections.
570 line_out = '%s_ip.system(%s)' % (line_info.pre_whitespace,
570 line_out = '%sget_ipython().system(%s)' % (line_info.pre_whitespace,
571 571 make_quoted_expr(transformed))
572 572
573 573 self.shell.log(line_info.line, line_out, line_info.continue_prompt)
@@ -597,7 +597,7 b' class ShellEscapeHandler(PrefilterHandler):'
597 597 return magic_handler.handle(line_info)
598 598 else:
599 599 cmd = line.lstrip().lstrip(ESC_SHELL)
600 line_out = '%s_ip.system(%s)' % (line_info.pre_whitespace,
600 line_out = '%sget_ipython().system(%s)' % (line_info.pre_whitespace,
601 601 make_quoted_expr(cmd))
602 602 # update cache/log and return
603 603 self.shell.log(line, line_out, line_info.continue_prompt)
@@ -607,13 +607,13 b' class ShellEscapeHandler(PrefilterHandler):'
607 607 class MagicHandler(PrefilterHandler):
608 608
609 609 handler_name = Str('magic')
610 esc_strings = List(['%'])
610 esc_strings = List([ESC_MAGIC])
611 611
612 612 def handle(self, line_info):
613 613 """Execute magic functions."""
614 614 ifun = line_info.ifun
615 615 the_rest = line_info.the_rest
616 cmd = '%s_ip.magic(%s)' % (line_info.pre_whitespace,
616 cmd = '%sget_ipython().magic(%s)' % (line_info.pre_whitespace,
617 617 make_quoted_expr(ifun + " " + the_rest))
618 618 self.shell.log(line_info.line, cmd, line_info.continue_prompt)
619 619 return cmd
@@ -656,7 +656,7 b' class AutoHandler(PrefilterHandler):'
656 656 # We only apply it to argument-less calls if the autocall
657 657 # parameter is set to 2. We only need to check that autocall is <
658 658 # 2, since this function isn't called unless it's at least 1.
659 if not the_rest and (self.autocall < 2) and not force_auto:
659 if not the_rest and (self.shell.autocall < 2) and not force_auto:
660 660 newcmd = '%s %s' % (ifun,the_rest)
661 661 auto_rewrite = False
662 662 else:
@@ -546,8 +546,11 b' class CachedOutput:'
546 546 # don't use print, puts an extra space
547 547 cout_write(self.output_sep)
548 548 outprompt = self.shell.hooks.generate_output_prompt()
549 # print "Got prompt: ", outprompt
549 550 if self.do_full_cache:
550 551 cout_write(outprompt)
552 else:
553 print "self.do_full_cache = False"
551 554
552 555 # and now call a possibly user-defined print mechanism
553 556 manipulated_val = self.display(arg)
@@ -31,4 +31,5 b' class A(object):'
31 31 a = A()
32 32
33 33 # Now, we force an exit, the caller will check that the del printout was given
34 _ip = get_ipython()
34 35 _ip.ask_exit()
@@ -26,7 +26,7 b' from IPython.core.component import Component, ComponentError'
26 26 from IPython.utils.traitlets import (
27 27 TraitletError, Int, Float, Str
28 28 )
29 from IPython.utils.ipstruct import Struct
29 from IPython.config.loader import Config
30 30
31 31
32 32 #-----------------------------------------------------------------------------
@@ -138,9 +138,9 b' class TestComponentConfig(TestCase):'
138 138 self.assertEquals(c2.config, c3.config)
139 139
140 140 def test_custom(self):
141 config = Struct()
142 config.FOO = 'foo'
143 config.BAR = 'bar'
141 config = Config()
142 config.foo = 'foo'
143 config.bar = 'bar'
144 144 c1 = Component(None, config=config)
145 145 c2 = Component(c1)
146 146 c3 = Component(c2)
@@ -156,19 +156,19 b' class TestComponentConfig(TestCase):'
156 156
157 157 def test_inheritance(self):
158 158 class MyComponent(Component):
159 a = Int(1, config_key='A')
160 b = Float(1.0, config_key='B')
159 a = Int(1, config=True)
160 b = Float(1.0, config=True)
161 161 c = Str('no config')
162 config = Struct()
163 config.A = 2
164 config.B = 2.0
162 config = Config()
163 config.MyComponent.a = 2
164 config.MyComponent.b = 2.0
165 165 c1 = MyComponent(None, config=config)
166 166 c2 = MyComponent(c1)
167 self.assertEquals(c1.a, config.A)
168 self.assertEquals(c1.b, config.B)
169 self.assertEquals(c2.a, config.A)
170 self.assertEquals(c2.b, config.B)
171 c4 = MyComponent(c2, config=Struct())
167 self.assertEquals(c1.a, config.MyComponent.a)
168 self.assertEquals(c1.b, config.MyComponent.b)
169 self.assertEquals(c2.a, config.MyComponent.a)
170 self.assertEquals(c2.b, config.MyComponent.b)
171 c4 = MyComponent(c2, config=Config())
172 172 self.assertEquals(c4.a, 1)
173 173 self.assertEquals(c4.b, 1.0)
174 174
@@ -20,14 +20,15 b' from IPython.testing import tools as tt'
20 20
21 21 def test_rehashx():
22 22 # clear up everything
23 _ip.alias_table.clear()
23 _ip = get_ipython()
24 _ip.alias_manager.alias_table.clear()
24 25 del _ip.db['syscmdlist']
25 26
26 27 _ip.magic('rehashx')
27 28 # Practically ALL ipython development systems will have more than 10 aliases
28 29
29 yield (nt.assert_true, len(_ip.alias_table) > 10)
30 for key, val in _ip.alias_table.items():
30 yield (nt.assert_true, len(_ip.alias_manager.alias_table) > 10)
31 for key, val in _ip.alias_manager.alias_table.items():
31 32 # we must strip dots from alias names
32 33 nt.assert_true('.' not in key)
33 34
@@ -65,6 +66,7 b' def doctest_hist_r():'
65 66 # This test is known to fail on win32.
66 67 # See ticket https://bugs.launchpad.net/bugs/366334
67 68 def test_obj_del():
69 _ip = get_ipython()
68 70 """Test that object's __del__ methods are called on exit."""
69 71 test_dir = os.path.dirname(__file__)
70 72 del_file = os.path.join(test_dir,'obj_del.py')
@@ -221,13 +223,14 b' class TestMagicRun(object):'
221 223 self.fname = fname
222 224
223 225 def run_tmpfile(self):
226 _ip = get_ipython()
224 227 # This fails on Windows if self.tmpfile.name has spaces or "~" in it.
225 228 # See below and ticket https://bugs.launchpad.net/bugs/366353
226 229 _ip.magic('run "%s"' % self.fname)
227 230
228 231 def test_builtins_id(self):
229 232 """Check that %run doesn't damage __builtins__ """
230
233 _ip = get_ipython()
231 234 # Test that the id of __builtins__ is not modified by %run
232 235 bid1 = id(_ip.user_ns['__builtins__'])
233 236 self.run_tmpfile()
@@ -241,12 +244,14 b' class TestMagicRun(object):'
241 244 be a dict (it should be a module) by a previous use of %run. So we
242 245 also check explicitly that it really is a module:
243 246 """
247 _ip = get_ipython()
244 248 self.run_tmpfile()
245 249 tt.assert_equals(type(_ip.user_ns['__builtins__']),type(sys))
246 250
247 251 def test_prompts(self):
248 252 """Test that prompts correctly generate after %run"""
249 253 self.run_tmpfile()
254 _ip = get_ipython()
250 255 p2 = str(_ip.outputcache.prompt2).strip()
251 256 nt.assert_equals(p2[:3], '...')
252 257
@@ -261,7 +266,7 b' class TestMagicRun(object):'
261 266
262 267 # Multiple tests for clipboard pasting
263 268 def test_paste():
264
269 _ip = get_ipython()
265 270 def paste(txt, flags='-q'):
266 271 """Paste input text, by default in quiet mode"""
267 272 hooks.clipboard_get = lambda : txt
@@ -21,14 +21,14 b' def hnd_magic(line,mo):'
21 21 var = mo.group('varname')
22 22 cmd = mo.group('cmd')
23 23 expr = make_quoted_expr(cmd)
24 return itpl('$var = _ip.magic($expr)')
24 return itpl('$var = get_ipython().magic($expr)')
25 25
26 26 def hnd_syscmd(line,mo):
27 27 """ Handle a = !ls """
28 28 var = mo.group('varname')
29 29 cmd = mo.group('cmd')
30 30 expr = make_quoted_expr(itpl("sc -l =$cmd"))
31 return itpl('$var = _ip.magic($expr)')
31 return itpl('$var = get_ipython().magic($expr)')
32 32
33 33 def install_re_handler(pat, hnd):
34 34 ip.meta.re_prefilters.append((re.compile(pat), hnd))
@@ -1644,7 +1644,7 b' class ialias(Table):'
1644 1644 def __iter__(self):
1645 1645 api = ipapi.get()
1646 1646
1647 for (name, (args, command)) in api.alias_table.iteritems():
1647 for (name, (args, command)) in api.alias_manager.alias_table.iteritems():
1648 1648 yield Alias(name, args, command)
1649 1649
1650 1650
@@ -109,7 +109,7 b' def main():'
109 109 cmd = noext
110 110
111 111 key = mapper(cmd)
112 if key not in ip.alias_table:
112 if key not in ip.alias_manager.alias_table:
113 113 # Dots will be removed from alias names, since ipython
114 114 # assumes names with dots to be python code
115 115
@@ -159,7 +159,7 b' def slash_prefilter_f(self,line):'
159 159 """
160 160 from IPython.utils import genutils
161 161 if re.match('(?:[.~]|/[a-zA-Z_0-9]+)/', line):
162 return "_ip.system(" + genutils.make_quoted_expr(line)+")"
162 return "get_ipython().system(" + genutils.make_quoted_expr(line)+")"
163 163 raise TryNext
164 164
165 165 # XXX You do not need to understand the next function!
@@ -88,7 +88,7 b' def rehashdir_f(self,arg):'
88 88 if not arg:
89 89 arg = '.'
90 90 path = map(os.path.abspath,arg.split(';'))
91 alias_table = self.shell.alias_table
91 alias_table = self.shell.alias_manager.alias_table
92 92
93 93 if os.name == 'posix':
94 94 isexec = lambda fname:os.path.isfile(fname) and \
@@ -126,8 +126,8 b' def jobctrl_prefilter_f(self,line):'
126 126
127 127 line = ip.expand_aliases(fn,rest)
128 128 if not _jobq:
129 return '_ip.startjob(%s)' % genutils.make_quoted_expr(line)
130 return '_ip.jobq(%s)' % genutils.make_quoted_expr(line)
129 return 'get_ipython().startjob(%s)' % genutils.make_quoted_expr(line)
130 return 'get_ipython().jobq(%s)' % genutils.make_quoted_expr(line)
131 131
132 132 raise TryNext
133 133
@@ -157,6 +157,7 b" def magic_store(self, parameter_s=''):"
157 157 obj = ip.user_ns[args[0]]
158 158 except KeyError:
159 159 # it might be an alias
160 # This needs to be refactored to use the new AliasManager stuff.
160 161 if args[0] in self.alias_table:
161 162 staliases = db.get('stored_aliases',{})
162 163 staliases[ args[0] ] = self.alias_table[ args[0] ]
@@ -99,7 +99,7 b' def pxrunsource(self, source, filename="<input>", symbol="single"):'
99 99 # Case 3
100 100 # Because autopx is enabled, we now call executeAll or disable autopx if
101 101 # %autopx or autopx has been called
102 if '_ip.magic("%autopx' in source or '_ip.magic("autopx' in source:
102 if 'get_ipython().magic("%autopx' in source or 'get_ipython().magic("autopx' in source:
103 103 _disable_autopx(self)
104 104 return False
105 105 else:
@@ -353,14 +353,17 b' class TestHasTraitlets(TestCase):'
353 353 class A(HasTraitlets):
354 354 i = Int(config_key='VALUE1', other_thing='VALUE2')
355 355 f = Float(config_key='VALUE3', other_thing='VALUE2')
356 j = Int(0)
356 357 a = A()
357 self.assertEquals(a.traitlets(), dict(i=A.i, f=A.f))
358 traitlets = a.traitlets(config_key=lambda v: True)
359 self.assertEquals(traitlets, dict(i=A.i, f=A.f))
358 self.assertEquals(a.traitlets(), dict(i=A.i, f=A.f, j=A.j))
360 359 traitlets = a.traitlets(config_key='VALUE1', other_thing='VALUE2')
361 360 self.assertEquals(traitlets, dict(i=A.i))
362 traitlets = a.traitlets('config_key')
363 self.assertEquals(traitlets, dict(i=A.i, f=A.f))
361
362 # This passes, but it shouldn't because I am replicating a bug in
363 # traits.
364 traitlets = a.traitlets(config_key=lambda v: True)
365 self.assertEquals(traitlets, dict(i=A.i, f=A.f, j=A.j))
366
364 367
365 368 #-----------------------------------------------------------------------------
366 369 # Tests for specific traitlet types
@@ -458,19 +458,22 b' class HasTraitlets(object):'
458 458 """Get a list of all the names of this classes traitlets."""
459 459 return self.traitlets(**metadata).keys()
460 460
461 def traitlets(self, *args, **metadata):
461 def traitlets(self, **metadata):
462 462 """Get a list of all the traitlets of this class.
463 463
464 464 The TraitletTypes returned don't know anything about the values
465 465 that the various HasTraitlet's instances are holding.
466
467 This follows the same algorithm as traits does and does not allow
468 for any simple way of specifying merely that a metadata name
469 exists, but has any value. This is because get_metadata returns
470 None if a metadata key doesn't exist.
466 471 """
467 472 traitlets = dict([memb for memb in inspect.getmembers(self.__class__) if \
468 473 isinstance(memb[1], TraitletType)])
469 if len(metadata) == 0 and len(args) == 0:
470 return traitlets
471 474
472 for meta_name in args:
473 metadata[meta_name] = lambda _: True
475 if len(metadata) == 0:
476 return traitlets
474 477
475 478 for meta_name, meta_eval in metadata.items():
476 479 if type(meta_eval) is not FunctionType:
General Comments 0
You need to be logged in to leave comments. Login now