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

Spring Boot中的全局异常处理:@RestControllerAdvice的应用

在现代Web开发中,异常处理是一个不可或缺的部分。良好的异常处理不仅能提高系统的健壮性,还能提升用户体验。在Spring Boot中,全局异常处理的实现可以通过使用@RestControllerAdvice注解来完成。本文将详细介绍如何使用@RestControllerAdvice@ExceptionHandler来统一处理异常,并给出具体的实现示例。

1. @RestControllerAdvice概述

@RestControllerAdvice是Spring MVC提供的一个功能强大的注解,用于全局处理控制器中的异常。它相当于@ControllerAdvice@ResponseBody的组合,可以用于定义以下三种功能:

  1. @ExceptionHandler:处理特定的异常,并将响应返回给前端。
  2. @InitBinder:预处理Web请求数据的绑定。
  3. @ModelAttribute:将数据绑定到模型中,以便在控制器的@RequestMapping方法中使用。

@RestControllerAdvice自动被Spring的组件扫描机制检测到,若应用通过MVC命令空间或MVC Java编程方式配置,该功能默认自动开启。

2. 实现全局异常处理

在实现全局异常处理时,我们通常会定义一个异常处理类,这个类中包含多个异常处理方法,每个方法对应一种或多种异常类型。下面是一个典型的实现示例。

2.1 全局异常处理器

import com.sugon.cloud.lowcode.result.ReturnResult;
import lombok.extern.slf4j.Slf4j;
import org.mybatis.spring.MyBatisSystemException;
import org.springframework.web.HttpRequestMethodNotSupportedException;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestControllerAdvice;import javax.naming.AuthenticationException;
import javax.servlet.http.HttpServletRequest;import static com.sugon.cloud.lowcode.constants.SplitCharacter.LEFT_PARENTHESES;
import static com.sugon.cloud.lowcode.constants.SplitCharacter.RIGHT_PARENTHESES;
import static com.sugon.cloud.lowcode.result.CodeMessageEnum.*;@RestControllerAdvice
@Slf4j
public class GlobalExceptionHandler {@ExceptionHandler(value = BizException.class)@ResponseBodypublic ReturnResult bizExceptionHandler(HttpServletRequest req, BizException e) {log.error("发生业务异常: {}, 请求接口: {}", e.getMessage(), req.getRequestURI());return ReturnResult.error(e.getCode(), e.getMessage());}@ExceptionHandler(value = NullPointerException.class)@ResponseBodypublic ReturnResult exceptionHandler(HttpServletRequest req, NullPointerException e) {log.error("空指针异常信息: {}, 请求接口: {}", e, req.getRequestURI());return ReturnResult.error(NULL_POINT_ERROR_EXCEPTION.getCode(),NULL_POINT_ERROR_EXCEPTION.getMessage()+ RIGHT_PARENTHESES+ e.getMessage()+ LEFT_PARENTHESES);}@ExceptionHandler(value = HttpRequestMethodNotSupportedException.class)@ResponseBodypublic ReturnResult methodNotSupportedExceptionHandler(HttpServletRequest req, Exception e) {log.error("请求方法异常信息: {},请求接口: {}", e, req.getRequestURI());return ReturnResult.error(REQUEST_METHOD_ERROR.getCode(),REQUEST_METHOD_ERROR.getMessage() + RIGHT_PARENTHESES + e.getMessage() + LEFT_PARENTHESES);}@ExceptionHandler(value = MyBatisSystemException.class)@ResponseBodypublic ReturnResult sqlSyntaxErrorExceptionHandler(HttpServletRequest req, Exception e) {log.error("MyBatis系统异常信息: {},请求接口: {}", e, req.getRequestURI());return ReturnResult.error(INNER_FRAME_EXCEPTION.getCode(),INNER_FRAME_EXCEPTION.getMessage() + RIGHT_PARENTHESES + e.getMessage() + LEFT_PARENTHESES);}@ExceptionHandler(value = AuthenticationException.class)public ReturnResult incorrectCredentialsException(HttpServletRequest request, AuthenticationException e) {log.error("用户名或密码不正确: {}, 请求接口: {}", e, request.getRequestURI());return ReturnResult.error(USER_CREDENTIALS_ERROR);}@ExceptionHandler(value = UserException.class)public ReturnResult incorrectUserException(HttpServletRequest request, UserException e) {log.error("用户信息异常: {}, 请求接口: {}", e, request.getRequestURI());return ReturnResult.error(e.getCode(), e.getMessage());}@ExceptionHandler(value = Exception.class)@ResponseBodypublic ReturnResult exceptionHandler(HttpServletRequest req, Exception e) {e.printStackTrace();log.error("未知异常: {}, 请求接口: {}", e, req.getRequestURI());return ReturnResult.error(INTERNAL_SERVER_ERROR.getCode(),INTERNAL_SERVER_ERROR.getMessage() + RIGHT_PARENTHESES + e.getMessage() + LEFT_PARENTHESES);}
}

