最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

SpringBoot優(yōu)雅地實(shí)現(xiàn)全局異常處理的方法詳解

 更新時(shí)間:2022年08月18日 14:11:29   作者:慕歌  
這篇文章主要為大家詳細(xì)介紹了SpringBoot如何優(yōu)雅地實(shí)現(xiàn)全局異常處理,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下

前言

在前一節(jié)的學(xué)習(xí)中,慕歌帶大家使用了全局結(jié)果集返回,通過使用全局結(jié)果集配置,優(yōu)雅的返回后端數(shù)據(jù),為前端的數(shù)據(jù)拿取提供了非常好的參考。同時(shí)通過不同的狀態(tài)碼返回,我們能夠清晰的了解報(bào)錯(cuò)的位置,排除錯(cuò)誤。如果大家有需要,可以使用我提供的的同一結(jié)果集以及狀態(tài)碼,并且可以使用全局異常攔截,實(shí)現(xiàn)異常的標(biāo)準(zhǔn)返回。接下來,我們一起來了解如何使用全局異常處理吧!

異常工具

先定義一個(gè)合適 的異常處理類,在之后的異常都會(huì)以這種格式返回前端,前端根據(jù)我們的異常進(jìn)行自己的返回,以一種優(yōu)雅的方式呈現(xiàn)錯(cuò)誤,優(yōu)化用戶體驗(yàn)。
異常結(jié)果集:

/**
 * 返回結(jié)果封裝
 */

@Data
public class ResultVo {
    // 狀態(tài)碼
    private int code;

    // 狀態(tài)信息
    private String msg;

    // 返回對(duì)象
    private Object data;

    // 手動(dòng)設(shè)置返回vo
    public ResultVo(int code, String msg) {
        this.code = code;
        this.msg = msg;
    }

    // 手動(dòng)設(shè)置返回vo
    public ResultVo(int code, String msg, Object data) {
        this.code = code;
        this.msg = msg;
        this.data = data;
    }

    // 只返回狀態(tài)碼
    public ResultVo(StatusCode statusCode) {
        this.code = statusCode.getCode();
        this.msg = statusCode.getMsg();
    }

    // 默認(rèn)返回成功狀態(tài)碼,數(shù)據(jù)對(duì)象
    public ResultVo(Object data) {
        this.code = ResultCode.SUCCESS.getCode();
        this.msg = ResultCode.SUCCESS.getMsg();
        this.data = data;
    }

    // 返回指定狀態(tài)碼,數(shù)據(jù)對(duì)象
    public ResultVo(StatusCode statusCode, Object data) {
        this.code = statusCode.getCode();
        this.msg = statusCode.getMsg();
        this.data = data;
    }

    public ResultVo(StatusCode statusCode,String msg, Object data) {
        this.code = statusCode.getCode();
        this.msg = msg;
        this.data = data;
    }
}

異常狀態(tài)碼,通過返回的狀態(tài)碼,以及狀態(tài)信息,能夠高效反映錯(cuò)誤,并且可以全局統(tǒng)一管理,方便快捷:

@Getter
public enum ExceptionCode implements StatusCode {

    // 系統(tǒng)級(jí)別錯(cuò)誤碼
    ERROR(-1, "操作異常"),
    NOT_LOGIN(102, "請先登錄!"),
    NO_Role(102,"無權(quán)限"),
    NO_PERMISSION(102,"無權(quán)限"),
    OUT_TIME(102,"登錄信息過期"),
    DISABLE_ACCOUNT(102,"帳號(hào)已被禁用!"),
    EMAIL_DISABLE_LOGIN(102,"該郵箱賬號(hào)已被管理員禁止登錄!"),
    IP_REPEAT_SUBMIT(102,"訪問次數(shù)過多,請稍后重試"),
    ERROR_DEFAULT(105,"系統(tǒng)繁忙,請稍后重試");

    //異常碼
    private int code;
    //異常信息
    private String msg;

    //自定義方法
    ExceptionCode(int code, String msg) {
        this.code = code;
        this.msg = msg;
    }
}

當(dāng)我們對(duì)異常通過以上工具類進(jìn)行封裝之后,所有異常將以一種固定的格式返回,不會(huì)導(dǎo)致錯(cuò)亂:

{3 items
	"code":105
	"msg":"系統(tǒng)繁忙,請稍后重試"
	"data":NULL
}

異常處理

在spring boot中需要使用異常攔截器,攔截全局的異常,不直接將異常返回,而是在我們進(jìn)行處理之后,以一種清晰可讀的方式返回。并且前端能夠清晰解讀我們的異常,呈現(xiàn)給用戶。

//捕獲校驗(yàn)器異常
@RestControllerAdvice
public class ControllerExceptionAdvice {
    @ExceptionHandler({BindException.class})
    public ResultVo ValidExceptionHandler(BindException e) {
        // 從異常對(duì)象中拿到ObjectError對(duì)象
        ObjectError objectError = e.getBindingResult().getAllErrors().get(0);

        return new ResultVo(ResultCode.VALIDATE_ERROR.getCode(),objectError.getDefaultMessage());
    }
}

