从my_module import覆盖...

时间:2018-06-28 16:27:40

标签: python python-2.7 python-import

我正在尝试使以下行为起作用:

from my_module import some_random_string

并且我的模块应该拦截它并基于some_random_string返回某些值。

我尝试设置导入挂钩,但无法按预期工作:

# custom_import.py
import sys

class MyImporter(object):
    def find_module(self, filename, path):
        print(filename, path)
        return "foobar"

    def load_module(self, module_name):
        print(module_name)
        return "foobar"

sys.meta_path.append(MyImporter())
# interactive console
>>> from custom_import import some_string
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: cannot import name some_string
>>>

为什么会这样,我该如何解决?

1 个答案:

答案 0 :(得分:1)

要能够导入my_module中不存在的任何对象(假设my_module存在并且可以访问),我们可以从简单包装my_module开始,例如

import importlib
import sys
import types


class ModuleWrapper:
    def __init__(self, module):
        self.module = module

    @property
    def __path__(self):
        return None

    def __getattr__(self, name):
        try:
            return getattr(self.module, name)
        except AttributeError:
            # returning `module` object is not necessary, 
            # can be something else
            return types.ModuleType(name)


my_module = importlib.import_module('my_module')
sys.modules['my_module'] = ModuleWrapper(my_module)

测试

具有项目结构

  

my_module.py

     

test.py

内容

  • my_module.py

    ...snippet above...
    some_name = 'Sample text'
    
  • test.py

    from my_module import some_name, z
    
    print(some_name)
    print(z)
    

执行

> python test.py

为我们提供了 Python2.7.0

Sample text
<module 'z' (built-in)>

Python3.5.4

Sample text
<module 'z'>