diff --git a/spring-core/src/main/java/org/springframework/util/Assert.java b/spring-core/src/main/java/org/springframework/util/Assert.java index 16a191d1264..828f5273818 100644 --- a/spring-core/src/main/java/org/springframework/util/Assert.java +++ b/spring-core/src/main/java/org/springframework/util/Assert.java @@ -56,6 +56,51 @@ import java.util.function.Supplier; */ public abstract class Assert { + /** + * Assert a boolean expression, throwing an {@code IllegalStateException} + * if the expression evaluates to {@code false}. + *
Call {@link #isTrue} if you wish to throw an {@code IllegalArgumentException} + * on an assertion failure. + *
+ * Assert.state(id == null, + * () -> "ID for " + entity.getName() + " must not already be initialized"); + *+ * @param expression a boolean expression + * @param messageSupplier a supplier for the exception message to use if the + * assertion fails + * @throws IllegalStateException if {@code expression} is {@code false} + * @since 5.0 + */ + public static void state(boolean expression, Supplier
Call {@link #isTrue} if you wish to throw an {@code IllegalArgumentException} + * on an assertion failure. + *
Assert.state(id == null, "The id property must not already be initialized");+ * @param expression a boolean expression + * @param message the exception message to use if the assertion fails + * @throws IllegalStateException if {@code expression} is {@code false} + */ + public static void state(boolean expression, String message) { + if (!expression) { + throw new IllegalStateException(message); + } + } + + /** + * @deprecated as of 4.3.7, in favor of {@link #state(boolean, String)} + */ + @Deprecated + public static void state(boolean expression) { + state(expression, "[Assertion failed] - this state invariant must be true"); + } + /** * Assert a boolean expression, throwing an {@code IllegalArgumentException} * if the expression evaluates to {@code false}. @@ -480,11 +525,8 @@ public abstract class Assert { * @param type the type to check against * @param obj the object to check * @param messageSupplier a supplier for the exception message to use if the - * assertion fails; the message will be prepended to the message generated - * by this method in order to provide further context. It should normally end - * in ":" or "." so that the generated message looks OK when appended to it. + * assertion fails. See {@link #isInstanceOf(Class, Object, String)} for details. * @throws IllegalArgumentException if the object is not an instance of type - * @see Class#isInstance * @since 5.0 */ public static void isInstanceOf(Class> type, Object obj, Supplier
Assert.instanceOf(Foo.class, foo, "Processing Foo:");+ *
Assert.instanceOf(Foo.class, foo, "Foo expected");* @param type the type to check against * @param obj the object to check - * @param message a message which will be prepended to the message generated - * by this method in order to provide further context. It should normally end - * in ":" or "." so that the generated message looks OK when appended to it. + * @param message a message which will be prepended to provide further context. + * If it is empty or ends in ":" or ";" or "," or ".", a full exception message + * will be appended. If it ends in a space, the name of the offending object's + * type will be appended. In any other case, a ":" with a space and the name + * of the offending object's type will be appended. * @throws IllegalArgumentException if the object is not an instance of type - * @see Class#isInstance */ public static void isInstanceOf(Class> type, Object obj, String message) { notNull(type, "Type to check against must not be null"); @@ -518,29 +561,20 @@ public abstract class Assert { * @param type the type to check against * @param obj the object to check * @throws IllegalArgumentException if the object is not an instance of type - * @see Class#isInstance */ public static void isInstanceOf(Class> type, Object obj) { isInstanceOf(type, obj, ""); } - private static void instanceCheckFailed(Class> type, Object obj, String message) { - String className = (obj != null ? obj.getClass().getName() : "null"); - throw new IllegalArgumentException(StringUtils.hasLength(message) ? message + ": " + className : - "Object of class [" + className + "] must be an instance of " + type); - } - /** * Assert that {@code superType.isAssignableFrom(subType)} is {@code true}. *
- * Assert.isAssignable(Number.class, myClass, () -> "Processing " + myClass.getSimpleName() + ":"); + * Assert.isAssignable(Number.class, myClass, () -> "Processing " + myAttributeName + ":"); ** @param superType the super type to check against * @param subType the sub type to check * @param messageSupplier a supplier for the exception message to use if the - * assertion fails; the message will be prepended to the message generated - * by this method in order to provide further context. It should normally end - * in ":" or "." so that the generated message looks OK when appended to it. + * assertion fails. See {@link #isAssignable(Class, Class, String)} for details. * @throws IllegalArgumentException if the classes are not assignable * @since 5.0 */ @@ -553,12 +587,14 @@ public abstract class Assert { /** * Assert that {@code superType.isAssignableFrom(subType)} is {@code true}. - *
Assert.isAssignable(Number.class, myClass);+ *
Assert.isAssignable(Number.class, myClass, "Number expected");* @param superType the super type to check against * @param subType the sub type to check - * @param message a message which will be prepended to the message generated - * by this method in order to provide further context. It should normally end - * in ":" or "." so that the generated message looks OK when appended to it. + * @param message a message which will be prepended to provide further context. + * If it is empty or ends in ":" or ";" or "," or ".", a full exception message + * will be appended. If it ends in a space, the name of the offending sub type + * will be appended. In any other case, a ":" with a space and the name of the + * offending sub type will be appended. * @throws IllegalArgumentException if the classes are not assignable */ public static void isAssignable(Class> superType, Class> subType, String message) { @@ -579,54 +615,50 @@ public abstract class Assert { isAssignable(superType, subType, ""); } - private static void assignableCheckFailed(Class> superType, Class> subType, String message) { - throw new IllegalArgumentException(StringUtils.hasLength(message) ? message + ": " + subType : - subType + " is not assignable to " + superType); - } - /** - * Assert a boolean expression, throwing an {@code IllegalStateException} - * if the expression evaluates to {@code false}. - *
Call {@link #isTrue} if you wish to throw an {@code IllegalArgumentException} - * on an assertion failure. - *
- * Assert.state(id == null, - * () -> "ID for " + entity.getName() + " must not already be initialized"); - *- * @param expression a boolean expression - * @param messageSupplier a supplier for the exception message to use if the - * assertion fails - * @throws IllegalStateException if {@code expression} is {@code false} - * @since 5.0 - */ - public static void state(boolean expression, Supplier
Call {@link #isTrue} if you wish to throw an {@code IllegalArgumentException} - * on an assertion failure. - *
Assert.state(id == null, "The id property must not already be initialized");- * @param expression a boolean expression - * @param message the exception message to use if the assertion fails - * @throws IllegalStateException if {@code expression} is {@code false} - */ - public static void state(boolean expression, String message) { - if (!expression) { - throw new IllegalStateException(message); + private static void assignableCheckFailed(Class> superType, Class> subType, String msg) { + String result = ""; + boolean defaultMessage = true; + if (StringUtils.hasLength(msg)) { + if (endsWithSeparator(msg)) { + result = msg + " "; + } + else { + result = messageWithTypeName(msg, subType); + defaultMessage = false; + } } + if (defaultMessage) { + result = result + (subType + " is not assignable to " + superType); + } + throw new IllegalArgumentException(result); } - /** - * @deprecated as of 4.3.7, in favor of {@link #state(boolean, String)} - */ - @Deprecated - public static void state(boolean expression) { - state(expression, "[Assertion failed] - this state invariant must be true"); + private static boolean endsWithSeparator(String msg) { + return (msg.endsWith(":") || msg.endsWith(";") || msg.endsWith(",") || msg.endsWith(".")); + } + + private static String messageWithTypeName(String msg, Object typeName) { + return msg + (msg.endsWith(" ") ? "" : ": ") + typeName; } private static String nullSafeGet(Supplier