Merge branch '6.2.x'
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2022 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,6 +16,7 @@
|
||||
|
||||
package org.springframework.test.context.aot;
|
||||
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.context.ApplicationContextInitializer;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
@@ -25,9 +26,9 @@ import org.springframework.test.context.SmartContextLoader;
|
||||
|
||||
/**
|
||||
* Strategy interface for loading an {@link ApplicationContext} for build-time
|
||||
* {@linkplain #loadContextForAotProcessing AOT processing} as well as run-time
|
||||
* {@linkplain #loadContextForAotRuntime AOT execution} for an integration test
|
||||
* managed by the Spring TestContext Framework.
|
||||
* {@linkplain #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
* AOT processing} as well as run-time {@linkplain #loadContextForAotRuntime
|
||||
* AOT execution} for an integration test managed by the Spring TestContext Framework.
|
||||
*
|
||||
* <p>{@code AotContextLoader} is an extension of the {@link SmartContextLoader}
|
||||
* SPI that allows a context loader to optionally provide ahead-of-time (AOT)
|
||||
@@ -42,6 +43,30 @@ import org.springframework.test.context.SmartContextLoader;
|
||||
*/
|
||||
public interface AotContextLoader extends SmartContextLoader {
|
||||
|
||||
/**
|
||||
* Load a new {@link ApplicationContext} for AOT build-time processing based
|
||||
* on the supplied {@link MergedContextConfiguration}, configure the context,
|
||||
* and return the context.
|
||||
* <p>The default implementation of this method throws an
|
||||
* {@link UnsupportedOperationException}. Note, however, that the framework
|
||||
* invokes {@link #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)}
|
||||
* as of Spring Framework 6.2.4.
|
||||
* @param mergedConfig the merged context configuration to use to load the
|
||||
* application context
|
||||
* @return a new {@code GenericApplicationContext}
|
||||
* @throws ContextLoadException if context loading failed
|
||||
* @see #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
* @see #loadContextForAotRuntime(MergedContextConfiguration, ApplicationContextInitializer)
|
||||
* @deprecated as of Spring Framework 6.2.4, in favor of
|
||||
* {@link #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)};
|
||||
* to be removed in Spring Framework 8.0
|
||||
*/
|
||||
@Deprecated(since = "6.2.4", forRemoval = true)
|
||||
default ApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig) throws Exception {
|
||||
throw new UnsupportedOperationException(
|
||||
"Invoke loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints) instead");
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a new {@link ApplicationContext} for AOT build-time processing based
|
||||
* on the supplied {@link MergedContextConfiguration}, configure the context,
|
||||
@@ -65,13 +90,23 @@ public interface AotContextLoader extends SmartContextLoader {
|
||||
* throw new ContextLoadException(context, ex);
|
||||
* }
|
||||
* </pre>
|
||||
* <p>For backward compatibility, the default implementation of this method
|
||||
* delegates to {@link #loadContextForAotProcessing(MergedContextConfiguration)}.
|
||||
* Note, however, that the framework only invokes this method as of Spring
|
||||
* Framework 6.2.4.
|
||||
* @param mergedConfig the merged context configuration to use to load the
|
||||
* application context
|
||||
* @param runtimeHints the runtime hints
|
||||
* @return a new {@code GenericApplicationContext}
|
||||
* @throws ContextLoadException if context loading failed
|
||||
* @since 6.2.4
|
||||
* @see #loadContextForAotRuntime(MergedContextConfiguration, ApplicationContextInitializer)
|
||||
*/
|
||||
ApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig) throws Exception;
|
||||
default ApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig,
|
||||
RuntimeHints runtimeHints) throws Exception {
|
||||
|
||||
return loadContextForAotProcessing(mergedConfig);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a new {@link ApplicationContext} for AOT run-time execution based on
|
||||
@@ -98,7 +133,7 @@ public interface AotContextLoader extends SmartContextLoader {
|
||||
* be applied to the context in order to recreate bean definitions
|
||||
* @return a new {@code GenericApplicationContext}
|
||||
* @throws ContextLoadException if context loading failed
|
||||
* @see #loadContextForAotProcessing(MergedContextConfiguration)
|
||||
* @see #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
*/
|
||||
ApplicationContext loadContextForAotRuntime(MergedContextConfiguration mergedConfig,
|
||||
ApplicationContextInitializer<ConfigurableApplicationContext> initializer) throws Exception;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2024 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -331,7 +331,7 @@ public class TestContextAotGenerator {
|
||||
* create {@link GenericApplicationContext GenericApplicationContexts}.
|
||||
* @throws TestContextAotException if an error occurs while loading the application
|
||||
* context or if one of the prerequisites is not met
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration)
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
*/
|
||||
private GenericApplicationContext loadContextForAotProcessing(
|
||||
MergedContextConfiguration mergedConfig) throws TestContextAotException {
|
||||
@@ -345,7 +345,7 @@ public class TestContextAotGenerator {
|
||||
|
||||
if (contextLoader instanceof AotContextLoader aotContextLoader) {
|
||||
try {
|
||||
ApplicationContext context = aotContextLoader.loadContextForAotProcessing(mergedConfig);
|
||||
ApplicationContext context = aotContextLoader.loadContextForAotProcessing(mergedConfig, this.runtimeHints);
|
||||
if (context instanceof GenericApplicationContext gac) {
|
||||
return gac;
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2023 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -19,6 +19,7 @@ package org.springframework.test.context.support;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.context.ApplicationContextInitializer;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
@@ -225,8 +226,13 @@ public abstract class AbstractDelegatingSmartContextLoader implements AotContext
|
||||
* {@code ApplicationContext} from the supplied merged context configuration
|
||||
* @since 6.0
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration)
|
||||
* @deprecated as of Spring Framework 6.2.4, in favor of
|
||||
* {@link #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)};
|
||||
* to be removed in Spring Framework 8.0
|
||||
*/
|
||||
@Deprecated(since = "6.2.4", forRemoval = true)
|
||||
@Override
|
||||
@SuppressWarnings("removal")
|
||||
public final ApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig) throws Exception {
|
||||
AotContextLoader loader = getAotContextLoader(mergedConfig);
|
||||
if (logger.isTraceEnabled()) {
|
||||
@@ -236,6 +242,33 @@ public abstract class AbstractDelegatingSmartContextLoader implements AotContext
|
||||
return loader.loadContextForAotProcessing(mergedConfig);
|
||||
}
|
||||
|
||||
/**
|
||||
* Delegates to an appropriate candidate {@code SmartContextLoader} to load
|
||||
* an {@link ApplicationContext} for AOT processing.
|
||||
* <p>Delegation is based on explicit knowledge of the implementations of the
|
||||
* default loaders. See {@link #loadContext(MergedContextConfiguration)} for
|
||||
* details.
|
||||
* @param mergedConfig the merged context configuration to use to load the application context
|
||||
* @param runtimeHints the runtime hints
|
||||
* @return a new application context
|
||||
* @throws IllegalArgumentException if the supplied merged configuration is {@code null}
|
||||
* @throws IllegalStateException if neither candidate loader is capable of loading an
|
||||
* {@code ApplicationContext} from the supplied merged context configuration
|
||||
* @since 6.2.4
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
*/
|
||||
@Override
|
||||
public final ApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig,
|
||||
RuntimeHints runtimeHints) throws Exception {
|
||||
|
||||
AotContextLoader loader = getAotContextLoader(mergedConfig);
|
||||
if (logger.isTraceEnabled()) {
|
||||
logger.trace("Delegating to %s to load context for AOT processing for %s"
|
||||
.formatted(name(loader), mergedConfig));
|
||||
}
|
||||
return loader.loadContextForAotProcessing(mergedConfig, runtimeHints);
|
||||
}
|
||||
|
||||
/**
|
||||
* Delegates to an appropriate candidate {@code SmartContextLoader} to load
|
||||
* an {@link ApplicationContext} for AOT run-time execution.
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2022 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -21,6 +21,7 @@ import java.util.Arrays;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.beans.factory.support.BeanDefinitionReader;
|
||||
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
@@ -126,10 +127,41 @@ public abstract class AbstractGenericContextLoader extends AbstractContextLoader
|
||||
* @throws Exception if context loading failed
|
||||
* @since 6.0
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration)
|
||||
* @deprecated as of Spring Framework 6.2.4, in favor of
|
||||
* {@link #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)};
|
||||
* to be removed in Spring Framework 8.0
|
||||
*/
|
||||
@Deprecated(since = "6.2.4", forRemoval = true)
|
||||
@Override
|
||||
@SuppressWarnings("removal")
|
||||
public final GenericApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig)
|
||||
throws Exception {
|
||||
|
||||
return loadContext(mergedConfig, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a {@link GenericApplicationContext} for AOT build-time processing based
|
||||
* on the supplied {@link MergedContextConfiguration}.
|
||||
* <p>In contrast to {@link #loadContext(MergedContextConfiguration)}, this
|
||||
* method does not
|
||||
* {@linkplain org.springframework.context.ConfigurableApplicationContext#refresh()
|
||||
* refresh} the {@code ApplicationContext} or
|
||||
* {@linkplain org.springframework.context.ConfigurableApplicationContext#registerShutdownHook()
|
||||
* register a JVM shutdown hook} for it. Otherwise, this method implements
|
||||
* behavior identical to {@link #loadContext(MergedContextConfiguration)}.
|
||||
* @param mergedConfig the merged context configuration to use to load the
|
||||
* application context
|
||||
* @param runtimeHints the runtime hints
|
||||
* @return a new application context
|
||||
* @throws Exception if context loading failed
|
||||
* @since 6.2.4
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
*/
|
||||
@Override
|
||||
public final GenericApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig,
|
||||
RuntimeHints runtimeHints) throws Exception {
|
||||
|
||||
return loadContext(mergedConfig, true);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2023 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -20,6 +20,7 @@ import jakarta.servlet.ServletContext;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.context.ApplicationContextInitializer;
|
||||
@@ -120,10 +121,41 @@ public abstract class AbstractGenericWebContextLoader extends AbstractContextLoa
|
||||
* @throws Exception if context loading failed
|
||||
* @since 6.0
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration)
|
||||
* @deprecated as of Spring Framework 6.2.4, in favor of
|
||||
* {@link #loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)};
|
||||
* to be removed in Spring Framework 8.0
|
||||
*/
|
||||
@Deprecated(since = "6.2.4", forRemoval = true)
|
||||
@Override
|
||||
@SuppressWarnings("removal")
|
||||
public final GenericWebApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig)
|
||||
throws Exception {
|
||||
|
||||
return loadContext(mergedConfig, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Load a {@link GenericWebApplicationContext} for AOT build-time processing based
|
||||
* on the supplied {@link MergedContextConfiguration}.
|
||||
* <p>In contrast to {@link #loadContext(MergedContextConfiguration)}, this
|
||||
* method does not
|
||||
* {@linkplain org.springframework.context.ConfigurableApplicationContext#refresh()
|
||||
* refresh} the {@code ApplicationContext} or
|
||||
* {@linkplain org.springframework.context.ConfigurableApplicationContext#registerShutdownHook()
|
||||
* register a JVM shutdown hook} for it. Otherwise, this method implements
|
||||
* behavior identical to {@link #loadContext(MergedContextConfiguration)}.
|
||||
* @param mergedConfig the merged context configuration to use to load the
|
||||
* application context
|
||||
* @param runtimeHints the runtime hints
|
||||
* @return a new web application context
|
||||
* @throws Exception if context loading failed
|
||||
* @since 6.2.4
|
||||
* @see AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
*/
|
||||
@Override
|
||||
public final GenericWebApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig,
|
||||
RuntimeHints runtimeHints) throws Exception {
|
||||
|
||||
return loadContext(mergedConfig, true);
|
||||
}
|
||||
|
||||
@@ -187,7 +219,7 @@ public abstract class AbstractGenericWebContextLoader extends AbstractContextLoa
|
||||
* register a JVM shutdown hook for it
|
||||
* @return a new web application context
|
||||
* @see org.springframework.test.context.SmartContextLoader#loadContext(MergedContextConfiguration)
|
||||
* @see org.springframework.test.context.aot.AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration)
|
||||
* @see org.springframework.test.context.aot.AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
*/
|
||||
private GenericWebApplicationContext loadContext(
|
||||
MergedContextConfiguration mergedConfig, boolean forAotProcessing) throws Exception {
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.test.context.aot;
|
||||
|
||||
import org.springframework.context.ApplicationContextInitializer;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
import org.springframework.context.support.GenericApplicationContext;
|
||||
import org.springframework.context.support.StaticApplicationContext;
|
||||
import org.springframework.test.context.MergedContextConfiguration;
|
||||
import org.springframework.test.context.support.AbstractContextLoader;
|
||||
|
||||
/**
|
||||
* @author Sam Brannen
|
||||
* @since 6.2.4
|
||||
*/
|
||||
class AbstractAotContextLoader extends AbstractContextLoader implements AotContextLoader {
|
||||
|
||||
@Override
|
||||
public final GenericApplicationContext loadContext(MergedContextConfiguration mergedConfig) {
|
||||
return new StaticApplicationContext();
|
||||
}
|
||||
|
||||
@Override
|
||||
public final GenericApplicationContext loadContextForAotRuntime(MergedContextConfiguration mergedConfig,
|
||||
ApplicationContextInitializer<ConfigurableApplicationContext> initializer) {
|
||||
|
||||
return loadContext(mergedConfig);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected final String getResourceSuffix() {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
/*
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.test.context.aot;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.aot.generate.InMemoryGeneratedFiles;
|
||||
import org.springframework.aot.hint.ExecutableMode;
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.support.GenericApplicationContext;
|
||||
import org.springframework.test.context.ContextConfiguration;
|
||||
import org.springframework.test.context.ContextConfigurationAttributes;
|
||||
import org.springframework.test.context.MergedContextConfiguration;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.aot.hint.predicate.RuntimeHintsPredicates.reflection;
|
||||
|
||||
/**
|
||||
* Tests for registering run-time hints within an {@link AotContextLoader}, tested
|
||||
* via the {@link TestContextAotGenerator}.
|
||||
*
|
||||
* @author Sam Brannen
|
||||
* @since 6.2.4
|
||||
*/
|
||||
class AotContextLoaderRuntimeHintsTests {
|
||||
|
||||
@Test // gh-34513
|
||||
void aotContextLoaderCanRegisterRuntimeHints() {
|
||||
RuntimeHints runtimeHints = new RuntimeHints();
|
||||
TestContextAotGenerator generator = new TestContextAotGenerator(new InMemoryGeneratedFiles(), runtimeHints);
|
||||
|
||||
generator.processAheadOfTime(Stream.of(TestCase.class));
|
||||
|
||||
assertThat(reflection().onMethod(ConfigWithMain.class, "main").invoke()).accepts(runtimeHints);
|
||||
}
|
||||
|
||||
|
||||
@ContextConfiguration(classes = ConfigWithMain.class, loader = RuntimeHintsAwareAotContextLoader.class)
|
||||
static class TestCase {
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
static class ConfigWithMain {
|
||||
|
||||
public static void main(String[] args) {
|
||||
// Mimics main() method for Spring Boot app
|
||||
}
|
||||
}
|
||||
|
||||
static class RuntimeHintsAwareAotContextLoader extends AbstractAotContextLoader {
|
||||
|
||||
@Override
|
||||
public void processContextConfiguration(ContextConfigurationAttributes configAttributes) {
|
||||
/* no-op */
|
||||
}
|
||||
|
||||
@Override
|
||||
public GenericApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig,
|
||||
RuntimeHints runtimeHints) throws Exception {
|
||||
|
||||
// Mimics SpringBootContextLoader
|
||||
Method mainMethod = mergedConfig.getClasses()[0].getMethod("main", String[].class);
|
||||
runtimeHints.reflection().registerMethod(mainMethod, ExecutableMode.INVOKE);
|
||||
|
||||
return loadContext(mergedConfig);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,109 @@
|
||||
/*
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.test.context.aot;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.context.support.GenericApplicationContext;
|
||||
import org.springframework.test.context.MergedContextConfiguration;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.mockito.BDDMockito.never;
|
||||
import static org.mockito.BDDMockito.spy;
|
||||
import static org.mockito.BDDMockito.then;
|
||||
|
||||
/**
|
||||
* Unit tests for {@link AotContextLoader}.
|
||||
*
|
||||
* @author Sam Brannen
|
||||
* @since 6.2.4
|
||||
*/
|
||||
class AotContextLoaderTests {
|
||||
|
||||
/**
|
||||
* Verifies that a legacy {@link AotContextLoader} which only overrides
|
||||
* {@link AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration)
|
||||
* is still supported.
|
||||
*/
|
||||
@Test // gh-34513
|
||||
@SuppressWarnings("removal")
|
||||
void legacyAotContextLoader() throws Exception {
|
||||
// Prerequisites
|
||||
assertDeclaringClasses(LegacyAotContextLoader.class, LegacyAotContextLoader.class, AotContextLoader.class);
|
||||
|
||||
AotContextLoader loader = spy(new LegacyAotContextLoader());
|
||||
MergedContextConfiguration mergedConfig = new MergedContextConfiguration(getClass(), null, null, null, loader);
|
||||
|
||||
loader.loadContextForAotProcessing(mergedConfig, new RuntimeHints());
|
||||
|
||||
then(loader).should().loadContextForAotProcessing(mergedConfig);
|
||||
}
|
||||
|
||||
/**
|
||||
* Verifies that a modern {@link AotContextLoader} which only overrides
|
||||
* {@link AotContextLoader#loadContextForAotProcessing(MergedContextConfiguration, RuntimeHints)
|
||||
* is supported.
|
||||
*/
|
||||
@Test // gh-34513
|
||||
@SuppressWarnings("removal")
|
||||
void runtimeHintsAwareAotContextLoader() throws Exception {
|
||||
// Prerequisites
|
||||
assertDeclaringClasses(RuntimeHintsAwareAotContextLoader.class, AotContextLoader.class, RuntimeHintsAwareAotContextLoader.class);
|
||||
|
||||
AotContextLoader loader = spy(new RuntimeHintsAwareAotContextLoader());
|
||||
MergedContextConfiguration mergedConfig = new MergedContextConfiguration(getClass(), null, null, null, loader);
|
||||
|
||||
loader.loadContextForAotProcessing(mergedConfig, new RuntimeHints());
|
||||
|
||||
then(loader).should(never()).loadContextForAotProcessing(mergedConfig);
|
||||
}
|
||||
|
||||
|
||||
private static void assertDeclaringClasses(Class<? extends AotContextLoader> loaderClass,
|
||||
Class<?> declaringClassForLegacyMethod, Class<?> declaringClassForNewMethod) throws Exception {
|
||||
|
||||
Method legacyMethod = loaderClass.getMethod("loadContextForAotProcessing", MergedContextConfiguration.class);
|
||||
Method newMethod = loaderClass.getMethod("loadContextForAotProcessing", MergedContextConfiguration.class, RuntimeHints.class);
|
||||
|
||||
assertThat(legacyMethod.getDeclaringClass()).isEqualTo(declaringClassForLegacyMethod);
|
||||
assertThat(newMethod.getDeclaringClass()).isEqualTo(declaringClassForNewMethod);
|
||||
}
|
||||
|
||||
|
||||
private static class LegacyAotContextLoader extends AbstractAotContextLoader {
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("removal")
|
||||
public GenericApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig) {
|
||||
return loadContext(mergedConfig);
|
||||
}
|
||||
}
|
||||
|
||||
private static class RuntimeHintsAwareAotContextLoader extends AbstractAotContextLoader {
|
||||
|
||||
@Override
|
||||
public GenericApplicationContext loadContextForAotProcessing(MergedContextConfiguration mergedConfig,
|
||||
RuntimeHints runtimeHints) {
|
||||
|
||||
return loadContext(mergedConfig);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2023 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -38,7 +38,7 @@ import static org.assertj.core.api.Assertions.assertThatNoException;
|
||||
* @author Sam Brannen
|
||||
* @since 6.1
|
||||
*/
|
||||
class TestPropertySourceRuntimeHintsTests extends AbstractAotTests {
|
||||
class TestPropertySourceRuntimeHintsTests {
|
||||
|
||||
private final RuntimeHints runtimeHints = new RuntimeHints();
|
||||
|
||||
@@ -93,7 +93,7 @@ class TestPropertySourceRuntimeHintsTests extends AbstractAotTests {
|
||||
static class WildcardLocationPatternTestCase {
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
static class Config {
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2024 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -20,6 +20,7 @@ import java.util.Arrays;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
import org.springframework.test.context.MergedContextConfiguration;
|
||||
@@ -79,7 +80,7 @@ class AnnotationConfigContextLoaderTests {
|
||||
AnnotatedFooConfigInnerClassTestCase.class, EMPTY_STRING_ARRAY,
|
||||
new Class<?>[] {AnnotatedFooConfigInnerClassTestCase.FooConfig.class},
|
||||
EMPTY_STRING_ARRAY, contextLoader);
|
||||
ConfigurableApplicationContext context = contextLoader.loadContextForAotProcessing(mergedConfig);
|
||||
ConfigurableApplicationContext context = contextLoader.loadContextForAotProcessing(mergedConfig, new RuntimeHints());
|
||||
assertThat(context.isActive()).as("ApplicationContext is active").isFalse();
|
||||
assertThat(Arrays.stream(context.getBeanDefinitionNames())).anyMatch(name -> name.contains("FooConfig"));
|
||||
context.close();
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2024 the original author or authors.
|
||||
* Copyright 2002-2025 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -21,6 +21,7 @@ import java.util.Arrays;
|
||||
import org.junit.jupiter.api.Nested;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
@@ -181,7 +182,7 @@ class DelegatingSmartContextLoaderTests {
|
||||
private void assertApplicationContextLoadsForAotProcessing(MergedContextConfiguration mergedConfig,
|
||||
String expectedBeanDefName) throws Exception {
|
||||
|
||||
ApplicationContext context = loader.loadContextForAotProcessing(mergedConfig);
|
||||
ApplicationContext context = loader.loadContextForAotProcessing(mergedConfig, new RuntimeHints());
|
||||
assertThat(context).isInstanceOf(ConfigurableApplicationContext.class);
|
||||
ConfigurableApplicationContext cac = (ConfigurableApplicationContext) context;
|
||||
assertThat(cac.isActive()).as("ApplicationContext is active").isFalse();
|
||||
|
||||
Reference in New Issue
Block a user