package com.ab.http.ssl; import java.security.KeyStore; import java.security.KeyStoreException; import java.security.NoSuchAlgorithmException; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; import java.util.Date; import javax.net.ssl.TrustManager; import javax.net.ssl.TrustManagerFactory; import javax.net.ssl.X509TrustManager; /** * © 2012 amsoft.cn * 名称:EasyX509TrustManager.java * 描述:SSL自签名的实现类 * * @author 还如一梦中 * @version v1.0 * @date:2013-11-13 上午9:00:52 */ public class EasyX509TrustManager implements X509TrustManager { private X509TrustManager standardTrustManager = null; /** * Constructor for EasyX509TrustManager. */ public EasyX509TrustManager(KeyStore keystore) throws NoSuchAlgorithmException, KeyStoreException { super(); TrustManagerFactory factory = TrustManagerFactory .getInstance(TrustManagerFactory.getDefaultAlgorithm()); factory.init(keystore); TrustManager[] trustmanagers = factory.getTrustManagers(); if (trustmanagers.length == 0) { throw new NoSuchAlgorithmException("no trust manager found"); } this.standardTrustManager = (X509TrustManager) trustmanagers[0]; } /** * 执行客户端的安全策略 */ @Override public void checkClientTrusted(X509Certificate[] certificates, String authType) throws CertificateException { standardTrustManager.checkClientTrusted(certificates, authType); } /** * 执行服务器的安全策略 * 检查签名、信任链中证书的有效日期和CRLs * 清除因证书过期出现的问题 */ @Override public void checkServerTrusted(X509Certificate[] certificates, String authType) throws CertificateException { // Clean up the certificates chain and build a new one. // Theoretically, we shouldn't have to do this, but various web servers // in practice are mis-configured to have out-of-order certificates or // expired self-issued root certificate. // int chainLength = certificates.length; if (certificates.length > 1) { // 1. we clean the received certificates chain. // We start from the end-entity certificate, tracing down by // matching // the "issuer" field and "subject" field until we can't continue. // This helps when the certificates are out of order or // some certificates are not related to the site. int currIndex; for (currIndex = 0; currIndex < certificates.length; ++currIndex) { boolean foundNext = false; for (int nextIndex = currIndex + 1; nextIndex < certificates.length; ++nextIndex) { if (certificates[currIndex].getIssuerDN().equals( certificates[nextIndex].getSubjectDN())) { foundNext = true; // Exchange certificates so that 0 through currIndex + 1 // are in proper order if (nextIndex != currIndex + 1) { X509Certificate tempCertificate = certificates[nextIndex]; certificates[nextIndex] = certificates[currIndex + 1]; certificates[currIndex + 1] = tempCertificate; } break; } } if (!foundNext) break; } // 2. we exam if the last traced certificate is self issued and it // is expired. // If so, we drop it and pass the rest to checkServerTrusted(), // hoping we might // have a similar but unexpired trusted root. int chainLength = currIndex + 1; X509Certificate lastCertificate = certificates[chainLength - 1]; Date now = new Date(); if (lastCertificate.getSubjectDN().equals( lastCertificate.getIssuerDN()) && now.after(lastCertificate.getNotAfter())) { --chainLength; } } // standardTrustManager.checkServerTrusted(certificates, authType); } /** * @see javax.net.ssl.X509TrustManager#getAcceptedIssuers() */ @Override public X509Certificate[] getAcceptedIssuers() { return this.standardTrustManager.getAcceptedIssuers(); } }