Author Archives: cyberaka

About cyberaka

I am an experienced Senior Solution Architect with proven history of designing robust and highly available Java based solutions. I am skilled in architecting designing and developing scalable, highly available, fault tolerant and concurrent systems which can serve high volume traffic. I have hands on experience in designing RESTful MicroServices architecture using Spring Boot, Spring Cloud, MongoDB, Java 8, Redis and Kafka. I like TDD (JUnit), BDD (Cucumber) and DDD based development as required for my projects. I have used AWS primarily for cloud based deployment and I like developing cloud enabled POC as a hobby in my spare time. I have deigned and developed CI/CD pipeline using Jenkins and leveraged Docker, Kubernetes for containerizing and deploying some of my applications. I am highly experienced in creating high performing technical teams from scratch. As an ex-entrepreneur I am very much involved in the business side of the IT industry. I love interacting with clients to understand their requirements and get the job done.

Throttling & Tuning Spring Boot

One of my Spring-Boot projects was battling with overloaded CPU and unresponsive / slow server response at times when there is more traffic. I have explored and implemented caching but my problem was with excessive connections coming in and server itself becoming slow. I could have setup multiple instances and do some kind of auto-scaling but given limited budget and hardware I wanted to put in some hard limits on my Spring-Boot app as to how much traffic it can take in and when it can give up gracefully (there is no shame in rejecting traffic with HTTP status 503 if the server infrastructure is overloaded).

I found a blog post entry from Netflix on how to tune Apache Tomcat and another article on how to tune Rest Controller code itself to implement a rudimentary Rate Limiter. I was glad to find the RateLimiter implementation in Goggle Guava library which I ultimately ended up using (for now). However I think the annotation driven RateLimiter is also a very good solution which is certainly very powerful and I will take it out for a spin sometime in near future.

The basic lesson learnt from this exercise:
– Tweak Tomcat and keep a watch on the acceptCount parameter which technically puts in a limit of how much traffic reaches your Rest controller.
– Use a RateLimiter on your hot APIs (which have higher latency) and don’t let your application get abused beyond a limit.
– Scale horizontally if the limits set above result in lot of traffic getting rejected.

Nginx gzip compression and load balancing.

To tune performance of my REST endpoints in past I have enabled Gzip compression in my nginx server configuration. So technically a large json response becomes gzipped and the network latency as a result goes down.

There is a good documentation of this feature on the nginx website which does a pretty good job.

However there is a catch which prevents this technique from working on local development system (while the same config works in production linux instance). I finally found an answer as to why this doesn’t work in some of my local environment.

To do static load balancing I use the upstream concept of nginx which is documented again on the nginx website. The performance is reasonable and the implementation is quite simple for a requirement which needs a simple failover implementation. However for advanced implementation we can always go to haproxy which is very good open source load balancer.

Issues Faced While Upgrading to JDK 11 and Spring Boot 2.2.5

I had a old project which was running on JDK 8 and Spring Boot 1.5.x which I just upgraded to JDK 11 and Spring Boot 2.2.5. I faced some hiccups in the process but it is finally done and the application is up and running. I will be documenting some of the issues faced in this process.

Spring Data
All instances of findOne() had to be replaced with findByID() which returns Optional<Entity> reference. I ended up removing lots of null checks by leveraging the Optional features of “orElse”, “orThrow” and “ifPresent” methods provided by Optional interface. It definitely is a better way to handle null.

JAXB runtime error
After migration the application booted up fine but on doing some specific operation I observed this error on console

java.lang.ClassNotFoundException: javax.xml.bind.DatatypeConverter

It seems this class has been moved out of the core library in JDK. This error kind of stumped me as some posts on internet suggested adding the following entry in pom.xml

<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>2.3.1</version>
<scope>runtime</scope>
</dependency>

However this didn’t help and I ended up using the following library to finally get rid of this issue:

<dependency>
<groupId>jakarta.xml.bind</groupId>
<artifactId>jakarta.xml.bind-api</artifactId>
</dependency>

Apache POI / Tika Library
This is another runtime issue faced during this application operation.

