当前位置: 首页 > 后端技术 > Python

在Dockerfile中优雅地激活virtualenv

时间:2023-03-26 12:47:26 Python

作者:ItamarTurner-Trauring最近更新时间:2020年6月25日,最初创建于2019年3月20日在将Python应用程序打包到Docker映像中时,通常会使用virtualenv。例如,您可能正在进行多阶段构建以获得较小的图像。由于您使用的是virtualenv,因此您需要激活它-但如果您刚开始使用Dockerfile,那么天真的方法将行不通。即使您确实知道如何去做,通常的方法也是重复的,因此容易出错。有一种激活virtualenv的简单方法,我将在本文中演示。但首先,我们将介绍一些其他不太优雅(或损坏!)的方法。注意:在讨论的主题之外,本文中的Dockerfile不是最佳实践的示例,因为增加的复杂性会模糊本文的重点。因此,如果您想在生产环境中使用Docker来运行Python应用程序,这里有两种应用最佳实践的方法:如果您想自己动手:包含示例和参考的详细清单如果您希望尽快完成工作设置:模板已经为您实施最佳实践的地方无效如果您只是盲目地将shell脚本转换为Dockerfile,您最终会得到一些看起来正确但实际上已损坏的东西:FROMpython:3.8-slim-busterRUNpython3-mvenv/opt/venv#这是错误的!运行。/opt/venv/bin/activate#安装依赖项:COPYrequirements.txt.RUNpipinstall-rrequirements.txt#运行应用程序:COPYmyapp.py。CMD["python","myapp.py"]它因两个不同的原因而中断:Dockerfile中的每个RUN行都是一个不同的进程。单独激活运行RUN不会影响未来的RUN调用。出于所有实际目的,这是无人值守的。当您运行生成的Docker镜像时,它将运行CMD——它也不会在virtualenv中运行,因为它也不受RUN进程的影响。重复的最有效方法一种解决方案是在virtualenv中显式使用二进制文件的路径。在这种情况下,我们只有两次重复,但在更复杂的情况下,您需要一遍又一遍地重复。除了缺乏可读性之外,重复也是错误的来源。当您向Python程序添加更多调用时,很容易忘记添加神奇的/opt/venv/bin/前缀。它将(大部分)工作:FROMpython:3.8-slim-busterRUNpython3-mvenv/opt/venv#Installdependencies:COPYrequirements.txt.RUN/opt/venv/bin/pipinstall-rrequirements.txt#运行application:COPYmyapp.py.CMD["/opt/venv/bin/python","myapp.py"]唯一需要注意的是,如果任何Python进程启动了一个子进程,该子进程将不会在virtualenv中运行。完全有效的重复您可以通过单独激活virtualenvRUN和:CMD:FROMpython:3.8-slim-busterRUNpython3-mvenv/opt/venv#Installdependencies:COPYrequirements.txt.RUN./opt/venv/bin来解决这个问题/activate&&pipinstall-rrequirements.txt#运行应用程序:COPYmyapp.py.CMD。/opt/venv/bin/activate&&execpythonmyapp.py(您可以在exec处理中获得正确的信号。)我们可以通过优雅的方式了解激活的实际作用很容易将激活想象成某种神秘的魔法,绘制的五角星用鲜血将Python安全地困住。但它只是软件,而且是相当简单的软件。virtualenv文档甚至会告诉您activate“绝对方便”。如果您去阅读activate的代码,它会做很多事情:它可以找出您正在运行的shell。它向您的shell添加停用功能并混淆pydoc。它更改shell提示以包括virtualenv名称。如果有人碰巧设置了PYTHONHOME环境变量,它将取消设置。它设置了两个环境变量:VIRTUAL_ENV和PATH。前四个基本和Docker的使用无关,所以只剩下最后一个了。VIRTUAL_ENV大部分时间没有作用,但一些工具(例如诗歌打包工具)使用它来检测您是否在virtualenv中运行。最重要的部分是设置PATH:PATH是一个目录列表,用于搜索要运行的命令。activate只是将virtualenv的bin/目录添加到列表的开头。我们可以通过设置适当的环境变量来激活:Docker的ENV命令将应用于后续的RUN和CMD。结果是以下Dockerfile:FROMpython:3.8-slim-busterENVVIRTUAL_ENV=/opt/venvRUNpython3-mvenv$VIRTUAL_ENVENVPATH="$VIRTUAL_ENV/bin:$PATH"#Installdependencies:COPYrequirements.txt.RUNpipinstall-rrequirements.txt#Runtheapplication:COPYmyapp.py.CMD["python","myapp.py"]现在virtualenv可以自动使用CMD运行,无需重复或记住任何东西。软件不是魔法事情是这样的:一个与原始版本一样简单的版本,但实际上是正确的。没有重复,错误余地更少。当某些事情看起来不必要地复杂时,请深入研究并弄清楚它是如何工作的。您使用的软件可能比您想象的更简单(或更简单),并提供更优雅的解决方案,但需要做更多的工作。______________________________________你明天可能会离开,但是\|并不意味着你今天不在这里|\。于家澳编辑/----------------------------------\^__^\(oo)\_______(__)\)\/\||----w|||||?2020连字符企业有限责任公司。版权所有。