def _import(name, filename=None):
"""
Run the given callable in a 'sandboxed' environment.
Currently, this includes saving and restoring the contents of
sys and __builtins__; and suppressing stdin, stdout, and stderr.
"""
# Note that we just do a shallow copy of sys. In particular,
# any changes made to sys.modules will be kept. But we do
# explicitly store sys.path.
old_sys = sys.__dict__.copy()
old_sys_path = sys.path[:]
old_builtins = __builtin__.__dict__.copy()
# Add the current directory to sys.path, in case they're trying to
# import a module by name that resides in the current directory.
# But add it to the end -- otherwise, the explicit directory added
# in get_value_from_filename might get overwritten
sys.path.append('')
# Suppress input and output. (These get restored when we restore
# sys to old_sys).
sys.stdin = sys.stdout = sys.stderr = _dev_null
sys.__stdin__ = sys.__stdout__ = sys.__stderr__ = _dev_null
# Remove any command-line arguments
sys.argv = ['(imported)']
try:
try:
if filename is None:
return __import__(name)
else:
# For importing scripts:
return imp.load_source(name, filename)
except KeyboardInterrupt: raise
except:
exc_typ, exc_val, exc_tb = sys.exc_info()
if exc_val is None:
estr = '%s' % (exc_typ,)
else:
estr = '%s: %s' % (exc_typ.__name__, exc_val)
if exc_tb.tb_next is not None:
estr += ' (line %d)' % (exc_tb.tb_next.tb_lineno,)
raise ImportError(estr)
finally:
# Restore the important values that we saved.
__builtin__.__dict__.clear()
__builtin__.__dict__.update(old_builtins)
sys.__dict__.clear()
sys.__dict__.update(old_sys)
sys.path = old_sys_path
评论列表
文章目录