2.2 自定义业务异常类

import com.sugon.cloud.lowcode.result.BaseResultInterface;
import com.sugon.cloud.lowcode.result.CodeMessageEnum;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;@ApiModel(description= "业务异常数据")
public class BizException extends RuntimeException implements BaseResultInterface {private static final long serialVersionUID = 1L;@ApiModelProperty(value = "错误码")private String code;@ApiModelProperty(value = "错误信息")private String message;public BizException() {super();}public BizException(CodeMessageEnum codeMessageEnum) {super(codeMessageEnum.getCode());this.code = codeMessageEnum.getCode();this.message = codeMessageEnum.getMessage();}public BizException(CodeMessageEnum codeMessageEnum, Throwable cause) {super(codeMessageEnum.getCode(), cause);this.code = codeMessageEnum.getCode();this.message = codeMessageEnum.getMessage();}public BizException(CodeMessageEnum codeMessageEnum, String message, Throwable cause) {super(codeMessageEnum.getCode(), cause);this.code = codeMessageEnum.getCode();this.message = message;}public BizException(String message) {super(message);this.message = message;}public BizException(String code, String message) {super(code);this.code = code;this.message = message;}public BizException(String code, String message, Throwable cause) {super(code, cause);this.code = code;this.message = message;}@Overridepublic Throwable fillInStackTrace() {return this;}@Overridepublic String getCode() {return this.code;}@Overridepublic String getMessage() {return this.message;}
}

3. 统一返回格式

在上述代码中,所有的异常处理方法返回的是ReturnResult对象,它封装了返回给前端的数据。ReturnResult类的设计使得前端可以统一解析和展示错误信息。

3.1 返回结果类

import com.alibaba.fastjson.JSONObject;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Getter;
import lombok.Setter;import static com.sugon.cloud.lowcode.result.CodeMessageEnum.*;@Setter
@Getter
@ApiModel(description= "返回响应数据")
public class ReturnResult<T> {@ApiModelProperty(value = "状态码")private String code;@ApiModelProperty(value = "响应信息")private String message;@ApiModelProperty(value = "响应对象")private T result;@ApiModelProperty(value = "是否成功")private boolean success = true;public ReturnResult() {}public ReturnResult(CodeMessageEnum codeMessageEnum) {this.code = codeMessageEnum.getCode();this.message = codeMessageEnum.getMessage();}public static ReturnResult success() {return success(null);}public static <T> ReturnResult<T> success(T data) {return success(SUCCESS, data);}public static <T> ReturnResult<T> loginSuccess(T data) {return success(SUCCESS_LOGIN, data);}public static ReturnResult loginOutSuccess() {return success(SUCCESS_LOGOUT, null);}private static <T> ReturnResult<T> success(CodeMessageEnum codeMessageEnum, T data) {ReturnResult<T> result = new ReturnResult<>();result.setCode(codeMessageEnum.getCode());result.setMessage(codeMessageEnum.getMessage());result.setResult(data);return result;}public static ReturnResult error(CodeMessageEnum codeMessageEnum) {return error(codeMessageEnum.getCode(), codeMessageEnum.getMessage());}public static ReturnResult error(CodeMessageEnum codeMessageEnum, String message) {return error(codeMessageEnum.getCode(), message);}public static ReturnResult error(String code, String message) {ReturnResult result = new ReturnResult();result.setCode(code);result.setMessage(message);result.setSuccess(false);return result;}@Overridepublic String toString() {return JSONObject.toJSONString(this);}
}

