Java向指定URL发送请求出现net.ssl.SSLHandshakeException: PKIX path building failed异常
作者:互联网
1 Java在做向指定 Url 发送 get 请求时报错
1.1 异常信息:javax.net.ssl.SSLHandshakeException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
2 原因分析
1. 网上搜的:google发现stackoverflow上不少人反应,twitter和新浪微博的api也会报这个异常,不少人反映客户端需要导入证书,其实大可不必,如果要导证书的话,用户不得哭了。。
2. 我是做WebSSO单点登录,要调到统一授权页面获取Xml信息,获取结果的时候报的错。
3. 用的第一种方式发送get请求,报这个错误!!!
/** * 向指定的地址发送get请求 * * @param url * @return */ public static String getRequest(String url) { try { URL urlObj = new URL(url); URLConnection connection = urlObj.openConnection(); InputStream is = connection.getInputStream(); byte[] b = new byte[1024]; int len; StringBuilder sb = new StringBuilder(); while ((len = is.read(b)) != -1) { sb.append(new String(b, 0, len)); } return sb.toString(); } catch (Exception e) { e.printStackTrace(); } return null; }
3. 换一种发送get请求,还是报这个错误!!!
添加项目依赖
<dependency> <groupId>org.apache.httpcomponents</groupId> <artifactId>httpclient</artifactId> <version>4.5.13</version> </dependency>
测试方法
import java.io.IOException; import org.apache.http.HttpEntity; import org.apache.http.client.ClientProtocolException; import org.apache.http.client.methods.CloseableHttpResponse; import org.apache.http.client.methods.HttpGet; import org.apache.http.impl.client.CloseableHttpClient; import org.apache.http.impl.client.HttpClients; import org.apache.http.util.EntityUtils; public class SendGetRequest { public static void main(String[] args) throws IOException { // 向url发送GET请求 String url = ""; CloseableHttpClient httpClient = HttpClients.createDefault(); try { HttpGet httpGet = new HttpGet(url); CloseableHttpResponse httpResponse = httpClient.execute(httpGet); try { System.out.println(httpResponse.getStatusLine()); HttpEntity httpEntity = httpResponse.getEntity(); // 添加处理返回数据的代码 // 例如将返回的数据转换为字符串并输出 System.out.println(EntityUtils.toString(httpEntity)); EntityUtils.consume(httpEntity); } finally { httpResponse.close(); } } catch (ClientProtocolException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } finally { httpClient.close(); } } }
3 解决方法
3.1 我的可能是单点登录统一授权的url有限制出现的问题,朋友们可以试下上面两种请求方式
3.2 手动导入证书到本地证书库(不推荐)
可以参考 导入证书
3.3 调整发生请求的代码,信任所有证书
1. trustAllHosts 该方法放任所以请求,不在校验时候有证书
/** * Trust every server - dont check for any certificate */ private static void trustAllHosts() { final String TAG = "trustAllHosts"; // Create a trust manager that does not validate certificate chains TrustManager[] trustAllCerts = new TrustManager[]{new X509TrustManager() { public X509Certificate[] getAcceptedIssuers() { return new X509Certificate[]{}; } public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException { } public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { } }}; // Install the all-trusting trust manager try { SSLContext sc = SSLContext.getInstance("TLS"); sc.init(null, trustAllCerts, new java.security.SecureRandom()); HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory()); } catch (Exception e) { e.printStackTrace(); } }
2. https.setHostnameVerifier(DO_NOT_VERIFY); 表示信任所有的证书
final static HostnameVerifier DO_NOT_VERIFY = new HostnameVerifier() { public boolean verify(String hostname, SSLSession session) { return true; } };
3. 发送请求的代码
/** * 向指定的地址发送get请求忽略证书 * * @param httpUrl * @return */ public static String httpGet(String httpUrl) { BufferedReader input = null; StringBuilder sb = null; URL url = null; HttpURLConnection con = null; try { url = new URL(httpUrl); trustAllHosts(); HttpsURLConnection https = (HttpsURLConnection) url.openConnection(); if (url.getProtocol().toLowerCase().equals("https")) { https.setHostnameVerifier(DO_NOT_VERIFY); con = https; } else { con = (HttpURLConnection) url.openConnection(); } input = new BufferedReader(new InputStreamReader(con.getInputStream())); sb = new StringBuilder(); String s; while ((s = input.readLine()) != null) { sb.append(s).append("\n"); } } catch (Exception e1) { e1.printStackTrace(); } finally { // close buffered if (input != null) { try { input.close(); } catch (IOException e) { e.printStackTrace(); } } // disconnecting releases the resources held by a connection so they may be closed or reused if (con != null) { con.disconnect(); } } return sb == null ? null : sb.toString(); } final static HostnameVerifier DO_NOT_VERIFY = new HostnameVerifier() { public boolean verify(String hostname, SSLSession session) { return true; } }; /** * Trust every server - dont check for any certificate */ private static void trustAllHosts() { final String TAG = "trustAllHosts"; // Create a trust manager that does not validate certificate chains TrustManager[] trustAllCerts = new TrustManager[]{new X509TrustManager() { public X509Certificate[] getAcceptedIssuers() { return new X509Certificate[]{}; } public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException { } public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { } }}; // Install the all-trusting trust manager try { SSLContext sc = SSLContext.getInstance("TLS"); sc.init(null, trustAllCerts, new java.security.SecureRandom()); HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory()); } catch (Exception e) { e.printStackTrace(); } }
4. 完整的工具类代码
package http; import javax.net.ssl.*; import java.io.*; import java.net.HttpURLConnection; import java.net.URL; import java.net.URLConnection; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; /** * 向url发送请求 */ public class SendRequestUtil { /** * 向指定的地址发送get请求 * * @param url * @return */ public static String getRequest(String url) { try { URL urlObj = new URL(url); URLConnection connection = urlObj.openConnection(); InputStream is = connection.getInputStream(); byte[] b = new byte[1024]; int len; StringBuilder sb = new StringBuilder(); while ((len = is.read(b)) != -1) { sb.append(new String(b, 0, len)); } return sb.toString(); } catch (Exception e) { e.printStackTrace(); } return null; } /** * 向指定的地址发送post请求 * * @param url url * @param data 参数 * @return */ public static String postRequest(String url, String data) { try { URL urlObj = new URL(url); URLConnection connection = urlObj.openConnection(); // 发送数据,把状态设置为可发送 connection.setDoOutput(true); // 获取输出流 OutputStream os = connection.getOutputStream(); os.write(data.getBytes()); os.close(); InputStream is = connection.getInputStream(); byte[] b = new byte[1024]; int len; StringBuilder sb = new StringBuilder(); while ((len = is.read(b)) != -1) { sb.append(new String(b, 0, len)); } return sb.toString(); } catch (Exception e) { e.printStackTrace(); } return null; } /** * 向指定的地址发送get请求忽略证书 * * @param httpUrl * @return */ public static String httpGet(String httpUrl) { BufferedReader input = null; StringBuilder sb = null; URL url = null; HttpURLConnection con = null; try { url = new URL(httpUrl); trustAllHosts(); HttpsURLConnection https = (HttpsURLConnection) url.openConnection(); if (url.getProtocol().toLowerCase().equals("https")) { https.setHostnameVerifier(DO_NOT_VERIFY); con = https; } else { con = (HttpURLConnection) url.openConnection(); } input = new BufferedReader(new InputStreamReader(con.getInputStream())); sb = new StringBuilder(); String s; while ((s = input.readLine()) != null) { sb.append(s).append("\n"); } } catch (Exception e1) { e1.printStackTrace(); } finally { // close buffered if (input != null) { try { input.close(); } catch (IOException e) { e.printStackTrace(); } } // disconnecting releases the resources held by a connection so they may be closed or reused if (con != null) { con.disconnect(); } } return sb == null ? null : sb.toString(); } final static HostnameVerifier DO_NOT_VERIFY = new HostnameVerifier() { public boolean verify(String hostname, SSLSession session) { return true; } }; /** * Trust every server - dont check for any certificate */ private static void trustAllHosts() { final String TAG = "trustAllHosts"; // Create a trust manager that does not validate certificate chains TrustManager[] trustAllCerts = new TrustManager[]{new X509TrustManager() { public X509Certificate[] getAcceptedIssuers() { return new X509Certificate[]{}; } public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException { } public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { } }}; // Install the all-trusting trust manager try { SSLContext sc = SSLContext.getInstance("TLS"); sc.init(null, trustAllCerts, new java.security.SecureRandom()); HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory()); } catch (Exception e) { e.printStackTrace(); } } }SendRequestUtil
标签:building,Java,String,url,return,failed,new,null,public 来源: https://www.cnblogs.com/liyhbk/p/15986458.html