SpringBoot系列<五>全局异常处理
1、介绍
在日常开发中发生了异常,往往是需要通过一个统一的异常处理处理所有异常,来保证客户端能够收到友好的提示。SpringBoot在页面 发生异常的时候会自动把请求转到/error,SpringBoot内置了一个BasicErrorController对异常进行统一的处理,当然也可以自定义这个路径,默认为/error
server:
error:
path: /custom/error
BasicErrorController提供两种返回错误一种是页面返回、当你是页面请求的时候就会返回页面,另外一种是json请求的时候就会返回json错误
2、通用Exception处理
通过使用@ControllerAdvice来进行统一异常处理,@ExceptionHandler(value = Exception.class)来指定捕获的异常
下面针对两种异常进行了特殊处理分别返回页面和json数据,使用这种方式有个局限,无法根据不同的头部返回不同的数据格式,而且无法针对404、403等多种状态进行处理
全局异常请求处理代码如下:
定义异常处理类:
@RestControllerAdvice
public class GlobalControllerExceptionHandler {
private static final Log LOG=LogFactory.getLog(GlobalControllerExceptionHandler.class);
@ExceptionHandler(value = Exception.class)
public ModelAndView globalErrorHandler(Exception ex) {
LOG.error(ex);
ModelAndView modelAndView = new ModelAndView();
modelAndView.setViewName("defaultError");
return modelAndView;
}
@ExceptionHandler(value = GlobalRunTimeException.class)
public Map myExceptionHandler(GlobalRunTimeException ex){
Map map = new HashMap();
map.put("code", ex.getCode());
map.put("message" , ex.getMessage());
return map;
}
自定义异常:
@Data
@NoArgsConstructor
@AllArgsConstructor
public class GlobalRunTimeException extends RuntimeException implements Serializable{
private static final long serialVersionUID = -4156688065333355731L;
private String code;
private String message;
}
测试Controller:
@RequestMapping(value = "/ex")
public void testException() throws Exception{
throw new Exception();
//throw new GlobalRunTimeException("1001","自定义全局错误");
}
自定义的默认异常处理页:
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8" />
<title>统一异常处理</title>
</head>
<body>
<h1>默认异常处理页面</h1>
</body>
</html>
注:这里采用的是JSP解析,所以系统会去根据SpringMVC视图解析配置去寻找defaultError页面;
3、自定义BaseErrorController继承BasicErrorController处理错误
BaseErrorController可以根据自己的需求自定义errorHtml()和error()两个方法,实现不同的请求不同的返回,具体的可以看下BasicErrorController该类;
SpringBoot提供了一种特殊的Bean定义方式,可以让我们容易的覆盖已经定义好的Controller,原生的BasicErrorController是定义在ErrorMvcAutoConfiguration中的
具体代码如下:
@Bean
@ConditionalOnMissingBean(value = ErrorController.class, search = SearchStrategy.CURRENT)
public BasicErrorController basicErrorController(ErrorAttributes errorAttributes) {
return new BasicErrorController(errorAttributes, this.serverProperties.getError(),
this.errorViewResolvers);
}
可以看到这个注解@ConditionalOnMissingBean 意思就是定义这个bean 当 ErrorController.class 这个没有定义的时候, 意思就是说只要我们在代码里面定义了自己的ErrorController.class时,这段代码就不生效了,所以我们只需要自定义一个ErrorController接口类,并在ErrorMvcAutoConfiguration.class之前先加载自定义的ErrorController接口类即可;
我这里的是选择继承默认的BasicErrorController.class,重写需要自定义的部分,更多的去看下BasicErrorController该类及该类关联关系;
还没有评论,来说两句吧...