28
votes

I have upgraded to spring boot 2.1 release and I have got strange exception when starting up the application.

The bean 'dataSource', defined in BeanDefinition defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceConfiguration$Hikari.class], could not be registered. A bean with that name has already been defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceConfiguration$Hikari.class] and overriding is disabled.

The full error message is:

[o.s.b.w.s.c.AnnotationConfigServletWebServerApplicationContext] Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.support.BeanDefinitionOverrideException: Invalid bean definition with name 'dataSource' defined in BeanDefinition defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceConfiguration$Hikari.class]: Cannot register bean definition [Root bean: class [org.springframework.aop.scope.ScopedProxyFactoryBean]; scope=; abstract=false; lazyInit=false; autowireMode=0; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=null; factoryMethodName=null; initMethodName=null; destroyMethodName=null; defined in BeanDefinition defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceConfiguration$Hikari.class]] for bean 'dataSource': There is already [Root bean: class [null]; scope=refresh; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=false; primary=false; factoryBeanName=org.springframework.boot.autoconfigure.jdbc.DataSourceConfiguration$Hikari; factoryMethodName=dataSource; initMethodName=null; destroyMethodName=(inferred); defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceConfiguration$Hikari.class]] bound.

Beans must not be overridden according to our policy and it's disabled with:

spring.main.allow-bean-definition-overriding=false

I don't have any data source configuration in my application code. The only option that triggers this error is @EnableAutoConfiguration and in my application properties I have set the data source type to:

spring.datasource.type=com.zaxxer.hikari.HikariDataSource

The boot application is initialized with

@SpringBootApplication
@EnableAutoConfiguration
public class MyApplication extends SpringBootServletInitializer {

    public static void main(String[] args) {
        new MyApplication()
            .configure(new SpringApplicationBuilder(MyApplication.class))
            .run(args);
    }
}

There is also configuration class that imports various other configurations:

@Configuration
@ImportResource(locations = {
    "classpath*:conf/spring/*.xml",
    "classpath*:conf/spring/core/*.xml",
    "classpath*:conf/spring/plugin/**/*.xml"
})
@EnableAsync
@EnableRetry
@EnableCaching
@EnableBatchProcessing
@EnableCircuitBreaker
public class AppConfig {
    ...
}

Does anyone knows what could cause that issue and where to search?

It didn't happened prior to Spring Boot 2.1 (i.e. 2.0.5).

7
You don't need to set the datasource type (hikari is the default) and spring.main.allow-bean-definition-overriding=false is the default. Could you add the full stack trace and add your @SpringBootApplication annotated class?M. Deinum
@M.Deinum I have updated question with full error details and application configuration classes.Mariusz Miesiak
Remove @EnableAutoConfiguration that is already implied by @SpringBootApplication. Also your setup is a bit strange, why extend the SpringBootServletInitializer without implementing the correct methods? and what you do in your main method is also not standard just use SpringApplication.run(MyuApplication.class, args); instead of what you have now.M. Deinum
@M.Deinum it's still the same error after applying all those changes.Mariusz Miesiak
For some reason it appears that the DataSource auto-configuration is being processed twice. As @M.Deinum suggests, that could be due to component scanning being too broad among other things. It’s impossible to say for sure without seeing all the relevant pieces of your application. Can you provide a minimal, complete, and verifiable example?Andy Wilkinson

7 Answers

29
votes

I ran into a similar problem with this today and the following spring cloud config issue helped me: Issue 1142.

We were using Spring Cloud Config which is not compatible with Spring Boot 2.1.0 as of yet. The Greenwich release train of Spring Cloud will be compatible with Spring Boot 2.1.0.

Your @EnableCircuitBreaker annotation leads me to believe you might also be using a version of Spring Cloud that is not compatible with the 2.1.0 release of Spring Boot.

9
votes

I ran into a similar problem and it is very generic (sometimes there are duplicated annotation sometimes duplicated beans). In case when you have duplicated annotation like @EnableJpaRepository the error message not mention this annotation at all. The best way to find where the problem is:

Open class DefaultListableBeanFactory There should be code like this:

BeanDefinition existingDefinition = (BeanDefinition)this.beanDefinitionMap.get(beanName);
        if (existingDefinition != null) {
            if (!this.isAllowBeanDefinitionOverriding()) {
                throw new BeanDefinitionOverrideException(beanName, beanDefinition, existingDefinition);
            }

Put a breakpoint in line with throw new. Then existingDefinition.source.className is pointing to configuration which is already registered and here is the problem. When you check the beanDefinition.source.className you will compare both classes and find where duplicated code or annotation is, just delete/fix them.

7
votes

Adding following Property in application.properties would solve the issue .

spring.main.allow-bean-definition-overriding=true

Further one might have to add another property to resolve another issue mentioned : https://github.com/openzipkin/zipkin/issues/2043

management.metrics.web.server.auto-time-requests=false

0
votes

For Spring Boot 2+ you can exclude auto-configuration

@SpringBootApplication(exclude = ElasticsearchDataAutoConfiguration.class)
     public class YourApplication {
 ... }
0
votes

I got this issue when I try to configure Redis in my project, finally I resolve it by using:

@SpringBootApplication(exclude = { DataSourceAutoConfiguration.class, HibernateJpaAutoConfiguration.class})

I use SpringBoot 2.4.2

-1
votes

org.springframework.cloud:spring-cloud-context:2.0.2.RELEASE

RefreshAutoConfiguration causes this issue when refreshing HikariDatasource in

a possible fix is

spring.cloud.refresh.enabled = false
-1
votes

I had the same problem and I was searching for a better and more general solution and I found the following:

1- check here to see what versions of spring cloud is compatible with your boot version spring cloud

2- after that, go here to pick the exact version you like spring cloud releases

These steps solved the problem for me without any other steps of configs. But, for you it could be another incompatible dependency. It does not have to be spring cloud .