Add shortcut to register an executable with a mode
See gh-29011
This commit is contained in:
parent
c164b918c0
commit
5aa8583159
|
|
@ -46,7 +46,6 @@ import org.springframework.aot.generate.GeneratedClass;
|
|||
import org.springframework.aot.generate.GeneratedMethod;
|
||||
import org.springframework.aot.generate.GenerationContext;
|
||||
import org.springframework.aot.generate.MethodReference;
|
||||
import org.springframework.aot.hint.ExecutableHint;
|
||||
import org.springframework.aot.hint.ExecutableMode;
|
||||
import org.springframework.aot.hint.FieldHint;
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
|
|
@ -914,9 +913,6 @@ public class AutowiredAnnotationBeanPostProcessor implements SmartInstantiationA
|
|||
|
||||
private static final String INSTANCE_PARAMETER = "instance";
|
||||
|
||||
private static final Consumer<ExecutableHint.Builder> INTROSPECT = builder -> builder
|
||||
.withMode(ExecutableMode.INTROSPECT);
|
||||
|
||||
private static final Consumer<FieldHint.Builder> ALLOW_WRITE = builder -> builder
|
||||
.allowWrite(true);
|
||||
|
||||
|
|
@ -1024,7 +1020,7 @@ public class AutowiredAnnotationBeanPostProcessor implements SmartInstantiationA
|
|||
INSTANCE_PARAMETER);
|
||||
}
|
||||
else {
|
||||
hints.reflection().registerMethod(method, INTROSPECT);
|
||||
hints.reflection().registerMethod(method, ExecutableMode.INTROSPECT);
|
||||
CodeBlock arguments = new AutowiredArgumentsCodeGenerator(this.target,
|
||||
method).generateCode(method.getParameterTypes());
|
||||
CodeBlock injectionCode = CodeBlock.of("args -> $L.$L($L)",
|
||||
|
|
|
|||
|
|
@ -28,12 +28,10 @@ import java.util.Map;
|
|||
import java.util.Objects;
|
||||
import java.util.function.BiFunction;
|
||||
import java.util.function.BiPredicate;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Predicate;
|
||||
|
||||
import org.springframework.aot.generate.GeneratedMethods;
|
||||
import org.springframework.aot.hint.ExecutableHint;
|
||||
import org.springframework.aot.hint.ExecutableMode;
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.beans.BeanInfoFactory;
|
||||
|
|
@ -83,8 +81,6 @@ class BeanDefinitionPropertiesCodeGenerator {
|
|||
|
||||
private static final String BEAN_DEFINITION_VARIABLE = BeanRegistrationCodeFragments.BEAN_DEFINITION_VARIABLE;
|
||||
|
||||
private static final Consumer<ExecutableHint.Builder> INVOKE_HINT = hint -> hint.withMode(ExecutableMode.INVOKE);
|
||||
|
||||
private static final BeanInfoFactory beanInfoFactory = new ExtendedBeanInfoFactory();
|
||||
|
||||
private final RuntimeHints hints;
|
||||
|
|
@ -195,7 +191,7 @@ class BeanDefinitionPropertiesCodeGenerator {
|
|||
for (PropertyValue propertyValue : propertyValues) {
|
||||
Method writeMethod = writeMethods.get(propertyValue.getName());
|
||||
if (writeMethod != null) {
|
||||
this.hints.reflection().registerMethod(writeMethod, INVOKE_HINT);
|
||||
this.hints.reflection().registerMethod(writeMethod, ExecutableMode.INVOKE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,7 +28,6 @@ import org.springframework.aot.generate.AccessVisibility;
|
|||
import org.springframework.aot.generate.GeneratedMethod;
|
||||
import org.springframework.aot.generate.GeneratedMethods;
|
||||
import org.springframework.aot.generate.GenerationContext;
|
||||
import org.springframework.aot.hint.ExecutableHint;
|
||||
import org.springframework.aot.hint.ExecutableMode;
|
||||
import org.springframework.beans.factory.support.InstanceSupplier;
|
||||
import org.springframework.beans.factory.support.RegisteredBean;
|
||||
|
|
@ -69,9 +68,6 @@ class InstanceSupplierCodeGenerator {
|
|||
|
||||
private static final CodeBlock NO_ARGS = CodeBlock.of("");
|
||||
|
||||
private static final Consumer<ExecutableHint.Builder> INTROSPECT = hint -> hint
|
||||
.withMode(ExecutableMode.INTROSPECT);
|
||||
|
||||
|
||||
private final GenerationContext generationContext;
|
||||
|
||||
|
|
@ -128,7 +124,7 @@ class InstanceSupplierCodeGenerator {
|
|||
Constructor<?> constructor, boolean dependsOnBean, Class<?> declaringClass) {
|
||||
|
||||
this.generationContext.getRuntimeHints().reflection()
|
||||
.registerConstructor(constructor, INTROSPECT);
|
||||
.registerConstructor(constructor, ExecutableMode.INTROSPECT);
|
||||
if (!dependsOnBean && constructor.getParameterCount() == 0) {
|
||||
if (!this.allowDirectSupplierShortcut) {
|
||||
return CodeBlock.of("$T.using($T::new)", InstanceSupplier.class,
|
||||
|
|
@ -225,7 +221,7 @@ class InstanceSupplierCodeGenerator {
|
|||
Class<?> beanClass, Method factoryMethod, Class<?> declaringClass, boolean dependsOnBean) {
|
||||
|
||||
this.generationContext.getRuntimeHints().reflection()
|
||||
.registerMethod(factoryMethod, INTROSPECT);
|
||||
.registerMethod(factoryMethod, ExecutableMode.INTROSPECT);
|
||||
if (!dependsOnBean && factoryMethod.getParameterCount() == 0) {
|
||||
CodeBlock.Builder code = CodeBlock.builder();
|
||||
code.add("$T.<$T>forFactoryMethod($T.class, $S)", BeanInstanceSupplier.class,
|
||||
|
|
|
|||
|
|
@ -25,12 +25,10 @@ import java.lang.reflect.RecordComponent;
|
|||
import java.lang.reflect.Type;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.Set;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.aot.hint.ExecutableHint;
|
||||
import org.springframework.aot.hint.ExecutableMode;
|
||||
import org.springframework.aot.hint.MemberCategory;
|
||||
import org.springframework.aot.hint.ReflectionHints;
|
||||
|
|
@ -54,9 +52,6 @@ public class BindingReflectionHintsRegistrar {
|
|||
|
||||
private static final Log logger = LogFactory.getLog(BindingReflectionHintsRegistrar.class);
|
||||
|
||||
private static final Consumer<ExecutableHint.Builder> INVOKE = builder -> builder
|
||||
.withMode(ExecutableMode.INVOKE);
|
||||
|
||||
private static final String KOTLIN_COMPANION_SUFFIX = "$Companion";
|
||||
|
||||
/**
|
||||
|
|
@ -127,7 +122,7 @@ public class BindingReflectionHintsRegistrar {
|
|||
}
|
||||
|
||||
private void registerRecordHints(ReflectionHints hints, Set<Type> seen, Method method) {
|
||||
hints.registerMethod(method, INVOKE);
|
||||
hints.registerMethod(method, ExecutableMode.INVOKE);
|
||||
MethodParameter methodParameter = MethodParameter.forExecutable(method, -1);
|
||||
Type methodParameterType = methodParameter.getGenericParameterType();
|
||||
if (!seen.contains(methodParameterType)) {
|
||||
|
|
@ -138,7 +133,7 @@ public class BindingReflectionHintsRegistrar {
|
|||
private void registerPropertyHints(ReflectionHints hints, Set<Type> seen, @Nullable Method method, int parameterIndex) {
|
||||
if (method != null && method.getDeclaringClass() != Object.class
|
||||
&& method.getDeclaringClass() != Enum.class) {
|
||||
hints.registerMethod(method, INVOKE);
|
||||
hints.registerMethod(method, ExecutableMode.INVOKE);
|
||||
MethodParameter methodParameter = MethodParameter.forExecutable(method, parameterIndex);
|
||||
Type methodParameterType = methodParameter.getGenericParameterType();
|
||||
if (!seen.contains(methodParameterType)) {
|
||||
|
|
|
|||
|
|
@ -158,6 +158,17 @@ public class ReflectionHints {
|
|||
typeHint -> typeHint.withConstructor(mapParameters(constructor), constructorHint));
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the need for reflection on the specified {@link Constructor},
|
||||
* using the specified {@link ExecutableMode}.
|
||||
* @param constructor the constructor that requires reflection
|
||||
* @param mode the requested mode
|
||||
* @return {@code this}, to facilitate method chaining
|
||||
*/
|
||||
public ReflectionHints registerConstructor(Constructor<?> constructor, ExecutableMode mode) {
|
||||
return registerConstructor(constructor, constructorHint -> constructorHint.withMode(mode));
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the need for reflection on the specified {@link Constructor},
|
||||
* enabling {@link ExecutableMode#INVOKE}.
|
||||
|
|
@ -165,7 +176,7 @@ public class ReflectionHints {
|
|||
* @return {@code this}, to facilitate method chaining
|
||||
*/
|
||||
public ReflectionHints registerConstructor(Constructor<?> constructor) {
|
||||
return registerConstructor(constructor, constructorHint -> constructorHint.withMode(ExecutableMode.INVOKE));
|
||||
return registerConstructor(constructor, ExecutableMode.INVOKE);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -179,6 +190,17 @@ public class ReflectionHints {
|
|||
typeHint -> typeHint.withMethod(method.getName(), mapParameters(method), methodHint));
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the need for reflection on the specified {@link Method},
|
||||
* using the specified {@link ExecutableMode}.
|
||||
* @param method the method that requires reflection
|
||||
* @param mode the requested mode
|
||||
* @return {@code this}, to facilitate method chaining
|
||||
*/
|
||||
public ReflectionHints registerMethod(Method method, ExecutableMode mode) {
|
||||
return registerMethod(method, methodHint -> methodHint.withMode(mode));
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the need for reflection on the specified {@link Method},
|
||||
* enabling {@link ExecutableMode#INVOKE}.
|
||||
|
|
@ -186,7 +208,7 @@ public class ReflectionHints {
|
|||
* @return {@code this}, to facilitate method chaining
|
||||
*/
|
||||
public ReflectionHints registerMethod(Method method) {
|
||||
return registerMethod(method, methodHint -> methodHint.withMode(ExecutableMode.INVOKE));
|
||||
return registerMethod(method, ExecutableMode.INVOKE);
|
||||
}
|
||||
|
||||
private List<TypeReference> mapParameters(Executable executable) {
|
||||
|
|
|
|||
|
|
@ -176,6 +176,16 @@ class ReflectionHintsTests {
|
|||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void registerConstructorWithMode() {
|
||||
this.reflectionHints.registerConstructor(
|
||||
TestType.class.getDeclaredConstructors()[0], ExecutableMode.INTROSPECT);
|
||||
assertTestTypeConstructorHint(constructorHint -> {
|
||||
assertThat(constructorHint.getParameterTypes()).isEmpty();
|
||||
assertThat(constructorHint.getMode()).isEqualTo(ExecutableMode.INTROSPECT);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void registerConstructorWithEmptyCustomizerAppliesConsistentDefault() {
|
||||
this.reflectionHints.registerConstructor(TestType.class.getDeclaredConstructors()[0],
|
||||
|
|
@ -219,6 +229,18 @@ class ReflectionHintsTests {
|
|||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void registerMethodWithMode() {
|
||||
Method method = ReflectionUtils.findMethod(TestType.class, "setName", String.class);
|
||||
assertThat(method).isNotNull();
|
||||
this.reflectionHints.registerMethod(method, ExecutableMode.INTROSPECT);
|
||||
assertTestTypeMethodHints(methodHint -> {
|
||||
assertThat(methodHint.getName()).isEqualTo("setName");
|
||||
assertThat(methodHint.getParameterTypes()).containsOnly(TypeReference.of(String.class));
|
||||
assertThat(methodHint.getMode()).isEqualTo(ExecutableMode.INTROSPECT);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void registerMethodWithEmptyCustomizerAppliesConsistentDefault() {
|
||||
Method method = ReflectionUtils.findMethod(TestType.class, "setName", String.class);
|
||||
|
|
|
|||
|
|
@ -64,13 +64,13 @@ class MessageMappingReflectiveProcessor implements ReflectiveProcessor {
|
|||
}
|
||||
|
||||
protected void registerMethodHints(ReflectionHints hints, Method method) {
|
||||
hints.registerMethod(method, hint -> hint.withMode(ExecutableMode.INVOKE));
|
||||
hints.registerMethod(method, ExecutableMode.INVOKE);
|
||||
registerParameterHints(hints, method);
|
||||
registerReturnValueHints(hints, method);
|
||||
}
|
||||
|
||||
protected void registerParameterHints(ReflectionHints hints, Method method) {
|
||||
hints.registerMethod(method, hint -> hint.withMode(ExecutableMode.INVOKE));
|
||||
hints.registerMethod(method, ExecutableMode.INVOKE);
|
||||
for (Parameter parameter : method.getParameters()) {
|
||||
MethodParameter methodParameter = MethodParameter.forParameter(parameter);
|
||||
if (Message.class.isAssignableFrom(methodParameter.getParameterType())) {
|
||||
|
|
|
|||
|
|
@ -63,13 +63,13 @@ class RequestMappingReflectiveProcessor implements ReflectiveProcessor {
|
|||
}
|
||||
|
||||
protected void registerMethodHints(ReflectionHints hints, Method method) {
|
||||
hints.registerMethod(method, hint -> hint.withMode(ExecutableMode.INVOKE));
|
||||
hints.registerMethod(method, ExecutableMode.INVOKE);
|
||||
registerParameterHints(hints, method);
|
||||
registerReturnValueHints(hints, method);
|
||||
}
|
||||
|
||||
protected void registerParameterHints(ReflectionHints hints, Method method) {
|
||||
hints.registerMethod(method, hint -> hint.withMode(ExecutableMode.INVOKE));
|
||||
hints.registerMethod(method, ExecutableMode.INVOKE);
|
||||
for (Parameter parameter : method.getParameters()) {
|
||||
MethodParameter methodParameter = MethodParameter.forParameter(parameter);
|
||||
if (methodParameter.hasParameterAnnotation(RequestBody.class) ||
|
||||
|
|
|
|||
Loading…
Reference in New Issue