Java SSLSocket with TLS1.3 and TLS_AES_128_GCM_SHA256 Cipher Tutorial

How to send TLS1.3 HTTPs request to your domain and print response?

SSLSocket class extends Sockets and provides secure socket using protocols such as the “Secure Sockets Layer” (SSL) or IETF “Transport Layer Security” (TLS) protocols.

In this tutorial we will set protocol TLS1.3 and cipher TLS_AES_128_GCM_SHA256.

Let’s get started:

  • Create file CrunchifySSLTLS13Tutorial.java
  • Set protocol: TLS1.3
  • Set Cipher: TLS_AES_128_GCM_SHA256
  • Make HTTP 1.0 call to crunchify.com
  • Make HTTP 1.0 call to google.com
  • Print response
package crunchify.com.tutorials;

import javax.net.ssl.SSLSocket;
import javax.net.ssl.SSLSocketFactory;
import java.io.*;

/**
 * @author Crunchify.com
 * version: 1.0
 * Tutorial: Java SSLSocket with TLS1.3 and TLS_AES_128_GCM_SHA256 Cipher Tutorial
 */

public class CrunchifySSLTLS13Tutorial {

    // TLS1.3: There are new ciphersuites that only work in TLSv1.3. The old ciphersuites cannot be used for TLSv1.3 connections and the new ones cannot be used in TLSv1.2 and below.
    //The new ciphersuites are defined differently and do not specify the certificate type (e.g. RSA, DSA, ECDSA) or the key exchange mechanism (e.g. DHE or ECHDE). This has implications for ciphersuite configuration.
    private static final String[] crunchifyProtocols = new String[]{ "TLSv1.3" };

    // TLS_AES_128_GCM_SHA256 Encryption: Advanced Encryption Standard with 128bit key in Galois/Counter mode (AES 128 GCM)
    // Hash: Secure Hash Algorithm 256 (SHA256)
    // RFC 8446
    private static final String[] crunchifyCipher = new String[]{ "TLS_AES_256_GCM_SHA384" };

    public static void main(String[] args) throws Exception {

        // This class extends Sockets and provides secure socket using protocols such as the "Secure Sockets Layer" (SSL) or IETF "Transport Layer Security" (TLS) protocols.
        SSLSocket crunchifySocket = null;
        PrintWriter crunchifyPrintWriter = null;
        BufferedReader crunchifyBufferReader = null;

        try {
            // initialize SSL Socket Factory
            SSLSocketFactory crunchifyFactory = (SSLSocketFactory) SSLSocketFactory.getDefault();

            crunchifySocket = (SSLSocket) crunchifyFactory.createSocket("google.com", 443);

            // Enable protocol : TLS 1.3
            crunchifySocket.setEnabledProtocols(crunchifyProtocols);

            // Enable Cipher: TLS_AES_128_GCM_SHA256
            crunchifySocket.setEnabledCipherSuites(crunchifyCipher);

            // Start Handshake
            crunchifySocket.startHandshake();

            // Creates a new PrintWriter, without automatic line flushing.
            crunchifyPrintWriter = new PrintWriter(new BufferedWriter(new OutputStreamWriter(crunchifySocket.getOutputStream())));

            crunchifyPrintWriter.println("GET / HTTP/1.0");
            crunchifyPrintWriter.println();
            crunchifyPrintWriter.flush();

            if (crunchifyPrintWriter.checkError())
                System.out.println("SSLSocketClient Error:  java.io.PrintWriter error");

            // Let's get response
            crunchifyBufferReader = new BufferedReader(new InputStreamReader(crunchifySocket.getInputStream()));

            String crunchifyStringLine;
            while ((crunchifyStringLine = crunchifyBufferReader.readLine()) != null)
                crunchifyLog(crunchifyStringLine);

        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            // Close Socket
            if (crunchifySocket != null)
                crunchifySocket.close();

            // Close PrintWriter
            if (crunchifyPrintWriter != null)
                crunchifyPrintWriter.close();

            // Close Buffer Reader
            if (crunchifyBufferReader != null)
                crunchifyBufferReader.close();
        }
    }

    private static void crunchifyLog(String crunchifyStringLine) {

        System.out.println(crunchifyStringLine);
    }

}

These are defined TLS1.3 protocols:

  • TLS_AES_128_CCM_8_SHA256
  • TLS_AES_128_CCM_SHA256
  • TLS_AES_128_GCM_SHA256
  • TLS_AES_256_GCM_SHA384
  • TLS_CHACHA20_POLY1305_SHA256

Result:

On Crunchify, we have TLS1.3 enabled and hence there isn’t any error we got.