對(duì)特定異常進(jìn)行攔截,并包裝異常:

/**
 * 對(duì)返回結(jié)果進(jìn)行包裝
 */
@RestControllerAdvice(basePackages = {"channel.cert"})
public class ControllerResponseAdvice implements ResponseBodyAdvice<Object> {
    @Override
    public boolean supports(MethodParameter methodParameter, Class<? extends HttpMessageConverter<?>> aClass) {
        // response是ResultVo類型,或者注釋了NotControllerResponseAdvice都不進(jìn)行包裝
        return !methodParameter.getParameterType().isAssignableFrom(ResultVo.class);
    }

    @Override
    public Object beforeBodyWrite(Object data, MethodParameter returnType, MediaType mediaType, Class<? extends HttpMessageConverter<?>> aClass, ServerHttpRequest request, ServerHttpResponse response) {
        // String類型不能直接包裝
        if (returnType.getGenericParameterType().equals(String.class)) {
            ObjectMapper objectMapper = new ObjectMapper();
            try {
                // 將數(shù)據(jù)包裝在ResultVo里后轉(zhuǎn)換為json串進(jìn)行返回
                return objectMapper.writeValueAsString(new ResultVo(data));
            } catch (JsonProcessingException e) {
                throw new APIException(ResultCode.RESPONSE_PACK_ERROR, e.getMessage());
            }
        }
        // 否則直接包裝成ResultVo返回
        return new ResultVo(data);
    }
}

異常捕捉

自定義異常:

@Getter
public class APIException extends RuntimeException {
    private int code;
    private String msg;

    //自定義異枚舉
    public APIException(StatusCode statusCode){
        super(statusCode.getMsg());
        this.code = statusCode.getCode();
        this.msg = statusCode.getMsg();
    }

    // 手動(dòng)設(shè)置異常
    public APIException(StatusCode statusCode, String message) {
        // message用于用戶設(shè)置拋出錯(cuò)誤詳情,例如:當(dāng)前價(jià)格-5,小于0
        super(message);
        // 狀態(tài)碼
        this.code = statusCode.getCode();
        // 狀態(tài)碼配套的msg
        this.msg = statusCode.getMsg();
    }

    // 默認(rèn)異常使用APP_ERROR狀態(tài)碼
    public APIException(String errorMsg) {
        super(errorMsg);
        this.code = ExceptionCode.ERROR_DEFAULT.getCode();
        this.msg = ExceptionCode.ERROR_DEFAULT.getMsg();
    }

    //自定義參數(shù) 錯(cuò)誤碼 錯(cuò)誤信息
    public APIException(int errorCode, String errorMsg) {
        super(errorMsg);
        this.code = errorCode;
        this.msg = ExceptionCode.ERROR_DEFAULT.getMsg();
    }

    //自定義參數(shù) 錯(cuò)誤碼 錯(cuò)誤信息 異常
    public APIException(int errorCode, String errorMsg, Throwable cause) {
        super(errorMsg);
        this.code = errorCode;
        this.msg = errorMsg;
    }
}

對(duì)自定義異常進(jìn)行捕獲,通過定義好的異常的結(jié)果集返回。

/**
 * 全局異常處理
 */
@Slf4j
@RestControllerAdvice
public class GlobalExceptionAdvice {

    // Assert業(yè)務(wù)異常
    @ExceptionHandler(IllegalArgumentException.class)
    public ResultVo AssertExceptionHandler(IllegalArgumentException ex) {
        log.error( " msg : " + ex.getMessage(), ex);
        if(StringUtils.isBlank(ex.getLocalizedMessage())){
            return new ResultVo(ExceptionCode.ERROR_DEFAULT);
        }
        return new ResultVo(ex.getMessage());
    }

    // 登錄失效異常
    @ExceptionHandler(SaTokenException.class)
    public ResultVo LoginOutExceptionHandler(SaTokenException ex) {
        log.error( " msg : " + ex.getMessage(), ex);
        return new ResultVo(ExceptionCode.OUT_TIME);
    }

    // 登錄異常
    @ExceptionHandler(NotLoginException.class)
    public ResultVo NotLoginExceptionHandler(NotLoginException ex) {
        log.error( " msg : " + ex.getMessage(), ex);
        return new ResultVo(ExceptionCode.NOT_LOGIN);
    }

    // 權(quán)限異常
    @ExceptionHandler(NotPermissionException.class)
    public ResultVo NotPermissionExceptionHandler(NotPermissionException ex) {
        log.error( " msg : " + ex.getMessage(), ex);
        return new ResultVo(ExceptionCode.NO_PERMISSION);
    }

    //角色異常
    @ExceptionHandler(NotRoleException.class)
    public ResultVo NotRoleExceptionHandler(NotRoleException ex) {
        log.error( " msg : " + ex.getMessage(), ex);
        return new ResultVo(ExceptionCode.NO_Role);
    }

