SpringMVC使用Hibernate Validator验证用户输入

简介:

一 简介

SpringMVC支持与JSR 349 Bean Validation API的集成。借助于Bean验证,可以非常容易地将验证元数据应用到实体类,并且通过合适的视图向用户展示可能的错误结果。在模型类中可以通过注解对属性验证进行定义,常见的注解有:@Size ,@Email ,@Pattern,@Max等,分别验证长度,邮箱格式,自定义正则表达式,最大值(PS:更多相关注解可以百度或者查API)


二 测试实例

(1)新建一个动态Java web项目,然后下载“Hibernate Validator”的jar包,下载地址:http://hibernate.org/validator/ ,最后是导入必要的几个jar包和springmvc所需要的jar包,最后的项目结构如下:

wKiom1cfZk6xzmoMAABI_YIswnQ310.png    wKiom1cfZoGg61rwAAAr0yIMEuA577.png

(2)配置文件web.xml:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
< 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_3_1.xsd"
          version = "3.1" >
 
     < servlet >
         < servlet-name >springmvc</ servlet-name >
         < servlet-class >org.springframework.web.servlet.DispatcherServlet</ servlet-class >
         < load-on-startup >1</ load-on-startup >
     </ servlet >
 
     < servlet-mapping >
         < servlet-name >springmvc</ servlet-name >
         < url-pattern >*.html</ url-pattern >
     </ servlet-mapping >
     
     < 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 >
 
</ web-app >

在web.xml中定义了springmvc处理请求的后缀是.html,同时设置了编码为UTF-8

(3)配置文件springmvc-servlet.xml:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
<? 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:context = "http://www.springframework.org/schema/context"
     xmlns:mvc = "http://www.springframework.org/schema/mvc"
     xsi:schemaLocation="http://www.springframework.org/schema/beans 
                             http://www.springframework.org/schema/beans/spring-beans-4.0.xsd 
                             http://www.springframework.org/schema/context
                             http://www.springframework.org/schema/context/spring-context-4.0.xsd
                             http://www.springframework.org/schema/mvc 
                             http://www.springframework.org/schema/mvc/spring-mvc-4.0.xsd">
 
     < context:component-scan  base-package = "cn.zifangsky.* *.controller"  />
 
     < context:annotation-config  />   <!-- 激活Bean中定义的注解 -->
     < mvc:annotation-driven  validator = "validator" /> 
 
     <!-- 视图相关配置 -->
     < bean
         class = "org.springframework.web.servlet.view.InternalResourceViewResolver" >
         < property  name = "prefix"  value = "/WEB-INF/pages/"  />   <!-- 视图前缀 -->
         < property  name = "suffix"  value = ".jsp"  />   <!-- 视图后缀 -->
     </ bean >
     
     < bean  id = "messageSource"
           class = "org.springframework.context.support.ReloadableResourceBundleMessageSource" >
         < property  name = "basename"  value = "classpath:errors"  />
     </ bean >
     
     < bean  id = "validator"  class = "org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" >
         < property  name = "validationMessageSource"  ref = "messageSource" />
     </ bean >
</ beans >

在这里,主要是配置了视图相关配置,国际化(PS:在这里就是根据中文和英文网页显示不同的错误提示信息),以及定义了验证相关的配置。需要注意的是,还需要在mvc命名空间的annotation-driven标签中定义验证程序

(4)两个国际化文件errors_zh_CN.properties和errors_en_US.properties:

errors_zh_CN.properties文件:

1
2
3
error.password = \u5BC6\u7801\u662F\u5FC5\u987B\u540C\u65F6\u5305\u542B\u5927\u5199\u5B57\u6BCD\u3001\u5C0F\u5199\u5B57\u6BCD\u548C\u6570\u5B57\u76846-20\u4F4D\u5B57\u7B26
error.username = \u7528\u6237\u540d\u9700\u8981\u0033\u002d\u0032\u0030\u4f4d
error.age = \u5e74\u9f84\u6700\u5927\u662f\u0031\u0032\u0030\u5c81

这里以键值对的形式定义了三个中文错误提示信息,需要注意的是使用了“Unicode编码”,如果开发工具不能自动编码的话,可以在这个网页进行手动转换编码:http://tool.chinaz.com/tools/unicode.aspx

errors_en_US.properties文件:

1
2
3
error.password = Passwords are 6-20 bit characters that must contain both upper and lower case letters and digits at the same time.
error.username = username needs 3-20 bit characters
error.age = Max age is 120 years old

(5)实体类User.java:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
package  cn.zifangsky.model;
 