/Library/Java/JavaVirtualMachines/jdk-13.0.1.jdk/Contents/Home/bin/java -javaagent:/Applications/IntelliJ IDEA.app/Contents/lib/idea_rt.jar=62909:/Applications/IntelliJ IDEA.app/Contents/bin -Dfile.encoding=UTF-8 -classpath /Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/target/classes:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/zxing-2.1.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/commons-logging-1.1.2.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/commons-collections-3.2.1.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/javax.mail.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/commons-io-2.4.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/commons-lang-2.6.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/commons-configuration-1.9.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/log4j-1.2.17.jar:/Users/crunchify/Documents/C/crunchify-github/CrunchifyTutorials/WebContent/WEB-INF/lib/commons-beanutils-1.8.3.jar:/Users/crunchify/.m2/repository/org/glassfish/javax.json/1.0.4/javax.json-1.0.4.jar:/Users/crunchify/.m2/repository/com/github/wnameless/json-flattener/0.2.2/json-flattener-0.2.2.jar:/Users/crunchify/.m2/repository/com/eclipsesource/minimal-json/minimal-json/0.9.4/minimal-json-0.9.4.jar:/Users/crunchify/.m2/repository/org/apache/commons/commons-lang3/3.4/commons-lang3-3.4.jar:/Users/crunchify/.m2/repository/com/google/code/gson/gson/2.8.0/gson-2.8.0.jar:/Users/crunchify/.m2/repository/net/jodah/expiringmap/0.5.7/expiringmap-0.5.7.jar:/Users/crunchify/.m2/repository/org/apache/httpcomponents/httpclient/4.3.6/httpclient-4.3.6.jar:/Users/crunchify/.m2/repository/org/apache/httpcomponents/httpcore/4.3.3/httpcore-4.3.3.jar:/Users/crunchify/.m2/repository/commons-codec/commons-codec/1.6/commons-codec-1.6.jar:/Users/crunchify/.m2/repository/org/json/json/20151123/json-20151123.jar:/Users/crunchify/.m2/repository/net/spy/spymemcached/2.12.3/spymemcached-2.12.3.jar:/Users/crunchify/.m2/repository/com/whalin/Memcached-Java-Client/3.0.2/Memcached-Java-Client-3.0.2.jar:/Users/crunchify/.m2/repository/commons-pool/commons-pool/1.5.6/commons-pool-1.5.6.jar:/Users/crunchify/.m2/repository/org/slf4j/slf4j-api/1.6.4/slf4j-api-1.6.4.jar:/Users/crunchify/.m2/repository/com/googlecode/xmemcached/xmemcached/2.4.5/xmemcached-2.4.5.jar:/Users/crunchify/.m2/repository/com/paypal/sdk/rest-api-sdk/1.14.0/rest-api-sdk-1.14.0.jar:/Users/crunchify/.m2/repository/commons-dbcp/commons-dbcp/20030825.184428/commons-dbcp-20030825.184428.jar:/Users/crunchify/.m2/repository/javax/ws/rs/javax.ws.rs-api/2.0/javax.ws.rs-api-2.0.jar:/Users/crunchify/.m2/repository/org/hamcrest/hamcrest-all/1.3/hamcrest-all-1.3.jar:/Users/crunchify/.m2/repository/log4j/log4j/1.2.17/log4j-1.2.17.jar:/Users/crunchify/.m2/repository/com/google/guava/guava/19.0/guava-19.0.jar:/Users/crunchify/.m2/repository/com/googlecode/json-simple/json-simple/1.1/json-simple-1.1.jar:/Users/crunchify/.m2/repository/commons-net/commons-net/2.0/commons-net-2.0.jar:/Users/crunchify/.m2/repository/asm/asm/3.3.1/asm-3.3.1.jar:/Users/crunchify/.m2/repository/axis/axis/1.4/axis-1.4.jar:/Users/crunchify/.m2/repository/org/apache/axis/axis-jaxrpc/1.4/axis-jaxrpc-1.4.jar:/Users/crunchify/.m2/repository/axis/axis-wsdl4j/1.5.1/axis-wsdl4j-1.5.1.jar:/Users/crunchify/.m2/repository/commons-beanutils/commons-beanutils/1.8.3/commons-beanutils-1.8.3.jar:/Users/crunchify/.m2/repository/commons-collections/commons-collections/3.2.1/commons-collections-3.2.1.jar:/Users/crunchify/.m2/repository/commons-configuration/commons-configuration/1.10/commons-configuration-1.10.jar:/Users/crunchify/.m2/repository/commons-io/commons-io/2.4/commons-io-2.4.jar:/Users/crunchify/.m2/repository/commons-discovery/commons-discovery/0.5/commons-discovery-0.5.jar:/Users/crunchify/.m2/repository/commons-lang/commons-lang/2.6/commons-lang-2.6.jar:/Users/crunchify/.m2/repository/commons-logging/commons-logging/1.1.3/commons-logging-1.1.3.jar:/Users/crunchify/.m2/repository/commons-logging/commons-logging-api/1.1/commons-logging-api-1.1.jar:/Users/crunchify/.m2/repository/javax/mail/mail/1.4.7/mail-1.4.7.jar:/Users/crunchify/.m2/repository/javax/activation/activation/1.1/activation-1.1.jar:/Users/crunchify/.m2/repository/javax/xml/jaxrpc-api/1.1/jaxrpc-api-1.1.jar:/Users/crunchify/.m2/repository/javax/servlet/javax.servlet-api/3.1.0/javax.servlet-api-3.1.0.jar:/Users/crunchify/.m2/repository/org/apache/axis/axis-saaj/1.4/axis-saaj-1.4.jar:/Users/crunchify/.m2/repository/wsdl4j/wsdl4j/1.6.3/wsdl4j-1.6.3.jar:/Users/crunchify/.m2/repository/com/google/zxing/core/3.2.1/core-3.2.1.jar:/Users/crunchify/.m2/repository/org/apache/commons/commons-compress/1.9/commons-compress-1.9.jar:/Users/crunchify/.m2/repository/mysql/mysql-connector-java/5.1.6/mysql-connector-java-5.1.6.jar:/Users/crunchify/.m2/repository/junit/junit/4.12/junit-4.12.jar:/Users/crunchify/.m2/repository/org/hamcrest/hamcrest-core/1.3/hamcrest-core-1.3.jar:/Users/crunchify/.m2/repository/ch/qos/logback/logback-classic/1.2.3/logback-classic-1.2.3.jar:/Users/crunchify/.m2/repository/ch/qos/logback/logback-core/1.2.3/logback-core-1.2.3.jar:/Users/crunchify/.m2/repository/org/springframework/spring-context/5.1.3.RELEASE/spring-context-5.1.3.RELEASE.jar:/Users/crunchify/.m2/repository/org/springframework/spring-aop/5.1.3.RELEASE/spring-aop-5.1.3.RELEASE.jar:/Users/crunchify/.m2/repository/org/springframework/spring-beans/5.1.3.RELEASE/spring-beans-5.1.3.RELEASE.jar:/Users/crunchify/.m2/repository/org/springframework/spring-core/5.1.3.RELEASE/spring-core-5.1.3.RELEASE.jar:/Users/crunchify/.m2/repository/org/springframework/spring-jcl/5.1.3.RELEASE/spring-jcl-5.1.3.RELEASE.jar:/Users/crunchify/.m2/repository/org/springframework/spring-expression/5.1.3.RELEASE/spring-expression-5.1.3.RELEASE.jar:/Users/crunchify/.m2/repository/org/springframework/spring-context-support/5.1.3.RELEASE/spring-context-support-5.1.3.RELEASE.jar crunchify.com.tutorials.CrunchifySSLTLS13Tutorial
HTTP/1.1 301 Moved Permanently
Server: nginx
Date: Sat, 18 Jul 2020 03:10:08 GMT
Content-Type: text/html
Content-Length: 162
Connection: close
Location: http://000000000.kinsta.com/
X-Content-Type-Options: nosniff

