【问题标题】:Deeply nested namespaced packages深度嵌套的命名空间包
【发布时间】:2019-09-24 17:33:11
【问题描述】:

我需要维护一些以这种方式构建的 ETL 工具,将任务和管道定义为 python 包的集合。考虑具有小核心的插件架构和嵌套命名空间/包/子包中的近千个插件。这还不是一团糟,整体质量相当不错,但setup.py__init__.py-s 看起来很hacky,有时在导入过程中会导致意想不到的问题。

我想稍微简化一下。从 Python 3.3 开始,我们可以通过创建不带__init__.py 的子目录将包放入命名空间。这正是我所需要的,但我想避免在源代码中深度嵌套子目录,因为大量的包非常小。在极端情况下,它们看起来像这样:

$ tree
.
├── setup.cfg
├── setup.py
└── src
    └── foo
        └── bar
            └── baz
                └── xyz
                    └── uvw
                        └── package
                            ├── actual_code.py
                            └── __init__.py

有没有办法使用隐式命名空间而没有如此深的结构,只需在setup.py(或者更好的setup.cfg)中的某处指定命名空间?换句话说,有没有一种简单的方式来判断:在foo.bar.baz.xyz.uvw命名空间中安装package

我想要这样的结构:

$ tree
.
├── setup.cfg
├── setup.py
└── src
    └── package
        ├── actual_code.py
        └── __init__.py

但安装过程要把package放到foo/bar/baz/xyz/uvw/package文件夹中,这样就可以用完整路径导入了。

编辑:这是个好主意吗?

【问题讨论】:

  • 您是否考虑过指定__all__example
  • 这不是为了缩短长期进口。我需要在安装后拥有那个深层结构,但我不希望它在源代码存储库中。

标签: python setuptools packaging


【解决方案1】:

这可以使用distutils.core.setuppackage_dir 参数(或setuptools 的等效参数)来实现。

只需修改您的 setup.py 以包含以下内容:

from distutils.core import setup

setup(# ... other setup arguments ...
      package_dir={'foo.bar.baz.xyz.uvw': 'src'},
      packages=['foo.bar.baz.xyz.uvw.package'],
     )

这里的关键部分是package_dir 说“foo.bar.baz.xyz.uvw 的内容是在src 目录中找到的”,而packages=['foo.bar.baz.xyz.uvw.package'] 告诉它期望找到并安装一个名为@987654330 的包@。

setup.cfg 等效项是:

[options]
package_dir=
    foo.bar.baz.xyz.uvw=src
packages = foo.bar.baz.xyz.uvw.package

【讨论】:

  • 仅供参考,我找不到使用setuptools.find_namespace_packages (或packages=find_namespace: 指令的setup.cfg 方法,使用[option.packages.find] 使用where 键)的便捷方法以避免需要手动列出packages 的内容,所以这确实有点多余(foo.bar.baz.xyz.uvw 必须输入多次)。如果有人知道如何做到这一点,请插话; find_namespace_packages 可以与列表推导一起使用,以编程方式修复前缀,但最好使用现有的 API。
  • 哦,原来如此。这几乎是完美的解决方案,谢谢!
  • 重复不是大问题,因为我还想为所有包创建单个模板。现在似乎有可能(而且非常简单)。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-01-06
  • 1970-01-01
  • 2020-04-14
  • 1970-01-01
  • 2015-07-13
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多