zoukankan      html  css  js  c++  java
  • Python升级后ssl模块不可用问题解决和浅析

    在Cent0S 7.5下将Python 2.7.5升级到Python 3.6.6后,发现ssl模块不可用,具体详细信息如下所示:

     

    [root@db-server ~]# pip list
    Package    Version
    ---------- -------
    pip        19.2.3 
    setuptools 39.0.1 
    WARNING: pip is configured with locations that require TLS/SSL, however the ssl module in Python is not available.
    Could not fetch URL https://pypi.org/simple/pip/: There was a problem confirming the ssl certificate: HTTPSConnectionPool(host='pypi.org', port=443): Max retries exceeded with url: /simple/pip/ (Caused by SSLError("Can't connect to HTTPS URL because the SSL module is not available.",)) - skipping
     
    [root@db-server ~]# python -V
    Python 3.6.6
     
    >>> import ssl
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
      File "/usr/local/lib/python3.6/ssl.py", line 101, in <module>
        import _ssl             # if we can't import it, let the error propagate
    ModuleNotFoundError: No module named '_ssl'
    >>> 
    >>> import socket
    >>> hasattr(socket,"SSL")
    False
    >>>

     

    检查发现openssl包已经安装了,然后按照网上的文章,修改Modules/Setup.dist中,找到SSL配置部分,如下截图所示

     

    [root@db-server ~]# yum list installed |grep openssl
    openssl.x86_64                        1:1.0.2k-19.el7                  @base    
    openssl-libs.x86_64                   1:1.0.2k-19.el7                  @base 

     

     

    # Socket module helper for SSL support; you must comment out the other

    # socket line above, and possibly edit the SSL variable:

    #SSL=/usr/local/ssl

    #_ssl _ssl.c

    #       -DUSE_SSL -I$(SSL)/include -I$(SSL)/include/openssl

    #       -L$(SSL)/lib -lssl -lcrypto

     

    # The crypt module is now disabled by default because it breaks builds

    # on many systems (where -lcrypt is needed), e.g. Linux (I believe).

    #

    # First, look at Setup.config; configure may have set this for you.

     

    #_crypt _cryptmodule.c # -lcrypt        # crypt(3); needs -lcrypt on some systems

     

    clip_image001[4]

     

    这里需要取消注释部分(上图红框附近部分的设置),设置SSL路径,但是这个SSL的安装路径在哪里呢? 我查找了一下,发现openssl的安装路径如下:

     

    [root@db-server ~]# whereis openssl
    openssl: /usr/bin/openssl /usr/lib64/openssl /usr/share/man/man1/openssl.1ssl.gz
    [root@db-server ~]# rpm -ql openssl
    /etc/pki/CA
    /etc/pki/CA/certs
    /etc/pki/CA/crl
    /etc/pki/CA/newcerts
    /etc/pki/CA/private
    /etc/pki/tls/certs/Makefile
    /etc/pki/tls/certs/make-dummy-cert
    /etc/pki/tls/certs/renew-dummy-cert
    /etc/pki/tls/misc/CA
    /etc/pki/tls/misc/c_hash
    /etc/pki/tls/misc/c_info
    /etc/pki/tls/misc/c_issuer
    /etc/pki/tls/misc/c_name
    /usr/bin/openssl
    /usr/share/doc/openssl-1.0.2k
    /usr/share/doc/openssl-1.0.2k/FAQ
    /usr/share/doc/openssl-1.0.2k/NEWS
    /usr/share/doc/openssl-1.0.2k/README
    /usr/share/doc/openssl-1.0.2k/README.FIPS
    /usr/share/doc/openssl-1.0.2k/README.legacy-settings
    /usr/share/licenses/openssl-1.0.2k
    /usr/share/licenses/openssl-1.0.2k/LICENSE
    /usr/share/man/man1/asn1parse.1ssl.gz
    /usr/share/man/man1/ca.1ssl.gz
    /usr/share/man/man1/ciphers.1ssl.gz
    /usr/share/man/man1/cms.1ssl.gz
    /usr/share/man/man1/crl.1ssl.gz
    /usr/share/man/man1/crl2pkcs7.1ssl.gz
    /usr/share/man/man1/dgst.1ssl.gz
    /usr/share/man/man1/dhparam.1ssl.gz
    /usr/share/man/man1/dsa.1ssl.gz
    /usr/share/man/man1/dsaparam.1ssl.gz
    /usr/share/man/man1/dss1.1ssl.gz
    /usr/share/man/man1/ec.1ssl.gz
    /usr/share/man/man1/ecparam.1ssl.gz
    /usr/share/man/man1/enc.1ssl.gz
    /usr/share/man/man1/errstr.1ssl.gz
    /usr/share/man/man1/gendsa.1ssl.gz
    /usr/share/man/man1/genpkey.1ssl.gz
    /usr/share/man/man1/genrsa.1ssl.gz
    /usr/share/man/man1/md2.1ssl.gz
    /usr/share/man/man1/md4.1ssl.gz
    /usr/share/man/man1/md5.1ssl.gz
    /usr/share/man/man1/mdc2.1ssl.gz
    /usr/share/man/man1/nseq.1ssl.gz
    /usr/share/man/man1/ocsp.1ssl.gz
    /usr/share/man/man1/openssl.1ssl.gz
    /usr/share/man/man1/pkcs12.1ssl.gz
    /usr/share/man/man1/pkcs7.1ssl.gz
    /usr/share/man/man1/pkcs8.1ssl.gz
    /usr/share/man/man1/pkey.1ssl.gz
    /usr/share/man/man1/pkeyparam.1ssl.gz
    /usr/share/man/man1/pkeyutl.1ssl.gz
    /usr/share/man/man1/req.1ssl.gz
    /usr/share/man/man1/ripemd160.1ssl.gz
    /usr/share/man/man1/rsa.1ssl.gz
    /usr/share/man/man1/rsautl.1ssl.gz
    /usr/share/man/man1/s_client.1ssl.gz
    /usr/share/man/man1/s_server.1ssl.gz
    /usr/share/man/man1/s_time.1ssl.gz
    /usr/share/man/man1/sess_id.1ssl.gz
    /usr/share/man/man1/sha.1ssl.gz
    /usr/share/man/man1/sha1.1ssl.gz
    /usr/share/man/man1/sha224.1ssl.gz
    /usr/share/man/man1/sha256.1ssl.gz
    /usr/share/man/man1/sha384.1ssl.gz
    /usr/share/man/man1/sha512.1ssl.gz
    /usr/share/man/man1/smime.1ssl.gz
    /usr/share/man/man1/speed.1ssl.gz
    /usr/share/man/man1/spkac.1ssl.gz
    /usr/share/man/man1/sslpasswd.1ssl.gz
    /usr/share/man/man1/sslrand.1ssl.gz
    /usr/share/man/man1/ts.1ssl.gz
    /usr/share/man/man1/verify.1ssl.gz
    /usr/share/man/man1/version.1ssl.gz
    /usr/share/man/man1/x509.1ssl.gz
    /usr/share/man/man5/config.5ssl.gz
    /usr/share/man/man5/openssl.cnf.5ssl.gz
    /usr/share/man/man5/x509v3_config.5ssl.gz
    /usr/share/man/man7/des_modes.7ssl.gz

     

    尝试了几个路径,例如SSL=/usr/lib64/openssl ,然后重新编译安装Python,发现依然报错,

     

    [root@db-server Python-3.6.6]# vi Modules/Setup.dist

     

     

    SSL=/usr/lib64/openssl

    _ssl _ssl.c

           -DUSE_SSL -I$(SSL)/include -I$(SSL)/include/openssl

           -L$(SSL)/lib -lssl -lcrypto

     

     

    #cd /tmp/Python-3.6.6

    #./configure --prefix=/usr/local

    #make

    #make install

     

    在Python的解压安装包里面,我查了一下setup.py , 搜索ssl关键字,发现有如下一些代码, 但是我在系统搜索了一下,居然找不到这些目录(ssl/include和/ssl/lib)和ssl.h这些文件。

    [root@db-server ~]# vi /tmp/Python-3.6.6/setup.py
        # Detect SSL support for the socket module (via _ssl)
            search_for_ssl_incs_in = [
                                  '/usr/local/ssl/include',
                                  '/usr/contrib/ssl/include/'
                                 ]
            ssl_incs = find_file('openssl/ssl.h', inc_dirs,
                                 search_for_ssl_incs_in
                                 )
            if ssl_incs is not None:
                krb5_h = find_file('krb5.h', inc_dirs,
                                   ['/usr/kerberos/include'])
                if krb5_h:
                    ssl_incs += krb5_h
            ssl_libs = find_library_file(self.compiler, 'ssl',lib_dirs,
                                         ['/usr/local/ssl/lib',
                                          '/usr/contrib/ssl/lib/'
                                         ] )
     
            if (ssl_incs is not None and
                ssl_libs is not None):
                exts.append( Extension('_ssl', ['_ssl.c'],
                                       include_dirs = ssl_incs,
                                       library_dirs = ssl_libs,
                                       libraries = ['ssl', 'crypto'],
                                       depends = ['socketmodule.h']), )
            else:
                missing.append('_ssl')

      

    clip_image002[4]

     

     

    [root@db-server ~]# ls -lrt /usr/lib64/openssl
    total 0
    drwxr-xr-x. 2 root root 218 Sep 20 07:00 engines
     
    [root@db-server ~]# ls /usr/local/ssl
    ls: cannot access /usr/local/ssl: No such file or directory
     
    [root@db-server ~]# find / -name ssl.h

     

    后面才搞清楚,openssl包只包含了可执行部分,openssl-devel才包含了头文件、头文件参考、某些库文件等以及跟开发相关的东西。所以只安装了openssl包是找不到相应的头文件的,安装完openssl-devel之后,验证确认这些目录和文件已经存在了。

     

    [root@db-server ~]# rpm -qa | grep openssl-devel
    [root@db-server ~]# rpm -qa | grep openssl
    openssl-1.0.2k-19.el7.x86_64
    openssl-libs-1.0.2k-19.el7.x86_64
     
    [root@db-server ~]# yum list installed |grep openssl-devel
    [root@db-server ~]# yum list installed |grep openssl
    openssl.x86_64                        1:1.0.2k-19.el7                  @base    
    openssl-libs.x86_64                   1:1.0.2k-19.el7                  @base    
    [root@db-server ~]# 
     
    [root@db-server ~]# yum install openssl-devel

     

    使用# rpm -ql  openssl-devel 定位安装安装路径为/usr/include/openssl,修改安装路径的Modules/Setup.dist文件,修改后的部分如下所示(对比上面截图),然后重新编译安装Python后问题彻底解决。

     

     

    # Socket module helper for SSL support; you must comment out the other

    # socket line above, and possibly edit the SSL variable:

    SSL=/usr/include/openssl

    _ssl _ssl.c

            -DUSE_SSL -I$(SSL)/include -I$(SSL)/include/openssl

            -L$(SSL)/lib -lssl –lcrypto

     

     

    clip_image003[4]

     

     

    参考资料:

     

    https://www.cnblogs.com/minglee/p/9232673.html

  • 相关阅读:
    转发和重定向的区别
    描述Session跟Cookie的区别(重要)
    JSP的4大域对象
    描述JSP的9大内置对象(不重要)
    描述JSP和Servlet的区别
    Pytest系列(16)- 分布式测试插件之pytest-xdist的详细使用
    Pytest系列(15)- 多重校验插件之pytest-assume的详细使用
    Pytest系列(14)- 配置文件pytest.ini的详细使用
    Pytest系列(13)- 重复执行用例插件之pytest-repeat的详细使用
    Pytest系列(12)- 测试结果生成HTML报告插件之pytest-html的详细使用
  • 原文地址:https://www.cnblogs.com/kerrycode/p/11554898.html
Copyright © 2011-2022 走看看