您的位置:首页 > 编程语言 > Java开发

Spring-Boot(五) 全局异常处理

2017-03-09 00:00 841 查看
http://nealma.com/2016/05/30/spring-boot-5-exception/

### 前言

广大码农同胞在写程序的时候,总是会遇到处理各种Exception,神马空指针啦,
再有就是处理DataBase的IO异常啦,反正哪都有他们的影子,真是阴魂不散啊。但是呢,
你又不能置之不理,那就求救于Spring的全局处理吧

:)~
开发环境:
OS: Mac 10.11.6
IDE: IDEA
Build: Maven

Spring-Boot默认实现了简单的错误页面,但是那个真是惨不忍睹。追求用户体验的你,当然想
换成自己的页面了,看着美美哒。

在实际工作中,我们不可能都是一出错就跳到html页面,根据我们自己的业务,我们通常还要以接口的形式
返回固定格式的数据,最多的就是json啦。

下面就以html和json两种形式介绍如何实现。

### html

现在只要能用注解,谁还实用xml来配置啊。
正好这里涉及到两个annotation类:
* @ControllerAdvice 全局异常处理类,不再需要每个Controller里一一定义
* @ExceptionHandler 定义针对每种类型的Exception

当然啦,如果你在业务中已经trycatch啦,那就别指望被处理了,你自己都处理了
别人当然不操心了

```java

/**
* 全局异常处理类
*/
@ControllerAdvice
public class GlobalExceptionHandler {

protected final Logger LOGGER = LoggerFactory.getLogger(getClass());

@ExceptionHandler(value = NullPointerException.class)
public ModelAndView defaultErrorHandler(HttpServletRequest req, Exception e) throws Exception {
LOGGER.error("[error] --> {}", e);
ModelAndView mav = new ModelAndView();
mav.addObject("exception", e);
mav.addObject("url", req.getRequestURL());
mav.setViewName("error");
return mav;
}
}

```

### JSON

在前面的基础上,添加输出json的方法,其中@ResponseBody是必须条件
```java
/**
* 全局异常处理类
*/
@ControllerAdvice
public class GlobalExceptionHandler {

protected final Logger LOGGER = LoggerFactory.getLogger(getClass());

@ExceptionHandler(value = NullPointerException.class)
public ModelAndView defaultErrorHandler(HttpServletRequest req, Exception e) throws Exception {
LOGGER.error("[error] --> {}", e);
ModelAndView mav = new ModelAndView();
mav.addObject("exception", e);
mav.addObject("url", req.getRequestURL());
mav.setViewName("error");
return mav;
}

@ExceptionHandler(value = AppException.class)
@ResponseBody
public MsgOut json(Exception ex) {
//TODO:记录日志
LOGGER.error("AppException", ex);

return MsgOut.error(ex);
}
}
```
### 结束
在Spring-Boot中,没有被全局处理类(GlobalExceptionHandler)捕获的异常,ErrorController会帮你补漏。
如果你使用Spring Validation来校验,要成功捕获 MethodArgumentNotValidException,
在控制器方法上就不能定义 BindingResult 参数接收校验结果,
不然如果校验失败 Spring 是不会抛出 MethodArgumentNotValidException 异常的,
自然而然在我们的 GlobalExceptionHandler 就无法处理了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息