在 Python 的项目中,如何管理所用的所有依赖库呢?最主流的作法是维护一份“requirements.txt”,记录下依赖库的名字及其版本号。python
那么,如何来生成这份文件呢?在上篇文章《由浅入深:Python 中如何实现自动导入缺失的库?》中,我提到了一种常规的方法:git
pip freeze > requirements.txt
复制代码
这种方法用起来方便,但有几点不足:github
可用于项目依赖管理的工具备不少,本文主要围绕与 requirements.txt 文件相关的、比较类似却又各具特点的 4 个三方库,简要介绍它们的使用方法,罗列一些显著的功能点。至于哪一个是最好的管理方案呢?卖个关子,请往下看……正则表达式
这是个很受欢迎的用于管理项目中依赖库的工具,能够用“pip install pipreqs”命令来安装。它的主要特色有:json
基本的命令选项以下:flask
Usage:
pipreqs [options] <path>
Options:
--use-local Use ONLY local package info instead of querying PyPI
--pypi-server <url> Use custom PyPi server
--proxy <url> Use Proxy, parameter will be passed to requests library. You can also just set the
environments parameter in your terminal:
$ export HTTP_PROXY="http://10.10.1.10:3128"
$ export HTTPS_PROXY="https://10.10.1.10:1080"
--debug Print debug information
--ignore <dirs>... Ignore extra directories
--encoding <charset> Use encoding parameter for file open
--savepath <file> Save the list of requirements in the given file
--print Output the list of requirements in the standard output
--force Overwrite existing requirements.txt
--diff <file> Compare modules in requirements.txt to project imports.
--clean <file> Clean up requirements.txt by removing modules that are not imported in project.
复制代码
其中需注意,极可能遇到编码错误:UnicodeDecodeError: 'gbk' codec can't decode byte 0xae in
。须要指定编码格式“--encoding=utf8”。工具
在已生成依赖文件“requirements.txt”的状况下,它能够强行覆盖、比对差别以及清除再也不使用的依赖项。测试
pigar 一样能够根据项目路径来生成依赖文件,并且会列出依赖库在文件中哪些位置使用到了。这个功能充分利用了 requirements.txt 文件中的注释,能够提供很丰富的信息。ui
pigar 对于查询真实的导入源颇有帮助,例如bs4
模块来自beautifulsoup4
库,MySQLdb
则来自于MySQL_Python
库。能够经过“-s”参数,查找真实的依赖库。编码
$ pigar -s bs4 MySQLdb
复制代码
它使用解析 AST 的方式,而非正则表达式的方式,能够很方便地从 exec/eval 的参数、文档字符串的文档测试中提取出依赖库。
另外,它对于不一样 Python 版本的差别能够很好地支持。例如,concurrent.futures
是 Python 3.2+ 的标准库,而在以前早期版本中,须要安装三方库futures
,才能使用它。pigar 作到了有效地识别区分。(PS:pipreqs 也支持这个识别,详见这个合入:github.com/bndr/pipreq…)
pip-tools 包含一组管理项目依赖的工具:pip-compile 与 pip-sync,可使用命令“pip install pip-tools”统一安装。它最大的优点是能够精准地控制项目的依赖库。
两个工具的用途及关系图以下:
pip-compile 命令主要用于生成依赖文件和升级依赖库,另外它能够支持 pip 的“Hash-Checking Mode ”,并支持在一个依赖文件中嵌套其它的依赖文件(例如,在 requirements.in 文件内,能够用“-c requirements.txt”方式,引入一个依赖文件)。
它能够根据 setup.py 文件来生成 requirements.txt,假如一个 Flask 项目的 setup.py 文件中写了“install_requires=['Flask']”,那么能够用命令来生成它的全部依赖:
$ pip-compile
#
# This file is autogenerated by pip-compile
# To update, run:
#
# pip-compile --output-file requirements.txt setup.py
#
click==6.7 # via flask
flask==0.12.2
itsdangerous==0.24 # via flask
jinja2==2.9.6 # via flask
markupsafe==1.0 # via jinja2
werkzeug==0.12.2 # via flask
复制代码
在不使用 setup.py 文件的状况下,能够建立“requirements.in”,在里面写入“Flask”,再执行“pip-compile requirements.in”,能够达到跟前面同样的效果。
pip-sync 命令能够根据 requirements.txt 文件,来对虚拟环境中进行安装、升级或卸载依赖库(注意:除了 setuptools、pip 和 pip-tools 以外)。这样能够有针对性且按需精简地管理虚拟环境中的依赖库。
另外,该命令能够将多个“*.txt”依赖文件归并成一个:
$ pip-sync dev-requirements.txt requirements.txt
复制代码
它的主要用途是展现 Python 项目的依赖树,经过有层次的缩进格式,显示它们的依赖关系,不像前面那些工具只会生成扁平的并列关系。
除此以外,它还能够:
它也有缺点,好比没法穿透虚拟环境。若是要在虚拟环境中工做,必须在该虚拟环境中安装 pipdeptree。由于跨虚拟环境会出现重复或冲突等状况,所以须要限定虚拟环境。可是每一个虚拟环境都安装一个 pipdeptree,仍是挺让人难受的。
好啦,4 种库介绍完毕,它们的核心功能都是分析依赖库,生成 requirements.txt 文件,同时,它们又具备一些差别,补齐了传统的 pip 的某些不足。
本文不对它们做全面的测评,只是选取了一些主要特性进行介绍,好在它们安装方便(pip install xxx),使用也简单,感兴趣的同窗不妨一试。
更多丰富的细节,请查阅官方文档:
公众号【Python猫】, 本号连载优质的系列文章,有喵星哲学猫系列、Python进阶系列、好书推荐系列、技术写做、优质英文推荐与翻译等等,欢迎关注哦。