我正在学习官方的Python 打包教程。我使用
conda
环境,但问题对于 venv
虚拟环境应该是相同的。
本教程提供了一个非常简单的示例包,其中包含一个模块且没有依赖项。该模块包含一个函数,该函数仅将传递的数字加一:
def add_one(number):
return number + 1
我创建了一个模仿
add_one
的新模块,只不过它使用 NumPy 将 1 数组添加到传递的数组中:
import numpy as np
def add_ones(array):
return array + np.ones(array.shape)
然后我创建了一个名为
conda
的 packaging
环境并安装了 build
和 twine
。我能够使用两个构建后端(Hatchling 和 Flit)成功打包示例包。我还可以将包上传到 TestPyPI。然后我就能够从 PyPI pip install
得到这个包了。如果我将其安装到缺少 NumPy 的环境中,导入当然会失败,但只要我将其安装到有 NumPy 的环境中,导入就可以并且函数运行成功。
我的问题是这种行为可靠吗?对于这个简单的示例,
build
在缺少包依赖项的环境中工作,例如我的 packaging
环境缺少 NumPy。
因为构建/打包通常不需要运行项目中的任何代码,所以 build 或打包项目的要求通常不需要很多(如果有的话)包的运行时要求。从最基本的意义上来说,“构建”一个包基本上只是压缩源文件。
您的包元数据(例如,如
setup.py
/setup.cfg
/pyproject.toml
或类似声明)应 指定您的运行时要求,例如 numpy
,以便在用户请求时不存在时安装它您要安装的软件包。这样,您的软件包在由像 pip
这样的软件包管理器安装后应该始终处于工作状态。
您的包结构必须包含一个
setup.py
文件,或者最好是一个具有 PEP 517兼容构建后端的
pyproject.toml
文件。在那里,您需要添加一个依赖关系表,将 NumPy 声明为您的项目的依赖项。
这将确保那些从索引接收您构建的包的人也会收到此元数据,从而收到供您的包使用的 NumPy 分发/轮。具体回答你的问题,如果没有明确声明你的项目的依赖项,这种行为目前是不可靠的。
PyPA 的
build
构建前端为您的项目准备源代码分发和轮子(这是可定制的),并且不需要“导入”您的项目本身(除非您有一个更复杂的构建过程,涉及 setuptools
或其他编译步骤)。可以为 Python 项目构建和分发分发格式,而无需包含导入/运行它所需的依赖项。
environment.yml
文件也可能很有意义,并为用户记录如何使用它来创建可重现的 conda
环境的过程。