Target Audience

Developers who are familiar with Java and Spring Boot [with maven]

We all are building various applications in Spring Boot. Spring boot is a simple lightweight spring application with the integrated server. We can run java[spring] application without any hassle, with most of the things are driven by application properties. We run single Spring Boot application in the single JVM. Many times we have to run more than one instance of the same application, to manage a large number of requests. We put these instances behind the load balancer, and load balancer will decide which instance should handle the current request.

Simple Pictorial Design

So our request comes to the load balancer. The load balancer is the entry point of the request. Here we have App 1, which have 3 instances.

Instance: Same Application running in the different server [or in there scope].

So, whenever request goes to any of the instances of App 1, it should behave in the same manner. We create multiple instances so that we can handle more requests. Consider these 3 green regions as separate JVM [seperate tomcat sever].

As we all know two JVMs does not tall to each other, We can consider JVM as an isolated boundary to run a Java application.

Problem Statement

Now suppose you want to somehow share data between these 3 different instances running on different JVM. Assume you need to count of the total number of request server by App 1. If we create a single variable in App1, which will be auto incremented each time request comes to application, it will not solve our problem. Lets name variable requestCounter. Now suppose the total number of request come to load balancer be 3.

Flow Of Request

Request 1 goes to instance 1

Request 2 goes to instance 2

Request 3 goes to instance 1

If We request for the total number of requests server by App 1

Instance 1 will return 2

Instance 2 will return 1

Instance 3 will return 0

Though App 1 serves total number 3 request, all instance provide the wrong result. This is because&nbsp; we are saving the requestCounter variable at an individual instance, thus every instance is giving the response of its state. We can either get the count from all the instance and sum it, but assume if you have hundred of instance of the same application, how you will do that.Even if we are ready to call each instance, we need to maintain the IP address of all the instances which can be very difficult.

For the same, we will you Hazelcast. What Hazelcast&nbsp; will do, it will share the state of variable among different instances [JVM].&nbsp; So in this blog, we will create a simple Spring Boot Application with HazelCast support. And try to share a single long variable among the different instances of Application.

Line 8 represents the instance name, it should be different for each instance, in our case Instance 1, Instance 2 and Instance 3

Line 9 represents the group. in our case it will be App 1, Since there can be much application you are running, you want to share hazelcast cluster among instances of the same app. In the code above we have used dev [App1]. On the same line, we have set the password also, as to avoid adding the cluster of different instance among the same group.

As a full stack developer, we need to create an application with both frontend-end and backend.

Today we will create a simple full stack application which will have a social login using Google authentication.The area on which we want to focus is how to integrate google social authentication to spring-boot, with logout functionality. And when angular 4 is used in spring-boot application to build the UI, how we will manage the routes, as we know that both angular and have routes, so how our application will resolve which route it has to call.

It will create the routes .First two route for setting and welcome is using href. normal HTML routes and then we have refined routes using routerLink.

Build the frontend application

ng build

Now we will make changes in spring application to consume this frontend code.First of all, we will add the code in our build.gradle to copy the frontend code and place it in resource so that it can be consume by spring-boot.

This view controller will enable the spring to resolve these URL as angular URL.

Now we are good to go.Run the spring boot application using gradle bootRun.it will start the application.Once you will try to react the application from the browser, it will navigate you to google login first.

On Successful login, you will see the angular page.So till now we are pretty much done with authentication part. Now comes the routing part.

Now try to navigate to welcome page and setting page using above router.In this case, the welcome route will be successful but setting URL will fail, as we have not mentioned it in ViewController.

But when we try the routes which are below one, every route will work fine, as it is using angular routes.

AOP stands for the Aspect-Oriented Programming. It is an approach to programming that allows global properties of a program to determine how it is compiled into an executable program. AOP can be used with object-oriented programming ( OOP ).It addresses the problem of cross-cutting concern.

All above is the technical definition, but now we will try to understand it in the more simpler term. Let suppose, as a developer you want to log request and response in the database whenever third-party API is called. One simple method is to add the logging code in the method itself. But should we add the code to log in method, as my method is not created for logging? Even if you are OK with adding the code to the method, now think if you have more than one method where you have to perform this logging. Now what? Will we write the logging code in each and every method?

No, what we will do, we will find some magic way, by which our logs should be automatically written to the database. And that magic is AOP.

Since by now we should know that AOP needs pointcut to perform the magic.Now suppose you just want to log whenever any method is called. If you put a simple annotation on any method, and your work is done.

In our previous post, we understand what annotation is, and how to create our custom annotations. Now we will try to understand how and when we can use annotation.

This is more sort of the suggestion rather than any rule of using experience.All this will be from my experience, it can change from person to person.

The common examples where I love to use annotations are:

Separating and Categorization

Every one of us loves to code and to protect our code we write test cases. We all are familiar with unit test cases and integration test cases. To reduce the build in time we always want to run these test cases in parallel.But to run them in parallel we first have to categorize these in two different buckets. we need some mechanism to identify what test cases are unit test cases and what are integration test cases.

