忽略Apache HTTPClient 4.5中的自签名证书 [英] Ignore self-signed certificates in Apache HTTPClient 4.5

查看:285
本文介绍了忽略Apache HTTPClient 4.5中的自签名证书的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试使用 Apache HTTPClient 4.5版 接受所有证书和/或接受自签名证书(教程链接这里

I am trying to accept all certificates, and/or accept self-signed certificates using Apache HTTPClient version 4.5 (tutorial link here)

我'已经从SO上的一堆帖子中解决了这个问题。到目前为止,他们都没有工作过。

I've been going through solutions to this problem from a bunch of posts on SO. So far none of them have worked.

我一直收到此错误: 尝试执行请求时出错。 javax.net.ssl.SSLHandshakeException:握手期间远程主机关闭连接

I keep getting this error: Error while trying to execute request. javax.net.ssl.SSLHandshakeException: Remote host closed connection during handshake

Apache Docs:

Apache Docs:

  • Apache v4.5 tutorial
  • SSL/TLS customization
  • Apache has a guide for version 3, but not version 4.

相关StackOverflow问题 - 以下是我尝试过的解决方案的一些链接:

Related StackOverflow Questions - Here's some links of the solutions I've tried:

  • Ignoring SSL certificate in Apache HttpClient 4.3
  • How to ignore SSL certificate errors in Apache HttpClient 4.0
  • Ignore SSL Certificate Errors with Java
  • Need to trust all the certificates during the development using Spring
  • How to handle invalid SSL certificates with Apache HttpClient?

请注意这些例子我也传递了我之前定义的cookie存储和代理凭证提供程序。这些都有效,我只是想添加SSL支持。

Note that in all these examples I am also passing a cookie store and a proxy credentials provider that I defined earlier. These are working, I'm just trying to add SSL support.

创建我自己的带有 SSLContextBuilder 的ssl上下文,并信任所有使用 TrustSelfSignedStrategy 的自签名策略。

Create my own ssl context with SSLContextBuilder and trust all self signed strategies with TrustSelfSignedStrategy.

SSLContextBuilder sshbuilder = new SSLContextBuilder();
sshbuilder.loadTrustMaterial(null, new TrustSelfSignedStrategy());
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sshbuilder.build());

CloseableHttpClient httpclient = HttpClients.custom()
    .setDefaultCredentialsProvider(credsProvider)
    .setDefaultCookieStore(cookieStore)
    .setSSLSocketFactory(sslsf)
    .build();

结果:没有用。得到尝试执行请求时出错。 javax.net.ssl.SSLHandshakeException:握手期间远程主机关闭连接

与上述相同,但添加 PoolingHttpClientConnectionManager

SSLContextBuilder builder = new SSLContextBuilder();
builder.loadTrustMaterial(null, new TrustSelfSignedStrategy());
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(builder.build(),SSLConnectionSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
Registry<ConnectionSocketFactory> registry = RegistryBuilder.<ConnectionSocketFactory>create()
        .register("http", new PlainConnectionSocketFactory())
        .register("https", sslsf)
        .build();
PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager(registry);
cm.setMaxTotal(2000);//max connection

CloseableHttpClient httpclient = HttpClients.custom()
    .setDefaultCredentialsProvider(credsProvider)
    .setDefaultCookieStore(cookieStore)
    .setSSLSocketFactory(sslsf)
    .setConnectionManager(cm)
    .build();

结果:没有用。得到尝试执行请求时出错。 javax.net.ssl.SSLHandshakeException:握手期间远程主机关闭连接

通过覆盖 TrustStrategy 简单接受所有证书(不建议这样做)

Simply accept ALL certificates by overriding the TrustStrategy (this is not recommended)

SSLContextBuilder builder = new SSLContextBuilder();
builder.loadTrustMaterial(null, new TrustStrategy() {
    @Override
    public boolean isTrusted(X509Certificate[] chain, String authType) throws CertificateException {
        return true;
    }
});
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(builder.build(),
    SSLConnectionSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);

CloseableHttpClient httpclient = HttpClients.custom()
    .setDefaultCredentialsProvider(credsProvider)
    .setDefaultCookieStore(cookieStore)
    .setSSLSocketFactory(sslsf)
    .build();

结果:没有用。得到尝试执行请求时出错。 javax.net.ssl.SSLHandshakeException:握手期间远程主机关闭连接

我在此答案中找到了有用的内容:

I found something useful from this answer:


从版本4.5开始,HttpClient禁用SSLv3协议版本
默认

As of version 4.5 HttpClient disables SSLv3 protocol version by default

这是他的解决方案给出:

Here's the solution he gave:

SSLContext sslcontext = SSLContexts.createSystemDefault();
SSLConnectionSocketFactory sslConnectionSocketFactory = new SSLConnectionSocketFactory(
        sslcontext, new String[] { "TLSv1", "SSLv3" }, null,
        SSLConnectionSocketFactory.getDefaultHostnameVerifier());

Registry<ConnectionSocketFactory> socketFactoryRegistry = RegistryBuilder.<ConnectionSocketFactory>create()
        .register("http", PlainConnectionSocketFactory.INSTANCE)
        .register("https", sslConnectionSocketFactory)
        .build();
PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager(socketFactoryRegistry);

httpclient = HttpClients.custom()
    .setDefaultCredentialsProvider(credsProvider)
    .setDefaultCookieStore(cookieStore)
    .setSSLSocketFactory(sslConnectionSocketFactory)
    .setConnectionManager(cm)
    .build();

结果:没有用。得到尝试执行请求时出错。 javax.net.ssl.SSLHandshakeException:握手期间远程主机关闭连接

推荐答案

以上之一在自签名证书的情况下,方法应该有效,但奇怪的是你在所有方法中都得到相同的异常。

One of the above approaches should work in case of self-signed certificates, but the weird thing is you are getting same exception in all the approaches.

我在SSL会话建立或握手协议中感觉到客户端或服务器不接受。

I feel during SSL session establishment or handshaking protocol is not being accepted either by client or by server.

这里最好的解决方案是调试应用程序。

The best solution here is to debug the application.

如果是tomcat,添加 - setenv.sh或setenv.bat文件中的Djavax.net.debug = all ,然后重新启动服务器。

In case of tomcat, add -Djavax.net.debug=all in setenv.sh or setenv.bat files and then restart the server.

或者你可以关注本教程

当连接到SSL时,OP只需更改端口:

The OP just needed to change the port when connecting to SSL:

//For HTTPS
HttpHost httpstarget = new HttpHost("mysite.com", 443, "https");

//For HTTP
HttpHost httptarget = new HttpHost("mysite.com", 80, "http");

这篇关于忽略Apache HTTPClient 4.5中的自签名证书的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