Spring Boot Apps- Technical Issues and Challenges


Hi, I am Malathi Boggavarapu working at Volvo Group and i live in Gothenburg, Sweden. I have been working on Java since several years and had vast experience and knowledge across various technologies.

This post is related to technical challenges that were being faced at daily work regarding Spring Boot applications. Please note, anyone who is willing to share the problems and solutions regarding Spring Boot applications, you are welcome to post them in comment box. I will add them to this post so that it would be helpful for others.

Let's also talk a bit about Spring Boot.

Spring Boot makes life easier when we want to integrate different libraries and frameworks in your application due to its dependency management structure. Spring boot causes intelligent collection of dependencies "The bill of materials" or BOM. The spring developers have taken the time to match up all the frameworks that you may want to include in your application with appropriate versions that work well with each other. For example if you are working with Spring version 4.2.3, you would want to use 1.3.3 of the logback-core since those two frameworks and their versions have a known working relationship. By using Spring Boot bill of materials, all these "version matches" have been setup already for you. If you ever started pointing dependencies manually by  including them in your build one by one, you may have to run into situation where you have to spend spare amount of time trying to find the right version of libraries that work well with each other. 

For more information about how Spring Boot works and how to create Spring Boot application from scratch, please visit my post http://passion4technologyenrichment.blogspot.com/2018/04/SpringBootApplication.html

I have had handful of experience regarding Spring Boot and i am posting the problems along with the solutions i came across while working with it. The problems vary from minor to major.

Question 1: java.lang.IllegalStateException - Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException

I had a JUnit test class which loads the main spring boot application class called Fleet. When i build the application using gradle or maven, below test class ApplicationTests failed because of missing annotation for one of the class while it is being used or Autowired in some other class. 

Example: I forgot to add @component annotation to a class X and Autowired the class X in another class Y inorder to use it. But as it is missing the annotation, Spring Boot could not identify the class X and as a result it could not load it. Hence it throws below exception while running JUnit test.

> Task :test

> contextLoads FAILED
    java.lang.IllegalStateException
        Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException
            Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException
                Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException

1 test completed, 1 failed

> Task :test FAILED

Below is my example JUnit test class.

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.springframework.test.context.web.WebAppConfiguration;

@RunWith(SpringJUnit4ClassRunner.class)
@SpringBootTest(classes = Fleet.class)
@WebAppConfigurationpublic class ApplicationTests {

   @Test   public void contextLoads() {
       // empty   }

}

Question 2

The below exception is thrown when we update ActiveMq with the version 5.12.2 and above. 
Because a new security feature is implemented in ActiveMq from version 5.12.2 onwards.

This class is not trusted to be serialized as ObjectMessage payload. 
Please take a look at http://activemq.apache.org/objectmessage.html for more information 
on how to configure trusted classes.

Solution

Inorder to resolve the above exception, we need to add a property to application.properties
spring.activemq.packages.trust-all=true

If you are still using ActiveMQ version below 5.12.2 then there is no need to add this property.
It just work with existing proeprties.

Question 3

org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'dataSource' 
defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceConfiguration$Hikari.class]: 
Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: 
Failed to instantiate [com.zaxxer.hikari.HikariDataSource]: Factory method 'dataSource' threw 
exception; nested exception is 
java.lang.IllegalStateException: Cannot load driver class: oracle.jdbc.driver.OracleDriver

Solution

We need to download ojdbc driver from oracle website and install it to your local maven repository. 
Below are the steps to install ojdbc driver to local maven repo. For more information visit my post 
Install ojdbc driver to Maven Local repo

Download ojdbc.jar

Go to Oracle website and download ojdbc jar file of your choice. It could be ojdbc6.jar or ojdbc8.jar. I prefer ojdbc8.jar.

Maven Install

mvn install:install-file -Dfile='{Path/to/your/ojdbc8.jar}' -DgroupId=com.oracle -DartifactId=ojdbc8 -Dversion=12.2.0.1 -Dpackaging=jar
Example:

Check the installed ojdbc in Mavel local repository

Now go to .m2/repository/com/ folder in your system and there you will find oracle installed in your local maven repo.

Update your build file(build.gradle or pom.xml)

Do not forget to add mavelLocal() to gradle build file as the jdbc driver is installed locally. Same is applicable to Maven pom.xml as well.
Gradle
buildscript { ext { springBootVersion = '2.1.1.RELEASE' } repositories { maven { url "https://plugins.gradle.org/m2/" } mavenCentral() mavenLocal() } dependencies { classpath("org.springframework.boot:spring-boot-gradle-plugin:${springBootVersion}") } } dependencies { implementation 'com.oracle:ojdbc8:12.2.0.1' }

Maven
<dependencies> <!-- ojdbc8.jar example --> <dependency> <groupId>com.oracle</groupId> <artifactId>ojdbc7</artifactId> <version>12.1.0</version> </dependency> </dependencies>
Question 4 
Field vehicleService in com.vgcs.dispatcherapi.controllers.VehicleController required a bean of type 'com.vgcs.dispatcherapi.services.VehicleService' that could not be found. The injection point has the following annotations: - @org.springframework.beans.factory.annotation.Autowired(required=true) Action: Consider defining a bean of type 'com.vgcs.dispatcherapi.services.VehicleService' in your configuration.

Solution

In the above exception VehicleService is AutoWired in VehicleController class but VehilceService
 implementation class is not annotated with Spring annotation @Service. So to resolve this
 error we just need to annotate the VehicleService interface implementation class with 
 @Service annotation.

Question 5

If the Spring Boot application is started successfully but could not reach any of your REST 
 endpoints either by hitting in the browser or by using Postman, then you might be missing to
 add arguemnts to @SpringBootApplciation annotation defined at class level of your main 
 Spring boot application class

Example:

@SpringBootApplication(scanBasePackages = {com/vgcs/})

In the above example, all the Spring annotated classes under the package com/vgcs will be scanned 
and initiated by the Spring framework.

This post do not have any END. We continue adding the problems and solutions that arise while we 
work with Spring Boot applications. 

Please post your Problems/Exceptions/Errors in the comment box below. This post can be updated 
accordingly.

Comments

Popular posts from this blog

Bash - Execute Pl/Sql script from Shell script

How to get client Ip Address using Java HttpServletRequest

How to install Portable JDK in Windows without Admin rights