4. 总结

通过@RestControllerAdvice@ExceptionHandler,我们可以在Spring Boot应用中实现全局异常处理,统一管理和处理所有异常。这样不仅可以

减少重复代码,还能使代码更加整洁,提高可维护性。同时,通过统一的返回格式,前端处理响应数据时也能更加方便。

希望这篇文章对您在Spring Boot中实现全局异常处理有所帮助。如有任何问题或建议,欢迎交流探讨。

相关文章:

Spring Boot中的全局异常处理:@RestControllerAdvice的应用

在现代Web开发中&#xff0c;异常处理是一个不可或缺的部分。良好的异常处理不仅能提高系统的健壮性&#xff0c;还能提升用户体验。在Spring Boot中&#xff0c;全局异常处理的实现可以通过使用RestControllerAdvice注解来完成。本文将详细介绍如何使用RestControllerAdvice和…...

指令数据的构建

文章目录 基于现有的 NLP 任务数据集构建基于日常对话数据构建基于合成数据构建指令微调(Instruction Tuning)是指使用自然语言形式的数据对预训练后的大语言模型进行参数微调,这一术语由谷歌研究员在 2022 年的一篇 ICLR 论文中正式提出。在另外一些参考文献中,指令微调也…...

论文解读(14)-GeoCLIP

加油&#xff0c;加油&#xff01; 原文&#xff1a; GeoCLIP: Clip-Inspired Alignment between Locations and Images for Effective Worldwide Geo-localization &#xff08;2309.16020 (arxiv.org)&#xff09; 这一篇的重点在于范围放宽到全球了 摘要 首先指出了目前…...

MySQL基础练习题16-电影评分

题目 准备数据 分析数据 总结 题目 查找评论电影数量最多的用户名。如果出现平局&#xff0c;返回字典序较小的用户名。 查找在 February 2020 平均评分最高 的电影名称。如果出现平局&#xff0c;返回字典序较小的电影名称。 准备数据 ## 创建库 create database db; u…...

CRMEB-众邦科技 使用笔记

1.启动项目报错 Unable to load authentication plugin ‘caching_sha2_password’. 参考&#xff1a;http://t.csdnimg.cn/5EqaE 解决办法&#xff1a;升级mysql驱动 <dependency><groupId>mysql</groupId><artifactId>mysql-connector-java</ar…...

npm与webpack的学习笔记

npm 定义&#xff1a;npm是Node.js标准的软件包管理器。它起初是作为下载和管理Node.js包依赖的方式&#xff0c;但其现在也已成为前端JavaScript中使用的工具。 包 包&#xff1a;将模块、代码、其他资料聚合成一个文件夹 包的分类&#xff1a; 项目包&#xff1a;主要用…...

Vue 生命周期选项:2.x 与 3.x 的全面解析及案例分享二

目录 Vue3.X生命周期 介绍 流程图 案例 ​​​​​​​this.$nextTick Vue 生命周期选项:2.x 与 3.x 的全面解析及案例分享一-CSDN博客 Vue3.X生命周期 介绍 beforeCreate:在实例初始化之后,数据观测 (data observer) 和 event/watcher 事件配置之前被调用。此时无法访…...

Linux centos7 安装sftp

这里写自定义目录标题 指定 SSH 默认端口 (通常是22)添加自定义端口确保 SFTP 子系统配置存在匹配自定义端口的配置 在 CentOS 7 上安装 SFTP 并使用自定义端口 22345 启动&#xff0c;同时不影响现有的 SSH 登录&#xff0c;可以按照以下步骤进行配置&#xff1a; 步骤 1: 安…...

Java未来还是霸主吗?Java 在当今企业中的未来到底是什么?

Java 及其生态系统对于许多现代企业的成功至关重要。它是一种多功能语言&#xff0c;对许多用例提供强大支持&#xff0c;并具有强大的新功能来应对棘手的情况。但您可能会问自己&#xff1a;Java 的未来是什么&#xff1f; 尽管自 1999 年以来 Java 一直是软件开发领域的关键角…...

