虚拟 python 环境

Author:王蒙
Tags:python 环境,开发环境
abstract:项目比较复杂的时候,可能需要构建虚拟的 Python 环境。虚拟Python环境不仅使项目可以有独立的包环境;而且方便重现项目需要的Python环境。

Audience

Python 开发

Prerequisites

Python, shell 脚本的执行

Problem

  • 什么时候需要虚拟 Python 环境
  • 如何构建虚拟 Python 环境
  • 进入/退出虚拟 Python 环境
  • 重现 Python 环境
  • pyenv 管理多个版本的 Python 解释器

Solution

  • 什么时候需要虚拟 Python 环境

    虚拟 Python 环境带来的最大好处是:

    • 项目独立的包环境。
    • 方便重现项目的 Python 环境。

    包依赖比较复杂时,需要虚拟的 Python 环境。

    Pycharm 使得操作虚拟 Python 环境非常简单,有 Pycharm 你可以一直用虚拟Python 环境。

  • 构建虚拟 Python 环境

    pyvenvvirtualenv 是构建虚拟 Python 环境的工具。而且两种工具的使用几乎完全一样。文本以 pyvenv 为例做介绍。

    # 构建名为 wangmeng-python Python 环境,名称可以随便取
    $ pyvenv wangmeng-python
    

    构建的结果是一个和之前 Python 版本相同,但只装了包管理工具(pip, setuptools 等),没有其他第三方包的干净的 Python 环境。

  • 进入/退出虚拟解释器环境

    $ cd wangmeng-python
    # 下一步有坑
    $ . ./bin/activate
    (pyvenv-python) $ which python
    /root/wangmeng-python/virtualenv-python/bin/python
    # 已经进入虚拟 Python 环境
    # 退出虚拟 Python 环境
    (pyvenv-python) $ deactivate
    $
    

    踩过的坑:

    • 执行 activate 脚本时,一定要使用 source 或者 . 的方式执行该脚本。

      切记必须以 . 或者 source 来执行 activate 脚本。sh activate 是没法让 linux shell 进入虚拟 Python 环境的。

      因为要修改 PATH 等等环境变量,且必须在当前 shell 进程中生效,所以必须使用 source 或者 . 来执行 activate 脚本。

  • 重现 Python 环境

    # 把当前环境的包依赖写入 requirements.txt。
    $ pip freeze > requirements.txt
    
    # 找个干净的(除了装包工具之外,没再装任何第三方包) Python 环境(Python 解释器版本要和之前的版本一致)。
    # 一般使用 **pyvenv** 或者 **virtualenv** 构建这样的环境。
    $ pyvenv restore-wangmeng-python
    $ . ./bin/activate
    # 在干净的环境中,使用 requirements.txt 装包,就能还原之前的 wangmeng-python 解析器环境。
    $ pip install -r requirements.txt
    
  • pyenv 管理多个版本的 Python 解释器。

    参考 https://github.com/pyenv/pyenv-installer 安装 pyenv, 在类 Unix 环境安装非常简单,在 windows 上我没有安装成功。

    下载安装新版本的 Python

    $ pyenv install 2.7.3
    Downloading Python-2.7.3.tgz...
    -> https://www.python.org/ftp/python/2.7.3/Python-2.7.3.tgz
    Installing Python-2.7.3...
    patching file ./Modules/readline.c
    Hunk #1 succeeded at 200 (offset -6 lines).
    Hunk #2 succeeded at 735 (offset -14 lines).
    Hunk #3 succeeded at 845 (offset -14 lines).
    Hunk #4 succeeded at 893 with fuzz 2 (offset -25 lines).
    Ignoring potentially dangerous file name ../Python-2.7.3/Lib/site.py
    patching file ./Lib/site.py
    patching file ./Lib/ssl.py
    Hunk #2 succeeded at 424 (offset -11 lines).
    patching file ./Modules/_ssl.c
    Hunk #1 succeeded at 65 (offset -2 lines).
    Hunk #2 succeeded at 304 (offset -4 lines).
    Hunk #3 succeeded at 1725 (offset -87 lines).
    WARNING: The Python readline extension was not compiled. Missing the GNU readline lib?
    WARNING: The Python bz2 extension was not compiled. Missing the bzip2 lib?
    WARNING: The Python sqlite3 extension was not compiled. Missing the SQLite3 lib?
    Installing pip from https://bootstrap.pypa.io/get-pip.py...
    Installed Python-2.7.3 to /home/wangmeng/.pyenv/versions/2.7.3
    

    查看当前系统可用的 Python 版本

    $ pyenv versions
    * system (set by /home/wangmeng/.pyenv/version)
      2.7.3
    

    在当前目录下,选择使用特定版本的 Python 解释器

    $ pyenv local 2.7.3
    $ pyenv versions
      system
    * 2.7.3 (set by /home/wangmeng/.python-version)
    

    在全局,选择使用特定版本的 Python 解释器

    $ pyenv global 2.7.3
    
    $ pyenv shell 2.7.3
    

    卸载 Python 解释器

    $ pyenv uninstall 2.7.3
    $ pyenv versions
    * system (set by /home/wangmeng/.python-version)