在大多数情况下,服务器所使用的根证书是自签名的,或者签名机构不在设备的信任证书列表中,这样使用httpclient进行https连接就会失败。解决这个问题的办法有两种,一是在发起https连接之前将服务器证书加到httpclient的信任证书列表中,这个相对来说比较复杂一些,很容易出错;另一种办法是让httpclient信任所有的服务器证书,这种办法相对来说简单很多,但安全性则差一些,但在某些场合下有一定的应用场景。这里要说明的就是后一种方法:
image.pngpublic class HttpsTest {
public static void test(Context context)throws Exception {
SSLContext sslContext = SSLContext.getInstance("TLS");
sslContext.init(null,new TrustManager[]{TRUST_ALL_MANAGER},null);
//ssl socket工厂创建socket
SSLSocketFactory socketFactory = sslContext.getSocketFactory();
SSLSocket socket = (SSLSocket) socketFactory.createSocket("www.12306.cn", 443);
doHttps(socket);
}
static void doHttps(Socket socket)throws Exception {
//接受数据的输入流
final BufferedReader br =new BufferedReader(new InputStreamReader(socket.getInputStream()));
//发送数据 输出流
BufferedWriter bw =new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
new Thread() {
public void run() {
while (true) {
String line =null;
try {
while ((line =br.readLine()) !=null) {
System.out.println("recv :" + line);
}
}catch (IOException e) {
e.printStackTrace();
}
}
}
}.start();
bw.write("GET / HTTP/1.1\r\n");
bw.write("Host: www.12306.cn\r\n\r\n");
bw.flush();
}
// 重写trust manager 忽略证书
private static final TrustManager TRUST_ALL_MANAGER =new X509TrustManager() {
@Override
public void checkClientTrusted(java.security.cert.X509Certificate[] arg0, String arg1)
throws CertificateException {
// TODO Auto-generated method stub
}
@Override
public void checkServerTrusted(java.security.cert.X509Certificate[] arg0, String arg1)
throws CertificateException {
// TODO Auto-generated method stub
}
@Override
public java.security.cert.X509Certificate[]getAcceptedIssuers() {
// TODO Auto-generated method stub
return null;
}
};
}
网友评论