pip不能安装我的软件包依赖

10

我在Github上开发了一个Python包,并发布到了PyPi。可以通过pip install PACKAGENAME进行安装,但是它不会处理setup.py文件中"install_requires"指定的依赖关系。

奇怪的是,关联的发布zip文件确实安装了所有依赖项。我尝试了不同的虚拟环境和不同的计算机,但它从未安装过依赖关系。感谢任何帮助。


1
请展示您的实际 setup.py - tripleee
2个回答

11

pip install pythutils会下载一个wheel包,如果有的话——而你的包是有的

在生成一个wheel包时,setuptools本地运行python setup.py,但不会将setup.py包含在wheel包中。下载你的wheel文件并解压缩它(它只是一个zip归档)——这里有你的主包目录pythutils和一个带有元数据的目录pythutils-1.1.1.dist-info。在元数据目录中有一个文件METADATA,通常列出了一些静态依赖项,但你的文件没有列出任何依赖项。因为在生成wheel包时,所有依赖项都已经被安装,所以所有动态代码路径都被跳过了。

你从Github release下载的归档文件需要安装依赖项,因为它不是一个wheel,所以pip会运行python setup.py install来使动态依赖项生效。
你可以怎么做?我的建议是避免使用动态依赖项。声明静态依赖项并允许pip决定要安装哪个版本:
install_requires=[
    'numpy==1.16.5; python_version>="2" and python_version<"3"',
    'numpy; python_version>="3"',
],

另一种方法是创建特定版本的wheel文件——一个用于Python 2,另一个用于Python 3,并具有固定的依赖项。
还有一种方法是根本不发布wheels,只发布sdist(源分发)。然后,pip被迫在目标机器上运行python setup.py install。这不是最好的方法,对于具有C扩展的包来说肯定会存在问题(用户必须拥有编译器和开发工具才能从源代码安装)。

1
太好了,非常有帮助。我按照你的建议直接将install_requires设置到安装文件中并运行了上传下一个版本到pypi的步骤,现在可以在python2.7和python3上正确安装所有依赖项。谢谢! - crazjo

2

您的setup.py会进行一系列检查,例如:

try:
    import numpy
except ImportError:
    if sys.version_info[0] == 2:
        install_requires.append('numpy==1.16.5')
    if sys.version_info[0] == 3:
        install_requires.append("numpy")

假定你运行它的系统已经安装了所有必需的模块,因此在 install_requires 中得到了一个空列表。但是这种做法是错误的;你应该简单地制作一个静态列表(或者两个静态列表,如果你真的想在同一个包中支持 Python 2 和 Python 3)。

很奇怪,我尝试在一个全新的虚拟环境中运行它(其中pip freeze没有返回任何内容),但仍然没有返回任何依赖项。不过,我现在已经按照@phd下面的答案步骤进行了操作,这样就可以了。谢谢。 - crazjo
感谢您的跟进。不过这里没有所谓的“上面”或“下面”,事实上,我现在看到phd的回复就在我的上方。 - tripleee

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接