pip install
命令用于安装包,在 Python Pip 参考手册 - pip install 命令 ( 一 ) 章节中我们介绍了 pip install
命令的基本用法,可用命令行参数和一些使用范例,但我们没有对 pip install
命令做一些深入的了解
本章节,我们就来深入了解 pip install
命令
pip install 简介
pip install
安装一个包时要经过几个阶段
- 确定基本的需求 ( requirements ),用户传递的参数会在这个阶段处理
- 解决依赖关系,要安装的内容会在这个阶段确定
- 构建 wheels,所有的依赖项目都会在此阶段编译成 wheel
- 安装所有的包,并卸载任何刚刚升级或替换的内容
参数处理
pip install
命令的第一阶段,在查看要安装的项目时,pip 会按照以下的顺序检查每个项目的类型
- 项目或归档 URL
- 本地项目 ( 必须包含
setup.py
,否则pip
会报错 ) - 本地文件 ( 一个 sdist 或 wheel 格式归档,名字则会采用这些格式的约定 )
- PEP440 指定的需求文件 ( requirements )
每个确定的项目都会添加到安装要满足的 requirements 集合中
确定名称和版本
pip install
命令的第二个阶段,会确定依赖关系,主要就是确定每个依赖的名称和版本
对于每个候选项,pip
需要知道项目名称和版本。
对于 wheel ( 由 .whl
文件扩展名标识 ),可以根据 Wheel
规范从文件名中获取。
对于本地目录或显式指定的 sdist
文件,可以使用 setup.py egg_info
命令获取项目的元数据。
对于通过索引定位的 sdists
,可以从文件名中解析出名称和项目版本 ( 虽然理论上说,这比使用 egg_info
命令稍差,但可以避免下载和处理不必要的文件数 )
而对于任意的 URL ,则可以通过 egg=name
参数 ( 请参阅 VCS 支持 ) 获取声明的项目名称
满足要求
一旦 pip
拥有了能够满足要求的集合,它就会使用 选择满足给定约束条件的最新版本 这种简单来安装每个需求的版本( 想要了解有关预发布版本的例外情况,可以参阅 此处)
所选版本的如果有多个来源可用,则会假定任何一个来源都是可可接受的,否则版本会有所不同
控制 setup_requires
Setuptools
为 setup_requires
提供了 setup()
关键字,用于在运行 setup.py
脚本之前设置需要预先安装的依赖项,而内部实现中,Setuptools 使用 easy_install
来安装这些依赖关系
pip 无法控制这些依赖项的位置,即使添加了包索引选项都不会有任何效果
如果需要实现定制,解决方案是配置 「 系统 」 或 「 个人 」 的 Distutils
配置文件 来管理履行
例如,要使依赖项位于备用索引处,请添加以下内容
[easy_install] index_url = https://my.index-mirror.com
要使依赖项位于本地目录而不是 PyPI
,请添加以下内容
[easy_install] allow_hosts = '' find_links = file:///path/to/local/archives/
构建系统接口
为了使 pip install
命令能够从源代码安装包,包的 setup.py
文件必须实现以下命令
setup.py egg_info [--egg-base XXX]
和
setup.py install --record XXX [--single-version-externally-managed] [--root XXX] [--compile|--no-compile] [--install-headers XXX]
egg_info
命令用于为包创建 egg
元数据,详细资料可以查看 setuptools
文档 https://setuptools.readthedocs.io/en/latest/setuptools.html#egg-info-create-egg-metadata-and-set-build-tags
install
应该实现将软件包安装到目标目录 XXX
的完整过程
为了可以用 「 可编辑 」模式 ( pip install -e
) 安装软件包,setup.py
必须实现以下命令
setup.py develop --no-deps
所以应该实现以 「 可编辑 」 模式安装包的完整过程
所有的包都会尝试安装到 wheels
中
setup.py bdist_wheel -d XXX
未来,pip install
可能还会调用 setup.py
中的另一个命令
setup.py clean
调用此命令以从构建中清除临时命令 ( TODO : 此命令需要更详细地调查 )
除了以上列出的这些,pip install
命令不会调用调用构建系统的其它命令
从 wheel
中安装包根本就不会调用构建系统