I'm trying to develop an app to communicate with amazon alexa using OKhttp3. Everything was working fine while I was trying the app on an android API 26.
But once I started using an android API 19 every request to https://avs-alexa-na.amazon.com/ started failing.
Before working for API 19 this was how I used this function to open the down channel.
final String url = "https://avs-alexa-na.amazon.com/";
final String version = "v20160207";
final Request request = new Request.Builder()
.get()
.header("Authorization", "Bearer " + myApplication.getAccessToken())
.url(url + version + "/directives")
.build();
try {
final OkHttpClient client = new OkHttpClient();
Response response = client.newCall(request).execute();
Log.i("Down channel", "opened");
} catch (Exception ex) {
Log.e("Down channel", "error Sending request " + ex.getLocalizedMessage());
}
But now this same function returns javax.net.ssl.SSLProtocolException: SSL handshake aborted: ssl=0xb969de80: Failure in SSL library, usually a protocol error error:14077410:SSL routines:SSL23_GET_SERVER_HELLO:sslv3 alert handshake failure (external/openssl/ssl/s23_clnt.c:741 0x8d954990:0x00000000)
So after following some posts on line I learned that android 19 doesn't install by default TLSv1.2 so I added a function to install it and started having this error :unexpected end of stream on Connection{avs-alexa-na.amazon.com:443, proxy=DIRECT@ hostAddress=avs-alexa-na.amazon.com/54.239.39.74:443 cipherSuite=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 protocol=http/1.1}
I started exploring other ways working with certificates (my certificate, and the one from amazon gotten by openssl s_client -connect avs-alexa-eu.amazon.com:443
:
SSLContext sslContext;
TrustManager[] trustManagers;
try {
final KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType());
keyStore.load(null, null);
final InputStream certInputStream = activity.getResources().openRawResource(R.raw.cert);
InputStream avscertInputStream = activity.getResources().openRawResource(R.raw.amazon_avs_cert);
final CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509");
final Certificate cert = certificateFactory.generateCertificate(certInputStream);
final Certificate avscert = certificateFactory.generateCertificate(avscertInputStream);
keyStore.setCertificateEntry("amazon_avs", avscert);
keyStore.setCertificateEntry("cert", cert);
final TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
trustManagerFactory.init(keyStore);
trustManagers = trustManagerFactory.getTrustManagers();
sslContext = SSLContext.getInstance("TLSv1.2");
sslContext.init(null, trustManagers, null);
return new OkHttpClient.Builder()
.sslSocketFactory(sslContext.getSocketFactory(), (X509TrustManager) trustManagers[0])
.build();
} catch (Exception e) {
e.printStackTrace();
return new OkHttpClient();
}
But it led to a java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
I'm lost, I don't know what I did wrong or what I did not do. Thanks for you help.