“PKIX 路径构建失败”和“无法找到请求目标的有效证书路径”

Posted

技术标签:

【中文标题】“PKIX 路径构建失败”和“无法找到请求目标的有效证书路径”【英文标题】:"PKIX path building failed" and "unable to find valid certification path to requested target" 【发布时间】:2014-01-31 07:22:01 【问题描述】:

我正在尝试使用 twitter4j 库为我的 java 项目获取推文,该库在 java.net.HttpURLConnection 的封面下使用(如堆栈跟踪所示)。在我第一次运行时,我收到关于证书sun.security.validator.ValidatorExceptionsun.security.provider.certpath.SunCertPathBuilderException 的错误。然后我通过以下方式添加了twitter证书:

C:\Program Files\Java\jdk1.7.0_45\jre\lib\security>keytool -importcert -trustcacerts -file PathToCert -alias ca_alias -keystore "C:\Program Files\Java\jdk1.7.0_45\jre\lib\security\cacerts"

但没有成功。以下是获取推文的过程:

public static void main(String[] args) throws TwitterException 
    ConfigurationBuilder cb = new ConfigurationBuilder();
    cb.setDebugEnabled(true)
        .setOAuthConsumerKey("myConsumerKey")
        .setOAuthConsumerSecret("myConsumerSecret")
        .setOAuthAccessToken("myAccessToken")
        .setOAuthAccessTokenSecret("myAccessTokenSecret");
    
    TwitterFactory tf = new TwitterFactory(cb.build());
    Twitter twitter = tf.getInstance();
    
    try 
        Query query = new Query("iphone");
        QueryResult result;
        result = twitter.search(query);
        System.out.println("Total amount of tweets: " + result.getTweets().size());
        List<Status> tweets = result.getTweets();
        
        for (Status tweet : tweets) 
            System.out.println("@" + tweet.getUser().getScreenName() + " : " + tweet.getText());
        
     catch (TwitterException te) 
        te.printStackTrace();
        System.out.println("Failed to search tweets: " + te.getMessage());
    

这是错误:

sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
Relevant discussions can be found on the Internet at:
    http://www.google.co.jp/search?q=d35baff5 or
    http://www.google.co.jp/search?q=1446302e
TwitterExceptionexceptionCode=[d35baff5-1446302e 43208640-747fd158 43208640-747fd158 43208640-747fd158], statusCode=-1, message=null, code=-1, retryAfter=-1, rateLimitStatus=null, version=3.0.5
    at twitter4j.internal.http.HttpClientImpl.request(HttpClientImpl.java:177)
    at twitter4j.internal.http.HttpClientWrapper.request(HttpClientWrapper.java:61)
    at twitter4j.internal.http.HttpClientWrapper.get(HttpClientWrapper.java:81)
    at twitter4j.TwitterImpl.get(TwitterImpl.java:1929)
    at twitter4j.TwitterImpl.search(TwitterImpl.java:306)
    at jku.cc.servlets.TweetsAnalyzer.main(TweetsAnalyzer.java:38)
Caused by: 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
    at sun.security.ssl.Alerts.getSSLException(Unknown Source)
    at sun.security.ssl.SSLSocketImpl.fatal(Unknown Source)
    at sun.security.ssl.Handshaker.fatalSE(Unknown Source)
    at sun.security.ssl.Handshaker.fatalSE(Unknown Source)
    at sun.security.ssl.ClientHandshaker.serverCertificate(Unknown Source)
    at sun.security.ssl.ClientHandshaker.processMessage(Unknown Source)
    at sun.security.ssl.Handshaker.processLoop(Unknown Source)
    at sun.security.ssl.Handshaker.process_record(Unknown Source)
    at sun.security.ssl.SSLSocketImpl.readRecord(Unknown Source)
    at sun.security.ssl.SSLSocketImpl.performInitialHandshake(Unknown Source)
    at sun.security.ssl.SSLSocketImpl.startHandshake(Unknown Source)
    at sun.security.ssl.SSLSocketImpl.startHandshake(Unknown Source)
    at sun.net.www.protocol.https.HttpsClient.afterConnect(Unknown Source)
    at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.connect(Unknown Source)
    at sun.net.www.protocol.http.HttpURLConnection.getInputStream(Unknown Source)
    at java.net.HttpURLConnection.getResponseCode(Unknown Source)
    at sun.net.www.protocol.https.HttpsURLConnectionImpl.getResponseCode(Unknown Source)
    at twitter4j.internal.http.HttpResponseImpl.<init>(HttpResponseImpl.java:34)
    at twitter4j.internal.http.HttpClientImpl.request(HttpClientImpl.java:141)
    ... 5 more
Caused by: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
    at sun.security.validator.PKIXValidator.doBuild(Unknown Source)
    at sun.security.validator.PKIXValidator.engineValidate(Unknown Source)
    at sun.security.validator.Validator.validate(Unknown Source)
    at sun.security.ssl.X509TrustManagerImpl.validate(Unknown Source)
    at sun.security.ssl.X509TrustManagerImpl.checkTrusted(Unknown Source)
    at sun.security.ssl.X509TrustManagerImpl.checkServerTrusted(Unknown Source)
    ... 20 more
Caused by: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
    at sun.security.provider.certpath.SunCertPathBuilder.engineBuild(Unknown Source)
    at java.security.cert.CertPathBuilder.build(Unknown Source)
    ... 26 more
Failed to search tweets: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target

【问题讨论】:

您好,请查看以下网址。我相信这些会对你有所帮助。 java-samples.com/showtutorial.php?tutorialid=210confluence.atlassian.com/display/JIRAKB/…。您必须将您的 ssl 证书添加到 java 信任库证书中(路径:jre/lib/security/cacerts)。 请参考this 答案以获得解决方案,并确认您将软件打包为捆绑的 jre 吗?如果是,则复制您的 cacerts 文件表单系统并替换该打包的 jre cacerts 文件。 试试这个***.com/a/9210661/4741746也许这就是你的答案 我刚刚使用了这个 Java 代码,对于 https,不要忘记将端口指定为 443。github.com/escline/InstallCert/blob/master/InstallCert.java 的 Java 代码将获取您的 CACERTS 文件并将所有这些加上当前证书您作为输入提供的 URL。就我而言,我将值硬编码为 host="mywebservice.uat.xyz.com";端口=443; passphrase="changeit".toCharArray();然后程序会创建一个名为“jssecacerts”的新文件,其中包含所有内容。将其重命名为“cacerts”并使用它。一切就绪。 这能回答你的问题吗? Resolving javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed Error? 【参考方案1】:

