Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/logging/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
重写Python导入而不导致受限执行模式_Python - Fatal编程技术网

重写Python导入而不导致受限执行模式

重写Python导入而不导致受限执行模式,python,Python,我需要重写lambda函数编译中的默认导入器,以便使用某些模块的替代版本。但是,lambda代码不需要以受限执行RE运行,因为只有经过授权的人才能生成正在编译的代码。我们还要求能够打开文件,这在RE中是不允许的: IOError: file() constructor not accessible in restricted mode 但是,为了覆盖导入器,我需要复制_内置__;模块,并将新的导入器分配给_导入_;。然而,使用“内置”的替代版本是导致RE的具体原因 如何在不引起RE副作用的情况

我需要重写lambda函数编译中的默认导入器,以便使用某些模块的替代版本。但是,lambda代码不需要以受限执行RE运行,因为只有经过授权的人才能生成正在编译的代码。我们还要求能够打开文件,这在RE中是不允许的:

IOError: file() constructor not accessible in restricted mode
但是,为了覆盖导入器,我需要复制_内置__;模块,并将新的导入器分配给_导入_;。然而,使用“内置”的替代版本是导致RE的具体原因

如何在不引起RE副作用的情况下简单地覆盖进口商

编辑:对于那些没有经历过这一点并且没有想象力的人:

def copy_module(m):
    x = type(m)(m.__name__, m.__doc__)
    x.__dict__.update(m.__dict__)
    return x

# Make sure we get the module in all situations (depending on where 
# __builtins__ is invoked, it may be a dictionary).
builtins = __import__('__builtin__')

custom_builtins = copy_module(builtins)
custom_builtins.__import__ = __import__

l = """\
with open('/dev/null') as f:
    pass
"""

c = compile(l, 'open_test', 'exec')

globals_ = {
    '__builtins__': custom_builtins, 
    '__name__': '__handler__', 
    '__doc__': None, 
    '__package__': None,
}

locals_ = {}

exec c in globals_, locals_
结果:

Traceback (most recent call last):
  File "import_replace_2.py", line 31, in <module>
    exec c in globals_, locals_
  File "open_test", line 1, in <module>
IOError: file() constructor not accessible in restricted mode

我没有得到这个错误。从python文档中:

__import\此函数由import语句调用。可以通过导入_u内置__;模块并分配给_内置_;._导入__;来替换它,以更改导入语句的语义

以下是我的作品,它做的一切与标准导入相同,但用数学取代垃圾邮件

>>> import builtins
>>> _import_alias = __import__
>>> builtins.__import__ = lambda module, *args, **kwargs: _import_alias(module.replace("spam", "math"), *args, **kwargs)
>>> import spam as math
>>> math.factorial(10)

重要的是要创建uuu import uuu的别名,并覆盖内置项。uuu import uuu,而不是标准的uu import。

您没有在侦听。这必须是导入的副本,并且您必须尝试文件/打开操作。你需要知道你在说什么才能做出回应。