如何在PyPi中的某个根包下组织我的包?

时间:2014-09-19 13:27:29

标签: python pip distutils

我有几个或多或少独立的包(请参阅下面的apack和bpack)。我想让他们都像这样:

import mycompany.apack.somemodule
import mycompany.bpack.somemodule

由于它们是独立的,因此每个都有单独的setup.py,以便将它们部署到PyPi,从而实现不同的发布周期。

这里有一个问题:是否可以将root包的子包与分离的释放过程(每个子包都有自己的setup.py)?如何实现?

这是我尝试过的,但无法让它发挥作用。 我当前的setup.py看起来像这样:

from distutils.core import setup
setup(
    name='mycompany-apack',
    version='0.1',
    packages=['mycompany.apack'],
    license='GPLv3')

这些setup.py正在dist-packages文件夹中创建以下结构:

mycompany
  apack
    __init__.py
    somemodule.py
  bpack
    __init__.py
    somemodule.py

既然我的mycompany没有__ init __.py(这是我的猜测),我收到了以下错误:

>>> import mycompany.apack.somemodule
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: No module named mycompany.apack.somemodule

1 个答案:

答案 0 :(得分:2)

简短回答

使用pkg_resources.declare_namespace项目中的setuptools

长答案

您可以使用setuptools而不是distutils。它支持依赖关系管理和命名空间,

对于apack,项目结构将如下所示:

/apack/
 |- mycompany/
 |   |- __init__.py (1)
 |   `- apack/
 |       |- __init__.py
 |       `- submodule.py
 `- setup.py

对于apack,您的setup.py将如下所示:

from setuptools import find_packages
from setuptools import setup

setup(
    name='apack',
    version='0.1',
    packages=find_packages())

标记为(1)的__init__.py将如下所示:

import pkg_resources
pkg_resources.declare_namespace(__name__)

bpack看起来非常相似,只有apack替换为bpack

我们假设还有一个cpack,它依赖于apack和bpack。

它看起来很相似,但setup.py看起来像这样:

from setuptools import find_packages
from setuptools import setup

setup(
    name='cpack',
    version='0.1',
    packages=find_packages(),
    install_requires=['apack', 'bpack'])

如果安装了cpack,也会安装apack和bpack。 由于名称空间声明,不会发生冲突

$ virtualenv venv
$ source virtualenv/bin/activate
$ pip install cpack
$ python
>>> from mycompany.apack import submodule
>>> from mycompany.bpack import submodule
>>> from mycompany.cpack import submodule