对不起我的英语不好.我尝试使用libruary OKhttp,我使用https进行post reqest.现在我有错误,当我尝试发布我的例子时,这是错误:
java.net.UnknownServiceException: Unable to find acceptable protocols. isFallback=false,modes=[ConnectionSpec(cipherSuites=[TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,TLS_DHE_RSA_WITH_AES_128_GCM_SHA256,TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA,TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,TLS_ECDHE_RSA_WITH_RC4_128_SHA,TLS_DHE_RSA_WITH_AES_128_CBC_SHA],tlsVersions=[TLS_1_2],supportsTlsExtensions=true)],supported protocols=[SSLv3,TLSv1]
我尝试修复它,但我不能这样做.我不知道我有什么错误
而且我的代码吼叫:
public class PostOKhttp extends AsyncTask<String,Void,String> { @Override protected String doInBackground(String...ulr) { Response response = null; OkHttpClient client = new OkHttpClient(); ConnectionSpec spec = new ConnectionSpec.Builder(ConnectionSpec.MODERN_TLS) .tlsVersions(TlsVersion.TLS_1_2) .cipherSuites( CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256,CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA,CipherSuite.TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,CipherSuite.TLS_ECDHE_RSA_WITH_RC4_128_SHA,CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA) .build(); client.setConnectionSpecs(Collections.singletonList(spec)); RequestBody postForm = new FormEncodingBuilder() .add("name","name") .build(); Request request = new Request.Builder() .url(ulr[0]) .addHeader("id","--") .addHeader("key","--") .post(postForm) .build(); try { response = client.newCall(request).execute(); Log.e("post",response.body().string()); } catch (Exception e) { Log.e("error",e.toString()); } return null; } @Override protected void onPostExecute(String result) { }
UDP:
使用CertificatePinner
String link = "example.net"; CertificatePinner certificatePinner = new CertificatePinner.Builder() .add(link,"sha1/DmxUShsZuNiqPQsX2Oi9uv2sCnw=") .add(link,"sha1/SXxoaOSEzPC6BgGmxAt/EAcsajw=") .add(link,"sha1/blhOM3W9V/bVQhsWAcLYwPU6n24=") .add(link,"sha1/T5x9IXmcrQ7YuQxXnxoCmeeQ84c=") .build(); client.setCertificatePinner(certificatePinner);
现在我有这个错误:
javax.net.ssl.SSLHandshakeException: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
解决方法
实际上问题是默认情况下未在Android< 5上启用TLSv1.1和TLSv1.2,并且要使用这些最新的安全协议进行连接,我们必须在Android< 5设备中启用. 因为默认情况下,android设备选择支持最高的协议来建立连接,但默认情况下不启用最高/最新安全协议(例如TLSV1.1或TLSV1.2)(仅启用SSLV3.0或TLSV1.0). 在android中启用TLSV1.1和TLSV1.2<五
import java.io.IOException; import java.net.InetAddress; import java.net.Socket; import java.net.UnknownHostException; import java.security.KeyManagementException; import java.security.NoSuchAlgorithmException; import javax.net.ssl.SSLContext; import javax.net.ssl.SSLSocket; import javax.net.ssl.SSLSocketFactory; /** * @author Bajrang Hudda */ public class MyTLSSocketFactory extends SSLSocketFactory { private SSLSocketFactory internalSSLSocketFactory; public MyTLSSocketFactory() throws KeyManagementException,NoSuchAlgorithmException { SSLContext context = SSLContext.getInstance("TLS"); context.init(null,null,null); internalSSLSocketFactory = context.getSocketFactory(); } @Override public String[] getDefaultCipherSuites() { return internalSSLSocketFactory.getDefaultCipherSuites(); } @Override public String[] getSupportedCipherSuites() { return internalSSLSocketFactory.getSupportedCipherSuites(); } @Override public Socket createSocket() throws IOException { return enableTLSOnSocket(internalSSLSocketFactory.createSocket()); } @Override public Socket createSocket(Socket s,String host,int port,boolean autoClose) throws IOException { return enableTLSOnSocket(internalSSLSocketFactory.createSocket(s,host,port,autoClose)); } @Override public Socket createSocket(String host,int port) throws IOException,UnknownHostException { return enableTLSOnSocket(internalSSLSocketFactory.createSocket(host,port)); } @Override public Socket createSocket(String host,InetAddress localHost,int localPort) throws IOException,localHost,localPort)); } @Override public Socket createSocket(InetAddress host,int port) throws IOException { return enableTLSOnSocket(internalSSLSocketFactory.createSocket(host,port)); } @Override public Socket createSocket(InetAddress address,InetAddress localAddress,int localPort) throws IOException { return enableTLSOnSocket(internalSSLSocketFactory.createSocket(address,localAddress,localPort)); } private Socket enableTLSOnSocket(Socket socket) { if(socket != null && (socket instanceof SSLSocket)) { ((SSLSocket)socket).setEnabledProtocols(new String[] {"TLSv1.1","TLSv1.2"}); } return socket; } }
现在将它添加到您的Okhttpclient中 –
protected static OkHttpClient getHttpClient(long timeout){ String hostname = Constants.HOST_NAME_DEBUG; CertificatePinner certificatePinner = new CertificatePinner.Builder() .add(hostname,"sha1/mBN/TTGneHe2Hq0yFG+SRt5nMZQ=") .add(hostname,"sha1/6CgvsAgBlX3PYiYRGedC0NZw7ys=") .build(); //specifying the specs; this is impotent otherwise android <5 won't work //And do note to include the android < 5 supported specs. ConnectionSpec spec = new ConnectionSpec.Builder(ConnectionSpec.MODERN_TLS) .tlsVersions(TlsVersion.TLS_1_1,TlsVersion.TLS_1_2) .cipherSuites( CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) .build(); final OkHttpClient okHttpClient = new OkHttpClient(); okHttpClient.setCertificatePinner(certificatePinner); okHttpClient.setConnectionSpecs(Collections.singletonList(spec)); try { // enabling the tlsv1.1 and tlsv.2 okHttpClient.setSslSocketFactory(new MyTLSSocketFactory()); } catch (KeyManagementException e) { e.printStackTrace(); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } return okHttpClient; }
现在最后在你的改造中添加它 –
RestAdapter restAdapter = new RestAdapter.Builder() .setEndpoint(Constants.API_URL) .setLogLevel(RestAdapter.LogLevel.FULL) .setErrorHandler(new ErrorHandler()) .setClient(getHttpClient()) .setRequestInterceptor(new SecureHeaderInterceptor(null)) .build();
就是这样,Happy Coding 原文链接:https://www.f2er.com/android/310133.html