塗塗影院管理系統這個demo中有個異常管理的標籤,用於捕獲 塗塗影院APP用戶異常信息 ,有小夥伴好奇,排除APP,後臺端的是如何處理全局異常的,故項目中的實際應用已記之。java
在使用全局異常處理以前,就目前咱們是如何處理程序中的異常信息的呢?數據庫
throws Exception + try-catch微信
怎麼講?app
在咱們目前項目中,每每事務發生在 Service 層,由於會牽扯到調用 Dao 跟數據庫打交道,當數據庫操做失敗時,會讓 Service 層拋出運行時異常,Spring 事物管理器就會進行回滾。ui
Service 拋出異常,那麼 Controller 必然要去捕獲,處理異常,因此,try-catch 就出現了。this
看一下Service:spa
public interface ServiceI{
## 保存實體的方法
public Serializable save(Entity entity) throws Exception;
}
看一下Controller的某個調用方法:設計
@PostMapping(value = "")
public AppResponse add(@RequestBody Entity entity, Errors errors){
AppResponse resp = new AppResponse();
try {
Entity endity = new Entity();
endity.setXxx();
ServiceI.save(dog);
## 返回數據
resp.setData(newDog);
}catch (BusinessException e){
resp.setFail(e.getMessage());
}catch (Exception e){
resp.setFail("操做失敗!");
}
return resp;
}
看上去也沒什麼別就,可是一個類中出現大面積的 try-catch ,就顯得很是難看且冗餘。code
若是使用 @ControllerAdvice + @ExceptionHandler 進行全局的 Controller 層異常處理,只要設計得當,就不再用在 Controller 層進行 try-catch 了。orm
定義全局異常處理類,@RestControllerAdvice 爲 @ResponseBody + @ControllerAdvice
@Slf4j
@RestControllerAdvice
public class RestCtrlExceptionHandler {
}
聲明異常處理方法,方法 handleException() 就會處理全部 Controller 層拋出的 Exception 及其子類的異常,這是最基本的用法了。
@ExceptionHandler(Exception.class)
@ResponseStatus(value = HttpStatus.OK)
public Result<Object> handleException(Exception e) {
String errorMsg = "Exception";
if (e!=null){
errorMsg = e.getMessage();
log.error(e.toString());
}
return new ResultUtil<>().setErrorMsg(500, errorMsg);
}
結合上邊一、2組合一下:
@Slf4j
@RestControllerAdvice
public class RestCtrlExceptionHandler {
@ExceptionHandler(TmaxException.class)
@ResponseStatus(value = HttpStatus.OK)
public Result<Object> handleXCloudException(TmaxException e) {
String errorMsg = "Tmax exception";
if (e!=null){
errorMsg = e.getMsg();
log.error(e.toString());
}
return new ResultUtil<>().setErrorMsg(500, errorMsg);
}
@ExceptionHandler(Exception.class)
@ResponseStatus(value = HttpStatus.OK)
public Result<Object> handleException(Exception e) {
String errorMsg = "Exception";
if (e!=null){
errorMsg = e.getMessage();
log.error(e.toString());
}
return new ResultUtil<>().setErrorMsg(500, errorMsg);
}
}
看一下 handleXCloudException() 方法
一般咱們須要拋出咱們自定義異常,而不是一有異常就所有進入 handleException 中,該方法中 TmaxException 即爲咱們自定義的異常。
@Data
public class TmaxException extends RuntimeException {
private String msg;
public TmaxException(String msg){
super(msg);
this.msg = msg;
}
}
這樣,咱們就能夠在 Controller 中拋出咱們定義的異常了,好比:
throw new TmaxException("鏈接ES失敗,請檢查ES運行狀態");
若是文章有錯的地方歡迎指正,你們互相留言交流。習慣在微信看技術文章,想要獲取更多的Java資源的同窗,能夠關注微信公衆號:niceyoo