1. Define an enumeration class
It contains information about exceptions that may occur in the system. Depending on the system, the exception number is assigned. For example, the exception number starting with 12 is for the procurement service, 10 is for the general exception, etc.
public enum BizCodeEnum {
NON_PURCHASE_REQUEST(12001,"采购需求为空"),
NON_PURCHASE_ORDER(12002,"采购单非法"),
PRODUCT_UP_EXCEPTION(11000,"商品上架异常"),
VALIDATE_EXCEPTION(10001,"数据校验错误"),
UNKNOWN_EXCEPTION(10000,"未知异常");
private int code;
private String message;
BizCodeEnum(int code, String message) {
this.code = code;
this.message = message;
}
public int getCode() {
return code;
}
public String getMessage() {
return message;
}
}
2. Customize an exception class
which contains a member variableBizCodeEnum bizCodeEnum
@Data
public class CustomException extends RuntimeException {
private static final long serialVersionUID = 1L;
private BizCodeEnum bizCodeEnum;
public CustomException(BizCodeEnum bizCodeEnum) {
this.bizCodeEnum = bizCodeEnum;
}
}
3. Define a unified return class
There is generally such a class in every system. Add a method to the class and accept one of the parameters defined above BizCodeEnum codeEnum
. The purpose is to encapsulate error information into the return class.
//本例是人人开源项目中的全局返回类R
public class R extends HashMap<String, Object> {
private static final long serialVersionUID = 1L;
public R() {
put("code", 0);
put("msg", "success");
}
public static R error(BizCodeEnum codeEnum) {
R r = new R();
r.put("code", codeEnum.getCode());
r.put("msg", codeEnum.getMessage());
return r;
}
//其他的省略
}
4. Use ControllerService for global exception capture
@RestControllerAdvice
@Slf4j
public class GulimallExceptionControllerAdvice {
@ExceptionHandler(CustomException.class)//专门处理上面的自定义异常
public R handleCustomException(CustomException customException){
log.error(customException.getBizCodeEnum().getMessage(),customException);
return R.error(customException.getBizCodeEnum());
}
}
5. Practice
When an error may occur in a certain code fragment, you only need to BizCodeEnum
define the exception code and error information in the code fragment, create a new exception in the code fragment where the exception may occur CustomException
, and pass in one BizCodeEnum
, throw it, and the client You can see the exception information correctly and the exception information will also be printed in the log.
if(xxx){
throw new CustumeException(BizCodeEnum.NON_PURCHASE_ORDER);
}
Known exceptions can also ControllerAdvice
be handled directly in , such as JSR303
field verification exception handling. You only need to ControllerAdvice
add the following code:
@ExceptionHandler(MethodArgumentNotValidException.class)
public R handleValidException(MethodArgumentNotValidException e){
log.error(BizCodeEnum.VALIDATE_EXCEPTION.getMessage(),e);
BindingResult bindingResult = e.getBindingResult();
Map<String, String> errorFieldMap = new HashMap<>();
bindingResult.getFieldErrors().forEach(fieldError -> {
String field = fieldError.getField();
String defaultMessage = fieldError.getDefaultMessage();
errorFieldMap.put(field,defaultMessage);
});
return R.error(BizCodeEnum.VALIDATE_EXCEPTION).put("data",errorFieldMap);
}