Java http SSL连接(双向认证)及共享Cookie方法
2017-03-29 本文已影响723人
flow__啊
SSL是什么
百度、谷歌自己搜吧,你以为我会在这里告诉你?
安全套接字(Secure Socket Layer,SSL)协议是Web浏览器与Web服务器之间安全交换信息的协议,提供两个基本的安全服务:鉴别与保密。
SSL是Netscape于1994年开发的,后来成为了世界上最著名的web安全机制,所有主要的浏览器都支持SSL协议。
目前有三个版本:2、3、3.1,最常用的是第3版,是1995年发布的。
SSL协议的三个特性
1 保密:在握手协议中定义了会话密钥后,所有的消息都被加密。
2 鉴别:可选的客户端认证,和强制的服务器端认证。
3 完整性:传送的消息包括消息完整性检查(使用MAC)。
SSL的位置
SSL介于应用层和TCP层之间。应用层数据不再直接传递给传输层,而是传递给SSL层,SSL层对从应用层收到的数据进行加密,并增加自己的SSL头。
** 这里是HTTP封装过的,不是直接操作的socket**
//封装操作
SSLContext sslcontext = SSLContexts
.custom()
.loadTrustMaterial(trustStore, new TrustSelfSignedStrategy()) //加载本地信任证书 信任自签名策略
.loadKeyMaterial(clientStore, "123456".toCharArray()) //加载本地证书
.build(); //构造
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslcontext); //制造一个socket
httpclient = HttpClients.custom().setSSLSocketFactory(sslsf).build(); //通过这个socket来生成一个http请求
// 创建http请求(get方式) delete put 全都有相应的方法
//共享一个cookie
HttpGet httpget = new HttpGet(url1);
HttpGet httpget2 = new HttpGet(url2);
//先上gradle配置
compile 'org.apache.httpcomponents:httpclient:4.5.2'
// https://mvnrepository.com/artifact/org.json/json
compile group: 'org.json', name: 'json', version: '20160810'
compile group: 'javax.mail', name: 'mail', version: '1.4.7'
compile group: 'org.bouncycastle', name: 'bcprov-jdk15on', version: '1.54'
compile group: 'org.bouncycastle', name: 'bcpkix-jdk15on', version: '1.54'
compile 'commons-codec:commons-codec:1.10'
testCompile group: 'junit', name: 'junit', version: '4.11'
//调用
String url1 = "https://mail.koal.com";
String url2 = "https://mail.koal.com/userMail!queryMailList.do?currentFolder.folderId=10";
//如果不想在操作COOKIE,就这么写
// url1为登录
// url2为拉取列表
//两次请求共用一个cookie
Getmail.ssl(url1, url2);
//两次请求用一个 cookieStore
// Getmail.ssl1(url1);
// Getmail.ssl2(url2);
import org.apache.http.HttpEntity;
import org.apache.http.ParseException;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.conn.ssl.TrustSelfSignedStrategy;
import org.apache.http.impl.client.BasicCookieStore;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.ssl.SSLContexts;
import org.apache.http.util.EntityUtils;
import org.json.JSONException;
import week4a.Certool.PfxHelper;
import week4a.utils.StringUtil;
import javax.net.ssl.SSLContext;
import java.io.FileInputStream;
import java.io.IOException;
import java.security.*;
import java.security.cert.CertificateException;
/**
* Created by Administrator on 2017/3/22.
*/
public class Getmail {
/**
* 进行一次SSL操作,两次请求,共享一个Cookie
* 进行两次SSL操作,一次次SSL,共享一个Cookie
* 列出SSl
* @param url1 第一个Url操作
* @param url2 第二个Url操作
* @return
* @throws UnrecoverableKeyException
* @throws CertificateException
* @throws IOException
* @throws KeyStoreException
* @throws NoSuchAlgorithmException
* @throws KeyManagementException
*/
public static String ssl(String url1, String url2) throws UnrecoverableKeyException, CertificateException, IOException, KeyStoreException, NoSuchAlgorithmException, KeyManagementException {
CloseableHttpClient httpclient = null;
KeyStore trustStore = KeyStore.getInstance(KeyStore.getDefaultType());
//需要证书二
//需要证书密码 123456
//CLIENT_CERT_PATH="E://证书/刘xx2.pfx";
KeyStore clientStore = PfxHelper.getKeyStore(StringUtil.CLIENT_CERT_PATH, StringUtil.CLIENT_KEY_STORE_PASSWORD);
// TKCLIENT_PATH= "D:/tkclient.jks";
// ------> 载入服务器端的keyStore TKCLIENT_PATH= "D:/tkclient.jks";
FileInputStream servlet_instream = new FileInputStream(StringUtil.TKCLIENT_PATH);
// 加载客户端和服务器的keyStore D:/kclient.jks
trustStore.load(servlet_instream, "123456".toCharArray());
servlet_instream.close();
// 相信自己的CA和所有自签名的证书
// 载入服务器端的keyStore TKCLIENT_PATH= "D:/tkclient.jks"; <------
// 相信自己的CA和所有自签名的证书 一个SSL 流~~~
SSLContext sslcontext = SSLContexts
.custom()
.loadTrustMaterial(trustStore, new TrustSelfSignedStrategy()) //加载本地信任证书 信任自签名策略
.loadKeyMaterial(clientStore, "123456".toCharArray()) //加载本地证书
.build(); //构造
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslcontext); //制造一个socket
httpclient = HttpClients.custom().setSSLSocketFactory(sslsf).build(); //通过这个socket来生成一个http请求
// 创建http请求(get方式) delete put 全都有相应的方法
//共享一个cookie
HttpGet httpget = new HttpGet(url1);
HttpGet httpget2 = new HttpGet(url2);
//读 第一次请求内容
System.out.println("executing request" + httpget.getRequestLine());
CloseableHttpResponse response = httpclient.execute(httpget);
//读 第二次请求内容
System.out.println("executing request2" + httpget2.getRequestLine());
CloseableHttpResponse response2 = httpclient.execute(httpget2);
//EntityUtils对象是org.apache.http.util下的一个工具类,用官方的解释是为HttpEntity对象提供的静态帮助类
HttpEntity entity = response2.getEntity();
System.out.println("----------------------------------------");
System.out.println(response2.getStatusLine());
if (entity != null) {
// System.out.println("Response content length: " + entity.getContentLength());
String re=EntityUtils.toString(entity, "GBK");
System.out.println(re);
EntityUtils.consume(entity);
return re;
}
response.close();
response2.close();
httpclient.close();
return null;
}
//分两次,共享cookie
// public static String CookieID = null;
//两次操作共享一个cookie
public static BasicCookieStore cookieStore = new BasicCookieStore();
/**
* HttpClient连接SSL
*
* @throws UnrecoverableKeyException
* @throws JSONException
*/
public static void ssl1(String url) throws Exception {
CloseableHttpClient httpclient = null;
try {
KeyStore trustStore = KeyStore.getInstance(KeyStore.getDefaultType());
//需要证书二
//需要证书密码 123456
//CLIENT_CERT_PATH="E://证书/刘xx2.pfx";
KeyStore clientStore = PfxHelper.getKeyStore(StringUtil.CLIENT_CERT_PATH, StringUtil.CLIENT_KEY_STORE_PASSWORD);
// TKCLIENT_PATH= "D:/tkclient.jks";
// ------> 载入服务器端的keyStore TKCLIENT_PATH= "D:/tkclient.jks";
FileInputStream servlet_instream = new FileInputStream(StringUtil.TKCLIENT_PATH);
try {
// 加载客户端和服务器的keyStore D:/kclient.jks
trustStore.load(servlet_instream, "123456".toCharArray());
servlet_instream.close();
} catch (CertificateException e) {
e.printStackTrace();
}
// 相信自己的CA和所有自签名的证书
// 载入服务器端的keyStore TKCLIENT_PATH= "D:/tkclient.jks"; <------
// 相信自己的CA和所有自签名的证书 一个SSL 流
SSLContext sslcontext = SSLContexts
.custom()
.loadTrustMaterial(trustStore, new TrustSelfSignedStrategy()) //加载本地信任证书 信息自签名策略
.loadKeyMaterial(clientStore, "123456".toCharArray()) //加载本地证书
.build(); //构造
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslcontext); //制造一个socket
httpclient = HttpClients.custom().setDefaultCookieStore(cookieStore).setSSLSocketFactory(sslsf).build(); //通过这个socket来生成一个http请求
// 创建http请求(get方式) delete put 全都有相应的方法
HttpGet httpget = new HttpGet(url);
// HttpGet httpget2 = new HttpGet("https://mail.koal.com/userMail!queryMailList.do?currentFolder.folderId=10");
System.out.println("executing request" + httpget.getRequestLine());
CloseableHttpResponse response = httpclient.execute(httpget);
response.close();
} catch (ParseException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (KeyStoreException e) {
e.printStackTrace();
} finally {
if (httpclient != null) {
try {
httpclient.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
public static void ssl2(String url) throws Exception {
//如上,就是添加一个json解析的过程
CloseableHttpClient httpclient = null;
try {
KeyStore trustStore = KeyStore.getInstance(KeyStore.getDefaultType());
KeyStore clientStore = PfxHelper.getKeyStore(StringUtil.CLIENT_CERT_PATH, StringUtil.CLIENT_KEY_STORE_PASSWORD);
FileInputStream servlet_instream = new FileInputStream(StringUtil.TKCLIENT_PATH);
try {
// 加载客户端和服务器的keyStore D:/kclient.jks
trustStore.load(servlet_instream, "123456".toCharArray());
} catch (CertificateException e) {
e.printStackTrace();
} finally {
try {
servlet_instream.close();
} catch (Exception ignore) {
}
}
// 相信自己的CA和所有自签名的证书
SSLContext sslcontext = SSLContexts
.custom()
.loadTrustMaterial(trustStore, new TrustSelfSignedStrategy())
.loadKeyMaterial(clientStore, "123456".toCharArray())
.build();
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslcontext);
httpclient = HttpClients.custom().setDefaultCookieStore(cookieStore).setSSLSocketFactory(sslsf).build();
// 创建http请求(get方式)
HttpGet httpget = new HttpGet(url);
System.out.println("executing request" + httpget.getRequestLine());
CloseableHttpResponse response = httpclient.execute(httpget);
try {
HttpEntity entity = response.getEntity();
System.out.println("----------------------------------------");
System.out.println(response.getStatusLine());
if (entity != null) {
System.out.println("Response content length: " + entity.getContentLength());
System.out.println(EntityUtils.toString(entity, "GBK"));
EntityUtils.consume(entity);
}
} finally {
response.close();
}
} catch (ParseException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (KeyStoreException e) {
e.printStackTrace();
} finally {
if (httpclient != null) {
try {
httpclient.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}