Python 虚拟环境工作原理解析

目录
  • 简介
  • 使用
  • 激活脚本
  • 工作原理
  • 关于 sys.prefix
  • 总结
  • 其它

Python 的虚拟环境用来创建一个相对独立的执行环境,尤其是一些依赖的三方包,最常见的如不同项目依赖同一个但是不同版本的三方包,而且,在虚拟环境中的安装包不会影响到系统的安装包。

不过,其具体的工作原理是怎样的,这里详细介绍。

简介

几乎每个语言都包含自己的包管理工具,这是一个非常复杂的话题,而不同语言选择的实现又略有区别,都会做一些选择和取舍。而 Python 的包管理解决方案很多,例如 pip、virtualenv、pyenv 等等。

不过 Python 语言本身的机制决定了其原理一样。

使用

比较常用的是 virtualenv 工具,可以参考 Guide to Python 中的详细介绍,另外,Python3 也提供了自己的虚拟环境创建模块,在创建完成后基本都是通过一个脚本启用独立环境。

例如,如下是使用 virtualenv 以及 venv 的虚拟环境创建过程。

$ mkdir /tmp/project && cd /tmp/project

$ virtualenv --no-site-packages foobar
$ python3 -m venv foobar

然后,就可以通过 source foobar/bin/activate 命令激活新环境。

激活脚本

所谓的独立环境,无非就是解决两个问题:A) 执行 Python 解析器所使用的版本;B) 使用独立的包。其中前者,在 Linux 主要是通过 PATH 环境变量设置,在 activate 脚本中有如下的内容。

VIRTUAL_ENV="/tmp/project/foobar"
export VIRTUAL_ENV

_OLD_VIRTUAL_PATH="$PATH"
PATH="$VIRTUAL_ENV/bin:$PATH"
export PATH

也就是将创建的目录添加到 PATH 环境变量最开始,那么就会优先查找该路径,这样就解决了 python 解析器独立的问题。

工作原理

如果要使用独立的包,那么关键就是如何在通过 import 导入时查找到所需的包。

包的查找顺序可以查看Python 模块简介 中的介绍,简单来说,就是先查看是否是内置模块,然后再从 sys.path 列表指定的地址中搜索。所以,这里的关键就是 sys.path 列表的生成。

关于 sys.prefix

在 Python 启动的时候,会先加载一个强依赖的 os.py 包,而查找这个包是根据解析器的当前路径,以及固定的查找规则来实现的。

简单来说,就是在当前路径加上 lib/python${VERSION}/os.py 逐层向上查找,注意,如果是 64 位的操作系统,那么会使用 lib64 替换掉之前的 lib 路径。

例如,默认的 Python3 的解析器路径为 /usr/bin/python3.6 ,那么基础路径是 /usr/bin/ ,所以,其查找顺序为。

/usr/bin/lib64/python3.6/os.py
/usr/lib64/python3.6/os.py
/lib64/python3.6/os.py

只要在任意路径上找到 os.py 包,那么就会退出查找,并设置好 sys.prefix 变量,详细可以通过 strace python 查看,会有如下的搜索路径。

stat("/usr/bin/Modules/Setup", 0x7fffb7146300) = -1 ENOENT (No such file or directory)
stat("/usr/bin/lib64/python2.7/os.py", 0x7fffb71462f0) = -1 ENOENT (No such file or directory)
stat("/usr/bin/lib64/python2.7/os.pyc", 0x7fffb71462f0) = -1 ENOENT (No such file or directory)
stat("/usr/lib64/python2.7/os.py", {st_mode=S_IFREG|0644, st_size=25910, ...}) = 0

在查找到 os.py 之后,会将该路径设置为 sys.prefix 变量,然后解析器就会到 ${sys.prefix}/lib/python${VERSION} 目录下查找包。

总结

那么其工作原理就是,将 python 解析器保存在 ${VENV_PATH}/bin/python ,然后创建 ${VENV_PATH}/lib/python${VERSION} 目录,并将相关的文件复制到该目录下,可以复制文件,也可以使用软连接。

其它

如上,如果是 Python3 就可以直接使用内置的 venv 模块,其原理与上述的相同,同时通过 pyvenv.cfg 配置文件来标识原始的 home 位置,该文件的内容如下。

home = /usr/bin
include-system-site-packages = false
version = 3.6.8

