当前位置: 首页 > news >正文

企业级异常处理方案:Spring Boot自定义异常全局拦截实战

1. 创建自定义异常类

public class ApproveException  extends Exception {public ApproveException() {}public ApproveException(String message) {super(message);}
}public class HandleException extends Exception {public HandleException() {}public HandleException(String message) {super(message);}
}public class QueryException extends Exception {public QueryException() {}public QueryException(String message) {super(message);}
}

2. 创建全局异常处理器

package jnpf.exception;import cn.dev33.satoken.exception.IdTokenInvalidException;
import cn.dev33.satoken.exception.NotLoginException;
import cn.dev33.satoken.exception.NotPermissionException;
import cn.dev33.satoken.exception.NotRoleException;
import jnpf.base.ActionResult;
import jnpf.base.ActionResultCode;
import jnpf.util.JsonUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.bind.annotation.RestControllerAdvice;import java.util.List;
import java.util.Map;@Slf4j
@RestController
@RestControllerAdvice
public class ResultException {@ResponseBody@ExceptionHandler(value = LoginException.class)public ActionResult loginException(LoginException e) {return ActionResult.fail(ActionResultCode.Fail.getCode(), e.getMessage());}@ResponseBody@ExceptionHandler(value = ImportException.class)public ActionResult loginException(ImportException e) {return ActionResult.fail(ActionResultCode.Fail.getCode(), e.getMessage());}@ResponseBody@ExceptionHandler(value = DataException.class)public ActionResult dataException(DataException e) {return ActionResult.fail(ActionResultCode.Fail.getCode(), e.getMessage());}@ResponseBody@ExceptionHandler(value = RuntimeException.class)public ActionResult dataException(RuntimeException e) {return ActionResult.fail(ActionResultCode.Fail.getCode(), e.getMessage());}@ResponseBody@ExceptionHandler(value = IllegalArgumentException.class)public ActionResult dataException(IllegalArgumentException e) {return ActionResult.fail(ActionResultCode.Fail.getCode(), e.getMessage());}@ResponseBody@ExceptionHandler(value = WorkFlowException.class)public ActionResult workFlowException(WorkFlowException e) {if (e.getCode() == 200) {List<Map<String, Object>> list = JsonUtil.getJsonToListMap(e.getMessage());return ActionResult.success(list);} else {return ActionResult.fail(e.getMessage());}}@ResponseBody@ExceptionHandler(value = WxErrorException.class)public ActionResult wxErrorException(WxErrorException e) {return ActionResult.fail(e.getError().getErrorCode(), "操作过于频繁");}@ResponseBody@ExceptionHandler(NotPermissionException.class)public ActionResult<Void> handleNotPermissionException(NotPermissionException e) {return ActionResult.fail(ActionResultCode.Fail.getCode(), "没有访问权限,请联系管理员授权");}@ResponseBody@ExceptionHandler(NotRoleException.class)public ActionResult<Void> handleNotRoleException(NotRoleException e) {return ActionResult.fail(ActionResultCode.ValidateError.getCode(), "没有访问权限,请联系管理员授权");}@ResponseBody@ExceptionHandler(NotLoginException.class)public ActionResult<Void> handleNotLoginException(NotLoginException e) {return ActionResult.fail(ActionResultCode.SessionOverdue.getCode(), "认证失败,无法访问系统资源");}@ResponseBody@ExceptionHandler(IdTokenInvalidException.class)public ActionResult<Void> handleIdTokenInvalidException(IdTokenInvalidException e) {return ActionResult.fail(ActionResultCode.SessionOverdue.getCode(), "无效内部认证,无法访问系统资源");}
}

3. 创建统一错误响应体

