Mac下python多版本
- 需要安装pyenv以支持多pytohn版本环境
- 需要安装virtualenv以支持python包环境隔离
- 但pyenv提供了virtualenv的插件,所以我们直接安装插件即可
- 一般安装了virtualenv后会安装virtualenvwrapper简化virtualenv的操作,但是pyenv的virtualenv的插件已经做了这个工作,不再建议安装pyenv-virtualenvwrapper(具体见这里)
- 所以我们安装pyenv以及virtualenv的插件即可
安装步骤:
以下安装采用brew
1. 查找是否有pyenv包
# Teron @ TeronsMac in ~ [22:26:16]
$ brew search pyenv
==> Searching local taps...
pyenv pyenv-pip-migrate pyenv-virtualenvwrapper
pyenv-ccache pyenv-virtualenv pyenv-which-ext
==> Searching taps on GitHub...
==> Searching blacklisted, migrated and deleted formulae...
2. 安装pyenv
# Teron @ TeronsMac in ~ [22:26:36]
$ brew install pyenv
Updating Homebrew...
==> Auto-updated Homebrew!
Updated 1 tap (homebrew/core).
==> Updated Formulae
angular-cli mongoose shairport-sync
convox paket vim
docker-machine-parallels povray xorriso
mongo-c-driver pygobject3 xtensor
==> Downloading https://homebrew.bintray.com/bottles/pyenv-1.1.3.sierra.bottle.t
Already downloaded: /Users/Teron/Library/Caches/Homebrew/pyenv-1.1.3.sierra.bottle.tar.gz
==> Pouring pyenv-1.1.3.sierra.bottle.tar.gz
? /usr/local/Cellar/pyenv/1.1.3: 581 files, 2.2MB
3. brew list查看pyenv是否安装
# Teron @ TeronsMac in ~ [22:29:43]
$ brew list
autoconf openssl readline
brew-cask-completion pkg-config sqlite
gdbm pyenv xz
makedepend python3
4. pyenv -v 查看已安装
# Teron @ TeronsMac in ~ [22:32:00]
$ pyenv -v
pyenv 1.1.3
# Teron @ TeronsMac in ~ [22:32:08]
$ pyenv versions
* system (set by /Users/Teron/.python-version)
5. pyenv基本命令
$ pyenv version # 查看当前系统使用的python版本
$ pyenv versions # 查看当前系统拥有的python版本
$ pyenv install --list: # 列出所有可以下载的python版本.
$ pyenv install 3.4.1 # 安装3.4.1,可使用-v参数查看详细输出
$ pyenv uninstall 3.4.1 # 卸载
$ pyenv local 3.4.1 # local仅对当前目录及子目录生效,告诉当前目录使用版本2.7.5,
$ pyenv global # 告诉全局环境使用某个版本,为了不破坏系统环境,不建议使用global设置全局版本
$ pyenv rehash # 重建环境变量,每当你增删 Python 版本或带有可执行文件的包(如 pip)以后,都应该执行一次本命令
6. 安装python2.7.13,3.6.2版本
# Teron @ TeronsMac in ~ [22:36:26] C:2
$ pyenv install 2.7.13
Downloading Python-2.7.13.tar.xz...
-> https://www.python.org/ftp/python/2.7.13/Python-2.7.13.tar.xz
Installing Python-2.7.13...
Installed Python-2.7.13 to /Users/Teron/.pyenv/versions/2.7.13
# Teron @ TeronsMac in ~ [22:38:33]
$ pyenv install 3.6.2
Installing Python-3.6.2...
Installed Python-3.6.2 to /Users/Teron/.pyenv/versions/3.6.2
# Teron @ TeronsMac in ~ [22:42:55]
$ pyenv versions
* system (set by /Users/Teron/.python-version)
2.7.13
3.6.2
# Teron @ TeronsMac in ~ [22:43:55]
$ pyenv rehash //Run this command after you install a new version of Python, or install a package that provides binaries.
7. 切换版本,发现没切过去,需要执行if which pyenv > /dev/null; then eval "$(pyenv init -)"; fi
# Teron @ TeronsMac in ~ [22:43:32]
$ pyenv local 2.7.13
# Teron @ TeronsMac in ~ [23:17:58]
$ python -V
Python 2.7.10
# Teron @ TeronsMac in ~ [23:20:15]
$ if which pyenv > /dev/null; then eval "$(pyenv init -)"; fi
# Teron @ TeronsMac in ~ [23:20:29]
$ python -V
Python 2.7.13
8. 需要往当前用户shell配置文件中写入以上配置,我的是zsh环境,则在.zshrc文件最后写入
if which pyenv > /dev/null; then eval "$(pyenv init -)"; fi
pyenv的魔法能够实现是因为它实际上重定义了你的Python命令:
$ which python
/Users/Teron/.pyenv/shims/python
当你尝试运行Python的时候,它首先查看当前目录下的.python-version目录来决定到底哪个版本的Python该运行。如果它没有发现这个文件,那么它之后回继续查找用户级别的文件~/.pyenv/version。
9. 安装pyenv-virtualenv
# Teron @ TeronsMac in ~ [23:23:49]
$ brew install pyenv-virtualenv
Updating Homebrew...
==> Auto-updated Homebrew!
Updated 1 tap (homebrew/core).
==> Updated Formulae
ruby-build streamlink
==> Downloading https://github.com/yyuu/pyenv-virtualenv/archive/v1.1.0.tar.gz
Already downloaded: /Users/Teron/Library/Caches/Homebrew/pyenv-virtualenv-1.1.0.tar.gz
==> ./install.sh
==> Caveats
To enable auto-activation add to your profile:
if which pyenv-virtualenv-init > /dev/null; then eval "$(pyenv virtualenv-init -)"; fi
==> Summary
? /usr/local/Cellar/pyenv-virtualenv/1.1.0: 20 files, 60.2KB, built in 1 second
# Teron @ TeronsMac in ~ [23:24:31]
$ brew list
autoconf openssl python3
brew-cask-completion pkg-config readline
gdbm pyenv sqlite
makedepend pyenv-virtualenv xz
10. 安装完同时也要在.zshrc中加入如下内容
if which pyenv-virtualenv-init > /dev/null; then eval "$(pyenv virtualenv-init -)"; fi
11. pyenv-virtualenv usage
pyenv virtualenv 2.7.13 env-test:创建名为env-test的虚拟环境,对应的版本为2.7.13
pyenv activate env-test:切换到env-test虚拟环境
pyenv deactivate:退回系统环境
# Teron @ TeronsMac in ~ [23:28:10]
$ pyenv virtualenv 2.7.13 env-test
Collecting virtualenv
Using cached virtualenv-15.1.0-py2.py3-none-any.whl
Installing collected packages: virtualenv
Successfully installed virtualenv-15.1.0
New python executable in /Users/Teron/.pyenv/versions/2.7.13/envs/env-test/bin/python2.7
Also creating executable in /Users/Teron/.pyenv/versions/2.7.13/envs/env-test/bin/python
Installing setuptools, pip, wheel...done.
Requirement already satisfied: setuptools in /Users/Teron/.pyenv/versions/2.7.13/envs/env-test/lib/python2.7/site-packages
Requirement already satisfied: pip in /Users/Teron/.pyenv/versions/2.7.13/envs/env-test/lib/python2.7/site-packages
# Teron @ TeronsMac in ~ [23:31:23]
$ pyenv versions
system
2.7.13
2.7.13/envs/env-test
* 3.6.2 (set by /Users/Teron/.python-version)
env-test
#### 后面的 set by /Users/Teron/.python-version意思指:
#### 我当前目录是/Users/Teron/,pyenv设置版本时,实际上是在当前目录创建.python-version文件记录版本;
$ cat .python-version
3.6.2
# Teron @ TeronsMac in ~ [23:31:34]
$ pyenv activate env-test
Failed to activate virtualenv.
Perhaps pyenv-virtualenv has not been loaded into your shell properly.
Please restart current shell and try again.
# 按要求重启终端窗口ok了
# Teron @ TeronsMac in ~ [23:32:47]
$ pyenv activate env-test
pyenv-virtualenv: prompt changing will be removed from future release. configure `export PYENV_VIRTUALENV_DISABLE_PROMPT=1' to simulate the behavior.
(env-test)
# Teron @ TeronsMac in ~ [23:32:50]
$ pip list
DEPRECATION: The default format will switch to columns in the future. You can use --format=(legacy|columns) (or define a format=(legacy|columns) in your pip.conf under the [list] section) to disable this warning.
pip (9.0.1)
setuptools (36.4.0)
wheel (0.30.0)
(env-test)
# Teron @ TeronsMac in ~ [23:33:53]
$ pip install requests
Collecting requests
Retrying (Retry(total=4, connect=None, read=None, redirect=None)) after connection broken by 'NewConnectionError('<pip._vendor.requests.packages.urllib3.connection.VerifiedHTTPSConnection object at 0x10bffbb90>: Failed to establish a new connection: [Errno 65] No route to host',)': /simple/requests/
Downloading requests-2.18.4-py2.py3-none-any.whl (88kB)
100% |████████████████████████████████| 92kB 104kB/s
Collecting certifi>=2017.4.17 (from requests)
Downloading certifi-2017.7.27.1-py2.py3-none-any.whl (349kB)
100% |████████████████████████████████| 358kB 54kB/s
Collecting chardet<3.1.0,>=3.0.2 (from requests)
Downloading chardet-3.0.4-py2.py3-none-any.whl (133kB)
100% |████████████████████████████████| 143kB 48kB/s
Collecting idna<2.7,>=2.5 (from requests)
Downloading idna-2.6-py2.py3-none-any.whl (56kB)
100% |████████████████████████████████| 61kB 30kB/s
Collecting urllib3<1.23,>=1.21.1 (from requests)
Downloading urllib3-1.22-py2.py3-none-any.whl (132kB)
100% |████████████████████████████████| 133kB 18kB/s
Installing collected packages: certifi, chardet, idna, urllib3, requests
Successfully installed certifi-2017.7.27.1 chardet-3.0.4 idna-2.6 requests-2.18.4 urllib3-1.22
(env-test)
# Teron @ TeronsMac in ~ [23:34:44]
$ pip list
DEPRECATION: The default format will switch to columns in the future. You can use --format=(legacy|columns) (or define a format=(legacy|columns) in your pip.conf under the [list] section) to disable this warning.
certifi (2017.7.27.1)
chardet (3.0.4)
idna (2.6)
pip (9.0.1)
requests (2.18.4)
setuptools (36.4.0)
urllib3 (1.22)
wheel (0.30.0)
(env-test)
# Teron @ TeronsMac in ~ [23:35:04]
$ pyenv deactivate
# Teron @ TeronsMac in ~ [23:35:35]
$ pip list
DEPRECATION: The default format will switch to columns in the future. You can use --format=(legacy|columns) (or define a format=(legacy|columns) in your pip.conf under the [list] section) to disable this warning.
pip (9.0.1)
setuptools (28.8.0)
# deactivate 后,pip list看不到env-test里安装的requests,环境隔离了
12. 列出所有的virtual环境,以及删除某个环境
# Teron @ TeronsMac in ~ [23:35:39]
$ pyenv virtualenvs
2.7.13/envs/env-test (created from /Users/Teron/.pyenv/versions/2.7.13)
env-test (created from /Users/Teron/.pyenv/versions/2.7.13)
# Teron @ TeronsMac in ~ [23:37:59]
$ pyenv uninstall env-test
pyenv-virtualenv: remove /Users/Teron/.pyenv/versions/2.7.13/envs/env-test? y
# Teron @ TeronsMac in ~ [23:39:01]
$ pyenv virtualenvs
# 可见刚才的env-test环境已经没了
# Teron @ TeronsMac in ~ [23:39:18]
$ pyenv versions
system
2.7.13
* 3.6.2 (set by /Users/Teron/.python-version)
以下是针对各个易混淆的概念做的说明
PyPI packages not in the standard library:
-
virtualenv
is a very popular tool that creates isolated Python environments for Python libraries. If you're not familiar with this tool, I highly recommend learning it, as it is a very useful tool, and I'll be making comparisons to it for the rest of this answer.It works by installing a bunch of files in a directory (eg:
env/
), and then modifying thePATH
environment variable to prefix it with a custombin
directory (eg:env/bin/
). An exact copy of thepython
orpython3
binary is placed in this directory, but Python is programmed to look for libraries relative to its path first, in the environment directory. It's not part of Python's standard library, but is officially blessed by the PyPA (Python Packaging Authority). Once activated, you can install packages in the virtual environment usingpip
. -
pyenv
is used to isolate Python versions. For example, you may want to test your code against Python 2.6, 2.7, 3.3, 3.4 and 3.5, so you'll need a way to switch between them. Once activated, it prefixes thePATH
environment variable with~/.pyenv/shims
, where there are special files matching the Python commands (python
,pip
). These are not copies of the Python-shipped commands; they are special scripts that decide on the fly which version of Python to run based on thePYENV_VERSION
environment variable, or the.python-version
file, or the~/.pyenv/version
file.pyenv
also makes the process of downloading and installing multiple Python versions easier, using the commandpyenv install
. -
pyenv-virtualenv
is a plugin forpyenv
by the same author aspyenv
, to allow you to usepyenv
andvirtualenv
at the same time conveniently. However, if you're using Python 3.3 or later,pyenv-virtualenv
will try to runpython -m venv
if it is available, instead ofvirtualenv
. You can usevirtualenv
andpyenv
together withoutpyenv-virtualenv
, if you don't want the convenience features. -
virtualenvwrapper
is a set of extensions tovirtualenv
(see docs). It gives you commands likemkvirtualenv
,lssitepackages
, and especiallyworkon
for switching between differentvirtualenv
directories. This tool is especially useful if you want multiplevirtualenv
directories. -
pyenv-virtualenvwrapper
is a plugin forpyenv
by the same author aspyenv
, to conveniently integratevirtualenvwrapper
intopyenv
. -
pipenv
, by Kenneth Reitz (the author ofrequests
), is a brand new (possibly experimental) project that aims to combine Pipfile, pip and virtualenv into one command on the command-line.
Standard library:
-
pyvenv
is a script shipped with Python 3 but deprecated in Python 3.6 as it had problems (not to mention the confusing name). In Python 3.6+, the exact equivalent ispython3 -m venv
. -
venv
is a package shipped with Python 3, which you can run usingpython3 -m venv
(although for some reason some distros separate it out into a separate distro package, such aspython3-venv
on Ubuntu/Debian). It serves a similar purpose tovirtualenv
, and works in a very similar way, but it doesn't need to copy Python binaries around (except on Windows). Use this if you don't need to support Python 2. At the time of writing, the Python community seems to be happy withvirtualenv
and I haven't heard much talk ofvenv
.