Java -> Flask Https Request: javax.net.ssl.SSLHandshakeException: PKIX path building failed - java

So I'm trying to send a HTTPS request to my Flask application. Before, it worked successfully using just HTTP. Now, I wanted to change it to HTTPS.
But it does not work unfortunately. In my Java IDE, and my Python IDE, I get these errors:
javax.net.ssl.SSLException: Unsupported or unrecognized SSL message (Java client side)
code 400, message Bad request version ("\x1bè\x13\x16)... and
"‚ ~ˆòÎ×ý›tYê >ôeïõ?2ŸÏËðÚü$ü^d ‰ô$NªO5~EN4ë=Y8õûb~ïÁ¢˜è) bÀ,À+Ì©À0̨À/ ŸÌª £ ž ¢À$À(À#À' k j g #À.À2À-À1À&ÀÀ%À)À" HTTPStatus.BAD_REQUEST* (Flask server side)
My code for sending the request is:
URL myURL = new URL(requestUrl);
HttpsURLConnection connection = (HttpsURLConnection) myURL.openConnection();
connection.setRequestMethod("GET");
System.out.println(connection.getResponseCode());
...
Basically, I just changed my connection object to Https, and also modified the URL string to use "https" instead. It worked perfect with HTTP, and now, nothing works with HTTPS.
What do I have to do to get it working with HTTPS?
EDIT: In my Flask application, I changed app.run to also include parameter ssl_context='adhoc'. Now I get a different exception:
javax.net.ssl.SSLHandshakeException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target

ssl_context='adhoc' is the right way.
This generates a custom SSL cert and you can access your Flask app via https.
But...
As this cert is self signed, your client (Browser, curl, or Java Application) does not trust the cert.
That is why you get error messages.
Have a look at the following blog post to learn more what you can do about it:
https://blog.miguelgrinberg.com/post/running-your-flask-application-over-https

Related

How to download SSL certificate from a LDAP Server using java ? and establish SSL connection using LDAPS?

I am trying to write a program for connecting LDAP server using java code..
Connection Type - SSL
I am getting SSLHandshakeException which says I will have to use 'server certificate' to establish ssl connection -
javax.naming.CommunicationException: :636 [Root exception is javax.net.ssl.SSLHandshakeException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target]
Could anyone please suggest how to download SSL certificate from the server using java code and then use that certificate while connecting to LDAP ?
Here are the solutions i have tried, but i did not work -
How to read a Certificate attribute (caCertificate) from LDAP server (Java)?
How to make a call, via Java, with ssl and certificate to an ldap (AD)?
NOTE - I cannot override functionality of certificate verification/validation using custom socket factory

SSL Certificate Issue for HTTPS GET request and not for HTTPS POST request

I am trying to write a java program to fetch call records from Empirix server. In order to fetch call records, first I need to generate a token id by sending a HTTPS POST request to a server https://webserver:8443/openam/json/authenticate. The inputs for the POST request will be my username and password. Once I fetch the token id, I am sending that as input to HTTPS GET request to same webserver but different port (https://webserver:443/restapi/v1/emergencyCalls/) fetch call records.
I have got the server certificate and stored it in keystore (cacerts). I am successfully able to get 200 ok response for POST method but I get -
"Exception in thread "main" javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target" issue when I call GET method in my program.
I have tested the connection using SSLPoke class and I am getting Successful Connection for java -Djavax.net.debug=all SSLPoke webserver 8443
I get the issue when I run java -Djavax.net.debug=all SSLPoke webserver 443
Im not sure how your app is configured but I recognize that error. The certificate is not where your application expects it to be. If you're able to print out the path it's using to retrieve the cert before it does, that may help.

Connection refused in rest assured for HTTPS request

I am trying to test a REST API having an ELB similar to below:
https://systemtest-inventory.com/v1/inventory/getInventory
When I tried the URL with postman chrome, it is giving me valid response.
But when I try to use it in Java program as below:
RestAssured.baseURI="https://systemtest-inventory.com/";
RestAssured.get("v1/inventory/getInventory").then().assertThat().contentType(ContentType.JSON);
It gives this error:
org.apache.http.conn.HttpHostConnectException: Connection to
https://systemtest-inventory.com refused
I am aware that I am using HTTPS and need to have security certificate trusted. However, I am not sure how to do it. Is there any way in Rest assured to test with HTTPS and not HTTP.
You could do something as below for ignoring HTTPS Validation:
given().config(RestAssured.config().sslConfig( new SSLConfig().relaxedHTTPSValidation());
To ignore the HTTPS Connection you can use:
RestAssured.useRelaxedHTTPSValidation();

JAVA - SSL - Client Certifcates

I've been developing a WS client using JAVA and I'm having a problem with SSL authentication. The WS are created on WCF and I have no access to the server, they work through HTTPS and uses a client certificate that needs to be installed on the client first. The server guys sent me a PFX certificate which I successfully installed on the OS (I'm using OS X) and I could then access the WS via a browser (Safari or FF are both that I tried which previously couldn't access the WSs).
I thought any app in the OS would use this certs but when I'm tried my JAVA app it didn't work; at first the following error was being thrown:
"javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target"
I solved this by exporting the certificate to a CER file and using the keytool command line tool to add the certificate into the "cacerts" keyStore JAVA uses. But after this error went away the following started appearing: "403, forbidden". This is obviously because it's not using the SSL client cert for the site but I haven't been able to find a way to send it to it. Any help would be appreciated.
The following is the code I use to post to the WS:
URL url = new URL(p_url);
HttpsURLConnection conn = (HttpsURLConnection) url.openConnection();
conn.setDoOutput(true);
conn.setRequestMethod("POST");
conn.setRequestProperty("Content-Type", contentType);
OutputStream out = conn.getOutputStream(); // on this line it shows the error
You can either create a specific SSLContext (using a KeyManager initialised with the keystore containing your client cert + private key), from which you derive an SSLSocketFactory, which you set into your HttpsURLConnection, or use the global settings.
You could set the following system properties (for the global settings):
javax.net.ssl.keyStore=path/to/keystore.pfx
javax.net.ssl.keyStoreType=PKCS12
javax.net.ssl.keyStorePassword=xxxxxxxxx
Alternatively, you can create your own KeyManagerFactory/KeyManager as described in this answer.
Since you've imported the server certificate in your cacerts, use null for the TrustManager[] argument of SSLContext.init() (it will pick up the default values).
In addition, since you're on OSX, you could use the KeychainStore directly. To do so, use ....keyStore=NONE, keyStoreType=KeychainStore and keyStorePassword=- (any password will do, since access to the key will be granted when you need it from the OS). I'm not sure if it works on Lion, though. Note that it may fail if you have more than one cert+private key in your store (see this issue).
Looks like you probably need to set up your own SSL SocketFactory,
http://vafer.org/blog/20061010073725/
I would think things have gotten better since 2006, so you may just need to specify a bunch of properties on the command line:
http://stackoverflow.com/questions/875467/java-client-certificates-over-https-ssl
You need to load the keystore they send you in your java application.
You can load it as a file from the file system in a Keystore object and use it. Read this example and especially the part about KeyManager i.e. createKeyManagers method.
Another option would be to load the keystore from windows. Read about Windows-MY provider

How to get source of html page from a https adress in java

I am trying to implement a download manager in java for rapidshare, I am using the rapidshare API.
The problem is that for example if you go to the following link
it redirects to a https page, but then when I read the content it always return me null in the InputStream
When I try to put a https link in the HttpURLConnection it always throws an exeption
javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path validation failed: java.security.cert.CertPathValidatorException: Path does not chain with any of the trust anchors
Use Apache Commons HTTPUtils . You can make a connection to HTTPS (thereby decrypting it) if you override the DefaultTrustManager class (to do nothing), create a new TrustManager with it, then bypass the hostname verifier with ALLOW_ALL_HOSTNAME_VERIFIER. Since your opening the connection to a place that you trust, there isn't a problem bypassing these things.

Categories