这种异常通常发生在受信任证书的PATH不匹配时。检查安全通信需要此服务器证书的配置或路径。

【讨论】:

您能否告诉我可以安装证书的确切配置。实际上我遇到了这个问题,我已经使用 keytool 安装了关于这个问题的证书,这工作了大约 20-30 分钟,然后服务器再次发出同样的错误。请帮我。我在这个问题上被困了 2 天。 我认为证书每 20-30 分钟更改一次 我面临类似的问题,但问题是:我的 java 选择 Java 应用程序的 $JAVA_HOME/lib/security/cacerts 的默认位置,尽管我提供了 -Djavax.net.ssl.trustStore=/myapp/ app.jks 谁能帮我解决这个问题:***.com/questions/33821785/…【参考方案2】:

在尝试构建证书文件以使我的 Java 6 安装与新的 twitter 证书一起工作数小时后,我终于偶然发现了一个非常简单的解决方案,隐藏在其中一个留言板的评论中。只需从 Java 7 安装中复制 cacerts 文件,然后覆盖 Java 6 安装中的那个。最好先备份 cacerts 文件,然后您只需将新文件复制进去,然后 BOOM!它只是工作。

请注意,我实际上将一个 Windows cacerts 文件复制到了 Linux 安装中,它工作得很好。

在新旧 Java jdk 安装中,该文件位于 jre/lib/security/cacerts

希望这可以避免其他人的烦恼。

【讨论】:

我正在尝试使用自签名证书访问 ssl 服务器,尝试使用 keytool 添加它的证书,但没有运气,有什么建议吗? 很高兴它起作用了。但是你知道根本原因是什么吗?是什么导致 java 6 证书失败.. java 7 证书如何解决问题 这做到了,虽然我从 icedtea 1.6 升级到 oracle 1.7。 :) 也可以考虑这个解决方案:***.com/questions/33439905/… 对于那些喜欢我的人来说,有时会错过明显的东西——确保你进入$JAVA_HOME/jre/lib,而不是$JAVA_HOME/lib——我花了一些时间错过了那个细节。【参考方案3】:

我偶然发现了这个问题,该问题需要花费数小时的研究才能解决,特别是自动生成的证书,与官方证书不同,它非常棘手,Java 不太喜欢它们。

请查看以下链接:Solve Problem with certificates in Java

