magic.py
147 lines
| 4.3 KiB
| text/x-python
|
PythonLexer
Brian E Granger
|
r1234 | # encoding: utf-8 | ||
__docformat__ = "restructuredtext en" | ||||
#------------------------------------------------------------------------------- | ||||
# Copyright (C) 2008 The IPython Development Team | ||||
# | ||||
# Distributed under the terms of the BSD License. The full license is in | ||||
# the file COPYING, distributed as part of this software. | ||||
#------------------------------------------------------------------------------- | ||||
#------------------------------------------------------------------------------- | ||||
# Imports | ||||
#------------------------------------------------------------------------------- | ||||
import os | ||||
import __builtin__ | ||||
# Local imports. | ||||
from util import Bunch | ||||
# fixme: RTK thinks magics should be implemented as separate classes rather than | ||||
# methods on a single class. This would give us the ability to plug new magics | ||||
# in and configure them separately. | ||||
class Magic(object): | ||||
""" An object that maintains magic functions. | ||||
""" | ||||
def __init__(self, interpreter, config=None): | ||||
# A reference to the interpreter. | ||||
self.interpreter = interpreter | ||||
# A reference to the configuration object. | ||||
if config is None: | ||||
# fixme: we need a better place to store this information. | ||||
config = Bunch(ESC_MAGIC='%') | ||||
self.config = config | ||||
def has_magic(self, name): | ||||
""" Return True if this object provides a given magic. | ||||
Parameters | ||||
---------- | ||||
name : str | ||||
""" | ||||
return hasattr(self, 'magic_' + name) | ||||
def object_find(self, name): | ||||
""" Find an object in the available namespaces. | ||||
fixme: this should probably be moved elsewhere. The interpreter? | ||||
""" | ||||
name = name.strip() | ||||
# Namespaces to search. | ||||
# fixme: implement internal and alias namespaces. | ||||
user_ns = self.interpreter.user_ns | ||||
internal_ns = {} | ||||
builtin_ns = __builtin__.__dict__ | ||||
alias_ns = {} | ||||
# Order the namespaces. | ||||
namespaces = [ | ||||
('Interactive', user_ns), | ||||
('IPython internal', internal_ns), | ||||
('Python builtin', builtin_ns), | ||||
('Alias', alias_ns), | ||||
] | ||||
# Initialize all results. | ||||
found = False | ||||
obj = None | ||||
space = None | ||||
ds = None | ||||
ismagic = False | ||||
isalias = False | ||||
# Look for the given name by splitting it in parts. If the head is | ||||
# found, then we look for all the remaining parts as members, and only | ||||
# declare success if we can find them all. | ||||
parts = name.split('.') | ||||
head, rest = parts[0], parts[1:] | ||||
for nsname, ns in namespaces: | ||||
try: | ||||
obj = ns[head] | ||||
except KeyError: | ||||
continue | ||||
else: | ||||
for part in rest: | ||||
try: | ||||
obj = getattr(obj, part) | ||||
except: | ||||
# Blanket except b/c some badly implemented objects | ||||
# allow __getattr__ to raise exceptions other than | ||||
# AttributeError, which then crashes us. | ||||
break | ||||
else: | ||||
# If we finish the for loop (no break), we got all members | ||||
found = True | ||||
space = nsname | ||||
isalias = (ns == alias_ns) | ||||
break # namespace loop | ||||
# Try to see if it is a magic. | ||||
if not found: | ||||
if name.startswith(self.config.ESC_MAGIC): | ||||
name = name[1:] | ||||
obj = getattr(self, 'magic_' + name, None) | ||||
if obj is not None: | ||||
found = True | ||||
space = 'IPython internal' | ||||
ismagic = True | ||||
# Last try: special-case some literals like '', [], {}, etc: | ||||
if not found and head in ["''", '""', '[]', '{}', '()']: | ||||
obj = eval(head) | ||||
found = True | ||||
space = 'Interactive' | ||||
return dict( | ||||
found=found, | ||||
obj=obj, | ||||
namespace=space, | ||||
ismagic=ismagic, | ||||
isalias=isalias, | ||||
) | ||||
def magic_pwd(self, parameter_s=''): | ||||
""" Return the current working directory path. | ||||
""" | ||||
return os.getcwd() | ||||
def magic_env(self, parameter_s=''): | ||||
""" List environment variables. | ||||
""" | ||||
return os.environ.data | ||||