package jnpf.base;import com.fasterxml.jackson.annotation.JsonInclude;import jnpf.base.vo.PageListVO;
import jnpf.base.vo.PaginationVO;
import jnpf.constant.MsgCode;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;import java.util.List;@Data
@JsonInclude(JsonInclude.Include.NON_NULL)
public class ActionResult<T> {@Schema(description = "状态码")private Integer code;@Schema(description = "返回信息")private String msg;@Schema(description = "返回数据")private T data;public static <T> ActionResult<T> success() {ActionResult<T> jsonData = new ActionResult<>();jsonData.setCode(200);jsonData.setMsg(MsgCode.SU000.get());return jsonData;}public static <T> ActionResult<T> success(String msg) {ActionResult<T> jsonData = new ActionResult<>();jsonData.setCode(200);jsonData.setMsg(msg);return jsonData;}public static <T> ActionResult<T> success(T object) {ActionResult<T> jsonData = new ActionResult<>();jsonData.setData(object);jsonData.setCode(200);jsonData.setMsg(MsgCode.SU000.get());return jsonData;}public static <T> ActionResult<T> success(String msg, T object) {ActionResult<T> jsonData = new ActionResult<>();jsonData.setData(object);jsonData.setCode(200);jsonData.setMsg(msg);return jsonData;}public static <T> ActionResult<T> fail(Integer code, String message) {ActionResult<T> jsonData = new ActionResult<>();jsonData.setCode(code);jsonData.setMsg(message);return jsonData;}public static ActionResult<String> fail(String msg, String data) {ActionResult<String> jsonData = new ActionResult<>();jsonData.setMsg(msg);jsonData.setData(data);return jsonData;}public static <T> ActionResult<T> fail(String msg) {ActionResult<T> jsonData = new ActionResult<>();jsonData.setMsg(msg);jsonData.setCode(400);return jsonData;}public static <T> ActionResult<PageListVO<T>> page(List<T> list, PaginationVO pagination) {ActionResult<PageListVO<T>> jsonData = new ActionResult<>();PageListVO<T> vo = new PageListVO<>();vo.setList(list);vo.setPagination(pagination);jsonData.setData(vo);jsonData.setCode(200);jsonData.setMsg(MsgCode.SU000.get());return jsonData;}public static <T> ActionResult<DataInterfacePageListVO<T>> page(List<T> list, PaginationVO pagination, String dataProcessing) {ActionResult<DataInterfacePageListVO<T>> jsonData = new ActionResult<>();DataInterfacePageListVO<T> vo = new DataInterfacePageListVO<>();vo.setList(list);vo.setPagination(pagination);vo.setDataProcessing(dataProcessing);jsonData.setCode(200);jsonData.setData(vo);jsonData.setMsg(MsgCode.SU000.get());return jsonData;}}

 4. 异常错误提示枚举

public enum ActionResultCode {/*** 成功*/Success(200, "成功"),/*** 失败*/Fail(400, "失败"),/*** 验证错误*/ValidateError(401, "验证错误"),/*** 异常*/Exception(500, "异常"),/*** 登录过期提示*/SessionOverdue(600, "登录过期,请重新登录"),/*** 踢出提示*/SessionOffLine(601, "您的帐号在其他地方已登录,被强制踢出"),/*** token失效*/SessionError(602, "Token验证失败");private int code;private String message;ActionResultCode(int code, String message) {this.code = code;this.message = message;}public Integer getCode() {return code;}public void setCode(Integer code) {this.code = code;}public String getMessage() {return message;}public void setMessage(String message) {this.message = message;}
}

关键点说明:

  1. @ControllerAdvice:标记为全局异常处理器

  2. @ExceptionHandler:指定处理的异常类型

  3. 响应实体:使用ActionResult可自定义HTTP状态码

  4. 异常优先级:Spring会匹配最具体的异常处理器

  5. 错误信息:包含时间戳、错误码、消息和请求路径

这样实现的全局异常处理器具有以下优点:

  • 统一处理控制器层所有异常

  • 支持自定义异常类型和错误码

  • 返回结构化的错误信息

  • 分离业务逻辑与错误处理

  • 支持HTTP状态码动态设置

  • 易于扩展和维护

http://www.dtcms.com/a/286563.html

相关文章:

  • 多线程的认识
  • 深入Java注解:从内置到元注解与自定义实战指南
  • 变量提升知识总结
  • 前后端数据交互,关于表单数据传输问题
  • 图机器学习(11)——链接预测
  • Linux和git常用命令
  • TF-IDF(Term Frequency - Inverse Document Frequency)
  • RFID技术赋能智慧物流:实现搬运环节的精准化与高效化
  • 【PTA数据结构 | C语言版】多叉堆的上下调整
  • 【LeetCode 2163. 删除元素后和的最小差值】解析
  • 上市公司-企业超额商誉数据(2005-2023年)-实证数据
  • 《C++继承深度引擎:从内存布局到多态全景拆解》​
  • 飞算科技:以创新科技引领数字化变革,旗下飞算 JavaAI 成开发利器
  • Linux Master 知识库 —— 致 Linux 系统工程师
  • 通信算法之294:LTE系统中的整数倍频偏估计
  • 太阳辐射监测站:洞察太阳能量的科技之眼
  • 【软件系统架构】系列七:系统性能——路由器性能深入解析
  • 告别宕机!Ubuntu自动重启定时任务设置(一键脚本/手动操作)
  • [Raspberry Pi]如何將無頭虛擬顯示器服務(headless display)建置在樹莓派的Ubuntu桌面作業系統中?
  • 汽车免拆诊断案例 | 07款丰田Hilux启动故障
  • Redis——MoreKey
  • 深入理解进程地址空间:虚拟内存与进程独立性
  • nodeJs笔记(六)
  • Ubuntu系统下交叉编译Android的X265库
  • 【leetcode】3202. 找出有效子序列的最大长度(2)
  • 联合利华发起TRO维权行动,OUAI商标或引发跨境圈大批量冻结
  • 密码学基础概念详解:从古典加密到现代密码体系
  • 函数指针和指针函数
  • 【非辐射复合】半导体中非辐射载流子复合的双能级机制
  • 储能BMS通信“卡壳”?CAN转EtherCAT让电池数据“跑起来”