Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

@Component not picked up by @ComponentScan if it has the same simple name as the main class #25952

Closed
Drezir opened this issue Oct 21, 2020 · 6 comments
Assignees
Labels
in: core Issues in core modules (aop, beans, core, context, expression) type: enhancement A general enhancement
Milestone

Comments

@Drezir
Copy link
Contributor

Drezir commented Oct 21, 2020

Hello,

I have accidentally named my worker @Component class same as my main application class with @SpringBootApplication and @ComponentScan annotations. I have correct structure by documentation because my main class is in root package and other classes are in sub-packages.

Seems like my @Component class is not being picked up by component scanning. It is in different package so I think this should work.

Spring version = 2.3.4.RELEASE.
Build tool = Gradle 6.6.1

Thanks.

@Drezir Drezir changed the title @Component not beeing picked up by @ComponentScan if same name as app class @Component not beeing picked up by @ComponentScan if it has a same name as main class Oct 21, 2020
@philwebb
Copy link
Member

This is an interesting issue. It appears that ClassPathBeanDefinitionScanner.checkCandidate returns false due to the result of isCompatible. This means that ConflictingBeanDefinitionException is not thrown and the duplicate bean definition is never registered.

Spring Boot does set DefaultListableBeanFactory.setAllowBeanDefinitionOverriding to false, so it seems odd that we're not getting a clear exception.

I'm going to transfer this issue to the Spring Framework team to see if there's anything that can be done to improve the situation.

@philwebb philwebb transferred this issue from spring-projects/spring-boot Oct 21, 2020
@spring-projects-issues spring-projects-issues added the status: waiting-for-triage An issue we've not yet triaged or decided on label Oct 21, 2020
@sbrannen
Copy link
Member

Does using FullyQualifiedAnnotationBeanNameGenerator help?

@sbrannen sbrannen added in: core Issues in core modules (aop, beans, core, context, expression) status: waiting-for-feedback We need additional information before we can continue labels Oct 22, 2020
@philwebb
Copy link
Member

I'm sure that would work-around the issue, but it still feels strange that we don't get an exception when setAllowBeanDefinitionOverriding is false.

@spring-projects-issues spring-projects-issues added status: feedback-provided Feedback has been provided and removed status: waiting-for-feedback We need additional information before we can continue labels Oct 26, 2020
@sbrannen
Copy link
Member

I'm sure that would work-around the issue, but it still feels strange that we don't get an exception when setAllowBeanDefinitionOverriding is false.

Understood.

I'm tentatively slating this for 5.3.1 for further investigation.

@sbrannen sbrannen added status: waiting-for-triage An issue we've not yet triaged or decided on and removed status: waiting-for-triage An issue we've not yet triaged or decided on status: feedback-provided Feedback has been provided labels Oct 26, 2020
@sbrannen sbrannen added this to the 5.3.1 milestone Oct 26, 2020
@sbrannen sbrannen changed the title @Component not beeing picked up by @ComponentScan if it has a same name as main class @Component not picked up by @ComponentScan if it has the same simple name as the main class Oct 26, 2020
@jhoeller
Copy link
Contributor

jhoeller commented Nov 9, 2020

I suppose it's the !(existingDefinition instanceof ScannedGenericBeanDefinition) check that makes it indicate compatibility here, looking like there was an explicit bean of the same name registered before (which we can consider an override for a scanned bean definition of the same name). Usually those overriding beans would be user-defined, but it looks like the Boot application instance is registered the same way?

@jhoeller jhoeller self-assigned this Nov 9, 2020
@jhoeller jhoeller modified the milestones: 5.3.1, 5.3.2 Nov 9, 2020
@jhoeller jhoeller modified the milestones: 5.3.2, 5.x Backlog Dec 7, 2020
@Drezir
Copy link
Contributor Author

Drezir commented Dec 15, 2021

Does it make sense to put additional if statement in to org.springframework.context.annotation.ClassPathBeanDefinitionScanner#doScan? That statement may throw a BeanDefinitionOverrideException if bean of the same name and of type AnnotatedGenericBeanDefinition does exist in registry (we could also check if candidate is type of ScannedGenericBeanDefinition)?

For this purpose it looks like that the code

		if (!this.registry.containsBeanDefinition(beanName)) {
			return true;
		}

harms this usecase and by removing it we may get ConflictingBeanDefinitionException but I do not know if we could cause any other troubles by deleting this.

I think that in this case it should not fail on BeanDefinitionOverrideException. ConflictingBeanDefinitionException makes sense to me more.

Or probably, checkCandidate may be extended to not control bean in registry only by name but also by simple type?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
in: core Issues in core modules (aop, beans, core, context, expression) type: enhancement A general enhancement
Projects
None yet
Development

No branches or pull requests

5 participants