使用SSL与Bouncy Castle进行Android到服务器通信

我知道这不是那么困难,但非常不幸的是我从昨天起就被困在这里并与之斗争,我在Android教程中遵循了这种相互认证 ,将密钥库置于资源中并尝试通过SSL连接到我的服务器,但是得到以下exception

java.lang.RuntimeException:org.spongycastle.jcajce.provider.asymmetric.x509.CertificateFactory $ ExCertificateException

我已将sslapptruststore.pfx文件放在res/raw/sslapptruststore.pfx并使用这段代码

 try { KeyStore clientCert = KeyStore.getInstance("PKCS12"); clientCert.load(getResources().openRawResource(R.raw.sslapptruststore), "123456".toCharArray());// this line causes exception HttpClient httpClient = null; HttpParams httpParams = new BasicHttpParams(); SSLSocketFactory sslSocketFactory = new SSLSocketFactory(clientCert, null, null); SchemeRegistry registry = new SchemeRegistry(); registry.register(new Scheme("https", sslSocketFactory, 8443)); httpClient = new DefaultHttpClient(new ThreadSafeClientConnManager(httpParams, registry), httpParams); HttpPost httpPost = new HttpPost( "https://192.168.1.113:8443/CertProvider"); httpPost.setHeader("Content-Type", "application/x-www-form-urlencoded"); List nameValuePair = new ArrayList(2); nameValuePair.add(new BasicNameValuePair("csr", csr.toString())); // Url Encoding the POST parameters httpPost.setEntity(new UrlEncodedFormEntity(nameValuePair)); // Making HTTP Request // HttpResponse response = null; ResponseHandler responseHandler = new BasicResponseHandler(); String response = ""; response = httpClient.execute(httpPost, responseHandler); } catch (Exception e) { Log.e("", e.getMessage()); } 

我也搜索过,但其他人正在使用.bks

任何帮助表示赞赏。

我已回答了一些问题,如下所示:

读入适用于Android App的PKCS12 / P12客户端证书文件

Android volley自签名HTTPS信任锚,用于找不到证书路径

你会找到

  private SSLSocketFactory getSSLSocketFactory_KeyStore(String keyStoreType, int keystoreResId, String keyPassword) throws CertificateException, KeyStoreException, IOException, NoSuchAlgorithmException, KeyManagementException { InputStream caInput = getResources().openRawResource(keystoreResId); // creating a KeyStore containing trusted CAs if (keyStoreType == null || keyStoreType.length() == 0) { keyStoreType = KeyStore.getDefaultType(); } KeyStore keyStore = KeyStore.getInstance(keyStoreType); keyStore.load(caInput, keyPassword.toCharArray()); // creating a TrustManager that trusts the CAs in the KeyStore String tmfAlgorithm = TrustManagerFactory.getDefaultAlgorithm(); TrustManagerFactory tmf = TrustManagerFactory.getInstance(tmfAlgorithm); tmf.init(keyStore); TrustManager[] wrappedTrustManagers = getWrappedTrustManagers(tmf.getTrustManagers()); SSLContext sslContext = SSLContext.getInstance("TLS"); sslContext.init(null, wrappedTrustManagers, null); return sslContext.getSocketFactory(); } 

.cert文件的.cert

与上面的第一个链接一样,在项目中,您可以调用以下两种方法之一:

如果使用密钥库文件:

 SSLSocketFactory sslSocketFactory = getSSLSocketFactory_KeyStore("PKCS12", R.raw.androidpkcs12, "123456789"); 

如果使用证书文件:

 SSLSocketFactory sslSocketFactory = getSSLSocketFactory_Certificate("PKCS12", R.raw.androidpkcs12_cert); 

P / S:如果这些方法在非活动类中,为了避免NPE,必须将ContextActivity传递给该类(如上面第一个链接中所示)。

希望这可以帮助!

我添加了以下类来解决问题

 import org.apache.http.conn.ssl.SSLSocketFactory; import java.io.IOException; import java.io.InputStream; import java.net.Socket; import java.security.KeyManagementException; import java.security.KeyStore; import java.security.KeyStoreException; import java.security.NoSuchAlgorithmException; import java.security.UnrecoverableKeyException; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; import java.util.ArrayList; import java.util.Arrays; import javax.net.ssl.KeyManager; import javax.net.ssl.KeyManagerFactory; import javax.net.ssl.SSLContext; import javax.net.ssl.TrustManager; import javax.net.ssl.TrustManagerFactory; import javax.net.ssl.X509TrustManager; /** * Allows you to trust certificates from additional KeyStores in addition to * the default KeyStore */ public class AdditionalKeyStoresSSLSocketFactory extends SSLSocketFactory{ protected SSLContext sslContext = SSLContext.getInstance("TLSv1"); public AdditionalKeyStoresSSLSocketFactory(KeyStore keyStore) throws NoSuchAlgorithmException, KeyManagementException, KeyStoreException, UnrecoverableKeyException { super(null, null, null, null, null, null); KeyManagerFactory keyManagerFactory = KeyManagerFactory .getInstance(KeyManagerFactory.getDefaultAlgorithm());; keyManagerFactory.init(keyStore, "123456".toCharArray()); sslContext.init(keyManagerFactory.getKeyManagers(), new TrustManager[]{new AdditionalKeyStoresTrustManager(keyStore)}, null); } @Override public Socket createSocket(Socket socket, String host, int port, boolean autoClose) throws IOException { return sslContext.getSocketFactory().createSocket(socket, host, port, autoClose); } @Override public Socket createSocket() throws IOException { return sslContext.getSocketFactory().createSocket(); } /** * Based on http://download.oracle.com/javase/1.5.0/docs/guide/security/jsse/JSSERefGuide.html#X509TrustManager */ public static class AdditionalKeyStoresTrustManager implements X509TrustManager { protected ArrayList x509TrustManagers = new ArrayList(); protected AdditionalKeyStoresTrustManager(KeyStore... additionalkeyStores) { final ArrayList factories = new ArrayList(); try { // The default Trustmanager with default keystore final TrustManagerFactory original = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm()); original.init((KeyStore) null); factories.add(original); for( KeyStore keyStore : additionalkeyStores ) { final TrustManagerFactory additionalCerts = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm()); additionalCerts.init(keyStore); factories.add(additionalCerts); } } catch (Exception e) { throw new RuntimeException(e); } /* * Iterate over the returned trustmanagers, and hold on * to any that are X509TrustManagers */ for (TrustManagerFactory tmf : factories) for( TrustManager tm : tmf.getTrustManagers() ) if (tm instanceof X509TrustManager) x509TrustManagers.add( (X509TrustManager)tm ); if( x509TrustManagers.size()==0 ) throw new RuntimeException("Couldn't find any X509TrustManagers"); } /* * Delegate to the default trust manager. */ public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException { final X509TrustManager defaultX509TrustManager = x509TrustManagers.get(0); defaultX509TrustManager.checkClientTrusted(chain, authType); } /* * Loop over the trustmanagers until we find one that accepts our server */ public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { for( X509TrustManager tm : x509TrustManagers ) { try { tm.checkServerTrusted(chain,authType); return; } catch( CertificateException e ) { // ignore } } throw new CertificateException(); } public X509Certificate[] getAcceptedIssuers() { final ArrayList list = new ArrayList(); for( X509TrustManager tm : x509TrustManagers ) list.addAll(Arrays.asList(tm.getAcceptedIssuers())); return list.toArray(new X509Certificate[list.size()]); } } }