异常: javax.net.ssl.SSLHandshakeException: PKIX path building failed: SunCertPathBuilderException

文章目录

      • 概述
        • 原因
      • 解决办法
        • 方法一:Java实现禁用 SSL验证(慎用)
        • 方法二:更新 Java 的安全证书(Java环境中缺少证书或证书无效的情况)
        • 方法三:更新操作系统根证书(操作系统根证书过期或不完整的情况)

概述

当我们使用 java.net.URL 或者 org.jsoup.Jsoup 等工具,去获取网页信息的时候,可能会因为证书原因报错:
javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OagZ6kv9-1679997652984)(../../img/image-20230328020220270.png)]

原因

这个错误通常是由于Java环境中 缺少证书或证书无效导致

如果操作系统根证书过期或者不完整,可能会导致这个错误出现,解决办法就是:更新操作系统根证书并重新启动计算机


**其它原因**
  • 如果是因为网络连接不稳定,也可能导致获取网页信息报错,可以检查网络连接是否正常,多试几次就行
  • 无URL访问权限或者URL错误无效,也可则可能会出现此错误

解决办法

方法一:Java实现禁用 SSL验证(慎用)
/**
     * 禁用SSL验证【注意:会禁用所有SSL验证,包括恶意攻击者可能使用的验证!!】
     * 
     * todo: 如果需要验证证书或主机名,需要自行实现相应的逻辑
     */
    public static void forbiddenCheckSslCertificate() {
        
        try {
            // 使用SSLContext类手动设置SSL证书验证
            SSLContext sslContext = SSLContext.getInstance("SSL");
            // X509TrustManager类用于信任所有证书
            sslContext.init(null, new TrustManager[]{new X509TrustManager() {
                
                @Override
                public void checkClientTrusted(java.security.cert.X509Certificate[] x509Certificates, String s) {
                }

                @Override
                public void checkServerTrusted(java.security.cert.X509Certificate[] x509Certificates, String s) {
                }

                @Override
                public java.security.cert.X509Certificate[] getAcceptedIssuers() {
                    return new java.security.cert.X509Certificate[0];
                }
                
            }}, new SecureRandom());
            
            HttpsURLConnection.setDefaultSSLSocketFactory(sslContext.getSocketFactory());
            
            // HostnameVerifier 类用于信任所有主机名
            HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() {
                @Override
                public boolean verify(String s, SSLSession sslSession) {
                    return true;
                }
            });

        } catch (NoSuchAlgorithmException | KeyManagementException e) {
            LogUtil.warn("execute exception = {}", e.getLocalizedMessage(), e);
        }
        
    }

【注意】:该方法会禁用所有 SSL验证,包括恶意攻击者可能使用的验证!
使用时只有在信任所有服务器并且没有其他解决方案时才应使用此方法!

方法二:更新 Java 的安全证书(Java环境中缺少证书或证书无效的情况)

Java安装目录中找到 jre\lib\security 文件目录,然后从官方网站下载最新的Java安全证书,将其添加到 cacerts 文件中【注意将 cacerts 文件备份

具体步骤

  1. 找到电脑上的Java安装目录(默认情况下,在 C:\Program Files\JavaC:\Program Files (x86)\Java 目录中)

  2. 在Java目录下,进入 jre\lib\security 文件目录

  3. 备份 cacerts 文件(备份以防万一可恢复,这个目录存放当前的Java安全证书)

  4. 去官网下载最新的Java安全证书
    地址: https://www.oracle.com/java/technologies/javase-downloads.html
    在Oracle的Java SE下载页面上找到最新的Java安全证书进行下载

  5. 添加新的Java安全证书到 cacerts 文件目录中
    使用Java的 keytool 工具将下载好的新的Java安全证书添加到 cacerts 文件中。
    eg: 在终端中,跳转到 jre\lib\security 目录,然后运行以下命令:

    keytool -import -alias mycert -file <这里填入下载好的需要添加的Java安全证书文件路径> -keystore cacerts
    

    这个过程中需要输入当前的 keystore 密码(默认为 changeit),然后输入 yes 添加新的证书。

    keystore 是Java中用于存储数字证书、私钥和公钥的安全存储区域。它是一个二进制文件,通常使用 Java keytool 工具进行创建和管理。在Java应用程序中,keystore 用于存储 SSL 证书、身份验证证书和加密密钥等敏感数据。可以使用Java的 SSL 套接字实现从 keystore 中加载数字证书以建立 SSL 连接。keystore 还可以用于数字签名和加密操作,以确保数据的完整性和安全性。在Java中,有两种类型的keystore

    • Java keystore(JKS)
    • PKCS12 keystore

    keystore 密码是用于保护 Java keystore 文件的密码。Java keystore 文件包含数字证书,私钥和公钥。在使用 keytool 工具添加或删除数字证书时,需要提供 keystore密码 以验证对keystore 文件的访问权限。默认情况下,Java keystore文件的密码为 changeit。当然如果在创建 keystore 文件时指定密码,则需要使用你制指定的密码。

  6. 重启Java应用程序测试是否已解决问题

【注意】:修改Java安全证书可能会影响其他Java应用程序的功能。所以,请做好备份,同时多测试!

方法三:更新操作系统根证书(操作系统根证书过期或不完整的情况)

如果操作系统根证书过期或者不完整,可能会导致这个错误出现。
更新操作系统根证书的具体操作流程可能因操作系统版本而异。通用的更新操作系统根证书的步骤如下:

  1. 打开 证书管理器
    • Windows操作系统中,可以通过打开cmd窗口(windows+R),输入certmgr.msc 回车打开 证书管理器
    • macOS操作系统中,通过打开 应用程序 文件夹,然后转到 实用工具 文件夹中的 钥匙串访问 应用程序来打开 钥匙串访问
  2. 导入新的根证书
    在 证书管理器 中,找到 可信任的 根证书颁发机构 文件夹,鼠标右键,选择【所有任务】 > 【导入】 选项。然后选择下载好的新的根证书文件,并按照向导中的说明完成导入
  3. 删除旧的根证书
    【证书管理器】中,找到旧的根证书,按照提示完成删除过程。
  4. 重启计算机
    重新启动计算机以确保更改生效。

【注意】:更新操作系统根证书可能会影响其他应用程序的功能。所以,请做好备份,同时多测试!

文章出处登录后可见!

已经登录?立即刷新

共计人评分,平均

到目前为止还没有投票!成为第一位评论此文章。

(0)
扎眼的阳光的头像扎眼的阳光普通用户
上一篇 2023年12月5日
下一篇 2023年12月5日

相关推荐