Restful统一处理异常的方法

最近遇到了统一异常处理的问题,当后端异常时,需要按照统一的格式向前端发送信息。

1、首先,需要规定返回数据的格式,这里新构建了返回格式类JsonResponse。

//省略get  set方法
public class JsonResponse<T> {
    private String code;
    private String msg;
    //data表示需要返回至上一层的数据
    private T data;

    //定义不包含data构造函数,意思是不需要data,但是需要自定义code和msg
    public JsonResponse(String code, String msg) {
        this.code = code;
        this.msg = msg;
    }

    //定义包含data的构造函数,默认msg为成功
    public JsonResponse(T data) {
        this.data = data;
        this.code = "0";
        this.msg = "success";
    }

    //编写成功的静态方法,调用第二个构造函数,但传参为null
    public static JsonResponse<String> success(){
        return new JsonResponse<>(null);
    }

    //编写成功的静态方法,调用第二个构造函数,但传参为datas
    public static JsonResponse<String> success(String data){
        return new JsonResponse<>(data);
    }

    //编写失败的静态方法,调用第一个构造函数,表示失败后不用返回。是固定的状态码和提示。
    public static JsonResponse<String> fail(){
        return new JsonResponse<>("1","fail!");
    }

    //编写失败的静态方法,不用返回。但可以自定义状态码和提示信息。
    public static JsonResponse<String> fail(String code , String msg){
        return new JsonResponse<>(code,msg);
    }
}

JsonResponse类中,包含三个需要返回的参数:code码、message提示消息、data数据。同时还定义了两个构造函数,分别携带data数据以及不携带data数据,最后,还定义了success、fail方法。这样不论是正常情况下还是异常情况下,都能够保证返回数据的一致性。

在正常情况下,需要重点关注data,即泛型就是data,return new JsonResponse<T>() 即可,这里的T就是需要返回的Java对象。

2、对于异常情况,就需要关注code码以及相应的异常信息。这里的异常主要分为两类(与运行时异常和非运行时异常不同,个人定义为主动抛出异常和被动抛出异常,主动异常是正常逻辑判断中的异常,需要显式处理;而被动抛出异常是本不应该的异常),对于主动抛出异常,定义了一个异常处理类:

public class ConditionException extends RuntimeException {

    public static final Long serialVersionUID = 1L ;

    private String code;

    //全参构造函数,自定义code
    public ConditionException(String name , String code){
        super(name);
        this.code = code;
    }

    //半参构造函数,固定code
    public ConditionException(String name){
        super(name);
        this.code = "500";
    }
//省略get  set
}

ConditionException需要继承RunTimeException,主要接住主动异常,并关注其中的code码和message信息,例子如下:

//获取密码并使用RSA解密的过程,并主动抛出异常        
String password = user.getPassword();
        String rawPassword;
        try {
            rawPassword = RSAUtil.decrypt(password);
        } catch (Exception e) {
            throw new ConditionException("解密失败!");
        }

3、spring框架中的@ControllerAdvice和@ExceptionHandle能够统一处理异常,具体如下:

@ControllerAdvice
@Order(value = Ordered.HIGHEST_PRECEDENCE)
public class CommonGlobalExceptionHandler {
    @ExceptionHandler(value = Exception.class)
    public JsonResponse<String> commonExceptionHandler(HttpServletRequest request , Exception e){
        String errMsg = e.getMessage();
        if (e instanceof ConditionException){
            String code = ((ConditionException)e).getCode();
            return new JsonResponse<>(code,errMsg);
        }else{
            return new JsonResponse<>("500",errMsg);
        }
    }
}

在ExceptionHandle类中,通过判断异常类型,如果是主动构建的ConditionException异常类,那么就获取其中的code等信息,然后new JsonResponse。这样就巧妙的将三者结合起来,最终使得正常和异常的信息均遵循统一的格式。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值