[SpringMVC from entry to actual combat tutorial] Chapter 9 SpringMVC data verification

Nine, SpringMVC data validation

	一般情况下,用户的输入是随意的,为了保证数据的合法性,数据验证是所有 Web 应用必须处理的问题。
	
	B/S系统中对http请求数据的校验多数在客户端进行,这也是出于简单及用户体验性上考虑。但是在一些安全性要求高的系统中服务端校验是不可缺少的,SpringMVC实现控制层添加校验。
	
	Spring MVC 有以下两种方法可以验证输入:
        利用 Spring 自带的验证框架
        利用 JSR 303 实现
	
	数据验证分为客户端验证和服务器端验证,客户端验证主要是过滤正常用户的误操作,通过 JavaScript 代码完成。服务器端验证是整个应用阻止非法数据的最后防线,通过在应用中编程实现。
	
	本章使用 JSR 303 实现服务器端的数据验证。
	
	JSR 303 是 Java 为 Bean 数据合法性校验所提供的标准框架。JSR 303 通过在 Bean 属性上标注类似于 @NotNull、@Max 等标准的注解指定校验规则,并通过标准的验证接口对 Bean 进行验证。
	
	JSR 303 不需要编写验证器,它定义了一套可标注在成员变量、属性方法上的校验注解,9.4章节所示。
	
	Spring MVC 支持 JSR 303 标准的校验框架,Spring 的 DataBinder 在进行数据绑定时,可同时调用校验框架来完成数据校验工作,非常简单方便。在 Spring MVC 中,可以直接通过注解驱动的方式来进行数据校验。
	
	Spring 本身没有提供 JSR 303 的实现,Hibernate Validator 实现了 JSR 303,所以必须在项目中加入来自 Hibernate Validator 库的 jar 文件(和Hibernate ORM没有任何关系)。

9.1 Front-end verification

index.jsp:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <base href="${pageContext.request.contextPath}/">
    <title>Title</title>
</head>
<body>
    <div style="text-align: center">
        <h1>数据验证</h1>
        <p><a href="views/front.jsp">前端验证</a></p>
        <p><a href="views/add.jsp">员工新增</a></p>
        <p><a href="views/edit.jsp">员工编辑</a></p>
    </div>
</body>
</html>

front.jsp:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <base href="${pageContext.request.contextPath}/">
    <title>Title</title>
    <script type="text/javascript" src="js/jquery-3.3.1.min.js"></script>
    <script type="text/javascript">
        //客户端验证
        //优点:快捷,减轻服务器的压力
        //缺点:可控制性低(比如浏览器设置->网站设置->禁用JS,那么前端校验就无效了。或者第三方工具发送请求)
        function doValidate(){
      
      
            var ename = $('#ename').val().trim();
            var job = $('#job').val().trim();
            var sal = $('#sal').val().trim();
            //if(!ename){
      
      
            if(ename==null || ename==''){
      
      
                alert('员工姓名不能为空');
                return false;
            }
            var reg1 = /^\S{2,8}$/;
            if(!reg1.test(ename)){
      
      
                alert('员工姓名必须为2~8位非空白字符');
                return false;
            }
            if(job==null || job==''){
      
      
                alert('员工岗位不能为空');
                return false;
            }
            if(sal==null || sal==''){
      
      
                alert('员工薪资不能为空');
                return false;
            }
            var reg2 = /^\d+(.\d{1,2})?$/;
            if(!reg2.test(sal)){
      
      
                alert('员工薪资必须为整数或两位小数');
                return false;
            }
            return true;
        }
    </script>
</head>
<body>
    <div style="text-align: center;">
        <h3>前端验证</h3>
        <form action="views/success.jsp" method="post" onsubmit="return doValidate()" >
            <p>员工姓名:<input type="text" id="ename" name="ename"></p>
            <p>员工岗位:<input type="text" id="job" name="job"></p>
            <p>员工薪资:<input type="text" id="sal" name="sal"></p>
            <p><button>提交</button></p>
        </form>
    </div>
</body>
</html>

