`

springmvc服务端数据验证的自定义验证与扩展使用

 
阅读更多

                   springmvc服务端数据验证的自定义验证与扩展使用

 

前面讲了基本的使用,现在讲一下扩展使用,

例如在注册时需要实现注册登录名的唯一性验证,这时可如下 实现:

 

1.创建一个验证登录名的限制注解。

/**
 * 验证登录名是否已被使用的限制注解
 */
@Target({ElementType.FIELD, ElementType.METHOD}) 
@Retention(RetentionPolicy.RUNTIME) 
@Constraint(validatedBy=LoginNameOnlyValidator.class)
public @interface LoginNameOnly {
        String message() default"登录名已被使用"; 
    
        Class<?>[] groups() default {}; 
        
        Class<? extends Payload>[] payload() default {}; 
}

 

2.建立这个注解的验证执行类:

 

注意:@Autowired
    private RegisterManager registerManager;  这是通过spring依赖注入,因为这里spring已经实现了对jsr-303的支持

 

/**
 * 登录名是否已被使用的注解验证的执行类
 */
public class LoginNameOnlyValidator implements ConstraintValidator<LoginNameOnly, String> {
    @Autowired
    private RegisterManager registerManager;

    @Override
    public void initialize(LoginNameOnly arg0) {}

    @Override
    public boolean isValid(String loginName, ConstraintValidatorContext arg1) {
        if(StringUtils.isBlank(loginName))
            return true;
        return registerManager.getloginNameIsUsed(loginName);
       
    }
}

 

3.在验证模型中使用:

    @LoginNameOnly
    public String getLoginName() {
        return this.loginName;
    }

就这样就可以了。不过如果是在修改过程中,则这个方法不能满足,恐怕只能结合采用编程式验证了。

 

二,这里要说另一种情况:就是对允许空的字段的验证,在界面传过来的值为这样的“”空字符串时,就是界面没有输入,在后台接受值后为“”,这时如果直接加一些验证,会出现验证无法通过。实际需要此时不验证或验证通过。

如字符如果有输入,则长度应为2-10,但可以为空,

我的解决办法是:重写一下长度验证的限制注解及长度验证的验证执行类。

2.1 先写长度的限制注解类

@Documented
@Constraint(validatedBy={LengthBValidator.class})
@Target({java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.ANNOTATION_TYPE, java.lang.annotation.ElementType.CONSTRUCTOR, java.lang.annotation.ElementType.PARAMETER})
@Retention(RetentionPolicy.RUNTIME)
public @interface LengthB
{
  public abstract int min();

  public abstract int max();

  public  String message();

  public  Class<?>[] groups()default {};

  public  Class<? extends Payload>[] payload()default {};

  @Target({java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.ANNOTATION_TYPE, java.lang.annotation.ElementType.CONSTRUCTOR, java.lang.annotation.ElementType.PARAMETER})
  @Retention(RetentionPolicy.RUNTIME)
  @Documented
  public static @interface List
  {
    public abstract Length[] value();
  }
}

 

2.2 再重写执行类,

 

public class LengthBValidator  implements ConstraintValidator<LengthB, CharSequence>
{
      private static final Log log = LoggerFactory.make();
      private int min;
      private int max;

      public void initialize(LengthB parameters)
      {
        this.min = parameters.min();
        this.max = parameters.max();
        validateParameters();
      }

      public boolean isValid(CharSequence value, ConstraintValidatorContext constraintValidatorContext) {
        if (value == null) {
          return true;
        }
        int length = value.length();
        if (length == 0) {
              return true;
         }
        return (length >= this.min) && (length <= this.max);
      }

      private void validateParameters() {
        if (this.min < 0) {
          throw log.getMinCannotBeNegativeException();
        }
        if (this.max < 0) {
          throw log.getMaxCannotBeNegativeException();
        }
        if (this.max < this.min)
          throw log.getLengthCannotBeNegativeException();
      }
    }

 

 

实质上加了这两行代码:

  if (length == 0) {
              return true;
         }就这样,为空字符串时,就能跳过验证了。

 

大家如果有更好的解决方式,希望能指教。

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics