我有一个使用自定义模块功能的烧瓶应用程序。
我的文件层次结构如下:
__init__.py
ec2/__init__.py
citrixlb/__init__.py
到目前为止,在根__init__.py
中我有一个from ec2 import *
子句来加载我的模块。
现在我添加了一项新功能'叫做citrixlb。
citrixlb和ec2中的__init__.py
文件都使用一些相同的功能来完成任务。
我在想做类似的事情:
__init__.py
common/__init__.py
ec2/__init__.py
citrixlb/__init__.py
如果我执行上述操作,并将所有常用功能移至common/__init__.py
,ec2/__init__.py
和citrixlb/__init__.py
将如何访问这些功能
在common/__init__.py
?
原因是
__init__.py
尽可能稀疏__init__.py
和citrixlb
中运行ec2
独立脚本。newdir/__init__.py
答案 0 :(得分:1)
如果我执行上述操作,并将所有常用功能移至
common/__init__.py
,ec2/__init__.py
和citrixlb/__init__.py
如何访问common/__init__.py
中的功能?
这正是explicit relative imports的设计目标:
from .. import common
或者,如果您坚持使用import *
:
from ..common import *
您可以使用绝对导入来执行此操作。假设您的顶级包名为mything
:
from mything import common
from mything.common import *
但在这种情况下,我认为相对版本你会更好。它不仅更简洁,更易于阅读,更强大(如果您重命名mything
,或重新组织其结构,或将整个包嵌入更大的包中......)。但是你可能想要阅读PEP 328中两个不同特征的基本原理来决定哪一个在这里对你更有吸引力。
有一件事:
我希望能够以
__init__.py
和citrixlb
作为独立脚本运行ec2
。
那,你做不到。作为顶级脚本在包内运行模块不应该工作。有时你会逃脱它。一旦你从兄弟姐妹或父母那里进口,你肯定不会逃脱它。
正确的方法是:
python -m mything.ec2
代替python mything/ec2/__init__.py
ec2
脚本,就像from mything.ec2 import main; main()
一样。后者是一种常见的模式,如果您正在构建setuptools
发行版,它可以自动为您构建ec2
脚本。当ec2
包裹在您的/usr/local/bin
中时,即使mything
site-packages
结束,也会自动使其仍然有效。有关详细信息,请参阅console_scripts
。