基本上,您必须将证书从服务器添加到 Java Home 证书。

    生成或获取您的证书并配置 Tomcat 以在 Servers.xml 中使用它 下载类InstallCert的Java源代码并在服务器运行时执行它,提供以下参数server[:port]。不需要密码,因为原始密码适用于 Java 证书(“changeit”)。 程序将连接到服务器,Java 将抛出异常,它将分析服务器提供的证书并允许您在执行程序的目录中创建一个jssecerts 文件(如果从 Eclipse 执行,则确保在Run -&gt; Configurations 中配置工作目录。 手动将该文件复制到$JAVA_HOME/jre/lib/security

执行这些步骤后,与证书的连接将不再在 Java 中生成异常。

以下源代码很重要,它从 (Sun) Oracle 博客中消失了,我发现它的唯一页面是在提供的链接上,因此我将其附在答案中以供参考。

/*
 * Copyright 2006 Sun Microsystems, Inc.  All Rights Reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 *   - Redistributions of source code must retain the above copyright
 *     notice, this list of conditions and the following disclaimer.
 *
 *   - Redistributions in binary form must reproduce the above copyright
 *     notice, this list of conditions and the following disclaimer in the
 *     documentation and/or other materials provided with the distribution.
 *
 *   - Neither the name of Sun Microsystems nor the names of its
 *     contributors may be used to endorse or promote products derived
 *     from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
 * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */
/**
 * Originally from:
 * http://blogs.sun.com/andreas/resource/InstallCert.java
 * Use:
 * java InstallCert hostname
 * Example:
 *% java InstallCert ecc.fedora.redhat.com
 */

import javax.net.ssl.*;
import java.io.*;
import java.security.KeyStore;
import java.security.MessageDigest;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;

/**
 * Class used to add the server's certificate to the KeyStore
 * with your trusted certificates.
 */
public class InstallCert 

    public static void main(String[] args) throws Exception 
        String host;
        int port;
        char[] passphrase;
        if ((args.length == 1) || (args.length == 2)) 
            String[] c = args[0].split(":");
            host = c[0];
            port = (c.length == 1) ? 443 : Integer.parseInt(c[1]);
            String p = (args.length == 1) ? "changeit" : args[1];
            passphrase = p.toCharArray();
         else 
            System.out.println("Usage: java InstallCert [:port] [passphrase]");
            return;
        

        File file = new File("jssecacerts");
        if (file.isFile() == false) 
            char SEP = File.separatorChar;
            File dir = new File(System.getProperty("java.home") + SEP
                    + "lib" + SEP + "security");
            file = new File(dir, "jssecacerts");
            if (file.isFile() == false) 
                file = new File(dir, "cacerts");
            
        
        System.out.println("Loading KeyStore " + file + "...");
        InputStream in = new FileInputStream(file);
        KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
        ks.load(in, passphrase);
        in.close();

        SSLContext context = SSLContext.getInstance("TLS");
        TrustManagerFactory tmf =
                TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
        tmf.init(ks);
        X509TrustManager defaultTrustManager = (X509TrustManager) tmf.getTrustManagers()[0];
        SavingTrustManager tm = new SavingTrustManager(defaultTrustManager);
        context.init(null, new TrustManager[]tm, null);
        SSLSocketFactory factory = context.getSocketFactory();

        System.out.println("Opening connection to " + host + ":" + port + "...");
        SSLSocket socket = (SSLSocket) factory.createSocket(host, port);
        socket.setSoTimeout(10000);
        try 
            System.out.println("Starting SSL handshake...");
            socket.startHandshake();
            socket.close();
            System.out.println();
            System.out.println("No errors, certificate is already trusted");
         catch (SSLException e) 
            System.out.println();
            e.printStackTrace(System.out);
        

        X509Certificate[] chain = tm.chain;
        if (chain == null) 
            System.out.println("Could not obtain server certificate chain");
            return;
        

        BufferedReader reader =
                new BufferedReader(new InputStreamReader(System.in));

        System.out.println();
        System.out.println("Server sent " + chain.length + " certificate(s):");
        System.out.println();
        MessageDigest sha1 = MessageDigest.getInstance("SHA1");
        MessageDigest md5 = MessageDigest.getInstance("MD5");
        for (int i = 0; i < chain.length; i++) 
            X509Certificate cert = chain[i];
            System.out.println
                    (" " + (i + 1) + " Subject " + cert.getSubjectDN());
            System.out.println("   Issuer  " + cert.getIssuerDN());
            sha1.update(cert.getEncoded());
            System.out.println("   sha1    " + toHexString(sha1.digest()));
            md5.update(cert.getEncoded());
            System.out.println("   md5     " + toHexString(md5.digest()));
            System.out.println();
        

        System.out.println("Enter certificate to add to trusted keystore or 'q' to quit: [1]");
        String line = reader.readLine().trim();
        int k;
        try 
            k = (line.length() == 0) ? 0 : Integer.parseInt(line) - 1;
         catch (NumberFormatException e) 
            System.out.println("KeyStore not changed");
            return;
        

        X509Certificate cert = chain[k];
        String alias = host + "-" + (k + 1);
        ks.setCertificateEntry(alias, cert);

        OutputStream out = new FileOutputStream("jssecacerts");
        ks.store(out, passphrase);
        out.close();

        System.out.println();
        System.out.println(cert);
        System.out.println();
        System.out.println
                ("Added certificate to keystore 'jssecacerts' using alias '"
                        + alias + "'");
    

    private static final char[] HEXDIGITS = "0123456789abcdef".toCharArray();

    private static String toHexString(byte[] bytes) 
        StringBuilder sb = new StringBuilder(bytes.length * 3);
        for (int b : bytes) 
            b &= 0xff;
            sb.append(HEXDIGITS[b >> 4]);
            sb.append(HEXDIGITS[b & 15]);
            sb.append(' ');
        
        return sb.toString();
    

    private static class SavingTrustManager implements X509TrustManager 

        private final X509TrustManager tm;
        private X509Certificate[] chain;

        SavingTrustManager(X509TrustManager tm) 
            this.tm = tm;
        

        public X509Certificate[] getAcceptedIssuers() 
            throw new UnsupportedOperationException();
        

        public void checkClientTrusted(X509Certificate[] chain, String authType)
                throws CertificateException 
            throw new UnsupportedOperationException();
        

        public void checkServerTrusted(X509Certificate[] chain, String authType)
                throws CertificateException 
            this.chain = chain;
            tm.checkServerTrusted(chain, authType);
        
    

【讨论】:

注意创建的文件是 jssecacerts! 我尝试将此解决方案用于 Java 7 和 8。在 Java 7 上运行时,我尝试使用的所有远程存储库 url 都获得了 protocol_version 或 handshake_failure。 SandeepanNath:test sandeepan.nath$ java InstallCert repo1.maven.org:443 Loading KeyStore /Library/Java/JavaVirtualMachines/jdk1.7.0_80.jdk/Contents/Home/jre/lib/security/cacerts... Opening connection to repo1.maven.org:443 ... Starting SSL handshake... javax.net.ssl.SSLException: Received fatal alert: protocol_version .. Could not obtain server certificate chain【参考方案4】:
-Dmaven.wagon.http.ssl.insecure=true -Dmaven.wagon.http.ssl.allowall=true

用于跳转证书验证。

警告 仅用于开发目的是不安全的!

【讨论】:

@gorums 如何在 Eclipse 中设置它? 除非您想冒险在您的机器上运行任意恶意代码,否则不要这样做。被否决,因为它有可能危及任何运行它的机器。 仅仅因为它“有效”并不意味着它是安全的,你让所有遵循这个建议的人都处于危险之中。投反对票 @AceKing 关键是,如果您不验证证书,它是受信任的代码。也就是说,我认为这仍然是一个有用的答案。这样做的人只需要了解风险。 @EgorHans 这相当危险,如果你采用这种方法,你就会让自己受到 MITM 攻击。证书验证的要点之一是,如果有人劫持了 URL,您*不会*搞砸,因为您知道何时会发生这种情况。【参考方案5】:
    在浏览器中转到 URL:
firefox - 单击 HTTPS 证书链(URL 地址旁边的锁定图标)。点击"more info" &gt; "security" &gt; "show certificate" &gt; "details" &gt; "export.."。选择名称并选择文件类型 example.cer chrome - 点击左侧的站点图标到地址栏中的地址,选择“证书”->“详细信息”->“导出”并以“Der-encoded binary, single certificate”格式保存。

    现在您有了带有密钥库的文件,您必须将它添加到您的 JVM。确定 cacerts 文件的位置,例如。 C:\Program Files (x86)\Java\jre1.6.0_22\lib\security\cacerts.

    接下来在命令行中将example.cer文件导入cacerts(可能需要管理员命令提示符):

keytool -import -alias example -keystore "C:\Program Files (x86)\Java\jre1.6.0_22\lib\security\cacerts" -file example.cer

你会被要求输入密码,默认是changeit

重启你的 JVM/PC。

来源: http://magicmonster.com/kb/prg/java/ssl/pkix_path_building_failed.html

【讨论】:

我必须将路径放在引号中,并将其保存为 Base64 而不是 DER 哇..它就像在 chrome 中一样神奇,您只需单击左侧地址栏上的锁定图标,然后单击 details 并且不需要重新启动 请注意,应为链中的所有证书重复说明。命令行中证书的alias 名称也应该是唯一的。 如果你家是 JDK,请确保指定 jre 位于其中:keytool -import -alias example -keystore "C:\Program Files\Java\jdk1.8.0_73\jre\ lib\security\cacerts" - 文件 example.cer 对于收到“拒绝访问”错误的任何人,请确保您以管理员身份运行命令提示符。【参考方案6】:

我在 ubuntu 15.10 上遇到了同样的问题。请尝试在本地下载插件,例如https://github.com/lmenezes/elasticsearch-kopf/archive/master.zip 并使用以下命令安装:

sudo /usr/share/elasticsearch/bin/plugin install file:/home/dev/Downloads/elasticsearch-kopf-master.zip

路径可能因您的环境而异。

问候。

【讨论】:

【参考方案7】:

对我来说,出现证书错误是因为我让 fiddler 在后台运行并且这与证书混淆了。它充当代理,如此接近并重新启动 Eclipse。

【讨论】:

同样的问题发生在 eclipse 中,即使在关闭所有应用程序之后 @Atihska 这真的解决了我的问题。谢谢你,真的很感激 同样,我忘记了 Charles Proxy 正在运行,并得到了那个错误。停止查尔斯后,一切正常。【参考方案8】:

我的用户界面方法:

    从here下载密钥库浏览器 打开 $JAVA_HOME/jre/lib/security/cacerts 输入密码:changeit(在 Mac 上可以是 changeme) 导入您的 .crt 文件

CMD-行:

    keytool -importcert -file jetty.crt -alias jetty -keystore $JAVA_HOME/jre/lib/security/cacerts 输入密码:changeit(Mac上可以换我)

【讨论】:

在 mac 上,使用 CMD-Line,应该使用 sudo 来运行命令。 # sudo keytool -importcert -file jetty.crt -alias jetty -keystore $JAVA_HOME/jre/lib/security/cacerts 在 Windows 上,该命令有效:keytool -importcert -file dinardap_cert.cer –alias dinardap –keystore “%JAVA_HOME%/jre/lib/security/cacerts” 从哪里获取证书文件?我不知道该转到哪个 URL。 jetty.com? 我通过从网络浏览器导出证书、挂锁上的上下文操作获得了证书 这似乎比从命令行工作要简单得多。【参考方案9】:

当我的系统上同时存在 JDK 和 JRE 1.8.0_112 时,我的情况略有不同。

我使用已知命令将新的 CA 证书导入[JDK_FOLDER]\jre\lib\security\cacerts

keytool -import -trustcacerts -keystore cacerts -alias <new_ca_alias> -file <path_to_ca_cert_file>

不过,我仍然收到相同的 PKIX 路径构建失败 错误。

我使用java -Djavax.net.debug=all ... &gt; debug.log 向Java CLI 添加了调试信息。在 debug.log 文件中,以 trustStore 开头的行是: 实际上指向了在 [JRE_FOLDER]\lib\security\cacerts 中找到的 cacerts 存储。

在我的情况下,解决方案是将 JDK 使用的 cacerts 文件(添加了新的 CA)复制到 JRE 使用的文件上,从而解决了问题。

【讨论】:

我使用 keytool 直接将所需的证书导入到 JRE/lib/security/cacerts 中,但它对我没有任何改变 :( 仍然出现相同的错误,我还通过 IDE 添加了它们,甚至进入类路径并添加了一个 Bean 来指定密钥库的位置!!这太疯狂了 AF!【参考方案10】:

我想为 smtp.gmail.com 导入证书。唯一对我有用的解决方案是

    输入命令查看此证书

    D:\openssl\bin\openssl.exe s_client -connect smtp.gmail.com:465
    

    -----BEGIN CERTIFICATE----------END CERTIFICATE----- 之间的行复制并保存到文件gmail.cer

    运行

    keytool -import -alias smtp.gmail.com -keystore "%JAVA_HOME%/jre/lib/security/cacerts" -file C:\Users\Admin\Desktop\gmail.cer
    

    输入密码:changeit

    点击“是”导入证书

    重启Java

现在运行命令,一切顺利。

【讨论】:

如果您在证书导入期间收到“输入不是 X.509 证书”错误消息,请确保您也复制了 BEGIN CERTIFICATE 和 END CERTIFICATE 文本。 密码是带 n 的 changeit(或 mac 上的 changeme)【参考方案11】:

我在尝试通过他们的更新站点在 Eclipse 中安装 Cucumber-Eclipse 插件时遇到了这个问题。我收到了同样的 SunCertPathBuilderException 错误:

Unable to read repository at http://cucumber.io/cucumber-eclipse/update-site/content.xml.
    Unable to read repository at http://cucumber.io/cucumber-eclipse/update-site/content.xml.
    sun.security.validator.ValidatorException: PKIX path building failed: 
   sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target

虽然其他一些答案对于这个问题的给定情况是适当的和有帮助的,但它们对我的问题没有帮助和误导。

就我而言,问题在于为他们的更新站点提供的 URL 是:

https://cucumber.io/cucumber-eclipse/update-site

但是,当通过浏览器导航到它时,它会重定向到(注意添加的“.github”):

http://cucumber.github.io/cucumber-eclipse/update-site/

所以解决方法就是在eclipse中添加更新站点的时候简单的使用重定向版本的更新站点URL。

【讨论】:

您确定您回答的问题正确吗?原始问题中没有提到黄瓜... 我觉得我是。我收到了同样的 SunCertPathBuilderException 错误,在寻找解决方案时,发现了这个问题以及this one。但是,他们都没有适合我的情况的解决方案。我并没有试图回答如何将 Cucumber-Eclipse 插件站点添加到 Eclipse 的具体问题。我想为我遇到的问题(URL 重定向)提供上下文并解释它是如何解决的。 我已经更新了我的答案,明确表示我收到了同样的错误,并指出根本问题和解决方案不同。我觉得这是有效的,因为其他人在搜索相同的错误时可能会发现这个问题。如果您认为这有意义,请考虑更改您的投票。 谢谢。让事情变得更清楚,扭转了我的反对意见 不客气!感谢您抽出宝贵时间再次审核。【参考方案12】:

添加cacerts 对我不起作用。 启用带有标志-Djavax.net.debug=all 的日志后,才知道java 从jssecacerts 读取。

导入jssecacerts终于成功了。

【讨论】:

这里缺少的解释是Java将使用jssecacerts如果存在,否则cacerts【参考方案13】:

目标:

    使用 https 连接 验证 SSL 链 不要处理 cacerts 在运行时添加证书 不要丢失来自 cacerts 的证书

怎么做:

    定义自己的密钥库 将证书放入密钥库 使用我们的自定义类重新定义 SSL 默认上下文 ??? 利润

我的 Keystore 包装文件:

public class CertificateManager 

    private final static Logger logger = Logger.getLogger(CertificateManager.class);

    private String keyStoreLocation;
    private String keyStorePassword;
    private X509TrustManager myTrustManager;
    private static KeyStore myTrustStore;

    public CertificateManager(String keyStoreLocation, String keyStorePassword) throws Exception 
        this.keyStoreLocation = keyStoreLocation;
        this.keyStorePassword = keyStorePassword;
        myTrustStore = createKeyStore(keyStoreLocation, keyStorePassword);
    

    public void addCustomCertificate(String certFileName, String certificateAlias)
            throws Exception 
        TrustManagerFactory tmf = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
        tmf.init((KeyStore) null);
        Certificate certificate = myTrustStore.getCertificate(certificateAlias);
        if (certificate == null) 
            logger.info("Certificate not exists");
            addCertificate(certFileName, certificateAlias);
         else 
            logger.info("Certificate exists");
        
        tmf = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
        tmf.init(myTrustStore);
        for (TrustManager tm : tmf.getTrustManagers()) 
            if (tm instanceof X509TrustManager) 
                setMytrustManager((X509TrustManager) tm);
                logger.info("Trust manager found");
                break;
            
        
    

    private InputStream fullStream(String fname) throws IOException 
        ClassLoader classLoader = getClass().getClassLoader();
        InputStream resource = classLoader.getResourceAsStream(fname);
        try 
            if (resource != null) 
                DataInputStream dis = new DataInputStream(resource);
                byte[] bytes = new byte[dis.available()];
                dis.readFully(bytes);
                return new ByteArrayInputStream(bytes);
             else 
                logger.info("resource not found");
            
         catch (Exception e) 
            logger.error("exception in certificate fetching as resource", e);
        
        return null;
    

    public static KeyStore createKeyStore(String keystore, String pass) throws Exception 
        try 
            InputStream in = CertificateManager.class.getClass().getResourceAsStream(keystore);
            KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType());
            keyStore.load(in, pass.toCharArray());
            logger.info("Keystore was created from resource file");
            return keyStore;
         catch (Exception e) 
            logger.info("Fail to create keystore from resource file");
        

        File file = new File(keystore);
        KeyStore keyStore = KeyStore.getInstance("JKS");
        if (file.exists()) 
            keyStore.load(new FileInputStream(file), pass.toCharArray());
            logger.info("Default keystore loaded");
         else 
            keyStore.load(null, null);
            keyStore.store(new FileOutputStream(file), pass.toCharArray());
            logger.info("New keystore created");
        
        return keyStore;
    

    private void addCertificate(String certFileName, String certificateAlias) throws CertificateException,
            IOException, KeyStoreException, NoSuchAlgorithmException 
        CertificateFactory cf = CertificateFactory.getInstance("X.509");
        InputStream certStream = fullStream(certFileName);
        Certificate certs = cf.generateCertificate(certStream);
        myTrustStore.setCertificateEntry(certificateAlias, certs);
        FileOutputStream out = new FileOutputStream(getKeyStoreLocation());
        myTrustStore.store(out, getKeyStorePassword().toCharArray());
        out.close();
        logger.info("Certificate pushed");
    

    public String getKeyStoreLocation() 
        return keyStoreLocation;
    

    public String getKeyStorePassword() 
        return keyStorePassword;
    
    public X509TrustManager getMytrustManager() 
        return myTrustManager;
    
    public void setMytrustManager(X509TrustManager myTrustManager) 
        this.myTrustManager = myTrustManager;
    

如有必要,此类将创建密钥库,并能够在其中管理证书。现在为 SSL 上下文类:

public class CustomTrustManager implements X509TrustManager 

    private final static Logger logger = Logger.getLogger(CertificateManager.class);

    private static SSLSocketFactory socketFactory;
    private static CustomTrustManager instance = new CustomTrustManager();
    private static List<CertificateManager> register = new ArrayList<>();

    public static CustomTrustManager getInstance() 
        return instance;
    

    private X509TrustManager defaultTm;

    public void register(CertificateManager certificateManager) 
        for(CertificateManager manager : register) 
            if(manager == certificateManager) 
                logger.info("Certificate manager already registered");
                return;
            
        
        register.add(certificateManager);
        logger.info("New Certificate manager registered");
    

    private CustomTrustManager() 
        try 
            String algorithm = TrustManagerFactory.getDefaultAlgorithm();
            TrustManagerFactory tmf = TrustManagerFactory.getInstance(algorithm);

            tmf.init((KeyStore) null);
            boolean found = false;
            for (TrustManager tm : tmf.getTrustManagers()) 
                if (tm instanceof X509TrustManager) 
                    defaultTm = (X509TrustManager) tm;
                    found = true;
                    break;
                
            
            if(found) 
                logger.info("Default trust manager found");
             else 
                logger.warn("Default trust manager was not found");
            

            SSLContext sslContext = SSLContext.getInstance("TLS");
            sslContext.init(null, new TrustManager[]this, null);
            SSLContext.setDefault(sslContext);
            socketFactory = sslContext.getSocketFactory();
            HttpsURLConnection.setDefaultSSLSocketFactory(socketFactory);


            logger.info("Custom trust manager was set");
         catch (NoSuchAlgorithmException | KeyManagementException | KeyStoreException e) 
            logger.warn("Custom trust manager can't be set");
            e.printStackTrace();
        
    

    @Override
    public X509Certificate[] getAcceptedIssuers() 
        List<X509Certificate> out = new ArrayList<>();
        if (defaultTm != null) 
            out.addAll(Arrays.asList(defaultTm.getAcceptedIssuers()));
        
        int defaultCount = out.size();
        logger.info("Default trust manager contain " + defaultCount + " certficates");
        for(CertificateManager manager : register) 
            X509TrustManager customTrustManager = manager.getMytrustManager();
            X509Certificate[] issuers = customTrustManager.getAcceptedIssuers();
            out.addAll(Arrays.asList(issuers));
        
        logger.info("Custom trust managers contain " + (out.size() - defaultCount) + " certficates");
        X509Certificate[] arrayOut = new X509Certificate[out.size()];
        return out.toArray(arrayOut);
    

    @Override
    public void checkServerTrusted(X509Certificate[] chain,
                                   String authType) throws CertificateException 
        for(CertificateManager certificateManager : register) 
            X509TrustManager customTrustManager = certificateManager.getMytrustManager();
            try 
                customTrustManager.checkServerTrusted(chain, authType);
                logger.info("Certificate chain (server) was aproved by custom trust manager");
                return;
             catch (Exception e) 
            
        
        if (defaultTm != null) 
            defaultTm.checkServerTrusted(chain, authType);
            logger.info("Certificate chain (server) was aproved by default trust manager");
         else 
            logger.info("Certificate chain (server) was rejected");
            throw new CertificateException("Can't check server trusted certificate.");
        
    

    @Override
    public void checkClientTrusted(X509Certificate[] chain,
                                   String authType) throws CertificateException 
        try 
            if (defaultTm != null) 
                defaultTm.checkClientTrusted(chain, authType);
                logger.info("Certificate chain (client) was aproved by default trust manager");
             else 
                throw new NullPointerException();
            
         catch (Exception e) 
            for(CertificateManager certificateManager : register) 
                X509TrustManager customTrustManager = certificateManager.getMytrustManager();
                try 
                    customTrustManager.checkClientTrusted(chain, authType);
                    logger.info("Certificate chain (client) was aproved by custom trust manager");
                    return;
                 catch (Exception e1) 
                
            
            logger.info("Certificate chain (client) was rejected");
            throw new CertificateException("Can't check client trusted certificate.");
        
    

    public SSLSocketFactory getSocketFactory() 
        return socketFactory;
    

这个类作为单例,因为只允许一个 defaultSSL 上下文。所以,现在的用法:

            CertificateManager certificateManager = new CertificateManager("C:\\myapplication\\mykeystore.jks", "changeit");
            String certificatePath = "C:\\myapplication\\public_key_for_your_ssl_service.crt";
            try 
                certificateManager.addCustomCertificate(certificatePath, "alias_for_public_key_for_your_ssl_service");
             catch (Exception e) 
                log.error("Can't add custom certificate");
                e.printStackTrace();
            
            CustomTrustManager.getInstance().register(certificateManager);

可能,它不适用于此设置,因为我将证书文件保存在资源文件夹中,所以我的路径不是绝对的。但总的来说,它工作得很好。

【讨论】:

这种对available() 的双重滥用在它自己的Javadoc 中被特别警告。【参考方案14】:

1。检查证书

尝试在浏览器中加载目标 URL 并查看站点的证书(通常可以通过带有锁定标志的图标访问。它位于浏览器地址栏的左侧或右侧)是否已过期或因其他原因不受信任。

2。安装最新版本的 JRE 和 JDK

新版本通常附带更新的可信证书集。

如果可能,请卸载旧版本。这将使错误配置错误明确。

3。检查您的配置:

检查 JAVA_HOME 环境变量指向的位置。 检查您用于运行程序的 java 版本。在 IntelliJ 检查: 文件 -> 项目结构... -> 项目设置 -> 项目 -> 项目 SDK: 文件 -> 项目结构... -> 平台设置 -> SDK

4。从新的 Java 版本复制整个密钥库

如果您在 JDK 而非最新可用的 JDK 下开发 - 尝试用最新安装的 JRE 中的新文件替换 %JAVA_HOME%/jre/lib/security/cacerts 文件(首先制作备份副本),正如 @jeremy-goodell 在他的 answer 中所建议的那样

5。将证书添加到您的密钥库

如果以上都不能解决您的问题,请使用 keytool 将证书保存到 Java 的密钥库:

keytool -trustcacerts -keystore "%JAVA_HOME%jre\lib\security\cacerts" -storepass changeit -importcert -alias <alias_name> -file <path_to_crt_file>

可以从浏览器获取带有证书的文件,正如@MagGGG 在他的answer 中所建议的那样。

注意 1:您可能需要对链中的每个证书重复此操作,以获取您站点的证书。从根目录开始。

注意 2:&lt;alias_name&gt; 在 store 中的键中应该是唯一的,否则keytool 将显示错误。

要获取商店中所有证书的列表,您可以运行:

keytool -list -trustcacerts -keystore "%JAVA_HOME%jre\lib\security\cacerts" -storepass changeit

如果出现问题,这将帮助您从商店中删除证书:

keytool -delete -alias <alias_name> -keystore "%JAVA_HOME%jre\lib\security\cacerts" -storepass changeit

【讨论】:

这句话的详尽程度应该是公认的答案。 在 Mac 上应该是 keytool -list -trustcacerts -keystore "$JAVA_HOME/jre/lib/security/cacerts" -storepass changeit 我尝试使用 LetsEncrypt 生成的证书访问网站,升级到 Java 版本 >= 8u101 解决了问题 - letsencrypt.org/docs/certificate-compatibility【参考方案15】:

我遇到了同样的问题,并使用以下简单步骤解决了它:

1) 从谷歌下载 InstallCert.java

