Skip to content

Soft reference-based cache causes confusing exception message from AnnotationTypeMapping resolveAliasTarget #23010

Closed
@wilkinsona

Description

@wilkinsona

Method mirror = resolveAliasTarget(target, targetAliasFor, false);
if (mirror != attribute) {
throw new AnnotationConfigurationException(String.format(
"%s must be declared as an @AliasFor '%s', not '%s'.",
StringUtils.capitalize(AttributeMethods.describe(target)),
attribute.getName(), mirror.getName()));
}

I have a situation where mirror and attribute are different instances of the name attribute on @Bean. The use of != then results in the following exception:

Caused by: org.springframework.core.annotation.AnnotationConfigurationException: Attribute 'value' in annotation [org.springframework.context.annotation.Bean] must be declared as an @AliasFor 'name', not 'name'.
	at org.springframework.core.annotation.AnnotationTypeMapping.resolveAliasTarget(AnnotationTypeMapping.java:186) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMapping.resolveAliasTarget(AnnotationTypeMapping.java:130) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMapping.resolveAliasedForTargets(AnnotationTypeMapping.java:122) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMapping.<init>(AnnotationTypeMapping.java:99) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.addIfPossible(AnnotationTypeMappings.java:107) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.addAllMappings(AnnotationTypeMappings.java:68) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.<init>(AnnotationTypeMappings.java:61) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.<init>(AnnotationTypeMappings.java:46) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings$Cache.createMappings(AnnotationTypeMappings.java:215) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at java.util.concurrent.ConcurrentMap.computeIfAbsent(ConcurrentMap.java:324) ~[na:1.8.0_181]
	at org.springframework.core.annotation.AnnotationTypeMappings$Cache.get(AnnotationTypeMappings.java:211) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.forAnnotationType(AnnotationTypeMappings.java:179) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations$MergedAnnotationFinder.process(TypeMappedAnnotations.java:417) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations$MergedAnnotationFinder.doWithAnnotations(TypeMappedAnnotations.java:400) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations$MergedAnnotationFinder.doWithAnnotations(TypeMappedAnnotations.java:366) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.processMethodAnnotations(AnnotationsScanner.java:382) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.processMethodInheritedAnnotations(AnnotationsScanner.java:248) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.processMethod(AnnotationsScanner.java:231) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.process(AnnotationsScanner.java:109) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.scan(AnnotationsScanner.java:96) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.scan(AnnotationsScanner.java:77) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations.scan(TypeMappedAnnotations.java:244) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations.get(TypeMappedAnnotations.java:151) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations.get(TypeMappedAnnotations.java:133) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.findAutowiredAnnotation(AutowiredAnnotationBeanPostProcessor.java:508) ~[spring-beans-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.lambda$buildAutowiringMetadata$2(AutowiredAnnotationBeanPostProcessor.java:476) ~[spring-beans-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.util.ReflectionUtils.doWithLocalMethods(ReflectionUtils.java:320) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.buildAutowiringMetadata(AutowiredAnnotationBeanPostProcessor.java:471) ~[spring-beans-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.findAutowiringMetadata(AutowiredAnnotationBeanPostProcessor.java:438) ~[spring-beans-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessMergedBeanDefinition(AutowiredAnnotationBeanPostProcessor.java:233) ~[spring-beans-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyMergedBeanDefinitionPostProcessors(AbstractAutowireCapableBeanFactory.java:1081) ~[spring-beans-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:567) ~[spring-beans-5.2.0.M2.jar:5.2.0.M2]
	... 15 common frames omitted

The problem occurs when running a Spring Boot application with a very tightly constrained max heap. I suspect it's due to eviction from the soft reference cache used by AnnotationTypeMappings. It's not limited to @Bean as I have also seen it with @RequestMapping:

Caused by: org.springframework.core.annotation.AnnotationConfigurationException: Attribute 'value' in annotation [org.springframework.web.bind.annotation.RequestMapping] must be declared as an @AliasFor 'path', not 'path'.
	at org.springframework.core.annotation.AnnotationTypeMapping.resolveAliasTarget(AnnotationTypeMapping.java:186) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMapping.resolveAliasTarget(AnnotationTypeMapping.java:130) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMapping.resolveAliasedForTargets(AnnotationTypeMapping.java:122) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMapping.<init>(AnnotationTypeMapping.java:99) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.addIfPossible(AnnotationTypeMappings.java:107) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.addAllMappings(AnnotationTypeMappings.java:68) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.<init>(AnnotationTypeMappings.java:61) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.<init>(AnnotationTypeMappings.java:46) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings$Cache.createMappings(AnnotationTypeMappings.java:215) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at java.util.concurrent.ConcurrentMap.computeIfAbsent(ConcurrentMap.java:324) ~[na:1.8.0_181]
	at org.springframework.core.annotation.AnnotationTypeMappings$Cache.get(AnnotationTypeMappings.java:211) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationTypeMappings.forAnnotationType(AnnotationTypeMappings.java:179) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations$MergedAnnotationFinder.process(TypeMappedAnnotations.java:417) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations$MergedAnnotationFinder.doWithAnnotations(TypeMappedAnnotations.java:400) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations$MergedAnnotationFinder.doWithAnnotations(TypeMappedAnnotations.java:366) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.processMethodAnnotations(AnnotationsScanner.java:382) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.processMethodHierarchy(AnnotationsScanner.java:266) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.processMethod(AnnotationsScanner.java:236) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.process(AnnotationsScanner.java:109) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.scan(AnnotationsScanner.java:96) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotationsScanner.scan(AnnotationsScanner.java:77) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations.scan(TypeMappedAnnotations.java:244) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.TypeMappedAnnotations.get(TypeMappedAnnotations.java:151) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.core.annotation.AnnotatedElementUtils.findMergedAnnotation(AnnotatedElementUtils.java:633) ~[spring-core-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping.createRequestMappingInfo(RequestMappingHandlerMapping.java:262) ~[spring-webmvc-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping.getMappingForMethod(RequestMappingHandlerMapping.java:225) ~[spring-webmvc-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping.getMappingForMethod(RequestMappingHandlerMapping.java:65) ~[spring-webmvc-5.2.0.M2.jar:5.2.0.M2]
	at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.lambda$detectHandlerMethods$0(AbstractHandlerMethodMapping.java:271) ~[spring-webmvc-5.2.0.M2.jar:5.2.0.M2]
	... 26 common frames omitted

Metadata

Metadata

Assignees

Labels

in: coreIssues in core modules (aop, beans, core, context, expression)type: bugA general bug

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions