mirror of
https://github.com/spring-projects/spring-framework
synced 2026-06-08 17:33:33 +00:00
Add missing AOT support for method overrides (including @Lookup)
Closes gh-34642
This commit is contained in:
+185
-103
@@ -18,6 +18,7 @@ package org.springframework.context.aot;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.lang.reflect.Constructor;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Proxy;
|
||||
import java.util.List;
|
||||
import java.util.function.BiConsumer;
|
||||
@@ -51,7 +52,9 @@ import org.springframework.beans.factory.config.BeanPostProcessor;
|
||||
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
|
||||
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
|
||||
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
|
||||
import org.springframework.beans.factory.support.MethodReplacer;
|
||||
import org.springframework.beans.factory.support.RegisteredBean;
|
||||
import org.springframework.beans.factory.support.ReplaceOverride;
|
||||
import org.springframework.beans.factory.support.RootBeanDefinition;
|
||||
import org.springframework.beans.testfixture.beans.Employee;
|
||||
import org.springframework.beans.testfixture.beans.Pet;
|
||||
@@ -81,6 +84,7 @@ import org.springframework.context.testfixture.context.annotation.LazyConstructo
|
||||
import org.springframework.context.testfixture.context.annotation.LazyFactoryMethodArgumentComponent;
|
||||
import org.springframework.context.testfixture.context.annotation.LazyResourceFieldComponent;
|
||||
import org.springframework.context.testfixture.context.annotation.LazyResourceMethodComponent;
|
||||
import org.springframework.context.testfixture.context.annotation.LookupComponent;
|
||||
import org.springframework.context.testfixture.context.annotation.PropertySourceConfiguration;
|
||||
import org.springframework.context.testfixture.context.annotation.QualifierConfiguration;
|
||||
import org.springframework.context.testfixture.context.annotation.ResourceComponent;
|
||||
@@ -112,6 +116,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
void processAheadOfTimeWhenHasSimpleBean() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
applicationContext.registerBeanDefinition("test", new RootBeanDefinition(SimpleComponent.class));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("test");
|
||||
@@ -119,6 +124,99 @@ class ApplicationContextAotGeneratorTests {
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasNoAotContributions() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).isEmpty();
|
||||
assertThat(compiled.getSourceFile())
|
||||
.contains("beanFactory.setAutowireCandidateResolver(new ContextAnnotationAutowireCandidateResolver())")
|
||||
.contains("beanFactory.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE)");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasBeanFactoryInitializationAotProcessorExcludesProcessor() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
applicationContext.registerBeanDefinition("test",
|
||||
new RootBeanDefinition(NoOpBeanFactoryInitializationAotProcessor.class));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).isEmpty();
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasBeanRegistrationAotProcessorExcludesProcessor() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
applicationContext.registerBeanDefinition("test",
|
||||
new RootBeanDefinition(NoOpBeanRegistrationAotProcessor.class));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).isEmpty();
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWithPropertySource() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(PropertySourceConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
ConfigurableEnvironment environment = freshApplicationContext.getEnvironment();
|
||||
PropertySource<?> propertySource = environment.getPropertySources().get("testp1");
|
||||
assertThat(propertySource).isNotNull();
|
||||
assertThat(propertySource.getProperty("from.p1")).isEqualTo("p1Value");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWithQualifier() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(QualifierConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
QualifierConfiguration configuration = freshApplicationContext.getBean(QualifierConfiguration.class);
|
||||
assertThat(configuration).hasFieldOrPropertyWithValue("bean", "one");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWithInjectionPoint() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(InjectionPointConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBean("classToString"))
|
||||
.isEqualTo(InjectionPointConfiguration.class.getName());
|
||||
});
|
||||
}
|
||||
|
||||
@Test // gh-30689
|
||||
void processAheadOfTimeWithExplicitResolvableType() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
DefaultListableBeanFactory beanFactory = applicationContext.getDefaultListableBeanFactory();
|
||||
RootBeanDefinition beanDefinition = new RootBeanDefinition(One.class);
|
||||
beanDefinition.setResolvedFactoryMethod(ReflectionUtils.findMethod(TestHierarchy.class, "oneBean"));
|
||||
// Override target type
|
||||
beanDefinition.setTargetType(Two.class);
|
||||
beanFactory.registerBeanDefinition("hierarchyBean", beanDefinition);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBean(Two.class))
|
||||
.isInstanceOf(Implementation.class);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@Nested
|
||||
class Autowiring {
|
||||
|
||||
@@ -129,6 +227,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
AnnotationConfigUtils.AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME, AutowiredAnnotationBeanPostProcessor.class);
|
||||
applicationContext.registerBeanDefinition("autowiredComponent", new RootBeanDefinition(AutowiredComponent.class));
|
||||
registerIntegerBean(applicationContext, "number", 42);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("autowiredComponent", "number");
|
||||
@@ -138,11 +237,56 @@ class ApplicationContextAotGeneratorTests {
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasReplacer() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
registerBeanPostProcessor(applicationContext,
|
||||
AnnotationConfigUtils.AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME, AutowiredAnnotationBeanPostProcessor.class);
|
||||
RootBeanDefinition rbd = new RootBeanDefinition(AutowiredComponent.class);
|
||||
rbd.getMethodOverrides().addOverride(
|
||||
new ReplaceOverride("getCounter", "replacer"));
|
||||
applicationContext.registerBeanDefinition("autowiredComponent", rbd);
|
||||
registerIntegerBean(applicationContext, "number", 42);
|
||||
applicationContext.registerBean("replacer", DummyReplacer.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("autowiredComponent", "number", "replacer");
|
||||
AutowiredComponent bean = freshApplicationContext.getBean(AutowiredComponent.class);
|
||||
assertThat(bean.getEnvironment()).isSameAs(freshApplicationContext.getEnvironment());
|
||||
assertThat(bean.getCounter()).isEqualTo(44);
|
||||
assertThat(bean.getCounter(0)).isEqualTo(42);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasLookup() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
registerBeanPostProcessor(applicationContext,
|
||||
AnnotationConfigUtils.AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME, AutowiredAnnotationBeanPostProcessor.class);
|
||||
RootBeanDefinition rbd = new RootBeanDefinition(LookupComponent.class);
|
||||
rbd.getMethodOverrides().addOverride(
|
||||
new ReplaceOverride("getCounter", "replacer", List.of( "Integer")));
|
||||
applicationContext.registerBeanDefinition("autowiredComponent", rbd);
|
||||
registerIntegerBean(applicationContext, "number", 42);
|
||||
applicationContext.registerBean("replacer", DummyReplacer.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("autowiredComponent", "number", "replacer");
|
||||
LookupComponent bean = freshApplicationContext.getBean(LookupComponent.class);
|
||||
assertThat(bean.getEnvironment()).isSameAs(freshApplicationContext.getEnvironment());
|
||||
assertThat(bean.getCounter()).isEqualTo(42);
|
||||
assertThat(bean.getCounter(0)).isEqualTo(44);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasAutowiringOnUnresolvedGeneric() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(GenericTemplateConfiguration.class);
|
||||
applicationContext.registerBean("autowiredComponent", AutowiredGenericTemplate.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
AutowiredGenericTemplate bean = freshApplicationContext.getBean(AutowiredGenericTemplate.class);
|
||||
@@ -162,7 +306,6 @@ class ApplicationContextAotGeneratorTests {
|
||||
assertThat(runtimeHints.proxies().jdkProxyHints()).anySatisfy(proxyHint ->
|
||||
assertThat(proxyHint.getProxiedInterfaces()).isEqualTo(TypeReference.listOf(
|
||||
environment.getClass().getInterfaces())));
|
||||
|
||||
});
|
||||
}
|
||||
|
||||
@@ -226,15 +369,16 @@ class ApplicationContextAotGeneratorTests {
|
||||
AnnotationConfigUtils.AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME, AutowiredAnnotationBeanPostProcessor.class);
|
||||
applicationContext.registerBeanDefinition("testComponent", beanDefinition);
|
||||
TestGenerationContext generationContext = processAheadOfTime(applicationContext);
|
||||
|
||||
testCompiledResult(generationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("testComponent");
|
||||
assertions.accept(freshApplicationContext.getBean("testComponent", type), generationContext);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Nested
|
||||
class ResourceAutowiring {
|
||||
|
||||
@@ -247,6 +391,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
registerStringBean(applicationContext, "text2", "hello2");
|
||||
registerIntegerBean(applicationContext, "number", 42);
|
||||
applicationContext.registerBeanDefinition("resourceComponent", new RootBeanDefinition(ResourceComponent.class));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("resourceComponent", "text", "text2", "number");
|
||||
@@ -300,6 +445,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
AnnotationConfigUtils.COMMON_ANNOTATION_PROCESSOR_BEAN_NAME, CommonAnnotationBeanPostProcessor.class);
|
||||
applicationContext.registerBeanDefinition("testComponent", beanDefinition);
|
||||
TestGenerationContext generationContext = processAheadOfTime(applicationContext);
|
||||
|
||||
testCompiledResult(generationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("testComponent");
|
||||
@@ -308,6 +454,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Nested
|
||||
class InitDestroy {
|
||||
|
||||
@@ -318,6 +465,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
AnnotationConfigUtils.COMMON_ANNOTATION_PROCESSOR_BEAN_NAME, CommonAnnotationBeanPostProcessor.class);
|
||||
applicationContext.registerBeanDefinition("initDestroyComponent",
|
||||
new RootBeanDefinition(InitDestroyComponent.class));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("initDestroyComponent");
|
||||
@@ -337,6 +485,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
beanDefinition.setInitMethodName("customInit");
|
||||
beanDefinition.setDestroyMethodName("customDestroy");
|
||||
applicationContext.registerBeanDefinition("initDestroyComponent", beanDefinition);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).containsOnly("initDestroyComponent");
|
||||
@@ -346,94 +495,8 @@ class ApplicationContextAotGeneratorTests {
|
||||
assertThat(bean.events).containsExactly("init", "customInit", "destroy", "customDestroy");
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasNoAotContributions() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).isEmpty();
|
||||
assertThat(compiled.getSourceFile())
|
||||
.contains("beanFactory.setAutowireCandidateResolver(new ContextAnnotationAutowireCandidateResolver())")
|
||||
.contains("beanFactory.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE)");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasBeanFactoryInitializationAotProcessorExcludesProcessor() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
applicationContext.registerBeanDefinition("test",
|
||||
new RootBeanDefinition(NoOpBeanFactoryInitializationAotProcessor.class));
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).isEmpty();
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasBeanRegistrationAotProcessorExcludesProcessor() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
applicationContext.registerBeanDefinition("test",
|
||||
new RootBeanDefinition(NoOpBeanRegistrationAotProcessor.class));
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBeanDefinitionNames()).isEmpty();
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWithPropertySource() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(PropertySourceConfiguration.class);
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
ConfigurableEnvironment environment = freshApplicationContext.getEnvironment();
|
||||
PropertySource<?> propertySource = environment.getPropertySources().get("testp1");
|
||||
assertThat(propertySource).isNotNull();
|
||||
assertThat(propertySource.getProperty("from.p1")).isEqualTo("p1Value");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWithQualifier() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(QualifierConfiguration.class);
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
QualifierConfiguration configuration = freshApplicationContext.getBean(QualifierConfiguration.class);
|
||||
assertThat(configuration).hasFieldOrPropertyWithValue("bean", "one");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWithInjectionPoint() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(InjectionPointConfiguration.class);
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBean("classToString"))
|
||||
.isEqualTo(InjectionPointConfiguration.class.getName());
|
||||
});
|
||||
}
|
||||
|
||||
@Test // gh-30689
|
||||
void processAheadOfTimeWithExplicitResolvableType() {
|
||||
GenericApplicationContext applicationContext = new GenericApplicationContext();
|
||||
DefaultListableBeanFactory beanFactory = applicationContext.getDefaultListableBeanFactory();
|
||||
RootBeanDefinition beanDefinition = new RootBeanDefinition(One.class);
|
||||
beanDefinition.setResolvedFactoryMethod(ReflectionUtils.findMethod(TestHierarchy.class, "oneBean"));
|
||||
// Override target type
|
||||
beanDefinition.setTargetType(Two.class);
|
||||
beanFactory.registerBeanDefinition("hierarchyBean", beanDefinition);
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBean(Two.class))
|
||||
.isInstanceOf(Implementation.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Nested
|
||||
@CompileWithForkedClassLoader
|
||||
@@ -499,6 +562,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
void processAheadOfTimeWhenHasCglibProxyUseProxy() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(CglibConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBean("prefix", String.class)).isEqualTo("Hello0");
|
||||
@@ -510,6 +574,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
void processAheadOfTimeWhenHasCglibProxyAndAutowiring() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(AutowiredCglibConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(context -> {
|
||||
context.setEnvironment(new MockEnvironment().withProperty("hello", "Hi"));
|
||||
@@ -523,6 +588,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
void processAheadOfTimeWhenHasCglibProxyAndMixedAutowiring() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(AutowiredMixedCglibConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(context -> {
|
||||
context.setEnvironment(new MockEnvironment().withProperty("hello", "Hi")
|
||||
@@ -537,6 +603,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
void processAheadOfTimeWhenHasCglibProxyWithAnnotationsOnTheUserClasConstructor() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean("config", ValueCglibConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(context -> {
|
||||
context.setEnvironment(new MockEnvironment().withProperty("name", "AOT World"));
|
||||
@@ -551,6 +618,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
void processAheadOfTimeWhenHasCglibProxyWithArgumentsUseProxy() {
|
||||
GenericApplicationContext applicationContext = new AnnotationConfigApplicationContext();
|
||||
applicationContext.registerBean(ConfigurableCglibConfiguration.class);
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = createFreshApplicationContext(initializer);
|
||||
freshApplicationContext.setEnvironment(new MockEnvironment().withProperty("test.prefix", "Hi"));
|
||||
@@ -573,9 +641,9 @@ class ApplicationContextAotGeneratorTests {
|
||||
private String toCglibClassSimpleName(Class<?> configClass) {
|
||||
return configClass.getSimpleName() + CGLIB_CONFIGURATION_CLASS_SUFFIX;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Nested
|
||||
class ActiveProfile {
|
||||
|
||||
@@ -586,6 +654,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
if (aotProfiles.length != 0) {
|
||||
applicationContext.getEnvironment().setActiveProfiles(aotProfiles);
|
||||
}
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = new GenericApplicationContext();
|
||||
if (runtimeProfiles.length != 0) {
|
||||
@@ -604,17 +673,18 @@ class ApplicationContextAotGeneratorTests {
|
||||
Arguments.of(new String[] { "aot", "prod" }, new String[] { "aot", "prod" }, new String[] { "aot", "prod" }),
|
||||
Arguments.of(new String[] { "default" }, new String[] {}, new String[] {}));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Nested
|
||||
class XmlSupport {
|
||||
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasTypedStringValue() {
|
||||
GenericXmlApplicationContext applicationContext = new GenericXmlApplicationContext();
|
||||
applicationContext
|
||||
.load(new ClassPathResource("applicationContextAotGeneratorTests-values.xml", getClass()));
|
||||
applicationContext.load(
|
||||
new ClassPathResource("applicationContextAotGeneratorTests-values.xml", getClass()));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
Employee employee = freshApplicationContext.getBean(Employee.class);
|
||||
@@ -631,8 +701,9 @@ class ApplicationContextAotGeneratorTests {
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasTypedStringValueWithType() {
|
||||
GenericXmlApplicationContext applicationContext = new GenericXmlApplicationContext();
|
||||
applicationContext
|
||||
.load(new ClassPathResource("applicationContextAotGeneratorTests-values-types.xml", getClass()));
|
||||
applicationContext.load(
|
||||
new ClassPathResource("applicationContextAotGeneratorTests-values-types.xml", getClass()));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
Employee employee = freshApplicationContext.getBean(Employee.class);
|
||||
@@ -647,8 +718,9 @@ class ApplicationContextAotGeneratorTests {
|
||||
@Test
|
||||
void processAheadOfTimeWhenHasTypedStringValueWithExpression() {
|
||||
GenericXmlApplicationContext applicationContext = new GenericXmlApplicationContext();
|
||||
applicationContext
|
||||
.load(new ClassPathResource("applicationContextAotGeneratorTests-values-expressions.xml", getClass()));
|
||||
applicationContext.load(
|
||||
new ClassPathResource("applicationContextAotGeneratorTests-values-expressions.xml", getClass()));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
Employee employee = freshApplicationContext.getBean(Employee.class);
|
||||
@@ -663,8 +735,9 @@ class ApplicationContextAotGeneratorTests {
|
||||
@Test
|
||||
void processAheadOfTimeWhenXmlHasBeanReferences() {
|
||||
GenericXmlApplicationContext applicationContext = new GenericXmlApplicationContext();
|
||||
applicationContext
|
||||
.load(new ClassPathResource("applicationContextAotGeneratorTests-references.xml", getClass()));
|
||||
applicationContext.load(
|
||||
new ClassPathResource("applicationContextAotGeneratorTests-references.xml", getClass()));
|
||||
|
||||
testCompiledResult(applicationContext, (initializer, compiled) -> {
|
||||
GenericApplicationContext freshApplicationContext = toFreshApplicationContext(initializer);
|
||||
assertThat(freshApplicationContext.getBean("petInnerBean", Pet.class)
|
||||
@@ -673,11 +746,11 @@ class ApplicationContextAotGeneratorTests {
|
||||
.getName()).isEqualTo("Dofi");
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Nested
|
||||
class ExceptionHanding {
|
||||
class ExceptionHandling {
|
||||
|
||||
@Test
|
||||
void failureProcessingBeanFactoryAotContribution() {
|
||||
@@ -692,6 +765,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static void registerBeanPostProcessor(GenericApplicationContext applicationContext,
|
||||
String beanName, Class<?> beanPostProcessorClass) {
|
||||
|
||||
@@ -716,7 +790,7 @@ class ApplicationContextAotGeneratorTests {
|
||||
.getBeanDefinition());
|
||||
}
|
||||
|
||||
private Consumer<List<? extends JdkProxyHint>> doesNotHaveProxyFor(Class<?> target) {
|
||||
private static Consumer<List<? extends JdkProxyHint>> doesNotHaveProxyFor(Class<?> target) {
|
||||
return hints -> assertThat(hints).noneMatch(hint ->
|
||||
hint.getProxiedInterfaces().get(0).equals(TypeReference.of(target)));
|
||||
}
|
||||
@@ -771,7 +845,6 @@ class ApplicationContextAotGeneratorTests {
|
||||
public BeanFactoryInitializationAotContribution processAheadOfTime(ConfigurableListableBeanFactory beanFactory) {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -782,9 +855,9 @@ class ApplicationContextAotGeneratorTests {
|
||||
public BeanRegistrationAotContribution processAheadOfTime(RegisteredBean registeredBean) {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
static class FailingBeanFactoryInitializationAotContribution implements BeanFactoryInitializationAotProcessor {
|
||||
|
||||
@Override
|
||||
@@ -793,4 +866,13 @@ class ApplicationContextAotGeneratorTests {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class DummyReplacer implements MethodReplacer {
|
||||
|
||||
@Override
|
||||
public Object reimplement(Object obj, Method method, Object[] args) throws Throwable {
|
||||
return 44;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user