在Java中请求URL时忽略证书错误

我正在尝试打印一个URL(根本没有涉及浏览器),但URL目前正在抛出以下内容:

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 

我使用JEditorPane的setPage方法调用URL,该方法仅将URL作为参数。 假设我无法更改任何服务器端,我仍然需要访问此资源,我将如何忽略证书错误(或其他让我达到目标的东西)?

通过浏览器访问此URL告诉我该网站不受信任,并询问我是否要继续。

扩展JEditorPane以覆盖getStream()方法。

在该方法中,您可以打开URLConnection 。 测试它是否是HttpsURLConnection 。 如果是,请使用不执行任何检查的自定义X509TrustManager 初始化您自己的SSLContext 。 获取上下文的SSLSocketFactory并将其设置为连接的套接字工厂 。 然后从连接返回InputStream

这将破坏运行时保护用户免受恶意软件欺骗站点攻击的任何尝试。 如果这真的是你想要的……

这可能是因为您的密钥库中用于访问目标HTTPS URL的证书与来自服务器的证书不匹配。

您需要将证书导入JVM的密钥库。 获取密钥库证书以访问此URL,然后使用导入到主密钥库

keytool -importkeystore -srckeystore /path/to/custom/keystore -destkeystore $JAVA_HOME/jre/lib/security/cacerts

假设您使用的是$JAVA_HOME Java

我会用erickson解决方案。
另一种方法是将服务器的证书(可能是自签名的)添加到您的可信证书KeyStore(我会在您的测试环境中进行)。
使用:

 java InstallCert YourHost 

创建一个jssecacerts文件,然后将其复制到以下文件夹:

 $JAVA_HOME/jre/lib/security 

如果它与您每次都要联系的服务器相同,则可以通过将其添加到信任存储区来简单地信任该证书。 我不会将其添加到默认的cacerts文件中,但您可以创建自己的密钥库并通过javax.net.ssl.trustStore系统属性指定它。

最后,如果你想完全禁用PKIX检查(只有当你明白这会危及安全性时才会这样做),唯一的办法就是像erickson所建议的那样实现你自己的SSL上下文和信任管理器。

在相关的说明:我与WCF .net Web服务的相互认证身份validation导致我的测试环境出现问题。 我将这两行添加到我的代码中以解决问题并允许我解决问题:

 //Uncomment this in case server demands some unsafe operations System.setProperty("sun.security.ssl.allowUnsafeRenegotiation", "true"); //this command allowed me to see the detailed debugger log for detecting the //issue with my certs. System.setProperty("javax.net.debug","all"); 

以下是在Java / Windows / Unix世界中处理SSL协商和证书的好参考: 传输层安全性(TLS)重新协商问题自述文件