I'm trying to get Java to accept all certs over HTTPS. This is for testing purposes. Before I was getting a cert not found error. However, after adding the following code before my code I get a HTTPS hostname wrong: should be <sub.domain.com> error. The problem is my url IS that url. How do I get around this issue? The below is the code I've added to attempt to fix the problem..
// Create a trust manager that does not validate certificate chains
TrustManager[] trustAllCerts = new TrustManager[]{
new X509TrustManager() {
public java.security.cert.X509Certificate[] getAcceptedIssuers() {
return null;
}
public void checkClientTrusted(
java.security.cert.X509Certificate[] certs, String authType) {
}
public void checkServerTrusted(
java.security.cert.X509Certificate[] certs, String authType) {
}
}
};
// Install the all-trusting trust manager
try {
SSLContext sc = SSLContext.getInstance("SSL");
sc.init(null, trustAllCerts, new java.security.SecureRandom());
HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
} catch (Exception e) {
}
You need to set the a HostNameVarifier also
Ex:
import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.SSLSession;
public class TrustAllHostNameVerifier implements HostnameVerifier {
public boolean verify(String hostname, SSLSession session) {
return true;
}
}
Then
httpsConnection.setHostnameVerifier(new TrustAllHostNameVerifier ());
Related
I'm using OkHttp3 to establish a connection between android app and server. I have a self-signed certificate, which is needed to talk to the server. Problem was that android doesn't trust self-signed certs so I got code from this website to disable SSL verification. Now the problem is that I'm not sending a certificate with my request. If I add this certificate to trusted certificates I get "Trust anchor for certification path not found." error.
Current code:
#Override
protected Void doInBackground(Void... voids) {
try {
OkHttpClient client = ApiAuth.getUnsafeOkHttpClient();
Request request = new Request.Builder()
.url(url)
.get().build();
Response response = client.newCall(request).execute();
Log.d("Server connection", "connection established!");
Log.d("Server response -------------\n", String.valueOf(response));
} catch (IOException | NullPointerException e) {
e.printStackTrace();
Log.d("catch", "cought exception ");
}
return null; //(CertificateException | IOException | KeyStoreException | NoSuchAlgorithmException | KeyManagementException | NullPointerException e)
}
}
private static OkHttpClient getUnsafeOkHttpClient() {
try {
final TrustManager[] trustAllCerts = new TrustManager[] {
new X509TrustManager() {
#Override
public void checkClientTrusted(java.security.cert.X509Certificate[] chain, String authType) throws CertificateException {
}
#Override
public void checkServerTrusted(java.security.cert.X509Certificate[] chain, String authType) throws CertificateException {
}
#Override
public java.security.cert.X509Certificate[] getAcceptedIssuers() {
return new java.security.cert.X509Certificate[]{};
}
}
};
final SSLContext sslContext = SSLContext.getInstance("SSL");
sslContext.init(null, trustAllCerts, new java.security.SecureRandom());
final SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory();
OkHttpClient.Builder builder = new OkHttpClient.Builder();
builder.sslSocketFactory(sslSocketFactory, (X509TrustManager)trustAllCerts[0]);
builder.hostnameVerifier(new HostnameVerifier() {
#Override
public boolean verify(String hostname, SSLSession session) {
return true;
}
});
OkHttpClient okHttpClient = builder.build();
return okHttpClient;
} catch (Exception e) {
throw new RuntimeException(e);
}
Is there a better solution (that actually works)?
I got a response with postman. I disabled SSL verification and gave .pfx file in settings (or .crt and .key). How can I do the same in andorid studio?
I need to disable the SSL for a given url or for the restTemplate right know i can disable all the SSL's with the code bellow. How can i make this code for given URL only. Or how to disable it for the restTemplate.
public class SSLTool {
public static void disableCertificateValidation() {
// Create a trust manager that does not validate certificate chains
TrustManager[] trustAllCerts = new TrustManager[] {
new X509TrustManager() {
public X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[0];
}
public void checkClientTrusted(X509Certificate[] certs, String authType) {}
public void checkServerTrusted(X509Certificate[] certs, String authType) {}
}};
// Ignore differences between given hostname and certificate hostname
HostnameVerifier hv = new HostnameVerifier() {
public boolean verify(String hostname, SSLSession session) { return true; }
};
// Install the all-trusting trust manager
try {
SSLContext sc = SSLContext.getInstance("SSL");
sc.init(null, trustAllCerts, new SecureRandom());
HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
HttpsURLConnection.setDefaultHostnameVerifier(hv);
} catch (Exception e) {/* intentionally left blank */}
}
}
I solved this with the following code down below. here is the link to the source https://stackoverflow.com/a/42689331/16529288
TrustStrategy acceptingTrustStrategy = (X509Certificate[] chain, String authType) -> true;
SSLContext sslContext = org.apache.http.ssl.SSLContexts.custom()
.loadTrustMaterial(null, acceptingTrustStrategy)
.build();
SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext);
CloseableHttpClient httpClient = HttpClients.custom()
.setSSLSocketFactory(csf)
.build();
HttpComponentsClientHttpRequestFactory requestFactory =
new HttpComponentsClientHttpRequestFactory();
requestFactory.setHttpClient(httpClient);
RestTemplate restTemplate = new RestTemplate(requestFactory);
Returning RestTemplate with SSL disabled can be achieved via below(You can add other properties as your requirements.) :
CloseableHttpClient client = HttpClients.custom().setSSLHostnameVerifier(new HostnameVerifier() {
#Override
public boolean verify(String hostname, SSLSession session) {
return true;
}
}).setSSLHostnameVerifier(new HostnameVerifier() {
#Override
public boolean verify(String hostname, SSLSession session) {
return true;
}
}).build();
HttpComponentsClientHttpRequestFactory req = new HttpComponentsClientHttpRequestFactory(client);
RestTemplate template = new RestTemplate(req);
I got - closed connection -1 , draft org.java_websocket.drafts.Draft_17#75599672 refuses handshake , false - then changed the code as below:
Socket creation coode
webClient = new APICWebClient(new URI(getWebSocketUrl(currentApic.IPAddress, port)), new Draft_17());
webClient.connect();
Constructor:
public APICWebClient(URI serverURI, Draft draft) {
super(serverURI, draft);
SSLContext sslContext = null;
try {
sslContext = SSLContext.getDefault();
} catch (NoSuchAlgorithmException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
setWebSocketFactory(new DefaultSSLWebSocketClientFactory(sslContext));
logger.info("Socket object created");
}
Draft_17. I get : closed connection -1 , , true. Any help here. This happens during socket creation.
Need to create sslcontext like below. it skips the certificate. I was successfully able make a connection without certificate
SSLContext sslContext = SSLContext.getInstance("SSL");
// set up a TrustManager that trusts everything
sslContext.init(null, new TrustManager[] { new X509TrustManager() {
public X509Certificate[] getAcceptedIssuers() {
System.out.println("getAcceptedIssuers =============");
return null;
}
public void checkClientTrusted(X509Certificate[] certs,
String authType) {
System.out.println("checkClientTrusted =============");
}
public void checkServerTrusted(X509Certificate[] certs,
String authType) {
System.out.println("checkServerTrusted =============");
}
} }, new SecureRandom());
I'm getting javax.net.ssl.SSLHandshakeException: Connection closed by peer when i try to make https request from android app using HttpsURLConnection
Above the code for to make request and return a Bitmap.
protected Bitmap doInBackground(String... params) {
try {
// Create a trust manager that does not validate certificate chains
TrustManager[] trustAllCerts = new TrustManager[] {
new X509TrustManager() {
public java.security.cert.X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[0];
}
public void checkClientTrusted(
java.security.cert.X509Certificate[] certs, String authType) {
}
public void checkServerTrusted(
java.security.cert.X509Certificate[] certs, String authType) {
}
}
};
// Install the all-trusting trust manager
try {
SSLContext sc = SSLContext.getInstance("SSL");
sc.init(null, trustAllCerts, new java.security.SecureRandom());
HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
} catch (GeneralSecurityException e) {
e.printStackTrace();
}
HttpsURLConnection connection = (HttpsURLConnection)
new URL("www.example.com.br").openConnection();
connection.setHostnameVerifier(getHostnameVerifier("www.example.com.br");
connection.setRequestMethod("GET");
connection.setConnectTimeout(3000);
connection.setUseCaches(false);
connection.setAllowUserInteraction(false);
connection.connect();
setCookieActivity(connection.getHeaderField("Set-Cookie"));
return BitmapFactory.decodeStream(connection.getInputStream());
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
private HostnameVerifier getHostnameVerifier(final String url) {
HostnameVerifier hostnameVerifier = new HostnameVerifier() {
#Override
public boolean verify(String hostname, SSLSession session) {
HostnameVerifier hv =
HttpsURLConnection.getDefaultHostnameVerifier();
return hv.verify(url, session);
}
};
return hostnameVerifier;
}
I already tried many thing, but i get the same exception
This link works for many, but not for me.
telling java to accept self-signed ssl certificate
The question is very simple.
How to re-enable SSL certificate validation once the following code is executed ?
// Create a trust manager that does not validate certificate chains
TrustManager[] trustAllCerts = new TrustManager[] {
new X509TrustManager() {
public java.security.cert.X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[0];
}
public void checkClientTrusted(
java.security.cert.X509Certificate[] certs, String authType) {
}
public void checkServerTrusted(
java.security.cert.X509Certificate[] certs, String authType) {
}
}
};
// Install the all-trusting trust manager
try {
SSLContext sc = SSLContext.getInstance("SSL");
sc.init(null, trustAllCerts, new java.security.SecureRandom());
HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
} catch (GeneralSecurityException e) {
}
Try this:
try {
SSLContext sc = SSLContext.getInstance("SSL");
sc.init(null, null, null);
HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
} catch (GeneralSecurityException e) {
}
If a parameter of the init method is null, the default implementation is used.