Java 如何忽略自签名证书并消除对等未验证错误

Java 如何忽略自签名证书并消除对等未验证错误,java,apache-httpclient-4.x,self-signed,Java,Apache Httpclient 4.x,Self Signed,我试图向使用自签名证书的服务器发送Https Post请求,但收到一个异常,错误为:未通过身份验证的对等方 我在谷歌上搜索,发现问题的原因是服务器使用的是自签名的Certficate。我怎样才能消除这个错误 我正在使用以下功能发送post请求: public String sendPost(final String request, final String postData) throws ClientProtocolException, IOException { String r

我试图向使用自签名证书的服务器发送Https Post请求,但收到一个异常,错误为:
未通过身份验证的对等方

我在谷歌上搜索,发现问题的原因是服务器使用的是自签名的Certficate。我怎样才能消除这个错误

我正在使用以下功能发送post请求:

public String sendPost(final String request, final String postData) throws ClientProtocolException, IOException  {
    String result = null;
    CloseableHttpClient httpclient = HttpClients.createDefault();
    HttpPost httpPost = new HttpPost(request);
    ByteArrayEntity postDataEntity = new ByteArrayEntity(postData.getBytes());
    httpPost.setEntity(postDataEntity);
    CloseableHttpResponse response = httpclient.execute(httpPost);
    try {
        HttpEntity entity = response.getEntity();
        result = EntityUtils.toString(entity);
        EntityUtils.consume(entity);
    } finally {
        response.close();
    }
    return result;

}
我错过了什么来消除这个错误?我不想尝试捕捉这个异常。 我想正确配置它,以便接受自签名证书。我正在使用 Httpclient 4.1


谢谢大家!

您可以在web上找到关于这个问题的许多答案(包括ufk的答案),这些答案都是有效的,但根本不安全,因为它们完全忽略了自签名服务器证书

public String sendPost(final String request, final String postData) throws ClientProtocolException, IOException, NoSuchAlgorithmException, KeyManagementException  {
    String result = null;
    SSLContext sslContext = SSLContext.getInstance("SSL");

    // set up a TrustManager that trusts everything
    sslContext.init(null, new TrustManager[] { new X509TrustManager() {
                public X509Certificate[] getAcceptedIssuers() {
                        System.out.println("getAcceptedIssuers =============");
                        return null;
                }

                public void checkClientTrusted(X509Certificate[] certs,
                                String authType) {
                        System.out.println("checkClientTrusted =============");
                }

                public void checkServerTrusted(X509Certificate[] certs,
                                String authType) {
                        System.out.println("checkServerTrusted =============");
                }
    } }, new SecureRandom());

    CloseableHttpClient httpclient = HttpClients.custom().setSSLSocketFactory(new SSLSocketFactory(sslContext)).build();
    HttpPost httpPost = new HttpPost(request);
    ByteArrayEntity postDataEntity = new ByteArrayEntity(postData.getBytes());
    httpPost.setEntity(postDataEntity);
    CloseableHttpResponse response = httpclient.execute(httpPost);
    try {
        HttpEntity entity = response.getEntity();
        result = EntityUtils.toString(entity);
        EntityUtils.consume(entity);
    } finally {
        response.close();
    }
    return result;

}
这消除了SSL连接的许多好处,并使您面临中间人攻击

您可能想做的是信任特定的自签名服务器证书,而不是盲目地接受任何服务器证书

关键是在创建SSL上下文时将服务器证书链的副本放入信任存储中


这样做的代码有点太长,无法在这里发布,但碰巧的是,我正在写一篇关于在Android上这样做的博客文章。博客文章尚未发布,但示例代码可在上获得。

询问应该使用哪些特定的导入/jar来编译上述内容是否错误?