gpt4 book ai didi

java - Android:如何使用自签名证书和 SSL 缓存创建 HttpClient

转载 作者:行者123 更新时间:2023-11-29 09:30:24 25 4
gpt4 key购买 nike

我在实现与 Android 的 SSL 连接时遇到了一些麻烦。我的程序在特定的时间间隔内发送数据。为了减少发送的数据量,我想使用 SSL 缓存。有人知道如何在 Android 中使用自签名证书和 SSL 缓存创建 HttpClient 吗?

我想使用 HttpClient 类,我的解决方案如下所示(以 CastException 结尾):

private HttpClient getNewHttpClient(Context context, InputStream sslCertificate) {
SSLSessionCache sslSessionCache = new SSLSessionCache(context);
SSLCertificateSocketFactory socketFactory = (SSLCertificateSocketFactory) SSLCertificateSocketFactory.getDefault(15000, sslSessionCache);

KeyStore keyStore = getSSLKeyStore(sslCertificate);
TrustManagerFactory tmf = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
tmf.init(keyStore);

socketFactory.setTrustManagers(tmf.getTrustManagers());

HttpParams connectionParameters = new BasicHttpParams();
HttpProtocolParams.setVersion(connectionParameters , HttpVersion.HTTP_1_1);
HttpProtocolParams.setContentCharset(connectionParameters , HTTP.UTF_8);
HttpConnectionParams.setStaleCheckingEnabled(connectionParameters , false);
HttpConnectionParams.setConnectionTimeout(connectionParameters , 4 * 1000);
HttpConnectionParams.setSoTimeout(connectionParameters , 5 * 1000);
HttpConnectionParams.setSocketBufferSize(connectionParameters , 8192);
HttpClientParams.setRedirecting(connectionParameters , false);

SchemeRegistry registry = new SchemeRegistry();

registry.register(new Scheme("https", (SocketFactory) socketFactory , 443));
ClientConnectionManager connectionManager = new ThreadSafeClientConnManager(connectionParameters, registry);

HttpClient httpClient = new DefaultHttpClient(connectionManager, connectionParameters);

return httpClient;
}

这是在将新构建方案注册到 SchemeRegistry 时的 CastException

 W/System.err(343): java.lang.ClassCastException: org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl cannot be cast to org.apache.http.conn.scheme.SocketFactory

最佳答案

    public class SimpleSSLSocketFactory extends
org.apache.http.conn.ssl.SSLSocketFactory {
private javax.net.ssl.SSLSocketFactory sslFactory = HttpsURLConnection
.getDefaultSSLSocketFactory();

public SimpleSSLSocketFactory(KeyStore truststore)
throws NoSuchAlgorithmException, KeyManagementException,
KeyStoreException, UnrecoverableKeyException {
super(null);
try {
SSLContext context = SSLContext.getInstance("TLS");
TrustManager[] trustAllCerts = new TrustManager[] { new

X509TrustManager() {
public java.security.cert.X509Certificate[] getAcceptedIssuers() {
return new java.security.cert.X509Certificate[] {};
}
public void checkClientTrusted(X509Certificate[] chain,
String authType) throws CertificateException {
}

public void checkServerTrusted(X509Certificate[] chain,
String authType) throws CertificateException {
}
} };

// Initialize the socket factory
context.init(null, trustAllCerts, new SecureRandom());
sslFactory = context.getSocketFactory();
} catch (Exception e) {
e.printStackTrace();
}
}

@Override
public Socket createSocket(Socket socket, String host, int port,
boolean autoClose) throws IOException, UnknownHostException {
return sslFactory.createSocket(socket, host, port, autoClose);
}

@Override
public Socket createSocket() throws IOException {
return sslFactory.createSocket();
}

   U can call like this 


try {
SSLSocketFactory sslFactory = new SimpleSSLSocketFactory(null);
sslFactory
.setHostnameVerifier(SSLSocketFactory.
ALLOW_ALL_HOSTNAME_VERIFIER);
HttpParams params = new BasicHttpParams();
HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1);
HttpProtocolParams.setContentCharset(params, HTTP.UTF_8);
SchemeRegistry registry = new SchemeRegistry();
registry.register(new Scheme("http", PlainSocketFactory
.getSocketFactory(), 80));
registry.register(new Scheme("https", sslFactory, 443));
ClientConnectionManager ccm = new ThreadSafeClientConnManager(
params, registry);
DefaultHttpClient httpClient = new DefaultHttpClient(ccm, params);
HttpPost httpPost = new HttpPost(url);
HttpHost proxy = new HttpHost("50.104.5.277", 23333);

//httpPost.setHeader("Content-Type", "text/xml");
httpPost.setEntity(entity);
httpClient.getParams().setParameter(ConnRoutePNames.DEFAULT_PROXY,
proxy);
HttpResponse httpResponse = httpClient.execute(httpPost);
HttpEntity httpEntity = httpResponse.getEntity();
output = EntityUtils.toString(httpEntity);

// Toast.makeText(getApplicationContext(), xml, 1000).show();
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (UnrecoverableKeyException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (KeyStoreException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

return output;
}

关于java - Android:如何使用自签名证书和 SSL 缓存创建 HttpClient,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18658075/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com