Spring MVC数据校验与国际化
2015-07-01 14:09
609 查看
1、 JSR-303
JSR-303 是JAVA EE 6 中的一项子规范,叫做Bean Validation,官方参考实现是Hibernate Validator。此实现与Hibernate ORM 没有任何关系。JSR 303 用于对Java Bean 中的字段的值进行验证。
Spring MVC 3.x之中也大力支持 JSR-303,可以在控制器中对表单提交的数据方便地验证。
JSR 303内置的约束规则:
@AssertTrue / @AssertFalse
验证适用字段:boolean
注解说明:验证值是否为true / false
属性说明:-
@DecimalMax / @DecimalMin
验证适用字段:BigDecimal,BigInteger,String,byte,short,int,long
注解说明:验证值是否小于或者等于指定的小数值,要注意小数存在精度问题
属性说明:公共
@Digits
验证适用字段:BigDecimal,BigInteger,String,byte,short,int,long
注解说明:验证值的数字构成是否合法
属性说明:integer:指定整数部分的数字的位数。fraction: 指定小数部分的数字的位数。
@Future / @Past
验证适用字段:Date,Calendar
注解说明:验证值是否在当前时间之后 / 之前
属性说明:公共
@Max / @Min
验证适用字段:BigDecimal,BigInteger,String,byte,short,int,long
注解说明:验证值是否小于或者等于指定的整数值
属性说明:公共
@NotNull / @Null
验证适用字段:引用数据类型
注解说明:验证值是否为非空 / 空
属性说明:公共
@Pattern
验证适用字段:String
注解说明:验证值是否配备正则表达式
属性说明:regexp:正则表达式flags: 指定Pattern.Flag 的数组,表示正则表达式的相关选项。
@Size
验证适用字段:String,Collection,Map,数组
注解说明:验证值是否满足长度要求
属性说明:max:指定最大长度,min:指定最小长度。
@Valid
验证适用字段:引用类型
注解说明:验证值是否需要递归验证
属性说明:无
使用Spring MVC 和 JSR-303的标注做表单提交的服务器端验证时,@Valid 标注的Command对象和BindingResult参数一定要紧挨着。要不然数据绑定错误直接抛异常,不会封装成一个BindingResult对象。
2、Spring MVC数据校验
<mvc:annotation-driven/>会默认装配好一个LocalValidatorFactoryBean,通过在处理方法的入参上标注@Valid注解就可让Spring MVC在完成数据绑定后执行数据校验操作。
A、需要的额外的JAR包
除了Spring MVC本身的JAR包外,我们还需要一些额外的JAR包。
B、添加JSR 303注解
package cn.framelife.mvc.entity; import java.util.Date; import javax.validation.constraints.DecimalMax; import javax.validation.constraints.DecimalMin; import javax.validation.constraints.NotNull; import javax.validation.constraints.Past; import javax.validation.constraints.Pattern; import javax.validation.constraints.Size; import org.springframework.format.annotation.DateTimeFormat; import org.springframework.format.annotation.NumberFormat; public class User implements java.io.Serializable { private Integer id; /* * 测试的时候,发现在页面获取到的数据传到User模式后,都是非空的。 */ @NotNull(message = "用户名不能为空") private String username; @Size(min = 2, max = 6, message = "长度是2-6之间") private String password; @Past(message = "必须是一个过去的时间") @DateTimeFormat(pattern = "yyyy-MM-dd") private Date birthday; @DecimalMin(value = "1000.00", message = "工资必须大于1000.00") @DecimalMax(value = "10000.00", message = "工资必须小于10000.00") @NumberFormat(pattern = "#,###.##") private long salary; @Pattern(regexp = "1[3|4|5|8][0-9]\\d{4,8}", message = "手机号码不匹配") private String phone; public String getPhone() { return phone; } public void setPhone(String phone) { this.phone = phone; } public long getSalary() { return salary; } public void setSalary(long salary) { this.salary = salary; } public Date getBirthday() { return birthday; } public void setBirthday(Date birthday) { this.birthday = birthday; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } }
C、Controller中的处理
@Controller @RequestMapping("/user") public class UserControl { /** * 此方法是用于第一次给页面添加一个user模型数据的 */ @RequestMapping(value="/add",method = RequestMethod.GET) public ModelAndView initForm(){ User user = new User(); return new ModelAndView("/add").addObject(user); } /** * 给入参的模型对象User加入@Valid注解,说明这个对象里面的属性需要校验 * BindingResult入参是用以判断上面的校验是否出错 */ @RequestMapping("create") public ModelAndView createUser(@Valid User user,BindingResult bindingResult){ ModelAndView view = new ModelAndView(); System.out.println(user.getUsername()+"----"); //如果校验有问题,跑回原来的add.jsp页面,如果没问题跑到success.jsp页面 if(bindingResult.hasErrors()){ view.setViewName("/add"); }else{ view.setViewName("/success"); } return view; } }
D、页面输入及输出
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%> <!-- 导入spring的表单标签库 --> <%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <base href="<%=basePath%>"> <title>增加</title> <meta http-equiv="pragma" content="no-cache"> <meta http-equiv="cache-control" content="no-cache"> <meta http-equiv="expires" content="0"> <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> <meta http-equiv="description" content="This is my page"> <!-- <link rel="stylesheet" type="text/css" href="styles.css"> --> </head> <body> <!-- 在使用表单标签的时候需要获取到一个user模型数据,那我们不能直接访问页面(通过/user/add.abc访问),必须通过访问一次服务器,获取到一个user数据模型后才行,否则会出错 --> <form:form modelAttribute="user" action="user/create.abc"> <!-- 输出所有的错误信息 --> <form:errors path="*" /><br/> <hr/> <!-- 输出单个错误信息 --> <form:errors path="username" ></form:errors><br/> 用户名:<form:input path="username"/><br/> <form:errors path="password" ></form:errors><br/> 密 码:<form:password path="password"/><br/> <form:errors path="birthday" ></form:errors><br/> 生日:<form:input path="birthday"/><br/> <form:errors path="salary" ></form:errors><br/> 工资:<form:input path="salary"/><br/> <form:errors path="phone" ></form:errors><br/> 电话:<form:input path="phone"/><br/> <input type="submit"> </form:form> </body> </html>
3、通过国际化资源显示错误信息
A、校验属性/* * 使用资源文件,这里不再需要message参数 */ @Pattern(regexp = "1[3|4|5|8][0-9]\\d{4,8}") private String phone;
B、资源文件(src下的messages.properties)
Pattern.user.phone=\u624B\u673A\u53F7\u7801\u4E0D\u5339\u914D
上面键值对中,
键是校验类javax.validation.constraints.Pattern的类名+被校验的模型对象名+属性名
值是”手机号码不匹配”
C、配置本地化资源文件(mvc-servlet.xml)
<!-- 配置国际化资源文件 --> <!-- ReloadableResourceBundleMessageSource加载时,默认使用DefaultResourceLoader,他会先判断资源path是否带有classpath:前缀,如果有,用ClassPathResource去加载资源文件,如果没有试着用文件协议的url去访问,再没有就在contextPath即WEB-INF下查找 --> <bean id="messageSource" class="org.springframework.context.support.ReloadableResourceBundleMessageSource" p:basename="classpath:messages"> </bean>
D、显示
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%> <!-- 导入spring的表单标签库 --> <%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <base href="<%=basePath%>"> <title>增加</title> <meta http-equiv="pragma" content="no-cache"> <meta http-equiv="cache-control" content="no-cache"> <meta http-equiv="expires" content="0"> <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> <meta http-equiv="description" content="This is my page"> <!-- <link rel="stylesheet" type="text/css" href="styles.css"> --> </head> <body> <!-- 在使用表单标签的时候需要获取到一个user模型数据,那我们不能直接访问页面(通过/user/add.abc访问),必须通过访问一次服务器,获取到一个user数据模型后才行,否则会出错 --> <form:form modelAttribute="user" action="user/create.abc"> <!-- 输出所有的错误信息 --> <form:errors path="*" /><br/> <hr/> <!-- 输出单个错误信息 --> <form:errors path="username" ></form:errors><br/> 用户名:<form:input path="username"/><br/> <form:errors path="password" ></form:errors><br/> 密 码:<form:password path="password"/><br/> <form:errors path="birthday" ></form:errors><br/> 生日:<form:input path="birthday"/><br/> <form:errors path="salary" ></form:errors><br/> 工资:<form:input path="salary"/><br/> <form:errors path="phone" ></form:errors><br/> 电话:<form:input path="phone"/><br/> <input type="submit"> </form:form> </body> </html>
相关文章推荐
- DB2获取当前用户表、字段、索引等详细信息
- MySQL字段自增自减的SQL语句示例介绍
- SQL SERVER使用REPLACE将某一列字段中的某个值替换为其他的值
- access的备注字段限制64K
- 一句sql更新两个表并可更新对应的字段值具体实现
- vbs生成ACCESS数据里所有表的字段
- JavaScript面对国际化编程时的一些建议
- 在oracle数据库里创建自增ID字段的步骤
- Hibernate Oracle sequence的使用技巧
- jsp Hibernate批量更新和批量删除处理代码
- jsp hibernate的分页代码第1/3页
- JAVA+Hibernate 无限级分类
- SSH整合中 hibernate托管给Spring得到SessionFactory
- jsp hibernate 数据保存操作的原理
- hibernate中的增删改查实现代码
- 列出SQL Server中具有默认值的所有字段的语句
- php程序的国际化实现方法(利用gettext)
- PHP以指定字段为索引返回数据库所取的数据数组
- 解决hibernate+mysql写入数据库乱码
- java优化hibernate性能的几点建议