如果 include-system-site-packagestrue ,解释器启动时就会将系统的库添加到 sys.path 里面,这样在虚拟环境就可以 import 系统中安装的包了。

注意,Python3 提供的 venv 模块只能根据当前版本创建,不能支持 Python2 。

参考 Virtualenv官方文档,细节可以参考该文档。

Creation of virtual environments Python3 提供的 venv 介绍,包括常见参数以及配置文件。

← Older

到此这篇关于Python 虚拟环境工作原理解析的文章就介绍到这了,更多相关Python 虚拟环境原理内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • Python虚拟环境的原理及使用详解

    Python的虚拟环境极大地方便了人们的生活.本指南先介绍虚拟环境的基础知识以及使用方法,然后再深入介绍虚拟环境背后的工作原理. 注意:本指南在macOS Mojave系统上使用最新版本的Python 3.7.x. 1. 为什么使用虚拟环境? 虚拟环境为一系列潜在问题提供简单的解决方案,尤其是在以下几个方面: 允许不同的项目使用不同版本的程序包,从而解决依赖性问题.例如,可以将Project A v2.7用于Project X,并将Package A v1.3用于Project Y. 通过捕获需

  • Python虚拟环境Virtualenv使用教程

    virtualenv用于创建独立的Python环境,多个Python相互独立,互不影响,它能够: 1. 在没有权限的情况下安装新套件 2. 不同应用可以使用不同的套件版本 3. 套件升级不影响其他应用 安装 复制代码 代码如下: sudo apt-get install python-virtualenv 使用方法 [code] virtualenv [虚拟环境名称] 如,创建**ENV**的虚拟环境 复制代码 代码如下: virtualenv ENV 默认情况下,虚拟环境会依赖系统环境中的si

  • Python虚拟环境venv用法详解

    初衷: 在工作的时候,我们会有很多个项目,每个项目使用的库的版本不一样,导致我们切换项目的时候会很麻烦. 比如:我有两个django项目,项目一使用的版本是 django 1.7 , 项目二使用的版本是 django 2.2.两个项目平时都要维护,如果没有独立的环境,那我每次维护项目一的时候,我就需要安装 django 1.7,维护项目二的时候,我就要安装 django 2.2,这样会很麻烦. 所以我们需要给每个项目建立一个独立的环境,这个时候环境管理就派上用场了,我在维护项目一的时候,只需要使

  • Python虚拟环境virtualenv的安装与使用详解

    前言 动态语言Ruby.Python都有自己的虚拟环境,虚拟环境是程序执行时的独立执行环境,在同一台服务器中可以创建不同的虚拟环境供不同的系统使用,项目之间的运行环境保持独立性而相互不受影响.例如项目可以在基于Python2的环境中运行,而项目B可以在基于Python3的环境中运行.Python通virtualenv工具管理虚拟环境. 安装 virtualenv $ pip install virtualenv 使用方法 $ cd my_project_folder $ virtualenv v

  • Ubuntu20.04安装Python3的虚拟环境教程详解

    以下均在本人虚拟机上进行 1.安装pip3 sudo apt install python3-pip 2.安装虚拟环境 sudo apt install virtualenv sudo apt install virtualenvwrapper 3.修改配置文件设置环境变量 cd ~ vim .bashrc 在.bashrc文件后面加入下面两行 export WORKON_HOME=$HOME/.virtualenvs source /usr/share/virtualenvwrapper/vi

  • Python 虚拟环境工作原理解析

    目录 简介 使用 激活脚本 工作原理 关于 sys.prefix 总结 其它 Python 的虚拟环境用来创建一个相对独立的执行环境,尤其是一些依赖的三方包,最常见的如不同项目依赖同一个但是不同版本的三方包,而且,在虚拟环境中的安装包不会影响到系统的安装包. 不过,其具体的工作原理是怎样的,这里详细介绍. 简介 几乎每个语言都包含自己的包管理工具,这是一个非常复杂的话题,而不同语言选择的实现又略有区别,都会做一些选择和取舍.而 Python 的包管理解决方案很多,例如 pip.virtualen

  • Python unittest工作原理和使用过程解析

    这篇文章主要介绍了Python unittest工作原理和使用过程解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 1.unittest的工作原理: TestCase:一个testcase就是一条测试用例. setUp:测试环境的准备 tearDown:测试环境的还原 run:测试执行 TestSuite:测试套件或集合,多个测试用例的集合就是1个suite,一个suite可以包含多条测试用例,测试套件suite里面也可以嵌套测试套件suit

  • python sorted函数原理解析及练习

    这篇文章主要介绍了python sorted函数原理解析及练习,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 前两天学习了一下socket编程,在向某大神请教问题时被嫌弃了,有一种还没学会走就想跑的感觉.大神说我现在的水平应该去做一些像是操作文件.序列号等的小练习来加深理解.下面是他给我出的小练习: 1.datas = [['sherry',19,'female'],['flora',21,'female'],['june',15,'femal

  • Python matplotlib底层原理解析

    目录 1. matplotlib 框架组成 2. 脚本层(scripting) 3. 美工层(artist) 4. 后端层(backend) 复习回顾: 前期,我们已经学习了matplotlib模块相关的基础知识,对 matplotlib 模块折线图.饼图.柱状图进行操作. 我们都知道matplotlib 是偏向底层用于可视化数据处理的库,我们在绘制图表的时候主要步骤主要有四大步骤: 导入 matplotlib.pplot库 使用pandas/numpy模块对数据进行整分析理 调用pyplot中

  • react  Suspense工作原理解析

    目录 Suspense 基本应用 Suspense 原理 基本流程 源码解读 - primary 组件 源码解读 - 异常捕获 源码解读 - 添加 promise 回调 源码解读-Suspense 首次渲染 primary 组件加载完成前的渲染 primary 组件加载完成时的渲染 利用 Suspense 自己实现数据加载 Suspense 基本应用 Suspense 目前在 react 中一般配合 lazy 使用,当有一些组件需要动态加载(例如各种插件)时可以利用 lazy 方法来完成.其中

  • Pinia介绍及工作原理解析

    目录 什么是Pinia 如何使用Pinia 安装 创建store 在组件中使用store 在模板中使用store Pinia是如何工作的 什么是Pinia Pinia是Vue 3的状态管理库,它提供了一种简单.可靠和可扩展的方法来管理应用程序状态.它的目标是提供一个清晰的API,易于使用,并避免不必要的性能开销. Pinia与Vuex类似,但是它采用了更现代的API和一些更好的实践.Pinia将状态分为两类:响应式状态和非响应式状态.响应式状态是指可以在Vue组件中使用的状态,而非响应式状态是指

  • Android Handler工作原理解析

    简介 在Android 中,只有主线程才能操作 UI,但是主线程不能进行耗时操作,否则会阻塞线程,产生 ANR 异常,所以常常把耗时操作放到其它子线程进行.如果在子线程中需要更新 UI,一般是通过 Handler 发送消息,主线程接受消息并且进行相应的逻辑处理.除了直接使用 Handler,还可以通过 View 的 post 方法以及 Activity 的 runOnUiThread 方法来更新 UI,它们内部也是利用了Handler .在上一篇文章 Android AsyncTask源码分析

  • AQS(AbstractQueuedSynchronizer)抽象队列同步器及工作原理解析

    目录 前言 AQS是什么? 用银行办理业务的案例模拟AQS如何进行线程管理和通知机制 结语 前言 AQS 绝对是JUC的重要基石,也是面试中经常被问到的,所以我们要搞清楚这个AQS到底是什么?骑工作原理是什么? AQS是什么? AQS,AbstractQueuedSynchronizer,即队列同步器.它是构建锁或者其他同步组件的基础框架(如ReentrantLock.ReentrantReadWriteLock.Semaphore等),JUC并发包的作者(Doug Lea)期望它能够成为实现大

  • Beego AutoRouter工作原理解析

    目录 一.前言 二.从一个例子入手 AutoRouter的解析规则: 三.AutoRouter是如何工作的 结语 一.前言 Beego Web框架应该是国内Go语言社区第一个框架,个人觉得十分适合新手入门Go Web.笔者半年前写过一篇搭建Beego项目并实习简单功能的文章,大家有兴趣可以先看看. 其实我接触的大部分人都在学校学过Java Web,其实有Java Web的经验,上手Beego也会很舒服. 本文着重讲讲Beego的AutoRouter模块,会结合源码来讲讲,不过由于笔者技术水平有限

随机推荐