Spring異常處理:@ExceptionHandler 后端如何向前端拋異常詳解。

本文由作者三汪首發(fā)于簡書。


近來開始著手基于Spring Boot的Java后端開發(fā),糾結(jié)過應(yīng)該如何優(yōu)雅地向前端拋異常。幸而發(fā)現(xiàn)Spring提供了異常處理的手段。

Spring通過@ExceptionHandler來攔截系統(tǒng)運(yùn)行時(shí)拋出的相應(yīng)異常。其有效作用域是其所處的Controller,即它聲明的異常處理方法無法攔截、處理其他Controller類中拋出的異常。
但是我們還可以通過在類上使用@ControllerAdvice(控制器增強(qiáng)。該注解可以把其聲明的類中使用@ExceptionHandler、@InitBinder、@ModelAttribute注解的方法應(yīng)用到所有的 @RequestMapping注解的方法)聲明一個(gè)攔截全局異常的@ExceptionHandler。這樣做可以有效減少代碼冗余。具體如何使用,應(yīng)該視具體業(yè)務(wù)需求而定。

下面上代碼:

ErrorInfo.java(這個(gè)類是用來返回給前端的實(shí)體)

public class ErrorInfo {
    private boolean success;
    private String msg;
    private Object errors;

    public boolean isSuccess(){
        return this.success; 
    } 
    public String getMsg() { 
        return this.msg; 
    } 
    public Object getErrors() { 
        return this.errors; 
    }


    public void setSuccess(boolean success)
    {
      this.success = success; 
    } 
    
    public void setMsg(String msg) { 
        this.msg = msg; 
    } 
    
    public void setErrors(Object errors) { 
        this.errors = errors; 
    }
}

BizException.java(BizException是我們自定義的業(yè)務(wù)異常類)

public class BizException extends Exception{

    /** 
     * @fields serialVersionUID 
     */ 
    
    private static final long serialVersionUID = -2420754730135049197L;
    private Object data;
      
    public BizException() {
        super();
    }
    
    public BizException(String message) {
        super(message);
    }

    public Object getData() {
        return this.data;
    }
    public void setData(Object data) {
        this.data = data;
    }
}

GlobalExceptionHandler.java(這個(gè)類用于處理所有Controller中拋出的BizException)

@RestController
@ControllerAdvice
public class GlobalExceptionHandler {
    private final Logger logger = LoggerFactory.getLogger(getClass());
    @ExceptionHandler({BizException.class})
    @ResponseStatus(HttpStatus.BAD_REQUEST)
    @ResponseBody
    public  ErrorInfo handleBizException(BizException e){
        this.logger.info("------------全局捕獲BIZ異常開始------------");
        ErrorInfo r = new ErrorInfo();
        r.setSuccess(false);
        r.setMsg(e.getMessage());
        this.logger.info("ErrorInfo==" + ToStringBuilder.reflectionToString(r));
        this.logger.info("------------全局捕獲BIZ異常結(jié)束------------");
        return r;
        
    }
}

在這里,我們只聲明攔截了BizException,不過,ExceptionHandler中支持聲明攔截多個(gè) Exception,只需要在花括號中增加新的聲明即可。
@ResponseStatus用于設(shè)置返回給前端的Http狀態(tài)碼,個(gè)人建議設(shè)置成BAD_REQUEST,即400。

當(dāng)我們不需要全局?jǐn)r截異常的時(shí)候,我們可以這樣寫:
AssociationController .java(普通Controller類)

@RestController
public class AssociationController {
    
    private final Logger logger = LoggerFactory.getLogger(getClass());
    
    @Autowired
    IStudentService studentService;
    
    //其余方法略...

    @RequestMapping(value = "/student/get" , method = RequestMethod.GET)
    public Student getStudent(@RequestParam(value="name",required=false)String name) throws BizException{
        Student student = null;
        if (name != null) {
            if (name.equals("Chaves")) {
                throw new BizException("Chaves is invalid!");
            }
            student = studentService.findByName(name);
        }
        return student;     
    }
    
    @ExceptionHandler({BizException.class})
    @ResponseStatus(HttpStatus.BAD_REQUEST)
    @ResponseBody
    public  ErrorInfo handleBizException(BizException e){
        this.logger.info("------------當(dāng)前類AssociationController捕獲BIZ異常開始------------");
        ErrorInfo r = new ErrorInfo();
        r.setSuccess(false);
        r.setMsg(e.getMessage());
        this.logger.info("ErrorInfo==" + ToStringBuilder.reflectionToString(r));
        this.logger.info("------------當(dāng)前類AssociationController捕獲BIZ異常結(jié)束------------");
        return r;
    }
        
}

此時(shí),該ExcetionHandler只能攔截當(dāng)前類中產(chǎn)生的BizException。


以上。
希望我的文章對你能有所幫助。
我不能保證文中所有說法的百分百正確,但我能保證它們都是我的理解和感悟以及拒絕復(fù)制黏貼。
有什么意見、見解或疑惑,歡迎留言討論。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容