Version: 5.3.25 (via Boot 2.7.17)
I have an @Configuration
class defining an @Bean
method:
@Bean
@MyQualifier
ServiceObject serviceObject() {
new ServiceObject()
}
When @MyQualifier
is annotated with @javax.inject.Qualifier
, the Spring container does not treat it as a qualifier, resulting in duplicate-bean exceptions. Adding Spring's org.springframework.beans.factory.annotation.Qualifier
to the annotation type fixes the injection problem.
I have traced the problem as far as AbstractBeanFactory#getMergedLocalBeanDefinition(String)
, where the this.mergedBeanDefinitions
returns an mbd
that does not copy the @javax.inject.Qualifier
-annotated annotation (mbd.qualifiers
is empty). I am trying to figure out where the RootBeanDefinition
gets constructed and should have the qualifier recorded but doesn't.
Update: It appears the problem may be that the upstream library declares jakarta.inject-api
as an optional
dependency, so that the Spring container's check on whether javax.inject.Qualifier
is present on the classpath does not see it unless the consuming project independently requires the library (even though the intermediate @MyQualifier
is visible with no problems).
If this is the case, it would be convenient if possible to provide a warning if a meta-annotated annotation is found but the intermediate javax.inject.Qualifier
isn't, but in contrast to Boot's bytecode inspection I believe the core Spring container relies on plain JVM reflection and wouldn't have visibility on it.
Comment From: snicoll
If the Qualifier
annotation isn't available, @MyQualifier
isn't even considered. It's just one annotation like any other annotation so there's no way for the container to see it has to issue a warning.