【C++】类和对象——Lesson2

Hi~&#xff01;这里是奋斗的小羊&#xff0c;很荣幸您能阅读我的文章&#xff0c;诚请评论指点&#xff0c;欢迎欢迎 ~~ &#x1f4a5;&#x1f4a5;个人主页&#xff1a;奋斗的小羊 &#x1f4a5;&#x1f4a5;所属专栏&#xff1a;C &#x1f680;本系列文章为个人学习笔记…...

常用传感器讲解十五--触摸传感器(KY-036)

常用传感器讲解十五–触摸传感器&#xff08;KY-036&#xff09; 具体讲解 这个比较简单&#xff0c;就是触摸后给个信号 电路连接 在Arduino上将VCC引脚连接到5V。 将GND连接到Arduino的GND。 将OUT连接到Arduino上的D2 代码实现 void setup() {pinMode(2, INPUT);Seri…...

web后端--Spring事务管理

事务也要日志配置 !!!!debug前面记得加空格 logging:level:org.springframework.jdbc.support.JdbcTransactionManager: debugrollbackFor 默认情况下&#xff0c;只有出现RunTimeException才会回滚事务&#xff0c;rollbackfor属性用于控制出现何种异常类型&#xff0c;回滚…...

【Docker系列】Docker 中-d 和-it 的区别

&#x1f49d;&#x1f49d;&#x1f49d;欢迎来到我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里可以感受到一份轻松愉快的氛围&#xff0c;不仅可以获得有趣的内容和知识&#xff0c;也可以畅所欲言、分享您的想法和见解。 推荐:kwan 的首页,持续学…...

PHP回收废品平台系统小程序源码

&#x1f30d;绿色行动&#xff0c;从“回收废品平台系统”开始&#xff01;&#x1f69a; &#x1f6aa;【家门口的环保站&#xff0c;废品不再无处安放】 你是否曾为家里的旧报纸、空瓶子、废旧电器等废品头疼不已&#xff0c;不知该如何处理&#xff1f;现在&#xff0c;“…...

IIS解析漏洞~ IIS7.漏洞分析

IIS解析漏洞 文件解析漏洞是由于中间件错误的将特殊格式的文件解析成可执行网页文件(脚本)&#xff0c;配合文件上传漏洞进行GetShell的漏洞&#xff01; 1.2&#xff1a;IIS7.X 在IIS7.0和IIS7.5版本下也存在解析漏洞&#xff0c;在默认Fast-CGI开启状况下&#xff0c;在一个文…...

基于python+django的病人人信息管理系统及安全策略分析设计与实现

博主介绍&#xff1a; 大家好&#xff0c;本人精通Java、Python、C#、C、C编程语言&#xff0c;同时也熟练掌握微信小程序、Php和Android等技术&#xff0c;能够为大家提供全方位的技术支持和交流。 我有丰富的成品Java、Python、C#毕设项目经验&#xff0c;能够为学生提供各类…...

前端必知必会-html表单的input属性

文章目录 HTML 输入属性value 属性readonly 属性disabled 属性size 属性maxlength 属性min 和 max 属性multiple 属性pattern 属性placeholder 属性required 属性step 属性autofocus 属性height 和 width 属性list 属性autocomplete 属性总结 HTML 输入属性 本章介绍 HTML <…...

设计模式:详细拆解策略模式

策略模式 既然是详解&#xff0c;就不以案例开头了&#xff0c;直奔主题&#xff0c;先来看看什么是策略模式。 模式定义 定义一系列的算法&#xff0c;把它们一个个封装起来&#xff0c;并且使它们可相互替换。本模式 使得算法可独立于使用它的客户而变化。 结构 Strategy&a…...

Python正则表达式面试题分析总结

Python正则表达式面试题主要围绕Python内置的re模块展开&#xff0c;考察的是应聘者对于正则表达式的理解、使用以及在实际问题中的应用能力。以下是对这些面试题的详细分析总结&#xff1a; 正则表达式基础&#xff1a; re模块简介&#xff1a;Python中的re模块提供了正则表达…...

LeetCode题练习与总结:超过经理收入的员工--181