For this, we will try very simple use case. We will try to use annotation to identify our type of test cases.We will create a simple spring application with Gradle, which have few unit test cases and integration test cases.

Java is one of my favorite languages. It is simple. But some of its features are still not used very commonly. One of them is Annotations. Annotation is very simple and one of the powerful concept of java. If you have worked the on framework like spring , you may have seen there are Annotation to do most of the setting.

Though we have used annotation in many ways , still I have not seen my developer going for the creation of their custom annotation. This blog helps us to understand when and where we can utilize the power of annotation.

Annotation is a tag which can have metadata that can be attached to class, interface, methods or fields to indicate some additional information which can be used by Java compiler and JVM.

Example:- @Deprecated,@Override,@PostConstruct are some of the in build java annotation which we have been using.Here you have seen we have added the annotation at class , at attribute and even at method.

Why Annotations?

Prior to Annotations, XML was often used to have the metadata. The Large set of Architectures and developers often believe that XML maintenance is difficult and it is not very easy to read. Something was needed which should be more close to code.Annotations are easy to understand and more readable.

Uses Of Annotations

Information for the compiler — Annotations can be used by the compiler to detect errors or suppress warnings or to give some information to the compiler.[eg- @Serialization]

Runtime processing — Some annotations are available to be examined at runtime.[ It can be used as point cut in Aspect Oriented Programming]

Comments — Often people use annotation to provide comments, why I prefer annotations over the comment as it provides the structural way of commenting.[@Deprecated, any other custom annotation]

How Annotation Works?

Before using any concept we should understand how it works internally, only then we can explore the better way of using it and can use it properly.As we all know annotation does not contain any business knowledge.Then how it actually works?

When Java source code is compiled, annotations can be processed by compiler plug-ins called annotation processors. Processors can produce informational messages or create additional Java source files or resources, which in turn may be compiled and processed, and also modify the annotated code itself. The Java compiler conditionally stores annotation metadata in the class files, if the annotation has a RetentionPolicy of CLASS or RUNTIME(We will cover more about retention policy in further section). Later, the JVM or other programs can look for the metadata to determine how to interact with the program elements or change their behavior.

In addition to processing an annotation using an annotation processor, a Java programmer can write their own code that uses reflections to process the annotation

This package contains the interface called AnnotatedElement that is implemented by the Java reflection classes including Class, Constructor, Field, Method, and Package. The implementations of this interface are used to represent an annotated element of the program currently running in the Java Virtual Machine. This interface allows annotations to be read reflectively.

The AnnotatedElement interface provides access to annotations having RUNTIME retention. This access is provided by the getAnnotation, getAnnotations, and isAnnotationPresentmethods. Because annotation types are compiled and stored in byte code files just like classes, the annotations returned by these methods can be queried just like any regular Java object.

How to Build Custom Annotation?

Below is the simplest Annotation one can create.

public @interface CustomAnnotation {
}

Annotations itself can have some annotations, which tell us something about our new annotation.

Retention – It tells java how long any annotation will be retained during the different phase of code. Retention annotation have property RetentionPolicy which have 3 possible values:-

Source: Annotations are to be discarded by the compiler.

Class: Annotations are to be recorded in the class file by the compiler but need not be retained by the VM at run time.[DEFAULT]

Runtime: Annotations are to be recorded in the class file by the compiler and retained by the VM at run time so they may be read reflectively.

Note-A Retention meta-annotation has effect only if the meta-annotated type is used directly for annotation. It has no effect if the meta-annotated type is used as a member type in another annotation type.

Target: As we know we can put annotation at many different levels, at class, at attribute and many other. But as a developer, you might want to bound the use of your annotation at some level only, as your annotation can make sense some particular level.To declare the level this annotation is used.It has an attribute array of element type which can have all the possible level. There are different type elements in java.Most of them are self-explanatory.

Element Type

TYPE

FIELD

METHOD

PARAMETER

CONSTRUCTOR

LOCAL_VARIABLE

ANNOTATION_TYPE

PACKAGE

TYPE_PARAMETER [new in java 1.8]

eg <T extends @A Object & @B Comparable, U extends @C Cloneable>

TYPE_USE [new in java 1.8] eg –

Map<@NonNull String, @NonEmpty List<@Readonly Document>> files;

Inherited:- If this annotation is present it will be inherited to the subclass, By default it is not present. It will only be effective when the annotation is given at class level.

Documented:- Marks the annotation for inclusion in the documentation. Indicates that annotations with a type are to be documented by javadoc and similar tools by default.

Repeatable: Prior to Java 8 user were not allowed to give same anntation multiple times at same place.But If any annotation have repeatable annotation that can be put multiple time at same place.

In our custom annotation, we have two properties name and identifier. A value doesn’t have any default property, so whenever we use this CustomAnnotation it is mandated to give value attribute some value, otherwise, it gives error.On the other hand, identifier contain some default value, so we don’t have to compulsory give its value.

So, till now we have some basic idea how annotation work, and how to create an annotation.In the further blog, we will see the different situations where we can create our own custom annotations, and how to tell JVM to process these annotations.