import  javax.validation.constraints.Max;
import  javax.validation.constraints.Pattern;
import  javax.validation.constraints.Size;
 
import  org.hibernate.validator.constraints.Email;
 
public  class  User {
     @Size (min =  3 , max =  20 , message =  "{error.username}" )
     private  String username;
 
     @Email
     private  String email;
 
     @Pattern (regexp =  "^((?=.*\\d)(?=.*[a-z])(?=.*[A-Z])).{6,20}$" , message =  "{error.password}" )
     private  String password;
 
     @Max (value =  120 , message =  "{error.age}" )
     private  int  age;
 
     public  String getUsername() {
         return  username;
     }
 
     public  void  setUsername(String username) {
         this .username = username;
     }
 
     public  String getEmail() {
         return  email;
     }
 
     public  void  setEmail(String email) {
         this .email = email;
     }
 
     public  String getPassword() {
         return  password;
     }
 
     public  void  setPassword(String password) {
         this .password = password;
     }
 
     public  int  getAge() {
         return  age;
     }
 
     public  void  setAge( int  age) {
         this .age = age;
     }
 
}

这里验证了:用户名必须是3-20位,如果验证不通过则通过配置的“message”参数根据语言环境在前台页面显示错误提示信息;邮箱使用默认配置验证了邮箱格式是否正确;密码这一项通过一个正则表达式验证了必须是包含大写字母、小写字母和数字的6-20位的字符;年龄验证了最大是120岁

(6)UserController.java这个controller类:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
package  cn.zifangsky.controller;
 
import  javax.validation.Valid;
 
import  org.springframework.stereotype.Controller;
import  org.springframework.validation.BindingResult;
import  org.springframework.web.bind.annotation.RequestMapping;
import  org.springframework.web.bind.annotation.RequestMethod;
import  org.springframework.web.servlet.ModelAndView;
 
import  cn.zifangsky.model.User;
 
@Controller
public  class  UserController {
 
     @RequestMapping (value =  "/form" )
     public  ModelAndView user() {
         ModelAndView modelAndView =  new  ModelAndView( "userForm" );
         modelAndView.addObject( "user" new  User());
 
         return  modelAndView;
     }
 
     @RequestMapping (value =  "/result" , method = RequestMethod.POST)
     public  ModelAndView processUser( @Valid  User user, BindingResult result) {
         ModelAndView modelAndView =  new  ModelAndView( "userResult" );
         modelAndView.addObject( "u" , user);
         // 如果出现验证错误,则转到"userForm"视图
         if  (result.hasErrors()) {
             modelAndView.setViewName( "userForm" );
         else  {
             modelAndView.setViewName( "userResult" );
         }
 
         return  modelAndView;
     }
 
}

从代码可以看出,定义了两个方法,user方法负责处理”/form”请求,然后转到“userForm.jsp”这个视图页面;在processUser方法中,对用户输入的验证由@Valid注解触发,该注解被递归地应用到实体类User的各个属性中。同时在这个方法中接收了一个额外的参数result,该参数是一个BindingResult实例,通过使用该参数来检查在将请求参数映射到实体类属性的过程中是否发生了任何验证错误。最后是根据条件转到相关视图页面

(7)三个前台jsp页面:

i)根目录下的index.jsp:

1
<% response.sendRedirect("form.html"); %>

这个文件就简单的一句话,在项目启动时直接请求“form.html”

ii)userForm.jsp:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
<%@ page language="java" contentType="text/html; charset=UTF-8"
     pageEncoding="UTF-8"%>
<%@taglib uri="http://www.springframework.org/tags/form" prefix="mvc"%>
< html >
< head >
< title >SpringMVC Form表单验证</ title >
< style  type = "text/css" >
.formFieldError {
     background-color: #FAFFBD;
}
</ style >
</ head >
< body >
 
     < h2 >用户注册:</ h2 >
     < mvc:form  modelAttribute = "user"  action = "result.html" >
         < table >
             < tr >
                 < td >< mvc:label  path = "username" >用户名:</ mvc:label ></ td >
                 < td >< mvc:input  path = "username"  cssErrorClass = "formFieldError"  /></ td >
                 < td >< mvc:errors  path = "username"  /></ td >
             </ tr >
             < tr >
                 < td >< mvc:label  path = "email" >邮箱:</ mvc:label ></ td >
                 < td >< mvc:input  path = "email"  cssErrorClass = "formFieldError"  /></ td >
                 < td >< mvc:errors  path = "email"  /></ td >
             </ tr >
             < tr >
                 < td >< mvc:label  path = "password" >密码:</ mvc:label ></ td >
                 < td >< mvc:password  path = "password"
                         cssErrorClass = "formFieldError"  /></ td >
                 < td >< mvc:errors  path = "password"  /></ td >
             </ tr >
             < tr >
                 < td >< mvc:label  path = "age" >年龄:</ mvc:label ></ td >
                 < td >< mvc:input  path = "age"  cssErrorClass = "formFieldError"  /></ td >
                 < td >< mvc:errors  path = "age"  /></ td >
             </ tr >
             < tr >
                 < td  colspan = "3" >< input  type = "submit"  value = "Submit"  /></ td >
             </ tr >
         </ table >
     </ mvc:form >