2) 使用 javac InstallCert.java

编译

3) 使用 java InstallCert.java 运行 InstallCert.java,使用主机名和 https 端口,并在要求输入时按“1”。它将“localhost”添加为受信任的密钥库,并生成一个名为“jssecacerts”的文件,如下所示:

java InstallCert localhost:443

4) 将 jssecacerts 复制到 $JAVA_HOME/jre/lib/security 文件夹中

这里解决问题的主要来源是:

https://ankurjain26.blogspot.in/2017/11/javaxnetsslsslhandshakeexception.html

【讨论】:

链接已损坏。但它确实对我有用。【参考方案16】:

问题背景:

当我尝试在我的项目中运行 mvn clean install 并通过 Netbeans IDE clean and build 选项运行时,我遇到了以下错误。 此问题是由于当我们通过 NET beans IDE/通过命令提示符下载时证书不可用,但能够通过浏览器下载文件。

错误

Caused by: org.eclipse.aether.transfer.ArtifactTransferException: Could not transfer artifact com.java.project:product:jar:1.0.32 from/to repo-local (https://url/local-repo): sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target  

分辨率:

1.下载相关 URL 的证书:

通过“以管理员身份运行”启动 IE(否则,我们将无法下载证书) 在IE中输入url->https://url/local-repo (在我的例子中,这个 url 有一个不受信任的证书。) 点击证书错误->查看证书下载证书 选择详细信息选项卡 -> 复制到文件 -> 下一步 -> 选择“DER 编码二进制 X.509 (.CER) 将证书保存在某个位置,例如:c:/user/sheldon/desktop/product.cer 恭喜!您已成功下载该网站的证书

2。现在安装密钥库来解决问题。

运行 keytool 命令将下载的密钥库附加到 现有证书文件。 命令:在 jdk (JAVA_HOME) 的 bin 文件夹下的命令

C:\Program Files\Java\jdk1.8.0_141\jre\bin>keytool -importcert -file “C:/user/Sheldon/desktop/product.cer”-别名产品-keystore “C:/Program Files/Java/jdk1.8.0_141/jre/lib/security/cacerts”。

系统将提示您输入密码。输入密钥库密码: 再次为“信任此证书?[否]:”输入“changeit”,输入 “是”

示例命令行命令/输出:

keytool -importcert -file "C:/Users/sheldon/Desktop/product.cer" -alias product -keystore "C:/Program iles/Java/jdk1.8.0_141/jre/lib/security/cacerts"
Enter keystore password:
Trust this certificate? [no]:  yes
Certificate was added to keystore
恭喜!现在您应该已经摆脱了 Netbeans IDE 中的“PKIX 路径构建失败:sun.security.provider.certpath.SunCertPathBuilderException”错误。

【讨论】:

嗨,我按照所有步骤操作,但没有运气:( 除了 cacerts 之外,路径中还有其他证书吗?如果您还有其他的,请尝试将其添加到该证书中 感谢@Barani r,这是我的错误,我从 jre 执行命令并在我的 eclipse 中使用 JDK 无法下载证书,但在“以管理员身份运行”后运行良好。 @Baranir 我遇到了登录的麻烦(不记得我的主帐户是否通过 Facebook、Google 或 SO 链接)只是为了支持这个答案。起初它不起作用,但事实证明我缺少 -keystore 参数。各位,请不要省略 -keystore 参数。它不起作用,你会拔掉头上剩下的一些头发。除了笑话,+1 以获得可靠的答案。【参考方案17】:

这不是 Twitter 特定的答案,但这是您搜索此错误时出现的问题。如果您的系统在连接到在网络浏览器中查看时似乎具有有效证书的网站时收到此错误,这可能意味着该网站的证书链不完整 .

对于问题的简要总结:证书颁发机构不使用他们的根证书来签署任何旧证书。相反,他们(通常)签署 intermediate 证书,这些证书也设置了证书颁发机构标志(即,允许签署证书)。然后,当您从 CA 购买证书时,他们会使用这些中间证书之一签署您的 CSR。

您的 Java 信任库很可能只有根证书,而不是中间证书。

配置错误的站点可能会返回只是他们的签名证书。问题:它是使用不在您的信任库中的中间证书签名的。浏览器将通过下载或使用缓存的中间证书来处理这个问题;这最大限度地提高了网站的兼容性。然而,Java 和 OpenSSL 等工具不会。这将导致问题中的错误。

您可以使用Qualys SSL Test 验证此怀疑。如果你对一个网站运行它,它会说

此服务器的证书链不完整。

那就证实了。您还可以通过查看认证路径并查看文本 Extra Download 来了解这一点。

如何解决:服务器管理员需要配置 Web 服务器以返回中间证书。例如,对于 Comodo,这就是 .ca-bundle 文件派上用场的地方。例如,在带有 mod_ssl 的 Apache 配置中,您将使用 SSLCertificateChainFile 配置设置。对于 nginx,您需要连接中间证书和签名证书,并在 SSL 证书配置中使用它。您可以通过在线搜索“不完整的证书链”找到更多信息。

【讨论】:

你太棒了。谢谢!我的 Java 服务器的新构建出现问题,因为我忘记删除 SSLCertificateChainFile 前面的 # !!!真的很好解释。【参考方案18】:

这是答案https://***.com/a/36427118/1491414 的补充。谢谢@MagGGG

请确保您拥有管理员权限 请使用双引号作为密钥库路径 (-keystore C:\Program Files (x86)\Java\jre1.6.0_22\lib\security\cacerts"),因为在 Windows 操作系统中,默认安装位置是 Program Files 和由于程序文件之间存在空间,您将收到错误消息。

【讨论】:

谢谢,我现在将这些 cmets 添加到该答案中;)【参考方案19】:

我使用以下方法解决了这个问题-

    复制有连接问题的网址 进入android Studio->设置->Http设置 在“测试连接”中,粘贴该网址并按确定 单击确定后,Android Studio 将要求导入该证书 网址,导入它 就是这样。没有其他事情要做,我的问题就消失了。无需 也重启工作室。

【讨论】:

【参考方案20】:

当您使用 atlassian 软件前出现上述错误时。吉拉

2018-08-18 11:35:00,312 Caesium-1-4 WARN anonymous    Default Mail Handler [c.a.mail.incoming.mailfetcherservice] Default Mail Handler[10001]: javax.mail.MessagingException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target while connecting to host 'imap.xyz.pl' as user 'jira@xyz.pl' via protocol 'imaps, caused by: 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

您可以将证书添加到其受信任的密钥库中(将 missing_ca 更改为正确的证书名称):

keytool -importcert -file missing_ca.crt -alias missing_ca -keystore /opt/atlassian/jira/jre/lib/security/cacerts

如果要求输入密码,请输入changeit 并确认y

之后只需重新启动 jira。

【讨论】:

【参考方案21】:

我们得到上述错误的原因是 JDK 与许多受信任的证书颁发机构 (CA) 证书捆绑到一个名为“cacerts”的文件中,但该文件不知道我们的自签名证书。换句话说,cacerts 文件没有导入我们的自签名证书,因此不会将其视为受信任的实体,因此会出现上述错误。

How to fix the above error

要修复上述错误,我们只需将自签名证书导入 cacerts 文件即可。

首先,找到 cacerts 文件。我们需要找出 JDK 的位置。如果您通过 Eclipse 或 IntelliJ Idea 等 IDE 之一运行应用程序,请转到项目设置并找出 JDK 位置。 例如,在 Mac OS 上,cacerts 文件的典型位置是 /Library/Java/JavaVirtualMachines/ JDK_version/Contents/Home/jre/lib/security 在 Window 的机器上,它将位于 Installation_directory/JDK_version/jre/lib/security

找到 cacerts 文件后,现在我们需要将自签名证书导入此 cacerts 文件。如果不知道如何正确生成自签名证书,请查看上一篇文章。

如果您没有证书文件 (.crt) 而只有一个 .jks 文件,您可以使用以下命令生成一个 .crt 文件。如果你已经有一个 .crt/.pem 文件,那么你可以忽略下面的命令

##从密钥库(.jks 文件)生成证书####

keytool -export -keystore keystore.jks -alias selfsigned -file selfsigned.crt

以上步骤将生成一个名为 selfsigned.crt 的文件。现在将证书导入到 cacerts

现在将证书添加到 JRE/lib/security/cacerts (trustore)
keytool -importcert -file selfsigned.crt -alias selfsigned -keystore cacerts path

例如

keytool -importcert -file selfsigned.nextgen.crt -alias selfsigned.nextgen -keystore /Library/Java/JavaVirtualMachines/jdk1.8.0_171.jdk/Contents/Home/jre/lib/security/cacerts

就是这样,重新启动您的应用程序,它应该可以正常工作了。如果它仍然不起作用并获得 SSL 握手异常。这可能意味着您使用不同的域然后在证书中注册。

链接with detailed explanation and step by step resolution is over here.

【讨论】:

【参考方案22】:

如果您的存储库 URL 也适用于 HTTP 并且安全性不是问题,您可以转到 settings.xml(通常但不总是位于 %USERPROFILE%/.m2)和 对于 &lt;repository&gt;&lt;pluginRepository&gt; URL,将 HTTPS 替换为 HTTP

例如,这个:

<repository>
    <snapshots>
        <enabled>false</enabled>
    </snapshots>
    <id>central</id>
    <name>libs-release</name>
    <url>https://<artifactory>/libs-release</url>
</repository>

应该替换为:

<repository>
    <snapshots>
        <enabled>false</enabled>
    </snapshots>
    <id>central</id>
    <name>libs-release</name>
    <url>https://<artifactory>/libs-release</url>
</repository>

【讨论】:

【参考方案23】:

我通过传递 arg -Djavax.net.ssl.trustStore= 使用自己的信任库而不是 JRE

无论信任库中的证书如何,我都会收到此错误。对我来说,问题是在 arg 行上传递的属性的顺序。 当我输入 -Djavax.net.ssl.trustStore=& -Djavax.net.ssl.trustStorePassword= before -Dspring.config.location= & -jar args 时,我能够通过 https 成功调用我的休息电话。

【讨论】:

当我试图弄清楚如何让 maven 正常运行时,这对我有用。 -"Djavax.net.ssl.trustStore"=&lt;path&gt; 是我所需要的。谢谢。【参考方案24】:

如果您正在使用 CloudFoundry 并遇到证书问题,那么您必须确保再次推送带有证书的密钥库服务的 jar。简单地解除绑定、绑定和重启是行不通的。

【讨论】:

【参考方案25】:

如果您的 主机位于防火墙/代理后面,请在 cmd 中使用以下命令:

keytool -J-Dhttps.proxyHost=<proxy_hostname> -J-Dhttps.proxyPort=<proxy_port> -printcert -rfc -sslserver <remote_host_name:remote_ssl_port>

&lt;proxy_hostname&gt;&lt;proxy_port&gt; 替换为配置的HTTP 代理服务器。将&lt;remote_host_name:remote_ssl_port&gt; 替换为存在认证问题的远程主机(基本上是url)和端口之一。

将最后打印的证书内容复制并复制(同时复制开始和结束证书)。将其粘贴到文本文件中并为其提供 .crt 扩展名。现在使用 java keytool 命令将此证书导入 cacerts,它应该可以工作了。

keytool -importcert -file <filename>.crt -alias randomaliasname -keystore %JAVA_HOME%/jre/lib/security/cacerts -storepass changeit

【讨论】:

这篇文章真的拯救了我的一天。在通过添加代理详细信息对上述设置进行调整之前,我无法解决该问题。像冠军一样工作。【参考方案26】:

尝试复制 java cacerts:

cp /usr/lib/jvm/java-1.8.0-openjdk-1.8.0.172-9.b11.fc28.x86_64/jre/lib/security/cacerts $JAVA_HOME/jre/lib/security/cacerts

【讨论】:

【参考方案27】:

如果您在 Java 应用程序尝试与另一个应用程序/站点通信时在 linux 容器中看到此问题,那是因为证书被错误地导入到负载均衡器中。导入证书需要遵循一系列步骤,如果没有正确完成,您将看到类似

的问题
Caused by: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid 
certification path to requested target

一旦正确导入证书,就应该这样做。无需修改任何 JDK 证书。

【讨论】:

【参考方案28】:

这是一个解决方案,但以我遇到此问题的故事的形式:

尝试上面给出的所有解决方案(3天)我几乎死了,但对我没有任何效果。

我失去了所有希望。

我就此事联系了我的安全团队,因为我使用了代理,他们告诉他们最近更新了他们的安全政策。

我骂他们没通知开发者。

后来他们发布了一个新的“cacerts”文件,其中包含所有证书。

我删除了 %JAVA_HOME%/jre/lib/security 中的 cacerts 文件,它解决了我的问题。

因此,如果您遇到此问题,您的网络团队可能也会这样。

【讨论】:

【参考方案29】:

下载证书文件,并按照以下命令使用证书文件更新密钥库。

sudo keytool -importcert -alias “aws2” -file ~/Desktop/*aws.crt -keystore /Library/java/JavaVirtualMachines/jdk1.8.0_131.jdk/Contents/Home/jre/lib/security/cacerts

【讨论】:

【参考方案30】:

我为 Intellij Idea 解决了这个问题 我面临这个问题Alhouh,我改变了很多地方来解决问题。我找到了一个解决方案。右键单击你的项目,你会看到Maven,然后按Generate Sources And Update文件夹重新导入

完成了。

【讨论】:

以上是关于“PKIX 路径构建失败”和“无法找到请求目标的有效证书路径”的主要内容,如果未能解决你的问题,请参考以下文章

PKIX 路径构建失败:

获取 sbt 插件时“PKIX 路径构建失败”和“无法找到请求目标的有效认证路径”

PKIX 路径构建失败:我将证书添加到 carcert 仍然失败

PKIX 路径构建失败:wso2 oauth

SSLHandshakeException:PKIX 路径构建失败

PKIX 路径构建失败:无法找到请求目标的有效证书路径