zoukankan      html  css  js  c++  java
  • SpringMVC使用Hibernate-validator验证出现的错误

    缺少jar包

    SpringMVC可以使用Hibernate-validator作为效验的实现,需要的jar包:

    hibernate-validator.jar 

    validation-api.jar 

    jboss-logging.jar这三个jar,但是我添加jar包之后项目启动之后报一个错误:

    就是这个类找不到了,开始我还以为又是版本的问题,替换了几个不同的版本还是报这个错,最后我搜索得知这个TypeResolver类在classmate.jar 这个jar包,突然想起在做SSH整合的时候也有这个jar,只是Hibernate需要的jar,添加之后就可以了

    效验信息乱码

    我在springMVC.xml文件中配置了效验器:

    <!--效验器-->
        <bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
          <!--springMVC使用hibernate提供的效验器  -->
          <property name="providerClass"  value="org.hibernate.validator.HibernateValidator"/>
          <!--指定效验错误使用的资源文件,在资源文件中定义校验规则,如不指定默认使用classpath下的ValidationMessage.properties文件  -->
    <!--       <property name="validationMessageSource" ref="messageSource"/> -->
        </bean>
        <!--配置效验错误使用文件  -->
        <bean id="messageSource" class="org.springframework.context.support.ReloadableResourceBundleMessageSource">
          <property name="basenames">
           <list>
             <value>classpath:CustomValidationMessage</value>
           </list>
          </property>
          <property name="fileEncodings" value="utf-8"></property>
          <property name="cacheSeconds" value="120"></property>
        </bean>

    指向一个我自己写的CustomValidationMessage.properties文件,我在这个属性文件中配置效验失败的信息

    CustomValidationMessage.properties:

    # 添加效验错误信息
    items.name.length.error=请输入商品名称在1到30个字符之间
    items.price.isNull=请输入商品价格

    注意:properties文件一定要是utf-8编码的,这样我们就可以减少一个乱码的可能性,这个文件的编码可以在eclipse的设置中设置

    我在商品模型Items 这个pojo类的属性上添加效验的注解:

    最后在Controller中将错误信息传递到页面:

            //获取效验错误信息
            if(bindingResult.hasErrors()){
                //输出错误信息
                List<ObjectError> allErrors = bindingResult.getAllErrors();
                model.addAttribute("allErrors", allErrors);
                //返回到页面如果不进行查询,图片无法进行数据回现
                model.addAttribute("allErrors", allErrors);
                return "items/editItems";

    注意:使用效验器需要在Controller的方法形参上使用@Validated注解,并且在需要效验的pojo后面添加BindingResult,@Validated和BindingResult是成对出现的,顺序是固定的(一前一后)

    页面使用JSTL:

    <!-- 显示错误信息 -->
    <c:if test="${allErrors!=null }">
        <c:forEach items="${allErrors }" var="error">
                ${error.defaultMessage }<br/>
        </c:forEach>
    </c:if>

    很不幸在页面上出现了乱码

    我试了很多方法都没解决这个乱码问题,只有采用一个比较简单的方法:自己手动进行一次转码:

            //获取效验错误信息
            if(bindingResult.hasErrors()){
                //输出错误信息
                List<ObjectError> allErrors = bindingResult.getAllErrors();
                List<String> errorList=new ArrayList<String>();
                for (ObjectError objectError : allErrors) {
                    errorList.add(new String(objectError.getDefaultMessage().getBytes("ISO-8859-1"),"utf-8"));
                }
                //将错误信息传递到页面
                modelAndView.addObject("allErrors", errorList);
                return "items/editItems";

    自己创建一个list将错误信息从ISO-8859-1转成utf-8,再将这个list传递到页面,可以解决乱码

    页面也需要修改:

    <!-- 显示错误信息 -->
    <c:if test="${allErrors!=null }">
        <c:forEach items="${allErrors }" var="error">
            ${error }<br/>
        </c:forEach>
    </c:if>

    页面使用${error },因为这是使用我们自己封装的list,它里面不是ObjectError对象,也就没有defaultMessage属性了

    最后我发现即使在springMVC.xml文件中的validator属性中不配置messageSource(也就是不使用CustomValidationMessage.properties文件),直接在pojo类的属性上使用效验注解,在注解的message中使用类似硬编码的方式将错误信息写入:

    即使不用手动转码,页面还是使用${error.defaultMessage }不用变,也不会乱码,还是使用注解的方式比较方便,但是硬编码有不利于维护。

    更正

    这一阵子我需要使用SpringMVC的验证器,所以想着也不能总是自己手动编码,需要验证的字段太多了,而且SpringMVC也比较成熟了,应该有对应的解决方法。通过查看源码发现:org.springframework.context.support.ReloadableResourceBundleMessageSource 类继承于AbstractResourceBasedMessageSource类,这个类中有一个defaultEncoding 属性,查看这个属性的set方法,发现其才是处理Properties文件编码的字段,而之前配的fileEncodings是一个Properties类型的属性,给它配“UTF-8”毫无意义.

    而 AbstractResourceBasedMessageSource类 中的setDefaultEncoding(String)方法形参才是个String类型,这个方法的注释说的也很明白,就是在设置Properties文件字符编码的,默认使用ISO-8859-1,所以之前我们将ISO-8859-1转成UTF-8可以正确显示。

    接下来将之前配的fileEncodings改为defaultEncoding即可:

    <bean id="messageSource" class="org.springframework.context.support.ReloadableResourceBundleMessageSource">
      <property name="basename" value="classpath:messages"/>
      <property name="defaultEncoding" value="UTF-8"/>
      <property name="cacheSeconds" value="120"/>  
    </bean>

    也不需要我们自己去转码了,哎,以后遇到问题应该自己先去研究一下源码,说不定就可以很好的解决。

    既然说的SpringMVC验证问题,我开始想使用JSR303的@NotNull注解来验证一个非空字段,页面什么都不填进行提交,这个非空验证却不起作用,DeBug发现其实springMVC将页面的空字段设置为“[ ]”,而并非null,所以这个注解就不起作用了,改为使用org.hibernate.validator.constraints.NotEmpty 这个注解即可。

     
  • 相关阅读:
    多线程与线程池
    hdu1506 Largest Rectangle in a Histogram
    安装mathtype出问题卸载后 office2016打开mathtype弹错误窗口
    最小总代价 状压DP
    Sumsets 递推
    不容易系列之(4)——考新郎 递推
    超级楼梯 递推
    阿牛的EOF牛肉串(递推)
    子串查询(二维前缀数组) 2018"百度之星"程序设计大赛
    cf#513 B. Maximum Sum of Digits
  • 原文地址:https://www.cnblogs.com/lz2017/p/7301399.html
Copyright © 2011-2022 走看看