</ body >
</ html >

这个文件中定义的errors标签就是分别显示各个参数验证之后的错误提示信息

iii)userResult.jsp:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
<%@ page language="java" contentType="text/html; charset=UTF-8"
     pageEncoding="UTF-8"%>
<%@taglib uri="http://www.springframework.org/tags/form" prefix="mvc"%>
< html >
< head >
< title >SpringMVC Form表单验证结果</ title >
</ head >
< body >
     < h2 >用户注册结果</ h2 >
     < table >
         < tr >
             < td >用户名:</ td >
             < td >${u.username}</ td >
         </ tr >
         < tr >
             < td >邮箱:</ td >
             < td >${u.email}</ td >
         </ tr >
         < tr >
             < td >密码:</ td >
             < td >${u.password}</ td >
         </ tr >
         < tr >
             < td >年龄:</ td >
             < td >${u.age}</ td >
         </ tr >
     </ table >
</ body >
</ html >

这个文件只是简单的信息展示,不多做解释

三 测试

(1)中文环境下的错误提示:

项目启动后,使用中文类型的浏览器填写表单,可以发现,出现错误后显示的提示信息如下:

wKiom1cfZ3vzrANvAAA2FOO2T5Y787.png

可以发现,出现了预期的提示效果

(2)英文环境下的错误提示:

由于我装的浏览器是中文的,而且也不想更改浏览器的语言,因此我通过在提交表单时抓包手动更改Header中的“Accept-Language”这一项属性,改成“en-US,en;q=0.5”,相当于给服务端说我是英语环境(PS:q参数表示用户的喜爱度,不用管,随便设一个就行)

wKioL1cfaG6TZ8lCAABsq__Axro056.png

最后的显示效果如下:

wKiom1cfZ8fBcVKJAAA5xCyQEqw377.png

注:实际上,应该把页面中其他的一些中文也设置成国际化形式,那样就可以在英文环境中显示成英文了。不过为了减小理解难度,因此在这里就没有添加上这个步骤,当然我在后面可能会单独写一写SpringMVC的国际化



本文转自 pangfc 51CTO博客,原文链接:http://blog.51cto.com/983836259/1768033,如需转载请自行联系原作者

相关文章
|
7月前
|
网络安全
ssh(Spring+Spring mvc+hibernate)——DeptDaoImpl.java
ssh(Spring+Spring mvc+hibernate)——DeptDaoImpl.java
|
7月前
|
网络安全
ssh(Spring+Spring mvc+hibernate)——BaseDaoImpl.java
ssh(Spring+Spring mvc+hibernate)——BaseDaoImpl.java
|
7月前
|
Shell
sh(Spring+Spring mvc+hibernate)——IEmpDao.java
sh(Spring+Spring mvc+hibernate)——IEmpDao.java
|
7月前
|
Shell
sh(Spring+Spring mvc+hibernate)——IDeptDao.java
sh(Spring+Spring mvc+hibernate)——IDeptDao.java
|
7月前
|
网络安全
ssh(Spring+Spring mvc+hibernate)——Dept.java
ssh(Spring+Spring mvc+hibernate)——Dept.java
|
7月前
|
网络安全
ssh(Spring+Spring mvc+hibernate)——showDept.jsp
ssh(Spring+Spring mvc+hibernate)——showDept.jsp
|
7月前
|
网络安全
ssh(Spring+Spring mvc+hibernate)——applicationContext.xml
ssh(Spring+Spring mvc+hibernate)——applicationContext.xml
|
7月前
|
网络安全
ssh(Spring+Spring mvc+hibernate)——EmpController
ssh(Spring+Spring mvc+hibernate)——EmpController
|
7月前
|
Shell
sh(Spring+Spring mvc+hibernate)——BaseDao.java
sh(Spring+Spring mvc+hibernate)——BaseDao.java
|
7月前
|
前端开发 Java 网络安全
ssh(Spring+Spring mvc+hibernate)简单增删改查案例
ssh(Spring+Spring mvc+hibernate)简单增删改查案例