diff --git a/spring-core/src/main/java/org/springframework/core/ResolvableType.java b/spring-core/src/main/java/org/springframework/core/ResolvableType.java index 6ba088cfd1e..c1cc47261b8 100644 --- a/spring-core/src/main/java/org/springframework/core/ResolvableType.java +++ b/spring-core/src/main/java/org/springframework/core/ResolvableType.java @@ -221,9 +221,8 @@ public class ResolvableType implements Serializable { /** * Return the underlying source of the resolvable type. Will return a {@link Field}, * {@link MethodParameter} or {@link Type} depending on how the {@link ResolvableType} - * was constructed. With the exception of the {@link #NONE} constant, this method will - * never return {@code null}. This method is primarily to provide access to additional - * type information or meta-data that alternative JVM languages may provide. + * was constructed. This method is primarily to provide access to additional type + * information or meta-data that alternative JVM languages may provide. */ public Object getSource() { Object source = (this.typeProvider != null ? this.typeProvider.getSource() : null); @@ -1103,20 +1102,20 @@ public class ResolvableType implements Serializable { * convey generic information but if it implements {@link ResolvableTypeProvider} a * more precise {@link ResolvableType} can be used than the simple one based on * the {@link #forClass(Class) Class instance}. - * @param instance the instance - * @return a {@link ResolvableType} for the specified instance + * @param instance the instance (possibly {@code null}) + * @return a {@link ResolvableType} for the specified instance, + * or {@code NONE} for {@code null} * @since 4.2 * @see ResolvableTypeProvider */ - public static ResolvableType forInstance(Object instance) { - Assert.notNull(instance, "Instance must not be null"); + public static ResolvableType forInstance(@Nullable Object instance) { if (instance instanceof ResolvableTypeProvider) { ResolvableType type = ((ResolvableTypeProvider) instance).getResolvableType(); if (type != null) { return type; } } - return ResolvableType.forClass(instance.getClass()); + return (instance != null ? forClass(instance.getClass()) : NONE); } /** diff --git a/spring-core/src/test/java/org/springframework/core/ResolvableTypeTests.java b/spring-core/src/test/java/org/springframework/core/ResolvableTypeTests.java index 71b17e0da02..48641a7c70c 100644 --- a/spring-core/src/test/java/org/springframework/core/ResolvableTypeTests.java +++ b/spring-core/src/test/java/org/springframework/core/ResolvableTypeTests.java @@ -146,11 +146,9 @@ class ResolvableTypeTests { assertThat(typeVariable.isAssignableFrom(raw)).isTrue(); } - @Test - void forInstanceMustNotBeNull() throws Exception { - assertThatIllegalArgumentException() - .isThrownBy(() -> ResolvableType.forInstance(null)) - .withMessage("Instance must not be null"); + @Test // gh-28776 + void forInstanceNull() throws Exception { + assertThat(ResolvableType.forInstance(null)).isEqualTo(ResolvableType.NONE); } @Test