Troubleshoot Auto-Configurations in Spring Boot Applications
In this post, we will take a look at how to troubleshoot auto-configurations in Spring Boot applications.
What are Auto-Configurations?
Spring boot autoconfiguration is where the magic happens. The auto-configuration tries to automatically configure your application based on what’s in the classpath. For example, the h2 database jar in classpath will result in spring boot creating in-memory database beans.
Even though this feature is awesome, there are some cases where auto-configurations may fail. So you need to know how to troubleshoot auto-configurations. Even more so when you are trying to override the default auto-configurations.
Steps to troubleshoot Auto-Configurations in Spring Boot
Let’s go through a certain set of steps in detail to troubleshoot the auto-configurations.
Condition Evaluation Report
First of all, spring boot provides useful ConditionEvaluationReport
at the application startup. But this report is not visible in logs by default. To enable this, you need to add the following configuration to your application.properties
.
debug=true
Code language: Properties (properties)
This option enables all startup related debug info, including the Condition Evaluation Report. This report tells you which auto-configurations were matched or excluded from all available auto-configurations. For example, here is a sample output.
============================
CONDITIONS EVALUATION REPORT
============================
Positive matches:
-----------------
AopAutoConfiguration matched:
- @ConditionalOnProperty (spring.aop.auto=true) matched (OnPropertyCondition)
AopAutoConfiguration.ClassProxyingConfiguration matched:
- @ConditionalOnMissingClass did not find unwanted class 'org.aspectj.weaver.Advice' (OnClassCondition)
- @ConditionalOnProperty (spring.aop.proxy-target-class=true) matched (OnPropertyCondition)
....
Code language: Java (java)
The report contains all relevant information for us to troubleshoot auto-configuration classes.
- Positive matches – the auto-configuration which matched at least one condition (like a jar in classpath or properties entries etc)
- Negative matches – These are the configurations classes that didn’t satisfy any conditions. So Spring boot ignored them. Usually, you would see more of them.
- Exclusions – When you exclude certain configs using the
exclude
parameter of@SpringBootApplication
annotation, they will show up here. - Unconditional classes – These items always execute as they are Core auto configurations and spring boot relies on it to boot up.
For example, When you add thymeleaf starter into your classpath, then you can see the following entry in the Positive match.
ThymeleafAutoConfiguration matched:
- @ConditionalOnClass found required classes 'org.thymeleaf.templatemode.TemplateMode', 'org.thymeleaf.spring5.SpringTemplateEngine' (OnClassCondition)
Code language: Java (java)
This is because the ThymeleafAutoConfiguration class was looking for those two classes in the application classpath.Now that spring boot found these, it will run this auto-configuration and create beans related to thymeleaf.
Similarly, we can disable CacheAutoConfiguration by doing this.
@SpringBootApplication(exclude = CacheAutoConfiguration.class)
public class SpringBootTroubleshootAutoconfigApplication {
Code language: Java (java)
By doing that, you can see the following result in the conditions evaluation report.
Exclusions:
-----------
org.springframework.boot.autoconfigure.cache.CacheAutoConfiguration
Code language: Java (java)
The unconditional classes are always these five.
Unconditional classes:
----------------------
org.springframework.boot.autoconfigure.context.ConfigurationPropertiesAutoConfiguration
org.springframework.boot.autoconfigure.context.LifecycleAutoConfiguration
org.springframework.boot.autoconfigure.context.PropertyPlaceholderAutoConfiguration
org.springframework.boot.autoconfigure.availability.ApplicationAvailabilityAutoConfiguration
org.springframework.boot.autoconfigure.info.ProjectInfoAutoConfiguration
Code language: Java (java)
If you understand these key points, then you can easily troubleshoot which auto-configuration was loaded and how to fix them
Read The Logs about troubleshooting messages
In error cases, spring boot will write a detailed troubleshoot message with clues on how to fix them. This spring boot feature is known as failure analyzers. For example, If you add spring-data-jpa starter, but not any properties related to datasource, then you will get the following output.
As you see, the error message tells you that it doesn’t find spring.datasource.url
(or at least an embedded datasource). The suggested action is to add an embedded database like H2 or check if appropriate profiles for the database is currently active. You might also see similar errors when port 8080 is already in use.
Read the source of Auto-Configurations
The documentation doesn’t cover every situation that a programmer might face. For this reason, you must be ready to get your hands greasy. All the auto-configuration classes are part of the spring-boot-autoconfigure.jar
. And this JAR comes with its source which you can easily download through IDE or see online.
All auto-configuration classes follow the “**AutoConfiguration” naming convention. So if you are looking for Redis related auto-configurations, you could search for RedisAutoConfiguration without any doubt.
Look for @Conditional annotations
And if you see the source of this class, you can see that the configuration can only come in to effect if redis related classes are available in classpath.
On successful condition, the auto configuration adds RedisTemplate
beans and also imports two other configuration classes. So it is nice to explore these classes yourself.
Troubleshoot @Configuration properties
Make sure you are using the correct configuration properties values by checking their relevant POJOs. For example, the above screenshot tells us that the RedisProperties
class is activated as a configuration properties class. By checking this class, we can see that it matches all properties under spring.redis.*
. This would be the place to check which data type those values should be.
For example, spring.redis.client-type
is an Enum and it can only take LETTUCE or JEDIS. If you provide any other value, then your application won’t start. You can find such details only if you pay attention to the source of the libraries.
Summary
To conclude, Troubleshooting auto-configurations may look hard at the beginning. But internally they are a bunch of bean definitions with some conditions to activate them. You can try these steps in any of our sample projects at the official GitHub repository.