springmvc
在处理请求过程中出现异常信息交由异常处理器进行处理,自定义异常处理器可以实现一个系统的异常处理逻辑。
一、异常处理思路
系统中异常包括两类:预期异常和运行时异常RuntimeException
,前者通过捕获异常从而获取异常信息,后者主要通过规范代码开发、测试通过手段减少运行时异常的发生。
系统的dao、service、controller
出现都通过throws Exception
向上抛出,最后由springmvc
前端控制器交由异常处理器进行异常处理,如下图:
二、自定义异常类
为了区别不同的异常通常根据异常类型自定义异常类,这里我们创建一个自定义系统异常,如果controller、service、dao
抛出此类异常说明是系统预期处理的异常信息。
package com.jiayifan.ssm.exception;
/**
* 系统自定义异常类
* @author 贾一帆
*
*/
public class CustomException extends Exception {
private String message;
public CustomException(String message) {
super(message);
this.message = message;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
}
三、自定义异常处理器
package com.jiayifan.ssm.exception;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.web.servlet.HandlerExceptionResolver;
import org.springframework.web.servlet.ModelAndView;
/**
* 全局异常处理器
* @author 贾一帆
*
*/
public class CustomExceptionResolver implements HandlerExceptionResolver {
@Override
public ModelAndView resolveException(HttpServletRequest request,
HttpServletResponse response, Object handler,
Exception exception) {
//handler就是处理器适配器要执行的Handler对象(只有method)
//解析出异常类型
//如果该 异常类型是系统 自定义的异常,直接取出异常信息,在错误页面展示
CustomException customException = null;
if(exception instanceof CustomException){
customException = (CustomException)exception;
}else{
customException = new CustomException("未知错误");
}
//错误信息
String message = customException.getMessage();
ModelAndView modelAndView = new ModelAndView();
modelAndView.addObject("message",message);
modelAndView.setViewName("error");
return modelAndView;
}
}
四、错误页面
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>错误提示</title>
</head>
<body>
${message }
</body>
</html>
五、异常处理器配置
在springmvc.xml
中添加:
<!-- 全局异常处理器
只有实现了 HandlerExceptionResolver接口就是全局异常处理器
-->
<bean class="com.jiayifan.ssm.exception.CustomExceptionResolver"></bean>
六、异常测试
在controller、service、dao
中任意一处需要手动抛出异常。
如果是程序中手动抛出的异常,在错误页面中显示自定义的异常信息,如果不是手动抛出异常说明是一个运行时异常,在错误页面只显示“未知错误”。
在商品修改的controller
方法中抛出异常:
@RequestMapping(value="/editItems",method={RequestMethod.POST,RequestMethod.GET})
//@RequestParam中的value属性指定request传入的参数名称
//通过required属性指定这个参数是否必须要传入
//通过defaultValue属性可以设置默认值,如果id参数没有传入,就会将默认值和形参绑定
public String editItems(Model model,@RequestParam(value="id",required=true,defaultValue="1") Integer items_id) throws Exception {
//调用sercice查询商品信息
ItemsCustom itemsCustom = itemsService.findItemsById(items_id);
//判断商品是否为空
if(itemsCustom == null) {
throw new CustomException("controller中修改的商品信息不存在");
}
//通过参数中的model将数据传到页面
model.addAttribute("itemsCustom",itemsCustom);
return "items/editItems";
}
在service
接口中抛出异常:
@Override
public ItemsCustom findItemsById(Integer id) throws Exception {
Items items = itemsMapper.selectByPrimaryKey(id);
if(items == null) {
throw new CustomException("service中修改的商品信息不存在");
}
//中间对商品信息进行业务处理
//业务处理代码
//返回扩展类
ItemsCustom itemsCustom = null;
//将items的内容拷贝到itemsCustom中
if(items != null) {
itemsCustom = new ItemsCustom();
BeanUtils.copyProperties(items, itemsCustom);
}
return itemsCustom;
}