success.jsp:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <base href="${pageContext.request.contextPath}/">
    <title>Title</title>
</head>
<body>
    <div style="text-align: center">
        <h1>操作成功</h1>
    </div>
</body>
</html>

9.2 Import data verification jar package

Method 1: Import jar package

insert image description here

Method 2: maven dependency configuration

<dependencies>
    <!-- spring核心包-->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-core</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>
    <!-- springbean包 -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-beans</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>
    <!-- springcontext包 -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-context</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>
    <!-- spring表达式包 -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-expression</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>
    <!-- springAOP包 -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-aop</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>
    <!-- springAspects包 -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-aspects</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>
    <!-- spring对web的支持 -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-web</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>
    <!-- springwebMVC -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>4.3.18.RELEASE</version>
    </dependency>

    <!-- 配置javaweb环境 -->
    <!-- servlet-api -->
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>javax.servlet-api</artifactId>
        <version>3.1.0</version>
        <scope>provided</scope>
    </dependency>
    <!-- jsp-api -->
    <dependency>
        <groupId>javax.servlet.jsp</groupId>
        <artifactId>jsp-api</artifactId>
        <version>2.1</version>
        <scope>provided</scope>
    </dependency>
    <!-- jstl -->
    <dependency>
        <groupId>javax.servlet</groupId>
        <artifactId>jstl</artifactId>
        <version>1.2</version>
    </dependency>

    <!-- jackson -->
    <dependency>
        <groupId>com.fasterxml.jackson.core</groupId>
        <artifactId>jackson-core</artifactId>
        <version>2.9.5</version>
    </dependency>
    <dependency>
        <groupId>com.fasterxml.jackson.core</groupId>
        <artifactId>jackson-databind</artifactId>
        <version>2.9.5</version>
    </dependency>
    <dependency>
        <groupId>com.fasterxml.jackson.core</groupId>
        <artifactId>jackson-annotations</artifactId>
        <version>2.9.5</version>
    </dependency>

    <!-- Hibernate Validator -->
    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-validator</artifactId>
        <version>5.4.1.Final</version>
    </dependency>
</dependencies>

9.3 Spring MVC configuration

web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">

    <!--字符编码过滤器-->
    <filter>
        <filter-name>CharacterEncodingFilter</filter-name>
        <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
        <init-param>
            <param-name>encoding</param-name>
            <param-value>UTF-8</param-value>
        </init-param>
    </filter>
    <filter-mapping>
        <filter-name>CharacterEncodingFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <!-- 通过隐藏域传参解决form表单的PUT与DELETE方式的请求 -->
    <filter>
        <filter-name>HiddenHttpMethodFilter</filter-name>
        <filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>HiddenHttpMethodFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <!-- 解决put请求传递参数的问题-->
    <filter>
        <filter-name>HttpPutFormContentFilter</filter-name>
        <filter-class>org.springframework.web.filter.HttpPutFormContentFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>HttpPutFormContentFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <!-- 配置前端控制器 -->
    <servlet>
        <servlet-name>springmvc</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <init-param>
            <param-name>contextConfigLocation</param-name>
            <param-value>classpath:springmvc.xml</param-value>
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>springmvc</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>

    <welcome-file-list>
        <welcome-file>/views/index.jsp</welcome-file>
    </welcome-file-list>
</web-app>

springmvc.xml:

<?xml version="1.0" encoding="UTF-8"?>
<beans
        xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns:p="http://www.springframework.org/schema/p"
        xmlns:context="http://www.springframework.org/schema/context"
        xmlns:aop="http://www.springframework.org/schema/aop"
        xmlns:mvc="http://www.springframework.org/schema/mvc"
        xsi:schemaLocation="http://www.springframework.org/schema/beans
    http://www.springframework.org/schema/beans/spring-beans.xsd
    http://www.springframework.org/schema/context
    http://www.springframework.org/schema/context/spring-context.xsd
    http://www.springframework.org/schema/aop
    http://www.springframework.org/schema/aop/spring-aop.xsd
    http://www.springframework.org/schema/mvc
    http://www.springframework.org/schema/mvc/spring-mvc.xsd">

    <!-- springmvc的注解式开发 -->
    <!-- 开启组件扫描 -->
    <context:component-scan base-package="com.newcapec"/>

    <!-- MVC注解驱动 -->
    <mvc:annotation-driven validator="validator"/>

    <!-- 配置视图解析器 -->
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <!-- 配置视图地址的前缀和后缀:简化视图地址 -->
        <property name="prefix" value="/views/"/>
        <property name="suffix" value=".jsp"/>
    </bean>

    <!--不拦截静态资源-->
    <mvc:default-servlet-handler/>

    <!-- 配置springmvc的数据校验器-->
    <bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
        <!-- 配置hibernate-validator框架中的数据校验器-->
        <property name="providerClass" value="org.hibernate.validator.HibernateValidator" />
    </bean>
</beans>

9.4 Verify annotation rules

9.4.1 Bean Validator built-in annotations

Validation Notes Validation data type illustrate
@AssertFalse Boolean,boolean Annotated element value must be false
@AssertTrue Boolean,boolean Annotated element value must be true
@DecimalMax(value) BigDecimal, BigInteger, byte, short, int, long and the corresponding packaging classes of basic data types, any subtype of Number, String (value represented by String) The value of the annotated element must be less than or equal to the value specified by @DecimalMax
@DecimalMin(value) Same as @DecimalMax requested The value of the annotated element must be greater than or equal to the value specified by @DecimalMin
@Digits (integer=integer digits, fraction=decimal digits) Same as @DecimalMax requested Maximum number of integer and decimal places for annotated element values
@Future Date types of java.util.Date, java.util.Calendar, Joda Time class library The annotated element value must be later than the current time
@Max(value) Same as @DecimalMax requested The value of the annotated element must be less than or equal to the value specified by @Max
@Min(value) Same as @DecimalMax requested The value of the annotated element must be greater than or equal to the value specified by @Min
@NotNull any type The annotated element value must not be null
@Null any type The annotated element value must be null
@Past Same as @Future request Annotated element values ​​must be older than the current time
@Pattern(regex=regular expression,flag=flag pattern) string The annotated element value must conform to the specified regular expression
@Size(max=, min=) String, Collection collection, Map collection, array The size of the annotated element value must be within the specified range

9.4.2 Annotations for Hibernate Validator Expansion

Validation Notes Validation data type illustrate
@Email string Annotated element value must be an email address
@Length(min=,max=) string The size of the annotated element value must be within the specified range
@NotBlank string Annotated element values ​​must be non-null, non-null, or non-whitespace characters. More powerful than @NotEmpty
@NotEmpty String, Collection collection, Map collection, array Annotated element values ​​must be non-null or non-null. More functional than @NotNull
@Range(min=,max=) BigDecimal, BigInteger, byte, short, int, long and corresponding wrapper classes of basic data types Annotated element values ​​must be in the appropriate range

9.5 Add validation rules

Hibernate Validator verifies the member variables in the entity class through annotations, that is, configures the verification rules on the member variables.

/**
 * hibernate validator数据验证框架
 * 作用:通过注解的方式进行数据验证,注解需要添加在实体的成员变量上
 * 
 * 注解中通过的属性:
 * message: 当前验证失败时给用户提示信息
 */
public class Emp {
    
    

    private Integer empno;
    @NotBlank(message = "员工姓名不能为空")
    @Length(message = "员工姓名必须为2~8位字符", min = 2, max = 8)
    private String ename;
    @NotBlank(message = "员工岗位不能为空")
    private String job;
    @NotNull(message = "员工薪资不能为空")
    @DecimalMin(message = "员工薪资不能低于1000", value = "1000")
    private Double sal;

    public Integer getEmpno() {
    
    
        return empno;
    }

    public void setEmpno(Integer empno) {
    
    
        this.empno = empno;
    }

    public String getEname() {
    
    
        return ename;
    }

    public void setEname(String ename) {
    
    
        this.ename = ename;
    }