一、题目描述 SQL Schema > Pandas Schema > 表&#xff1a;Employee ---------------------- | Column Name | Type | ---------------------- | id | int | | name | varchar | | salary | int | | managerId | int | ----…...

vscode里如何用git

打开vs终端执行如下&#xff1a; 1 初始化 Git 仓库&#xff08;如果尚未初始化&#xff09; git init 2 添加文件到 Git 仓库 git add . 3 使用 git commit 命令来提交你的更改。确保在提交时加上一个有用的消息。 git commit -m "备注信息" 4 …...

【人工智能】神经网络的优化器optimizer(二):Adagrad自适应学习率优化器

一.自适应梯度算法Adagrad概述 Adagrad&#xff08;Adaptive Gradient Algorithm&#xff09;是一种自适应学习率的优化算法&#xff0c;由Duchi等人在2011年提出。其核心思想是针对不同参数自动调整学习率&#xff0c;适合处理稀疏数据和不同参数梯度差异较大的场景。Adagrad通…...

【SpringBoot】100、SpringBoot中使用自定义注解+AOP实现参数自动解密

在实际项目中,用户注册、登录、修改密码等操作,都涉及到参数传输安全问题。所以我们需要在前端对账户、密码等敏感信息加密传输,在后端接收到数据后能自动解密。 1、引入依赖 <dependency><groupId>org.springframework.boot</groupId><artifactId...

MVC 数据库

MVC 数据库 引言 在软件开发领域,Model-View-Controller(MVC)是一种流行的软件架构模式,它将应用程序分为三个核心组件:模型(Model)、视图(View)和控制器(Controller)。这种模式有助于提高代码的可维护性和可扩展性。本文将深入探讨MVC架构与数据库之间的关系,以…...

【ROS】Nav2源码之nav2_behavior_tree-行为树节点列表

1、行为树节点分类 在 Nav2(Navigation2)的行为树框架中,行为树节点插件按照功能分为 Action(动作节点)、Condition(条件节点)、Control(控制节点) 和 Decorator(装饰节点) 四类。 1.1 动作节点 Action 执行具体的机器人操作或任务,直接与硬件、传感器或外部系统…...

mac:大模型系列测试

0 MAC 前几天经过学生优惠以及国补17K入手了mac studio,然后这两天亲自测试其模型行运用能力如何&#xff0c;是否支持微调、推理速度等能力。下面进入正文。 1 mac 与 unsloth 按照下面的进行安装以及测试&#xff0c;是可以跑通文章里面的代码。训练速度也是很快的。 注意…...

pgsql:还原数据库后出现重复序列导致“more than one owned sequence found“报错问题的解决

问题&#xff1a; pgsql数据库通过备份数据库文件进行还原时&#xff0c;如果表中有自增序列&#xff0c;还原后可能会出现重复的序列&#xff0c;此时若向表中插入新行时会出现“more than one owned sequence found”的报错提示。 点击菜单“其它”-》“序列”&#xff0c;…...

Xcode 16 集成 cocoapods 报错

基于 Xcode 16 新建工程项目&#xff0c;集成 cocoapods 执行 pod init 报错 ### Error RuntimeError - PBXGroup attempted to initialize an object with unknown ISA PBXFileSystemSynchronizedRootGroup from attributes: {"isa">"PBXFileSystemSynchro…...

UE5 音效系统

一.音效管理 音乐一般都是WAV,创建一个背景音乐类SoudClass,一个音效类SoundClass。所有的音乐都分为这两个类。再创建一个总音乐类&#xff0c;将上述两个作为它的子类。 接着我们创建一个音乐混合类SoundMix&#xff0c;将上述三个类翻入其中&#xff0c;通过它管理每个音乐…...

【java】【服务器】线程上下文丢失 是指什么

目录 ■前言 ■正文开始 线程上下文的核心组成部分 为什么会出现上下文丢失&#xff1f; 直观示例说明 为什么上下文如此重要&#xff1f; 解决上下文丢失的关键 总结 ■如果我想在servlet中使用线程&#xff0c;代码应该如何实现 推荐方案&#xff1a;使用 ManagedE…...