WARNING: An illegal reflective access operation has occurred
 WARNING: Illegal reflective access by org.apache.poi.openxml4j.util.ZipSecureFile$1 (file:/Users/562320/.m2/repository/org/apache/tika/tika-app/1.15/tika-app-1.15.jar) to field java.io.FilterInputStream.in
 WARNING: Please consider reporting this to the maintainers of org.apache.poi.openxml4j.util.ZipSecureFile$1
 WARNING: Use --illegal-access=warn to enable warnings of further illegal reflective access operations
 WARNING: All illegal access operations will be denied in a future release
 Jun 29, 2020 3:14:17 AM org.apache.catalina.core.StandardWrapperValve invoke
 SEVERE: Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.apache.poi.openxml4j.exceptions.OpenXML4JRuntimeException: Fail to save: an error occurs while saving the package : class org.apache.poi.openxml4j.util.ZipSecureFile$ThresholdInputStream cannot be cast to class java.util.zip.ZipFile$ZipFileInputStream (org.apache.poi.openxml4j.util.ZipSecureFile$ThresholdInputStream is in unnamed module of loader 'app'; java.util.zip.ZipFile$ZipFileInputStream is in module java.base of loader 'bootstrap')] with root cause
 java.lang.ClassCastException: class org.apache.poi.openxml4j.util.ZipSecureFile$ThresholdInputStream cannot be cast to class java.util.zip.ZipFile$ZipFileInputStream (org.apache.poi.openxml4j.util.ZipSecureFile$ThresholdInputStream is in unnamed module of loader 'app'; java.util.zip.ZipFile$ZipFileInputStream is in module java.base of loader 'bootstrap')
     at java.base/java.util.zip.ZipFile$ZipFileInflaterInputStream.available(ZipFile.java:480)

This issue got resolved after upgrading the Apache Tika, Apache POI to latest version. I also had to upgrade the apache-commons-lang package to apache-commons-lang3 package.

Progress Bar implementation in Java for Terminal application

Th e”\r” character basically reverts the current cursor back to the 1st column in the current line. This concept should basically work on Mac, Linux and Windows. So to test it I wrote a quick hack and it worked properly:

public class ProgressBar {

    public static void main(String[] args) {
        int size = 10;
        for (int i=1; i<size; i++) {
            try {
                Thread.sleep(500);
                System.out.print("|" + "=".repeat(i) + ">" + " ".repeat(size-i) + "|\r");
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        System.out.print("|" + "=".repeat(size) + "|\r");
    }
}

// Initial Output
// |=>        |
// Final Output
// |==========|

I got the desired output and a humble do nothing progress bar did come up on terminal. To further this idea I did some internet search and I ended up finding this repo on GitHub. It basically allows you to implement beautiful progress bars for terminal based Java application. The basic concept is the same but it provides much more functionality.

Block a shell script till a server boots up

This small script blocks a shell script / docker compose command script till a dependent server boots up.

#!/usr/bin/env bash

while :
do
  response=$(curl --write-out %{http_code} --silent --output /dev/null -X GET "$1")
  if [[ "$response" -ne 200 ]] ; then
    echo "Server is not yet up >> $1 >> $response"
    sleep 1
  else
    echo "Server is up >> $1 >> $response"
    exit 1
  fi
done

Spring Cloud Configuration Issue

For a new project I was trying to setup a config server to connect my services together. Although the spring-cloud-config server works fine, I am not able to make my service talk to the config-server which is really strange as I am fairly well versed with Spring Cloud and usually setting up a dev environment is a no-brainer.

I have described my issue in stackoverflow to get help and I am debugging in parallel as well.

Bye Bye Hystrix

Hystrix used to be my tool of choice for implementing circuit breakers in my Spring Boot application. However there has been literally no commits in Hystrix github repo for past 1 year. It seems Netflix has moved on to resilience4j which will be actively maintained.

Resilience4j commit log is quite active and a lot of active work is going on in it.

However it should be noted that there is another mature library named Sentinel which seems to be quite feature rich and very well supported. It has been battle tested by Alibaba which is huge. In my next project I would be considering both Sentinel and Resilience4J in my choice for a reliable circuit breaker for my application.

Taking backup zip from multi-module Java project

I like to keep an archive of my code on a monthly basis. I wrote a small bash script to create zip out of my multi module Java projects. It gets the job done and can be improved to include resources and test folders as well. As of now I am only interested in the Java code zip backup.

!/bin/bash
 if [ -d "combined" ]; then
     echo "Removing existing zip files in combined .."
     rm combined/*.zip
 else
     echo "Creating combined folder.."
     mkdir combined
 fi
 for d in */ ; do
     if [ -d "$d/src/main/java" ]; then
         var="$(echo $d | sed 's/.$//')"
         echo "Processing $var .."
         cd $d/src/main/java
         zip -r ../../../../combined/$var.zip com
         cd ../../../..
     else
         echo "Ignoring .. $d"
     fi
 done