Pipenv,它的项目简介为 Python Development Workflow for Humans,是 Python 著名的 requests 库做者 kennethreitz 写的一个包管理工具,它能够为咱们的项目自动建立和管理虚拟环境并不是常方便地管理 Python 包,如今它也已是 Python 官方推荐的包管理工具。python
Pipenv 咱们能够简单理解为 pip 和 virtualenv 的集合体,它能够为咱们的项目自动建立和管理一个虚拟环境。virtualenv 在使用时咱们须要手动建立一个虚拟环境而后激活,Pipenv 会自动建立。另外咱们以前可能使用 requirements.txt 文件来标识项目所须要的依赖,可是这样会带来一些问题,若有的 requirements.txt 中只是将库名列出来了,没有严格指定版本号,这样就可能会致使不一样时间安装的库版本是不一样的,如 requirements.txt 文件中对 Django 的依赖只写了一个 django
,可能在 2016 年的时候运行安装会安装 Django 的 1.x 版本,到了 2017 年就会安装 Django 的 2.x 版本,因此可能致使一些麻烦。为了解决这个问题,Pipenv 直接弃用了 requirements.txt,会同时它会使用一个叫作 Pipfile 和 Pipfile.lock 的文件来管理项目所需的依赖包,而再也不是简单地使用 requirements.txt 文件来记录项目所须要的依赖。shell
总的来讲,Pipenv 能够解决以下问题:django
咱们不须要再手动建立虚拟环境,Pipenv 会自动为咱们建立,它会在某个特定的位置建立一个 virtualenv 环境,而后调用pipenv shell
命令切换到虚拟环境。安全
使用 requirements.txt 可能会致使一些问题,因此 Pipenv 使用 Pipfile 和 Pipfile.lock 来替代之,并且 Pipfile 若是不存在的话会自动建立,并且在安装、升级、移除依赖包的时候会自动更新 Pipfile 和 Pipfile.lock 文件。app
普遍使用 Hash 校验,保证安全性。ide
能够更清晰地查看 Python 包及其关系,调用 pipenv graph
便可呈现,结果简单明了。工具
可经过自动加载 .env 读取环境变量,简化开发流程。ui
本文内容基于 Python 3.6 说明,默认的 Python 解释器命令为python3
,包管理工具命令为 pip3
。this
Pipenv 是基于 Python 开发的包,因此能够直接用 pip 来安装,命令以下:url
pip3 install pipenv
另外还有多种安装方式,如 Pipsi、Nix、Homebrew,安装方式能够参考:http://pipenv.readthedocs.io/en/latest/#install-pipenv-today。
首先咱们能够新建一个项目,例如叫作 PipenvTest,而后新建一个 Python 脚本,例如叫 main.py,内容为:
import django
print(django.get_version())
直接用系统的 Python3 运行此脚本:
python3 main.py
结果以下:
1.11
咱们能够看到系统安装的 Django 版本是 1.11。可是咱们想要本项目基于 Django 2.x 开发,固然咱们能够选择将系统的 Django 版本升级,但这样又可能会影响其余的项目的运行,因此这并非一个好的选择。为了避免影响系统环境的 Django 版本,因此咱们能够用 Pipenv 来建立一个虚拟环境。
在该目录下,输入 pipenv
命令便可查看命令的完整用法:
Usage: pipenv [OPTIONS] COMMAND [ARGS]...
Options:
--update Update Pipenv & pip to latest.
--where Output project home information.
--venv Output virtualenv information.
--py Output Python interpreter information.
--envs Output Environment Variable options.
--rm Remove the virtualenv.
--bare Minimal output.
--completion Output completion (to be eval'd).
--man Display manpage.
--three / --two Use Python 3/2 when creating virtualenv.
--python TEXT Specify which version of Python virtualenv should use.
--site-packages Enable site-packages for the virtualenv.
--jumbotron An easter egg, effectively.
--version Show the version and exit.
-h, --help Show this message and exit.
Usage Examples:
Create a new project using Python 3.6, specifically:
$ pipenv --python 3.6
Install all dependencies for a project (including dev):
$ pipenv install --dev
Create a lockfile containing pre-releases:
$ pipenv lock --pre
Show a graph of your installed dependencies:
$ pipenv graph
Check your installed dependencies for security vulnerabilities:
$ pipenv check
Install a local setup.py into your virtual environment/Pipfile:
$ pipenv install -e .
Commands:
check Checks for security vulnerabilities and against PEP 508 markers
provided in Pipfile.
graph Displays currently–installed dependency graph information.
install Installs provided packages and adds them to Pipfile, or (if none
is given), installs all packages.
lock Generates Pipfile.lock.
open View a given module in your editor.
run Spawns a command installed into the virtualenv.
shell Spawns a shell within the virtualenv.
uninstall Un-installs a provided package and removes it from Pipfile.
update Uninstalls all packages, and re-installs package(s) in [packages]
to latest compatible versions.
接下来咱们首先验证一下当前的项目是没有建立虚拟环境的,调用以下命令:
pipenv --venv
结果以下:
No virtualenv has been created for this project yet!
这说明当前的项目还没有建立虚拟环境,接下来咱们利用 Pipenv 来建立一个虚拟环境:
pipenv --three
或
pipenv --python 3.6
均可以建立一个 Python3 的虚拟环境,--three
表明建立一个 Python3 版本的虚拟环境,--python
则能够指定特定的 Python 版本,固然 --two
则建立一个 Python2 版本的虚拟环境,但前提你的系统必须装有该版本的 Python 才能够。
执行完毕以后,样例输出以下:
Warning: the environment variable LANG is not set!
We recommend setting this in ~/.profile (or equivalent) for proper expected behavior.
Creating a virtualenv for this project…
Using /usr/local/bin/python3 to create virtualenv…
⠋Running virtualenv with interpreter /usr/local/bin/python3
Using base prefix '/usr/local/Cellar/python3/3.6.1/Frameworks/Python.framework/Versions/3.6'
New python executable in /Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/python3.6
Also creating executable in /Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/python
Installing setuptools, pip, wheel...done.
Virtualenv location: /Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E
这里显示 Pipenv 利用 /usr/local/bin/python3
做为 virtualenv 的解释器,而后在/Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin
目录下建立了一个新的 Python3 解释器,同时还建立了两个可执行文件别名 python3.6
和 python
,另外咱们还能够发现目录下多了一个 Pipfile 文件,这时虚拟环境就建立完成了。
咱们切换到 PipenvTest-VSTVh89E/bin
目录查看一下文件结构:
能够看到这里面包含了pip
、pip3
、pip3.6
、python
、python3
、python3.6
等可执行文件,实际上目录结构和使用 virtualenv 时是彻底同样的,只不过文件夹的位置不一样而已。
接下来咱们能够切换到该虚拟环境下执行命令,执行以下命令便可:
pipenv shell
执行完毕以后样例输出以下:
Spawning environment shell (/bin/zsh). Use 'exit' to leave.
source /Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/activate
CQC-MAC% source /Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/activate
(PipenvTest-VSTVh89E) CQC-MAC%
实际上这也和 virtualenv 激活的流程同样,也是调用了相似 source venv/bin/activate
方法将这个路径加到全局环境变量最前面,这样就会优先调用该路径下的 python
、python3
、python3.6
可执行文件了。
这时候咱们会发现命令行的样子就变了,前面多了一个 (PipenvTest-VSTVh89E) 的标识,表明当前咱们已经切换到了虚拟环境下。
这时咱们用 which 或 where 命令查看一下 Python 可执行文件的路径,命令以下:
(PipenvTest-VSTVh89E) CQC-MAC% which python3
/Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/python3
(PipenvTest-VSTVh89E) CQC-MAC% which python3.6
/Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/python3.6
(PipenvTest-VSTVh89E) CQC-MAC% which python
/Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/python
能够发现当前的 Python 可执行路径都被切换到了 PipenvTest-VSTVh89E/bin
目录下,调用的是虚拟环境中的 Python 解释器,这时咱们从新执行刚才的脚本,命令以下:
(PipenvTest-VSTVh89E) CQC-MAC% python3 main.py
这时咱们能够发现报了以下错误:
Traceback (most recent call last):
File "main.py", line 1, in <module>
import django
ModuleNotFoundError: No module named 'django'
这实际上是由于新的虚拟环境没有安装任何的 Python 第三方包,实际上若是直接使用 virtualenv 时也是这样的结果。这是由于新的虚拟环境是一个全新的 Python 环境,它默认只包含了 Python 内置的包以及 pip、wheel、setuptools 包,其余的第三方包都没有安装。
这时咱们可使用 Pipenv 来安装 django 包,命令以下:
pipenv install django
运行后输出结果以下:
Installing django…
Collecting django
Downloading Django-2.0.2-py3-none-any.whl (7.1MB)
Collecting pytz (from django)
Downloading pytz-2018.3-py2.py3-none-any.whl (509kB)
Installing collected packages: pytz, django
Successfully installed django-2.0.2 pytz-2018.3
Adding django to Pipfile's [packages]…
Locking [dev-packages] dependencies…
Locking [packages] dependencies…
Updated Pipfile.lock (e101fb)!
若是有这样的输出结果就表明成功安装了 Django,能够看到此时安装的 Django 版本为 2.0,表明咱们的虚拟环境成功安装了 Django 2.0 版本。
同时咱们还注意到它输出了一句话叫作 Updated Pipfile.lock
,这时咱们能够发现项目路径下又生成了一个 Pipfile.lock 文件,内容以下:
{
"_meta": {
"hash": {
"sha256": "7b9623243d9c22b1f333ee710aff70d0cbcdf1dd7e0aac69230dc76855d27270"
},
"host-environment-markers": {
"implementation_name": "cpython",
"implementation_version": "3.6.1",
"os_name": "posix",
"platform_machine": "x86_64",
"platform_python_implementation": "CPython",
"platform_release": "17.4.0",
"platform_system": "Darwin",
"platform_version": "Darwin Kernel Version 17.4.0: Sun Dec 17 09:19:54 PST 2017; root:xnu-4570.41.2~1/RELEASE_X86_64",
"python_full_version": "3.6.1",
"python_version": "3.6",
"sys_platform": "darwin"
},
"pipfile-spec": 6,
"requires": {},
"sources": [
{
"name": "pypi",
"url": "https://pypi.python.org/simple",
"verify_ssl": true
}
]
},
"default": {
"django": {
"hashes": [
"sha256:af18618ce3291be5092893d8522fe3919661bf3a1fb60e3858ae74865a4f07c2",
"sha256:9614851d4a7ff8cbd32b73c6076441f377c45a5bbff7e771798fb02c43c31f47"
],
"version": "==2.0.2"
},
"pytz": {
"hashes": [
"sha256:ed6509d9af298b7995d69a440e2822288f2eca1681b8cce37673dbb10091e5fe",
"sha256:f93ddcdd6342f94cea379c73cddb5724e0d6d0a1c91c9bdef364dc0368ba4fda",
"sha256:61242a9abc626379574a166dc0e96a66cd7c3b27fc10868003fa210be4bff1c9",
"sha256:ba18e6a243b3625513d85239b3e49055a2f0318466e0b8a92b8fb8ca7ccdf55f",
"sha256:07edfc3d4d2705a20a6e99d97f0c4b61c800b8232dc1c04d87e8554f130148dd",
"sha256:3a47ff71597f821cd84a162e71593004286e5be07a340fd462f0d33a760782b5",
"sha256:5bd55c744e6feaa4d599a6cbd8228b4f8f9ba96de2c38d56f08e534b3c9edf0d",
"sha256:887ab5e5b32e4d0c86efddd3d055c1f363cbaa583beb8da5e22d2fa2f64d51ef",
"sha256:410bcd1d6409026fbaa65d9ed33bf6dd8b1e94a499e32168acfc7b332e4095c0"
],
"version": "==2018.3"
}
},
"develop": {}
}
能够看到里面标识了 Python 环境基本信息,以及依赖包的版本及 hashes 值。
另外咱们还能够注意到 Pipfile 文件内容也有更新,[packages]
部分多了一句 django = "*"
,标识了本项目依赖于 Django,这个其实相似于 requirements.txt 文件。
那么到这里有小伙伴可能就会问了, Pipfile 和 Pipfile.lock 有什么用呢?
Pipfile 其实一个 TOML 格式的文件,标识了该项目依赖包的基本信息,还区分了生产环境和开发环境的包标识,做用上相似 requirements.txt 文件,可是功能更为强大。Pipfile.lock 详细标识了该项目的安装的包的精确版本信息、最新可用版本信息和当前库文件的 hash 值,顾明思义,它起了版本锁的做用,能够注意到当前 Pipfile.lock 文件中的 Django 版本标识为 ==2.0.2
,意思是当前咱们开发时使用的就是 2.0.2 版本,它能够起到版本锁定的功能。
举个例子,刚才咱们安装了 Django 2.0.2 的版本,即目前(2018.2.27)的最新版本。但可能 Django 之后还会有更新,好比某一天 Django 更新到了 2.1 版本,这时若是咱们想要从新部署本项目到另外一台机器上,假如此时不存在 Pipfile.lock 文件,只存在 Pipfile文件,因为 Pipfile 文件中标识的 Django 依赖为 django = "*"
,即没有版本限制,它会默认安装最新版本的 Django,即 2.1,但因为 Pipfile.lock 文件的存在,它会根据 Pipfile.lock 来安装,仍是会安装 Django 2.0.2,这样就会避免一些库版本更新致使不兼容的问题。
请记住:任何状况下都不要手动修改 Pipfile.lock 文件!
好,接下来咱们再回归正题,如今已经安装好了 Django 了,那么咱们从新运行此脚本即可以成功输出 Django 版本信息了:
(PipenvTest-VSTVh89E) CQC-MAC% python3 main.py
结果以下:
2.0.2
这样咱们就成功安装了 Django 2.x 了,和系统的 Django 1.11 没有任何冲突。
在此模式的命令行下,咱们就可使用虚拟环境下的 Python 解释器,并且所安装的依赖包对外部系统没有任何影响,并且使用 Pipfile 和 Pipfile.lock 来管理项目的依赖更加方便和健壮。
若是想要退出虚拟环境,只须要输入 exit
命令便可:
(PipenvTest-VSTVh89E) CQC-MAC% exit
➜ PipenvTest python3 main.py
1.11
输入退出命令以后,咱们从新再运行此脚本,就会从新使用系统的 Python 解释器,Django 版本又从新回到了 1.11。
由此能够看来,有了 Pipenv,咱们可使用 Pipfile 和 Pipfile.lock 来方便地管理和维护项目的依赖包,并且能够实现虚拟环境运行,避免了包冲突问题,可谓一箭双雕。
上文咱们介绍了 Pipenv 的基本操做,下面咱们再介绍一下它的一些经常使用命令。
咱们可使用 --venv
参数来得到虚拟环境路径:
pipenv --venv
样例输出以下:
/Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E
可见这个路径是一个标准的路径,Pipenv 会把虚拟环境统一放到 virtualenvs 文件夹下,而不是本项目路径下。
要获取虚拟环境 Python 解释器路径,可使用 --py
参数:
pipenv --py
样例输出以下:
/Users/CQC/.local/share/virtualenvs/PipenvTest-VSTVh89E/bin/python
默认状况下,新建立的虚拟环境是不包含任何第三方包的,但咱们也能够开启加载系统 Python 包功能,使用 --site-packages
便可:
pipenv --site-packages
这样建立的虚拟环境即可以使用系统已安装的 Python 包了。
要开启虚拟环境只须要执行以下命令:
pipenv shell
这样就能够进入虚拟环境,此时运行的 python
、python3
命令都是虚拟环境下的。
安装 Python 包咱们再也不须要 pip 来安装,直接使用 Pipenv 也可安装,如安装 requests,命令以下:
pipenv install requests
安装完成以后会同时更新项目目录下的 Pipfile 和 Pipfile.lock 文件。
有时候一些 Python 包是仅仅开发环境须要的,如 pytest,这时候咱们经过添加 --dev
参数便可,命令以下:
pipenv install pytest --dev
这时候,pytest 的依赖便会记录在 Pipfile 的 [dev-packages]
区域:
[dev-packages]
pytest = "*"
咱们可使用命令来清晰地呈现出当前安装的 Python 包版本及之间的依赖关系,命令以下:
pipenv graph
样例结果以下:
Django==2.0.2
- pytz [required: Any, installed: 2018.3]
pytest==3.4.1
- attrs [required: >=17.2.0, installed: 17.4.0]
- pluggy [required: <0.7,>=0.5, installed: 0.6.0]
- py [required: >=1.5.0, installed: 1.5.2]
- setuptools [required: Any, installed: 38.5.1]
- six [required: >=1.10.0, installed: 1.11.0]
requests==2.18.4
- certifi [required: >=2017.4.17, installed: 2018.1.18]
- chardet [required: >=3.0.2,<3.1.0, installed: 3.0.4]
- idna [required: <2.7,>=2.5, installed: 2.6]
- urllib3 [required: <1.23,>=1.21.1, installed: 1.22]
能够看到结果很是清晰,Django 当前安装了 2.0.2版本,依赖于 pytz 任何版本,已经安装了 2018.3 版本;pytest 已经安装了 3.4.1 版本,依赖 attrs>=17.2.0 版本,已经安装了 17.4.0 版本,另外还依赖 pluggy、py、setuptools、six 这些库。总之包的依赖关系一目了然。
卸载 Python 包也很是简单,如卸载 requests 包,命令以下:
pipenv uninstall requests
卸载完成以后,Pipfile 和 Pipfile.lock 文件一样会更新。
若是要卸载所有 Python 包,能够添加 --all
参数:
pipenv uninstall --all
有时候可能 Pipfile.lock 文件不存在或被删除了,这时候咱们可使用以下命令生成:
pipenv lock
以上即是一些经常使用的 Pipenv 命令,若是要查看更多用法能够参考其官方文档:https://docs.pipenv.org/#pipenv-usage。
本文介绍了 Pipenv 的基本用法,做为 pip 和 virtualenv 的结合体,咱们能够利用它更方便地建立和管理 Python 虚拟环境,还能够用更加科学的方式管理 Python 包,一箭双雕。
嗯,是时候抛弃 virtualenv 和 pip 了!