    public String getJob() {
    
    
        return job;
    }

    public void setJob(String job) {
    
    
        this.job = job;
    }

    public Double getSal() {
    
    
        return sal;
    }

    public void setSal(Double sal) {
    
    
        this.sal = sal;
    }

    @Override
    public String toString() {
    
    
        return "Emp{" +
                "empno=" + empno +
                ", ename='" + ename + '\'' +
                ", job='" + job + '\'' +
                ", sal=" + sal +
                '}';
    }
}

9.6 Capture verification error information

@Controller
@RequestMapping("/emp")
public class EmpController {
    
    
    /**
     * 开启数据验证
     *
     * @Validated 位置:形参
     * 作用:开启了请求参数的验证
     * 
     * 注意:@Validated注解不能单独使用,需要在每个开启数据验证的形参后,跟随一个BindingResult类型的形参
     * BindingResult:判断数据是否验证通过,并接收验证失败信息
     */
    @RequestMapping("/add")
    public String add(@Validated Emp emp, BindingResult bindingResult, Model model) {
    
    
        System.out.println(emp);
        //判断数据验证是否通过
        if (bindingResult.hasErrors()) {
    
    
            //数据验证没有全部通过
            List<ObjectError> list = bindingResult.getAllErrors();
            for (ObjectError objectError : list) {
    
    
                //getDefaultMessage()获取验证失败信息
                System.out.println(objectError.getDefaultMessage());
            }
            model.addAttribute("errors", list);
            return "add";
        }
        return "success";
    }
}

Note: @Validated means to verify when binding the formal parameters of the Controller method, the verification information is written into the BindingResult, and the BingdingResult is added after the entity class to be verified. A BindingResult corresponds to an entity class, and the BindingResult is placed in the entity class behind.

9.7 Display verification error information on the page

	在Controller中已经把错误列表对象存入作用域中,在页面直接取出,遍历并显示即可。

add.jsp:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
    <base href="${pageContext.request.contextPath}/">
    <title>Title</title>
</head>
<body>
    <div style="text-align: center;">
        <h3>员工新增</h3>
        <div style="color: red;">
            <ol>
                <c:forEach items="${errors}" var="e">
                    <li>${e.defaultMessage}</li>
                </c:forEach>
            </ol>
        </div>
        <form action="emp/add" method="post">
            <p>员工姓名:<input type="text" name="ename"></p>
            <p>员工岗位:<input type="text" name="job"></p>
            <p>员工薪资:<input type="text" name="sal"></p>
            <p><button>提交</button></p>
        </form>
    </div>
</body>
</html>

9.8 Group verification

	如果两处校验使用同一个实体类则可以设定校验分组,通过分组校验可以对每处的校验个性化。

9.8.1 Define group identifiers

To define a group identifier is to define an empty interface:

public interface EmpAddValidator {
    
    
    
}

public interface EmpEditValidator {
    
    
    
}

9.8.2 Add grouping in verification rules

/**
 * hibernate validator数据验证框架
 * 是通过注解的方式对数据进行验证
 * 注解需要添加在实体类的属性上,因为在springmvc中是通过实体类类型的形参接收请求参数
 * 
 * 注解中通用的属性:
 * message: 当前验证失败是给用户的提交信息
 * groups: 分组校验
 */
