[JAVA] OVal (annotation-based validation FW) code example

I tried using validation FW that can add input restrictions by annotation-based annotation called OVal. Make a note of the code example at that time.

Dependencies

pom.xml


<!-- https://mvnrepository.com/artifact/net.sf.oval/oval -->
<dependency>
    <groupId>net.sf.oval</groupId>
    <artifactId>oval</artifactId>
    <version>1.90</version>
</dependency>

build.gradle


// https://mvnrepository.com/artifact/net.sf.oval/oval
compile group: 'net.sf.oval', name: 'oval', version: '1.90'

When using with Spring

net.sf.oval.integration.spring.SpringValidator It seems that ʻorg.springframework.validation.Validator` is implemented. I haven't used it yet, so I will report it again when I try it.

Basic code example

Bean class


public class SampleBean{
    /** ID */
	@Assert(expr = "null!=_value&&''!=_value", lang = "js"
//lang =Is"bsh" / "beanshell", "groovy", or "js" / "javascript".Choose whichever you like and use it
//If it was about this@Maybe I should have used NotEmpty ...
    		,message="No ID has been entered")
    private String id;

    /** No */
    private Integer no;

    /**Registration date*/
    @Assert(expr = "null!=_value&&''!=_value", lang = "js"
    		,message="The registration date has not been entered")
    @MatchPattern(pattern=DateUtil.DATE_MATCH_PATTERN
    		,message="The format of the registration date is strange"
    		,when="js:null!=_value&&''!=_value")
    @DateRange(format=DateUtil.DATE_HH_MM_FORMAT,message="The date range of the registration date is incorrect")
    @ValidateWithMethod(methodName="isValidDate", parameterType=String.class)
			,message="Please enter the date of December")
    private String abcTime;

    //getter,setter omitted

    private boolean isValidDate(String arg){//I will return true only in December
        if(arg.matches("\d{4}/12/.*")){
            return true;
        }else{
            return false;
        }
    }
}

How to validate


net.sf.oval.Validator validator = new net.sf.oval.Validator();
List<ConstraintViolation> clist =  validator.validate( validatedObject );

I want to validate with a static method

In that case, it is not a standard function, so create your own validation annotation and check method. It's smarter to write in java8, but since I can only use the java7 environment (T-T), it's the java7 code.

ValidateWithStaticMethod.java(Annotation)


import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

import net.sf.oval.ConstraintTarget;
import net.sf.oval.ConstraintViolation;
import net.sf.oval.configuration.annotation.Constraint;
import net.sf.oval.configuration.annotation.Constraints;

@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ ElementType.FIELD, ElementType.PARAMETER, ElementType.METHOD, ElementType.TYPE })
@Constraint(checkWith = ValidateWithStaticMethodCheck.class)
public @interface ValidateWithStaticMethod {
    @Documented
    @Retention(RetentionPolicy.RUNTIME)
    @Target({ ElementType.FIELD, ElementType.PARAMETER, ElementType.METHOD, ElementType.TYPE })
    @Constraints
    public @interface List {
        ValidateWithStaticMethod[] value();
        String when() default "";
    }

    ConstraintTarget[] appliesTo() default ConstraintTarget.CONTAINER;

    String errorCode() default "net.sf.oval.constraint.ValidateWithMethod";

    boolean ignoreIfNull() default true;

    boolean ignoreIfNullOrEmpty() default true;

    String message() default "Message is not defined(ValidateWithStaticMethod)";

    Class<?> clazz();

    String methodName();

    String[] profiles() default {};

    int severity() default 0;

    String target() default "";

    String when() default "";
}

ValidateWithStaticMethodCheck.java(Check logic)



import static net.sf.oval.Validator.*;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.List;
import java.util.Map;
import java.util.WeakHashMap;

import net.sf.oval.ConstraintTarget;
import net.sf.oval.Validator;
import net.sf.oval.configuration.annotation.AbstractAnnotationCheck;
import net.sf.oval.context.OValContext;
import net.sf.oval.exception.ReflectionException;

/**
 *Check by Static method
 */
public class ValidateWithStaticMethodCheck extends AbstractAnnotationCheck<ValidateWithStaticMethod> {
    private static final long serialVersionUID = 1L;

    private final Map<Class<?>, Method> validationMethodsByClass = new WeakHashMap<Class<?>, Method>();

    private boolean ignoreIfNull;
    private boolean ignoreIfNullOrEmpty;
    private Class<?> clazz;
    private String methodName;

    @Override
    public void configure(final ValidateWithStaticMethod constraintAnnotation) {
        super.configure(constraintAnnotation);
        setMethodName(constraintAnnotation.methodName());
        setClazz(constraintAnnotation.clazz());
        setIgnoreIfNull(constraintAnnotation.ignoreIfNull());
        setIgnoreIfNullOrEmpty(constraintAnnotation.ignoreIfNullOrEmpty());
    }

    @Override
    protected Map<String, String> createMessageVariables() {
        final Map<String, String> messageVariables = getCollectionFactory().createMap(4);
        messageVariables.put("ignoreIfNull", Boolean.toString(ignoreIfNull));
        messageVariables.put("ignoreIfNullOrEmpty", Boolean.toString(ignoreIfNullOrEmpty));
        messageVariables.put("methodName", methodName);
        return messageVariables;
    }

    @Override
    protected ConstraintTarget[] getAppliesToDefault() {
        return new ConstraintTarget[] { ConstraintTarget.VALUES };
    }

    public String getMethodName() {
        return methodName;
    }

    public boolean isIgnoreIfNull() {
        return ignoreIfNull;
    }

    public boolean isSatisfied(final Object validatedObject, final Object valueToValidate, final OValContext context, final Validator validator)
            throws ReflectionException {
        if (valueToValidate == null && ignoreIfNull)
            return true;
        if(ignoreIfNullOrEmpty){
        	if (valueToValidate == null)
        		return true;
        	//If you want to add an empty judgment condition, please add it here
        	if ( valueToValidate instanceof String && "".equals(valueToValidate) )
        		return true;
        	if ( valueToValidate instanceof Object[] && 0==((Object[])valueToValidate).length )
        		return true;
        	if ( valueToValidate instanceof List && 0==((List<?>)valueToValidate).size() )
        		return true;
        }
        boolean result;
        Method method;
        try {
        	Class<?> parameterType = valueToValidate.getClass();
			method =  clazz.getMethod(methodName, parameterType);
	        result = (boolean)method.invoke(null, valueToValidate);
		} catch (NoSuchMethodException | SecurityException | IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
			throw new ReflectionException( e );
		}
        return result;
    }

    public void setIgnoreIfNull(final boolean ignoreIfNull) {
        this.ignoreIfNull = ignoreIfNull;
        requireMessageVariablesRecreation();
    }


    public void setIgnoreIfNullOrEmpty(final boolean ignoreIfNullOrEmpty) {
        this.ignoreIfNullOrEmpty = ignoreIfNullOrEmpty;
        requireMessageVariablesRecreation();
    }

	public Class<?> getClazz() {
		return clazz;
	}

	public void setClazz(Class<?> clazz) {
		this.clazz = clazz;
	}

	public void setMethodName(final String methodName) {
        this.methodName = methodName;
        synchronized (validationMethodsByClass) {
            validationMethodsByClass.clear();
        }
        requireMessageVariablesRecreation();
    }

}

How to annotate


//ValidationMethods.isFormatTelNo(String str)Code example when using
@ValidateWithStaticMethod(clazz=ValidationMethods.class
		,methodName="isFormatTelNo"
		,message="The phone number is wrong. .. ..")
private String telNo;

I want to add the same annotation multiple times

It seems that you should write like this.

@ValidateWithStaticMethod.List(value={
		@ValidateWithStaticMethod(clazz=ValidationMethods.class
				,methodName="isFormatTelNo"
				,message="The phone number format is strange"),
		@ValidateWithStaticMethod(clazz=ValidationMethods.class
				,methodName="isOkTelNumberSize"
				,message="The number of digits in the phone number is incorrect")
})
private String telNo;

List of annotations provided as standard

Recommended Posts

OVal (annotation-based validation FW) code example
Spring validation and error code