日本免费高清视频-国产福利视频导航-黄色在线播放国产-天天操天天操天天操天天操|www.shdianci.com

學無先后,達者為師

網站首頁 編程語言 正文

使用@ControllerAdvice和@ExceptionHandler構建全局異常處理器

作者:paul亡命天涯 更新時間: 2022-07-22 編程語言

@ControllerAdvice和、@ExceptionHandler可以構建全局異常處理器。

它們的底層原理是使用Spring AOP方式對被@RequestMaping聲明的方法進行增強,從而達到異常統一處理的目的。

這樣做的好處的就是不需要我們手動的對每一個異常進行try…catch。

首先@ControllerAdvice相當于通知類,同時又要具備切點表達式的身份,它會對所有被@RequestMaping聲明的方法進行增強。

而@ExceptionHandler聲明的方法相當于通知(增強方法)但它更加強大,它會對切入點進行上下文檢索其聲明的異常(@ExceptionHandler(value = Exception.class))所在,進行try…catch統一對異常進行處理。

全局異常處理流程:
1、創建自定義業務異常類;
2、創建一個類并聲明@ControllerAdvice,作為全局異常處理類
3、在全局異常處理類上,創建增強方法,聲明@ExceptionHandler檢索需要處理的異常。

自定業務義異常類:

/**
 * 自定義業務異常類
 */
public class CustomException extends Exception {
    public CustomException(String message){
        //拋出異常時自定義異常信息替代RuntimeException提供的message
        super(message);
    }
}

全局異常處理類:

@ControllerAdvice
@Slf4j
public class GlobalExceptionHandler {

    @ExceptionHandler(SQLIntegrityConstraintViolationException.class)
    @ResponseBody
    public R<String> exceptionHandler(SQLIntegrityConstraintViolationException ex) {
        String message = ex.getMessage();
        if (message.contains("Duplicate entry")) {
            String[] split = message.split(" ");
            return R.error(split[2] + "已存在");
        }
        return R.error("未知錯誤");
    }

    @ExceptionHandler(CustomException.class)
    @ResponseBody
    public R<String> customExceptionHandler(CustomException ce) {
        return R.error(ce.getMessage());
    }
}

測試:

比如這里有一個業務異常需要處理,分類關聯菜品,不能刪除:

@Override
    public R<String> delete(Long id) {

        LambdaQueryWrapper<Dish> dishLambdaQueryWrapper = new LambdaQueryWrapper<>();
        dishLambdaQueryWrapper.eq(Dish::getCategoryId, id);
        //判斷當前分類是否關聯了菜品
        if (dishMapper.selectCount(dishLambdaQueryWrapper) > 0) {
            throw new CustomException("當前分類下關聯了菜品,不能刪除");
        }
        
        LambdaQueryWrapper<Setmeal> setmealLambdaQueryWrapper = new LambdaQueryWrapper<>();
        setmealLambdaQueryWrapper.eq(Setmeal::getCategoryId, id);
        //判斷當前分類是否關聯了套餐
        if (setmealMapper.selectCount(setmealLambdaQueryWrapper) > 0) {
            throw new CustomException("當前分類下關聯了套餐,不能刪除");
        }

        categoryMapper.deleteById(id);

        return R.success("刪除分類成功");
    }

最終執行流程:

在這里插入圖片描述

增強后的代碼相當于:

@Override
    public R<String> delete(Long id) {

        LambdaQueryWrapper<Dish> dishLambdaQueryWrapper = new LambdaQueryWrapper<>();
        dishLambdaQueryWrapper.eq(Dish::getCategoryId, id);
        //判斷當前分類是否關聯了菜品
        if (dishMapper.selectCount(dishLambdaQueryWrapper) > 0) {
            throw new CustomException("當前分類下關聯了菜品,不能刪除");
        }
        
        LambdaQueryWrapper<Setmeal> setmealLambdaQueryWrapper = new LambdaQueryWrapper<>();
        setmealLambdaQueryWrapper.eq(Setmeal::getCategoryId, id);
        //判斷當前分類是否關聯了套餐
        if (setmealMapper.selectCount(setmealLambdaQueryWrapper) > 0) {
            try {
                throw new CustomException("當前分類下關聯了套餐,不能刪除");
            } catch (CustomException e) {
                return R.error(e.getMessage());
            }
        }

        categoryMapper.deleteById(id);

        return R.success("刪除分類成功");
    }

原文鏈接:https://blog.csdn.net/weixin_41786712/article/details/125919089

相關推薦

欄目分類
最近更新