public class Emp {
    
    
    @NotNull(message = "员工编号不能为空", groups = EmpEditValidator.class)
    private Integer empno;
    // @NotBlank(message = "员工姓名不能为空")
    @NotBlank(message = "员工姓名不能为空", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    // @Length(message = "员工姓名必须为2~8位字符",min = 2, max = 8)
    @Length(message = "员工姓名必须为2~8个字符", min = 2, max = 8, groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    private String ename;
    // @NotBlank(message = "员工岗位不能为空")
    @NotBlank(message = "员工岗位不能为空", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    private String job;
    // @NotNull(message = "员工薪资不能为空")
    @NotNull(message = "员工薪资不能为空", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    // @DecimalMin(message = "员工薪资不能低于1000",value = "1000")
    @DecimalMin(message = "员工薪资不能低于1000", value = "1000", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    private Double sal;

    public Integer getEmpno() {
    
    
        return empno;
    }

    public void setEmpno(Integer empno) {
    
    
        this.empno = empno;
    }

    public String getEname() {
    
    
        return ename;
    }

    public void setEname(String ename) {
    
    
        this.ename = ename;
    }

    public String getJob() {
    
    
        return job;
    }

    public void setJob(String job) {
    
    
        this.job = job;
    }

    public Double getSal() {
    
    
        return sal;
    }

    public void setSal(Double sal) {
    
    
        this.sal = sal;
    }

    @Override
    public String toString() {
    
    
        return "Emp{" +
                "empno=" + empno +
                ", ename='" + ename + '\'' +
                ", job='" + job + '\'' +
                ", sal=" + sal +
                '}';
    }
}

9.8.3 Specify grouping in @Validated annotation

@Controller
@RequestMapping("/emp")
public class EmpController {
    
    

    /**
     * 开启数据验证
     *
     * @Validated 位置:形参
     * 作用:开启了请求参数的验证
     * 属性:指定分组
     * 
     * 注意:@Validated注解不能单独使用,需要在每个开启数据验证的形参后,跟随一个BindingResult类型的形参
     * BindingResult:判断数据是否验证通过,并接收验证失败信息
     */
    @RequestMapping("/add")
    public String add(@Validated(EmpAddValidator.class) Emp emp, BindingResult bindingResult, Model model) {
    
    
        System.out.println(emp);
        //判断数据验证是否通过
        if (bindingResult.hasErrors()) {
    
    
            //数据验证没有全部通过
            List<ObjectError> list = bindingResult.getAllErrors();
            for (ObjectError objectError : list) {
    
    
                //getDefaultMessage()获取验证失败信息
                System.out.println(objectError.getDefaultMessage());
            }
            model.addAttribute("errors", list);
            return "add";
        }
        return "success";
    }

    @RequestMapping("/edit")
    public String edit(@Validated(EmpEditValidator.class) Emp emp, BindingResult bindingResult, Model model) {
    
    
        System.out.println(emp);
        //判断数据验证是否通过
        if (bindingResult.hasErrors()) {
    
    
            //数据验证没有全部通过
            List<ObjectError> list = bindingResult.getAllErrors();
            model.addAttribute("errors", list);
            return "edit";
        }
        return "success";
    }
}

9.8.4 Edit page

edit.jsp:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
    <base href="${pageContext.request.contextPath}/">
    <title>Title</title>
</head>
<body>
    <div style="text-align: center;">
        <h3>员工编辑</h3>
        <div style="color: red;">
            <ol>
                <c:forEach items="${errors}" var="e">
                    <li>${e.defaultMessage}</li>
                </c:forEach>
            </ol>
        </div>
        <form action="emp/edit" method="post">
            <p>员工编号:<input type="text" name="empno"></p>
            <p>员工姓名:<input type="text" name="ename"></p>
            <p>员工岗位:<input type="text" name="job"></p>
            <p>员工薪资:<input type="text" name="sal"></p>
            <p><button>提交</button></p>
        </form>
    </div>
</body>
</html>

9.9 Error message resource file

9.9.1 Resource files

When the attribute value verification fails, its prompt information can be configured in a resource file, and the file name defaults to classpath:ValidationMessages.properties:

emp.empno.NotNull=员工编号不能为空--2
emp.ename.NotBlank=员工姓名不能为空--2
emp.ename.Length=员工姓名必须为2~8位字符--2
emp.job.NotBlank=员工岗位不能为空--2
emp.salary.NotNull=员工薪资不能为空--2
emp.salary.DecimalMin=员工薪资不能低于1000--2

9.9.2 Entity classes

The data in the resource file is referenced by {} in the entity:

/**
 * hibernate validator数据验证框架
 * 是通过注解的方式对数据进行验证
 * 注解需要添加在实体类的属性上,因为在springmvc中是通过实体类类型的形参接收请求参数
 * <p>
 * 注解中通用的属性:
 * message : 当前验证失败是给用户的提交信息
 * groups : 分组校验
 */
public class Emp {
    
    
    // @NotNull(message = "员工编号不能为空",groups= EmpEditValidator.class)
    @NotNull(message = "{emp.empno.NotNull}", groups = EmpEditValidator.class)
    private Integer empno;
    // @NotBlank(message = "员工姓名不能为空")
    // @NotBlank(message = "员工姓名不能为空",groups= {EmpEditValidator.class, EmpAddValidator.class})
    @NotBlank(message = "{emp.ename.NotBlank}", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    // @Length(message = "员工姓名必须为2~8位字符",min = 2, max = 8)
    // @Length(message = "员工姓名必须为2~8个字符", min = 2, max = 8,groups= {EmpEditValidator.class, EmpAddValidator.class})
    @Length(message = "{emp.ename.Length}", min = 2, max = 8, groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    private String ename;
    // @NotBlank(message = "员工岗位不能为空")
    // @NotBlank(message = "员工岗位不能为空",groups= {EmpEditValidator.class, EmpAddValidator.class})
    @NotBlank(message = "{emp.job.NotBlank}", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    private String job;
    // @NotNull(message = "员工薪资不能为空")
    // @NotNull(message = "员工薪资不能为空",groups= {EmpEditValidator.class, EmpAddValidator.class})
    @NotNull(message = "{emp.salary.NotNull}", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    // @DecimalMin(message = "员工薪资不能低于1000",value = "1000")
    // @DecimalMin(message = "员工薪资不能低于1000", value = "1000", groups = {EmpEditValidator.class, EmpAddValidator.class})
    @DecimalMin(message = "{emp.salary.DecimalMin}", value = "1000", groups = {
    
    EmpEditValidator.class, EmpAddValidator.class})
    private Double sal;

    public Integer getEmpno() {
    
    
        return empno;
    }

    public void setEmpno(Integer empno) {
    
    
        this.empno = empno;
    }

    public String getEname() {
    
    
        return ename;
    }

    public void setEname(String ename) {
    
    
        this.ename = ename;
    }

    public String getJob() {
    
    
        return job;
    }

    public void setJob(String job) {
    
    
        this.job = job;
    }

    public Double getSal() {
    
    
        return sal;
    }

    public void setSal(Double sal) {
    
    
        this.sal = sal;
    }

    @Override
    public String toString() {
    
    
        return "Emp{" +
                "empno=" + empno +
                ", ename='" + ename + '\'' +
                ", job='" + job + '\'' +
                ", sal=" + sal +
                '}';
    }
}

9.9.3 Configuration

The error message resource file can also customize the name and location, and the configuration is as follows:

<!-- 配置springmvc的数据校验器-->
<bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
    <!-- 配置hibernate-validator框架中的数据校验器-->
    <property name="providerClass" value="org.hibernate.validator.HibernateValidator" />
    <!-- 在springmvc的数据校验中,默认的资源文件classpath:ValidationMessages.properties -->
    <!-- 指定校验使用的资源文件-->
    <property name="validationMessageSource" ref="validationMessageSource"></property>
</bean>

<!-- 配置validationMessageSource -->
<bean id="validationMessageSource" class="org.springframework.context.support.ReloadableResourceBundleMessageSource">
    <!-- 指定校验信息的资源文件的基本文件名称,不包括后缀,后缀默认是properties -->
    <property name="basenames">
        <list>
            <value>classpath:message</value>
        </list>
    </property>
    <!-- 指定文件的编码
    改属性为properties属性,键的值为文件名字加路径名,乱码需要在此处配置utf-8即可
    -->
    <property name="fileEncodings" >
        <props>
            <prop key="classpath:message">utf-8</prop>
        </props>
    </property>
    <!-- 对资源文件内容缓存的时间,单位秒 -->
    <property name="cacheSeconds" value="120"></property>
</bean>

Messages.properties -->


classpath:message utf-8 ```

Guess you like

Origin blog.csdn.net/ligonglanyuan/article/details/125328428