SpringBoot项目中异常的捕获和处理
Posted sysu_lluozh
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了SpringBoot项目中异常的捕获和处理相关的知识,希望对你有一定的参考价值。
一般在开发中,会有业务异常和程序异常两种
一、异常处理的意义
程序中往往在try-catch
异常的时候会进行重新抛出一个新的异常,如何捕获和处理异常在编码过程中具有重要的意义
- 提高健壮性,提前对可能发生的异常情况预判处理提高稳定性和可用性
如,预判网路异常然后在异常处理中进行重试 - 利于错误恢复和错误处理,针对不同的异常进行不同的处理
- 有利于发生异常时问题的排查和解决
如,通过logger可以知道错误发生的地方、错误详情等信息
如何处理异常信息可以提高代码的健壮性、稳定性和可用性等,接下来看看业务中如何进行异常的捕获和处理
二、定义错误码
首先需要自定义业务中错误状态码,方便状态码的管理
ErrorCodeEnum.java
package com.lluozh.fagent.config;
public enum ErrorCodeEnum {
/* 规范:错误码长度6位,单个领域前缀为前三位 */
/* 通用异常: 100xxx */
PARAM_INVALID(100001, "参数校验异常"),
NULL_POINTER(100002, "空指针异常")
UNKNOWN_ERROR(199999, "未知异常"),
/* 场景执行异常: 200xxx */
SCENE_JMX_EXECUTE_ERROR(200001, "场景执行异常");
private final int code;
private final String msg;
ErrorCodeEnum(int code, String msg) {
this.code = code;
this.msg = msg;
}
public int getCode() {
return code;
}
public String getMsg() {
return msg;
}
}
三、自定义异常类
不同的业务异常有可能有特定的处理逻辑,故除了需要定义通用的异常类,还需要根据业务的需求定义不同的业务自定义异常类
3.1 通用异常类
BizException.java
package com.lluozh.fagent.exception;
import lombok.extern.slf4j.Slf4j;
import com.lluozh.fagent.config.ErrorCodeEnum;
@Slf4j
public class BizException extends Exception {
private static final long serialVersionUID = 1L;
public BizException() {
super("");
}
public BizException(String message, Throwable cause) {
super(message, cause);
}
public BizException(String msg) {
super(msg);
}
}
3.2 业务自定义异常类
JmxExecuteException.java
package com.lluozh.fagent.exception;
import lombok.extern.slf4j.Slf4j;
import com.lluozh.fagent.config.ErrorCodeEnum;
@Slf4j
public class JmxExecuteException extends Exception {
private static final long serialVersionUID = 1L;
public JmxExecuteException() {
super("场景执行异常");
}
public JmxExecuteException(String message, Throwable cause) {
super(message, cause);
}
public JmxExecuteException(String msg) {
super(msg);
}
public int getCode() {
return ErrorCodeEnum.PARAM_INVALID.getCode();
}
public String getErrorMsg() {
return ErrorCodeEnum.PARAM_INVALID.getMsg();
}
}
四、定义异常捕获业务处理
有些异常类需要在捕获异常后处理一些特定的业务逻辑,比如下面场景执行异常捕获这个业务逻辑中,捕获到异常后需要变更场景执行的状态和节点的状态,故需要在异常捕获后使用切面的方式自定义部分异常处理逻辑
ExceptionHandlers.java
package com.lluozh.fagent.handler;
import com.lluozh.service.support.ApiResult;
import com.lluozh.fagent.service.SceneService;
import com.lluozh.fagent.entity.SceneStatusEntity;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.MissingServletRequestParameterException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import javax.servlet.http.HttpServletRequest;
/**
* @author lluozh
* @Description:
* @date 2021/8/27
*/
@Slf4j
@ControllerAdvice
public class ExceptionHandlers {
@Autowired
private SceneService sceneService;
/**
* 场景执行异常捕获
* @return
*/
@ExceptionHandler(value = JmxExecuteException.class)
@ResponseBody
public ApiResult<Void> handleJmxExecuteExceptionHandler(Exception e) {
log.error("场景执行异常!原因是:",e);
// 更新scene执行状态
sceneService.sceneStatusAlter(SceneStatusEntity.ExecStatus.ERROR, e.toString());
return ApiResult.fail(ErrorCodeEnum.SCENE_JMX_EXECUTE_ERROR.getCode(), e.getMessage());
}
/**
* 空指针的异常
* @return
*/
@ExceptionHandler(value =NullPointerException.class)
@ResponseBody
public ApiResult<Void> nullPointerExceptionHandler(Exception e) {
log.error("发生空指针异常!原因是:",e);
return ApiResult.fail(ErrorCodeEnum.NULL_POINTER.getCode(), ErrorCodeEnum.NULL_POINTER.getMsg());
}
/**
* 参数错误异常
* @return
*/
@ExceptionHandler(value= IllegalArgumentException.class)
@ResponseBody
public ApiResult<Void> illegalArgumentExceptionHandler(HttpServletRequest req, IllegalArgumentException e) {
log.error("发生参数错误异常!原因是:", e);
return ApiResult.fail(ErrorCodeEnum.PARAM_INVALID.getCode(), ErrorCodeEnum.PARAM_INVALID.getMsg());
}
/**
* 未知异常
* @param e
* @return
*/
@ExceptionHandler(value = Exception.class)
@ResponseBody
public ApiResult<Void> handleException(Exception e) {
return ApiResult.fail(ErrorCodeEnum.UNKNOWN_ERROR.getCode(), e.toString());
}
}
五、使用示例
JmeterExecuteEngine.java
package com.lluozh.fagent.jmeter.engine;
import com.lluozh.fagent.exception.JmxExecuteException;
// 加载执行的jmx文件
HashTree jmxTree;
try {
jmxTree = SaveService.loadTree(jmxFile);
} catch (Exception e) {
throw new JmxExecuteException("【JmxExecuteException】agent加载jmx文件异常!", e);
}
以上是关于SpringBoot项目中异常的捕获和处理的主要内容,如果未能解决你的问题,请参考以下文章