    //處理自定義異常
    @ExceptionHandler(APIException.class)
    public ResultVo APIExceptionHandler(APIException e) {
        log.error(e.getMessage(), e);
        return new ResultVo(e.getCode(), e.getMsg());
    }

    //處理運(yùn)行異常
    @ExceptionHandler(RuntimeException.class)
    public ResultVo RuntimeExceptionHandler(RuntimeException e) {
        log.error(e.getMessage(), e);
        return new ResultVo(ExceptionCode.ERROR_DEFAULT);
    }
}

通過以上自定義,我們就能在項(xiàng)目中,使用自定義異常,在我們認(rèn)為可能的報(bào)錯(cuò)處插入,當(dāng)發(fā)生錯(cuò)誤時(shí),我們更快定位是之前記錄的錯(cuò)誤點(diǎn)導(dǎo)致。

//查詢數(shù)字證書
    @Override
    public GroupUser searchCert(String certCode) {
        try {
            //查詢證書編號(hào)
            GroupUser user = queryCert(certCode);
            if(ObjectUtil.isNotNull(user)){
                return user;
            }
        }catch (Exception e){
            throw new APIException("區(qū)塊鏈調(diào)用失敗"+e);
        }
        return null;
    }

以上就是SpringBoot優(yōu)雅地實(shí)現(xiàn)異常處理的方法詳解的詳細(xì)內(nèi)容,更多關(guān)于SpringBoot全局異常處理的資料請關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • Java try-with-resource語法使用解析

    Java try-with-resource語法使用解析

    這篇文章主要介紹了Java try-with-resource語法使用解析,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-03-03
  • 字符串desede 3des加密示例分享

    字符串desede 3des加密示例分享

    這篇文章主要介紹了字符串desede 3des加密示例,大家參考使用吧
    2014-01-01
  • SpringBoot中的健康檢查詳解

    SpringBoot中的健康檢查詳解

    這篇文章主要介紹了SpringBoot中的健康檢查詳解,健康檢查是一種用來確保應(yīng)用程序和其所依賴的服務(wù)的狀態(tài)正常的機(jī)制,在本文中,我們將探討SpringBoot中的健康檢查是什么以及如何使用它來監(jiān)視應(yīng)用程序的狀態(tài),需要的朋友可以參考下
    2023-07-07
  • Project?Reactor?響應(yīng)式范式編程

    Project?Reactor?響應(yīng)式范式編程

    這篇文章主要為大家介紹了Project?Reactor?響應(yīng)式范式編程,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-04-04
  • spring boot教程之全局處理異常封裝

    spring boot教程之全局處理異常封裝

    這篇文章主要給大家介紹了關(guān)于spring boot教程之全局處理異常封裝的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家學(xué)習(xí)或者使用spring boot具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-09-09
  • spring cloud gateway請求跨域問題解決方案

    spring cloud gateway請求跨域問題解決方案

    這篇文章主要介紹了spring cloud gateway請求跨域問題解決方案,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-01-01
  • 理解Java中的靜態(tài)綁定和動(dòng)態(tài)綁定

    理解Java中的靜態(tài)綁定和動(dòng)態(tài)綁定

    這篇文章主要幫助大家理解Java中的靜態(tài)綁定和動(dòng)態(tài)綁定,在Java中存在兩種綁定方式,一種為靜態(tài)綁定,另一種就是動(dòng)態(tài)綁定,亦稱為后期綁定,感興趣的小伙伴們可以參考一下
    2016-02-02
  • Spring Cloud應(yīng)用實(shí)現(xiàn)配置自動(dòng)刷新過程詳解

    Spring Cloud應(yīng)用實(shí)現(xiàn)配置自動(dòng)刷新過程詳解

    這篇文章主要介紹了Spring Cloud應(yīng)用實(shí)現(xiàn)配置自動(dòng)刷新過程詳解,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2019-12-12
  • Java編程中的equals方法使用全解

    Java編程中的equals方法使用全解

    這篇文章主要介紹了Java編程中的equals方法使用全解,是Java入門學(xué)習(xí)中的基礎(chǔ)知識(shí),需要的朋友可以參考下
    2015-10-10
  • java使用Jsoup組件生成word文檔

    java使用Jsoup組件生成word文檔

    java使用Jsoup組件生成word文檔的方法
    2013-11-11

最新評(píng)論

斗六市| 靖边县| 勐海县| 梓潼县| 城固县| 曲周县| 奎屯市| 阳谷县| 施甸县| 济阳县| 海安县| 清镇市| 金门县| 额敏县| 鹤峰县| 松原市| 内黄县| 遵义县| 永善县| 开平市| 崇左市| 鄂托克前旗| 梁山县| 大田县| 汉阴县| 措美县| 黄龙县| 利津县| 开封市| 栾城县| 水城县| 微山县| 东乌| 本溪| 仙居县| 海淀区| 文山县| 边坝县| 长岭县| 济南市| 简阳市|