在之前的程序里面如果一旦出现了错误之后就会出现一堆大白板,这个白板会有一些错误信息(虽然这些错误信息
你可能看不懂,但是这些错误信息依然要告诉给用户).在SpringBoot里面针对于错误的处理一共提供有三种方式:
数据验证的错误,错误页的指派以及全局异常的处理。
2.1 数据验证
现在假设说要进行表单信息提交,肯定需要有一个表单,而后这个表单要将数据提交到VO类中,所以现在的基本实现
如下:
1、建立一个Member.java 的VO类:
package com.microboot.vo;
import java.io.Serializable;
import java.util.Date;
@SuppressWarnings("serial")
public class Member implements Serializable {
private String mid;
private Integer age;
private Double salary;
private Date birthday;
settter/getter 略掉
}
2、建立一个MemberController程序类,负责实现Member的控制层处理操作.
package com.microboot.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import com.microboot.util.controller.AbstractBaseController;
import com.microboot.vo.Member;
@Controller
public class MemberController extends AbstractBaseController{
// 增加前的准备操作路径
@RequestMapping(value="/addPre",method=RequestMethod.GET)
public String addPre() {
return "member_add";
}
@RequestMapping(value="/add",method=RequestMethod.POST)
@ResponseBody
public Object add(Member vo) {
return vo;
}
}
3、编写一个页面进行用户的表单填写(src/main/templates下建立):member_add.html
SpringBoot模板渲染
2、由于此时的程序之中需要进行日期的转换处理操作,那么就需要做一个转换处理的格式配置,修改
AbstractBaseController类,追加如下的转换操作绑定:
package com.microboot.util.controller;
import java.text.SimpleDateFormat;
import java.util.Locale;
import javax.annotation.Resource;
import org.springframework.beans.propertyeditors.CustomDateEditor;
import org.springframework.context.MessageSource;
import org.springframework.web.bind.WebDataBinder;
import org.springframework.web.bind.annotation.InitBinder;
public abstract class AbstractBaseController {
// 自动注入此资源的对象
@Resource
private MessageSource messageSource;
public String getMessage(String key, String ...args) {
return this.messageSource.getMessage(key, args,Locale.getDefault());
}
@InitBinder
public void initBinder(WebDataBinder binder) { // 在本程序里面需要针对于日期格式进行处理
// 首先建立一个可以将字符串转换为日期的工具程序类
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd") ;
// 明确的描述此时需要注册一个日期格式的转化处理程序类
binder.registerCustomEditor(java.util.Date.class, new CustomDateEditor(sdf, true));
}
}
5、此时的代码只是一个最为普通的处理操作,但是这个时候对于该程序也是存在如下问题的:
如果某些数据没有输入,则内容是null;
某些数据需要进行格式验证,例如:用户名应该是邮箱,这个信息应该进行邮箱验证;
所以现在如果要想进行这些的验证, SpringBoot里面有默认的支持,只不过这种支持未必是最好的,
在SpringBoot 里面为了方便用户编写验证专门提供有一个 hibernate-validation.jar 工具包,
这个工具包是由 hibernate 开发框架提供的。
6、 如果要想进行验证,那么首先要解决的问题就必须是错误的提示信息问题,而在SpringBoot里面对于
错误信息的保存,都要 求其保存在ValidationMessages.properties文件,在“src/main/resources”
目录中建立此文件;
ValidationMessages.properties
member.mid.notnull.error=用户名不允许为空!
member.mid.email.error=用户名的注册必须输入正确的邮箱!
member.mid.length.error=用户名的格式错误!
member.age.notnull.error=年龄不允许为空
member.age.digits.error=年龄必须是合法数字!
member.salary.notnull.error=工资不允许为空!
member.salary.digits.error=工资必须是合法数字!
member.birthday.notnull.error=生日不允许为空!
提示:你一个表单就需要编写这么多的配置项,那么如果要有几百个表单呢?这样的配置项太可怕了,
所以最好的数据检测还是利用拦截器处理最合适。
7、 修改 Member.java 程序类追加验证的处理方式:
package com.microboot.vo;
import java.io.Serializable;
import java.util.Date;
import javax.validation.constraints.Digits;
import javax.validation.constraints.NotNull;
import org.hibernate.validator.constraints.Email;
import org.hibernate.validator.constraints.Length;
@SuppressWarnings("serial")
public class Member implements Serializable {
@NotNull(message="{member.mid.notnull.error}")
@Email(message="{member.mid.email.error}")
@Length(min=6,message="{member.mid.length.error}")
private String mid ;
@NotNull(message="{member.age.notnull.error}")
@Digits(integer=3,fraction=0,message="{member.age.digits.error}")
private Integer age ;
@NotNull(message="{member.salary.notnull.error}")
@Digits(integer=20,fraction=2,message="{member.salary.digits.error}")
private Double salary ;
@NotNull(message="{member.birthday.notnull.error}")
private Date birthday ;
}
8、 修改 MemberController 类中的 add()方法来观察错误信息的显示:
package com.microboot.controller;
import java.util.Iterator;
import javax.validation.Valid;
import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.validation.ObjectError;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import com.microboot.util.controller.AbstractBaseController;
import com.microboot.vo.Member;
@Controller
public class MemberController extends AbstractBaseController{
// 增加前的准备操作路径
@RequestMapping(value = "/add", method = RequestMethod.POST)
@ResponseBody
public Object add(@Valid Member vo, BindingResult result) {
// 现在表示执行的验证出现错误
if (result.hasErrors()) {
// 获取全部错误信息
Iterator iterator = result.getAllErrors().iterator();
while (iterator.hasNext()) {
ObjectError error = iterator.next() ; // 取出每一个错误
System.out.println("【错误信息】code = " + error.getCode()
+ ",message = " + error.getDefaultMessage());
}
return result.getAllErrors() ;
} else {
return vo;
}
}
@RequestMapping(value = "/addPre", method = RequestMethod.GET)
public String addPre() { // 增加前的准备操作路径
return "member_add";
}
}
对于此类的验证大家理解即可,不需要将其作为重点,但是需要清楚,默认情况下 SpringBoot 提供的数据
验证需要通过注解 以及一系列的资源文件进行定义后才可以使用,而且所有的错误都必须用户自己来处理,
这一点的设计不如直接编写具体的反射拦截器方便。