1. 概述
這篇文章主要記錄下自己在開發(fā)過程中遇到的需要給OKHttpUtils添加證書的問題,其實(shí)默認(rèn)情況下絕大多數(shù)第三方聯(lián)網(wǎng)請(qǐng)求框架都是支持https的SSL證書的,說白了,我們?cè)陂_發(fā)過程中用的最多的還是OKHttp,因?yàn)镽etrofit也可以說是對(duì)OKHttp進(jìn)一步的封裝。那么解析來我們就來看下,OKHttp是如何添加證書的,如果不是對(duì)http與https不是很清楚的,可以先看下我的這篇文章。
2. 具體實(shí)現(xiàn)
2.1>:運(yùn)維會(huì)給你一個(gè)公鑰,就是購(gòu)買證書后的一個(gè)公鑰,類似于下圖所示:
圖片.png
2.2>:自己定義一個(gè)工具類,用于添加https的證書,代碼如下:
/**
* Email: 2185134304@qq.com
* Created by JackChen 2018/4/13 11:50
* Version 1.0
* Params:
* Description: https添加證書工具類
*/
public class APIManager {
private static final String CER_YILIAN = "-----BEGIN CERTIFICATE-----\n" +
"MIIFqjCCBJKgAwIBAgIQBx+15z+1utfoVQez3qb4ADANBgkqhkiG9w0BAQsFADBe\n" +
"MQswCQ"Fw0xODA0MDkwMDAwMDBaFw0xOTA0MDkxMjAwMDBaMBUxEzARBgNVBAMMCioudXBs\n" +
"b28uYTFJTQUNBMjAxOC5jcmwwTAYDVR0gBEUwQzA3\n" +
"AjAAMIIBAwYKKwYBBAHWeQIEAgSB9ASB8QDvAHUApLkJkLQYWBSHuxOizGdwCjw1\n" +
"oSFEWyxDmV8NodSm2JLEsRppc7i4vTrchPS/75EkXS+AMKfNyrRDw4u0uS1+EZMl\n" +
"P6Nl0JkGq1BJpvPhWCs=\n" +
"-----END CERTIFICATE-----\n" +
"-----BEGIN CERTIFICATE-----\n" +
"MIIEsT
"ysNyq0jEDQTkfa2pjmuWtMCNbBnhFXBYejfubIhaUbEv2FOQB3dCav+FPg5eEveX\n" +
"TVyMnGo=\n" +
"-----END CERTIFICATE-----";
static private TrustManager[] createTrustManagers(InputStream... certificates){
if (certificates == null || certificates.length <= 0) {
return null;
}
try
{
CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509");
KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType());
keyStore.load(null);
int index = 0;
for (InputStream certificate : certificates) {
String certificateAlias = Integer.toString(index++);
keyStore.setCertificateEntry(certificateAlias, certificateFactory.generateCertificate(certificate));
try {
if (certificate != null){
certificate.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());;
trustManagerFactory.init(keyStore);
return trustManagerFactory.getTrustManagers();
} catch (NoSuchAlgorithmException e){
e.printStackTrace();
} catch (CertificateException e) {
e.printStackTrace();
} catch (KeyStoreException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
static private HttpsUtils.SSLParams getSslSocketFactory(InputStream ... certificates){
HttpsUtils.SSLParams sslParams = new HttpsUtils.SSLParams();
try
{
TrustManager[] trustManagers = createTrustManagers(certificates);
SSLContext sslContext = SSLContext.getInstance("TLS");
final List<X509TrustManager> x509trustManagers = new ArrayList<X509TrustManager>();
for(TrustManager tm : trustManagers){
if(tm instanceof X509TrustManager){
x509trustManagers.add((X509TrustManager)tm);
}
}
X509TrustManager trustManager = new X509TrustManager() {
@Override
public void checkClientTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {
}
@Override
public void checkServerTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {
for(X509TrustManager tm : x509trustManagers){
tm.checkServerTrusted(x509Certificates, s);
}
}
@Override
public X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[0];
}
};
sslContext.init(null, new TrustManager[]{trustManager},null);
sslParams.sSLSocketFactory = sslContext.getSocketFactory();
sslParams.trustManager = trustManager;
return sslParams;
} catch (NoSuchAlgorithmException e) {
throw new AssertionError(e);
} catch (KeyManagementException e) {
throw new AssertionError(e);
}
}
/**
* OKHttp添加證書
* @return
*/
protected static OkHttpClient CheckOkhttps() {
try {
// HttpsUtils.SSLParams sslParams = HttpsUtils.getSslSocketFactory(new InputStream[]{new Buffer().writeUtf8(CER_YILIAN).inputStream()}, null, null);
HttpsUtils.SSLParams sslParams = getSslSocketFactory(new ByteArrayInputStream(CER_YILIAN.getBytes("UTF-8")));
OkHttpClient okHttpClient = new OkHttpClient.Builder()
.connectTimeout(60000L, TimeUnit.MILLISECONDS)
.readTimeout(60000L, TimeUnit.MILLISECONDS)
.addInterceptor(new LoggerInterceptor("TAG"))
.hostnameVerifier(new HostnameVerifier() {
@Override
public boolean verify(String hostname, SSLSession session) {
return true;
}
})
.sslSocketFactory(sslParams.sSLSocketFactory, sslParams.trustManager)
.build();
OkHttpUtils.initClient(okHttpClient);
return okHttpClient;
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
}
2.3>:然后在BaseApplication中調(diào)用 CheckOkhttps()方法即可,表示給OKHttp添加證書,代碼如下:
public class BaseApplication extends Application {
@Override
public void onCreate() {
super.onCreate();
CheckOkhttps() ;
}
以上就是給OKHttp添加https證書,當(dāng)然對(duì)于給OKHttp添加證書還有很多種方法,同時(shí)也還有很多場(chǎng)景,我這里只是簡(jiǎn)單的總結(jié)一下,如果還想看一下其他具體的方法,可以點(diǎn)擊下邊鏈接就ok。