记一次因升级宿主机 Python 导致的 ImportError

在升级ECS系统Python到3.6.3后,Django应用的uwsgi启动失败,出现ImportError。原因是Virtualenv未复制系统库文件,导致3.6.2版本的Python解释器尝试导入3.6.3版本的库,引发错误。解决方案是使用pyenv等工具管理多版本Python。
摘要由CSDN通过智能技术生成

我们有一个 Django 应用通过 uwsgi 跑在阿里云的 ECS 上,所用的系统是 Ubuntu 16.04,uwsgi 是通过 supervisord 来管理的,每个应用都在单独的 virtualenv 中运行,这就是大概的软件运行环境。

因为一些软件没有升级,阿里云一直提示存在安全漏洞,所以我就想把 ECS 上的系统升级一下。升级的过程并没有什么什么问题,毕竟用的阿里云自己维护的源,基本上不会出现什么版本依赖之类的问题。

出错场景

升级完成后重新启动 Django 应用,发现应用启动不起来,uwsgi 报错

from _ssl import HAS_SNI, HAS_ECDH, HAS_NPN, HAS_ALPN, HAS_TLSv1_3
ImportError: cannot import name 'HAS_TLSv1_3'

原因分析

从异常入手查找原因

抛出的异常意思是在_ssl模块中没有HAS_TLSv1_3的属性,于是我就去Python 文档中查询了一下这个属性,它的解释是这样的:

ssl.HAS_TLSv1_3
Whether the OpenSSL library has built-in support for the TLS 1.3 protocol.

New in version 3.6.3.

看到New in version 3.6.3.的字样,再去查系统的升级记录,我发现刚刚执行的升级中就把宿主机的 Python 从3.6.2升级到了3.6.3,此时我隐隐约约觉得就是因为此次升级导致了 uwsgi 启动时的报错。

但我升级的是宿主机的 Python,它又是如何影响到了 Virtualenv 中的 Python 呢?各位别急,我们接着往下挖。

HAS_TLSv1_3的定义

我们接着再去看抛出异常的那行代码,它在 Python 的标准库的ssl.py118行,具体内容如下:

from _ssl import HAS_SNI, HAS_ECDH, HAS_NPN, HAS_ALPN, HAS_TLSv1_3

我们可以看到,抛出异常就是因为Python解释器从_ssl模块中导入HAS_TLSv1_3时,出现了导入异常。

_ssl模块是用C语言编写的,它被编译进入了Python解释器中,它的代码位于 Python 源码的

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值