<html>
<head><title>301 Moved Permanently</title></head>
<body>
<center><h1>301 Moved Permanently</h1></center>
<hr><center>nginx</center>
</body>
</html>

Process finished with exit code 0

Try hitting Google.com. Just replace crunchify.com domain and re-run program.

Result with google.com domain:

HTTP/1.0 200 OK
Date: Sat, 18 Jul 2020 03:29:22 GMT
Expires: -1
Cache-Control: private, max-age=0
Content-Type: text/html; charset=ISO-8859-1
P3P: CP="This is not a P3P policy! See g.co/p3phelp for more info."
Server: gws

X-XSS-Protection: 0
X-Frame-Options: SAMEORIGIN

Set-Cookie: 1P_JAR=2020-07-18-03; expires=Mon, 17-Aug-2020 03:29:22 GMT; path=/; domain=.google.com; Secure
Set-Cookie: NID=204=BDdFDUl5oe-0jvYXe8O9RF8x2cYz5q6dy0JRxsdQYFYV86TqTAEIPYB5BwoZCiaM0oUQ5GovV9x8qAiflI3gSbt45VrVmrXCgQX687SyRPO1lh

I hope this tutorial will help you hit any URL with TLS1.3 protocol.

The post Java SSLSocket with TLS1.3 and TLS_AES_128_GCM_SHA256 Cipher Example appeared first on Crunchify.