spring-boot-route(四)全局異常處理

在開發中,咱們常常會使用try/catch塊來捕獲異常進行處理,若是有些代碼中忘記捕獲異常或者不可見的一些異常出現,就會響應給前端一些不友好的提示,這時候咱們可使用全局異常處理。這樣就不用在代碼中寫那些煩人的try/catch塊了,代碼的可讀性也會提升。前端

SpringBoot提供的的註解@ControllerAdvice表示開啓全局異常捕獲,在自定義的異常方法上使用ExceptionHandler來進行統一處理。java

下面一塊兒看看如何優雅的處理全局異常!git

一 定義響應狀態碼及信息的枚舉類

@Getter
public enum CodeEnum {
    
    SUCCESS(0,"請求成功"),
    ERROR(500,"未知異常"),
    ERROR_EMPTY_RESULT(1001,"查詢結果爲空"),
    ERROR_INCOMPLETE_RESULT(1002,"請求參數不全");
    
    private int code;
    private String message;
    CodeEnum(int code,String message){
        this.code = code;
        this.message = message;
    }
}

二 定義響應數據的實體類

@Slf4j
@Data
public class R<T> implements Serializable {

    private static final long serialVersionUID = 572235155491705152L;
    /**
     * 響應的狀態碼
     */
    private int code;
    /***
     * 響應的信息
     */
    private String message;
    /**
     * 響應數據
     */
    private T data;

    /**
     * 放入響應碼並返回
     * @param code
     * @param msg
     * @return
     */
    public R fillCode(int code,String msg){
        this.code = code;
        this.message = msg;
        return this;
    }

    /**
     * 放入響應碼並返回
     * @param codeEnum
     * @return
     */
    public R fillCode(CodeEnum codeEnum){
        this.code = codeEnum.getCode();
        this.message = codeEnum.getMessage();
        return this;
    }

    /**
     * 放入數據並響應成功狀態
     * @param data
     * @return
     */
    public R fillData(T data){
        this.code = CodeEnum.SUCCESS.getCode();
        this.message = CodeEnum.SUCCESS.getMessage();
        this.data = data;
        return this;
    }
}

三 自定義兩個異常

根據業務需求自定義異常,在本文中我定義了兩個異常,分別用做響應結果爲空時處理和請求參數錯誤時處理。github

@Data
public class EmptyResutlException extends RuntimeException {

    private static final long serialVersionUID = -8839210969758687047L;
    private int code;
    private String message;

    public EmptyResutlException(CodeEnum codeEnum){
        this.code = codeEnum.getCode();
        this.message = codeEnum.getMessage();
    }
}
@Data
public class RequestParamException extends RuntimeException {

    private static final long serialVersionUID = 4748844811214637041L;
    private int code;
    private String message;

    public RequestParamException(CodeEnum codeEnum){
        this.code = codeEnum.getCode();
        this.message = codeEnum.getMessage();
    }
}

四 定義全局異常處理類

因爲這裏我想要響應的結果爲實體類對象,所以我直接用@RestControllerAdvice來代替了@ControllerAdvice,這兩個註解的差異跟@Controller@RestController同樣,rest的響應體爲json格式的數據。spring

@RestControllerAdvice
@Slf4j
public class GlobalExceptionHandler {

    /**
     * 查詢結果爲空時處理
     * @param e
     * @return
     */
    @ExceptionHandler(EmptyResutlException.class)
    public R emptyResultExceptionHandler(EmptyResutlException e){
        log.error("查詢結果爲空:{}",e.getMessage());
        R result = new R();
        result.fillCode(e.getCode(),e.getMessage());
        return result;
    }

    /**
     * 請求參數錯誤時處理
     * @param e
     * @return
     */
    @ExceptionHandler(RequestParamException.class)
    public R requestParamExceptionHandler(RequestParamException e){
        log.error("請求參數不合法:{}",e.getMessage());
        R result = new R();
        result.fillCode(e.getCode(),e.getMessage());
        return result;
    }

    /**
     * 處理其餘異常
     * @param e
     * @return
     */
    @ExceptionHandler(Exception.class)
    public R exceptionHandler(Exception e){
        log.error("未知異常:{}",e.getMessage());
        R result = new R();
        result.fillCode(CodeEnum.ERROR);
        return result;
    }
}

五 自定義接口測試異常

@RestController
public class TestController {

    @GetMapping("getString")
    public R getString(String name){

        if(StringUtils.isEmpty(name)){
            throw new RequestParamException(1002,"請求參數name爲空");
        }else if ("Java旅途".equals(name)) {
            // 這裏沒有查詢操做,當請求參數是Java旅途的時候,模擬成查詢結果爲空
            throw new EmptyResutlException(1001,"查詢結果爲空");
        }
        // 這裏模擬一下除自定義異常外的其餘兩種異常
        int i = 0;
        i = 5/i;
        return new R().fillData(name);
    }
}

在實際開發中能夠自定義響應狀態碼的枚舉類和自定義異常以知足需求。json

此是spring-boot-route系列的第四篇文章,這個系列的文章都比較簡單,主要目的就是爲了幫助初次接觸Spring Boot 的同窗有一個系統的認識。本文已收錄至個人github,歡迎各位小夥伴star微信

githubhttps://github.com/binzh303/spring-boot-routeapp

點關注、不迷路

若是以爲文章不錯,歡迎關注點贊收藏,大家的支持是我創做的動力,感謝你們。spring-boot

若是文章寫的有問題,請不要吝嗇,歡迎留言指出,我會及時覈查修改。學習

若是你還想更加深刻的瞭解我,能夠微信搜索「Java旅途」進行關注。回覆「1024」便可得到學習視頻及精美電子書。天天7:30準時推送技術文章,讓你的上班路不在孤獨,並且每個月還有送書活動,助你提高硬實力!

相關文章
相關標籤/搜索