In the case of parameter validation, it is often necessary to define a validation annotation. This section describes how to define a validation annotation.

For more information on validation, see “Using Validation in SpringBoot.”

How do I customize a validation annotation?

Defining validation annotations yourself requires using @constraint. The @constraint annotation is described as follows:

* Marks an annotation as being a Bean Validation constraint. * <p/> * A given constraint annotation must be annotated by  a {@code @Constraint}
 * annotation which refers to its list of constraint validation implementations.
 * <p/>
 * Each constraint annotation must host the following attributes:
 * <ul>
 *     <li>{@code String message(a) default[...].; } which shoulddefault to an error
 *     message key made of the fully-qualified class name of the constraint followed by
 *     {@code .message}. For example {@code "{com.acme.constraints.NotSafe.message}"}</li>
 *     <li>{@codeClass<? >[] groups()default{}; }for user to customize the targeted
 *     groups</li>
 *     <li>{@code Class<? extends Payload>[] payload() default{}; }for
 *     extensibility purposes</li>
 * </ul>
 * <p/>
Copy the code

As you can see, @constraint uses it to note that our annotation is a Validation Constraint, and it also specifies the three annotation elements that we need when defining our own Validation annotation:

String message(a) default[...].; Class<? >[] groups()default {};
Class<? extends Payload>[] payload() default {};
Copy the code

We need to add a validator that meets our requirements. We need to add a validator that implements the following interface:

javax.validation.ConstraintValidator
Copy the code

Custom Validation annotates the case

Enumeration validation annotation @enum

The validation-API annotation and Hibernate extensions do not have validation for enumerations, which are required in some cases. Let’s define a validation annotation for ourselves as follows:

package com.lazycece.sbac.validation.constraint;

import com.lazycece.sbac.validation.constraint.validator.EnumValidator;

import javax.validation.Constraint;
import javax.validation.Payload;
import java.lang.annotation.Documented;
import java.lang.annotation.Repeatable;
import java.lang.annotation.Retention;
import java.lang.annotation.Target;

import static java.lang.annotation.ElementType.*;
import static java.lang.annotation.ElementType.PARAMETER;
import static java.lang.annotation.ElementType.TYPE_USE;
import static java.lang.annotation.RetentionPolicy.RUNTIME;

/ * * *@author lazycece
 * @date2019/2/15 * /
@Documented
@Target({METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER, TYPE_USE})
@Retention(RUNTIME)
@Repeatable(Enum.List.class)
@Constraint(validatedBy = {EnumValidator.class})
public @interface Enum {

    String message(a) default "{*.validation.constraint.Enum.message}"; Class
      [] groups() default {}; Class
      [] payload() default {}; /** * the enum's class-type * * @return Class */ Class
       clazz(); /** * the method's name ,which used to validate the enum's value * * @return method's name */ String method() default "ordinal"; /** * Defines several {@link Enum} annotations on the same element. * * @see Enum */ @Documented @Target({METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER, TYPE_USE}) @Retention(RUNTIME) @interface List { Enum[] value(); }}Copy the code

Enumeration validates the validator

The validator code for the annotation validation logic looks like this, judging by reflecting the value of the enumeration.

package com.lazycece.sbac.validation.constraint.validator;

import com.lazycece.sbac.validation.constraint.Enum;

import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;
import java.lang.reflect.Method;

/ * * *@author lazycece
 * @date2019/2/15 * /
public class EnumValidator implements ConstraintValidator<Enum.Object> {

    private Enum annotation;

    @Override
    public void initialize(Enum constraintAnnotation) {
        this.annotation = constraintAnnotation;
    }

    @Override
    public boolean isValid(Object value, ConstraintValidatorContext context) {
        if (value == null) {
            return false;
        }

        Object[] objects = annotation.clazz().getEnumConstants();
        try {
            Method method = annotation.clazz().getMethod(annotation.method());
            for (Object o : objects) {
                if (value.equals(method.invoke(o))) {
                    return true; }}}catch (Exception e) {
            throw new RuntimeException(e);
        }
        return false; }}Copy the code

use

The use of the @enum annotation requires the enumeration class and the method to get the enumeration value to be validated (the default is ordinal).

If we define an enumeration class like this, there are four ways to validate:

package com.lazycece.sbac.validation.enums;

/ * * *@author lazycece
 * @date2019/02/15 * /
public enum Role {

    ADMIN(1."ADMIN"),
    TEST(2."TEST"),
    DEVELOP(3."DEVELOP");

    private int value;
    private String desc;

    Role(int value, String desc) {
        this.value = value;
        this.desc = desc;
    }

    public int getValue(a) {
        return value;
    }

    public void setValue(int value) {
        this.value = value;
    }

    public String getDesc(a) {
        return desc;
    }

    public void setDesc(String desc) {
        this.desc = desc; }}Copy the code
  • The param parameter is the ordinal value of the enumeration
    @enum (clazz = Role. Class, message = "Role parameter error ")
    Copy the code
  • The param parameter is the name value of the enumeration
    @enum (clazz = Role. Class, method = "name", message = "Role parameter error ")
    Copy the code
  • The param parameter is the value of the enumeration
    @enum (clazz = Role. Class, method = "getValue", message = "Role parameter error ")
    Copy the code
  • The param parameter is desc for the enumeration
    @enum (clazz = Role. Class, method = "getDesc", message = "Role parameter error ")
    Copy the code

Example source code

Case source address: github.com/lazycece/sp…