我正在制作一个具有以下结构的Python库:
my_amazing_lib
+--- __init__.py
+--- _core.py
+--- _gui.py
在__init__.py
我有以下内容:
from ._core import core_lib
from ._gui import huge_lib_with_gui
__all__ = ['core_lib', 'huge_lib_with_gui']
目标是为用户提供API,以便他们可以使用:
from my_amazing_lib import core_lib
from my_amazing_lib import huge_lib_with_gui
取决于他们的需求。
问题是即使用户只需要huge_lib_with_gui
,Python也会自动导入core_lib
,这会导致各种问题:依赖性问题(例如gui libs),减速(例如{{} 1}}生成多个线程和后台作业,而huge_lib_with_gui
不需要这样做),等等。这个问题已经described here(Trap n°2)。
是否可以为 Python模块声明公开API ,但只导入每个用户需要的相关子模块?
该解决方案应适用于Python 2.7.10和Python> 3.3。
答案 0 :(得分:0)
我建议将库中昂贵的初始化部分保存在一个单独的子模块中,而不是直接将它包含在顶级包命名空间中。虽然您可以使用代理函数来公开顶级命名空间中昂贵位的API,而无需先行导入它,但它可能比它的价值更麻烦。
例如,在您的示例包布局中:
my_amazing_lib
+--- __init__.py
+--- _core.py
+--- _gui.py
您可能希望添加一个gui.py
文件,该文件将_gui
的公共API导入到干净的命名空间中。
gui.py
的内容将是:
from ._gui import huge_lib_with_a_gui
__all__ = ["huge_lib_with_a_gui"]
和__init__.py
文件看起来像:
from ._core import core_lib
__all__ = ["core_lib", "gui"] # don't import gui here, just name it as part of `__all__`
只需要图书馆核心部分的用户可以from my_amazing_lib import core_lib
,而需要gui资料的用户也可以添加from my_amazing_lib.gui import huge_lib_with_a_gui
。