我的编程空间,编程开发者的网络收藏夹
学习永远不晚

SpringBoot实现全局异常处理方法总结

短信预约 -IT技能 免费直播动态提醒
省份

北京

  • 北京
  • 上海
  • 天津
  • 重庆
  • 河北
  • 山东
  • 辽宁
  • 黑龙江
  • 吉林
  • 甘肃
  • 青海
  • 河南
  • 江苏
  • 湖北
  • 湖南
  • 江西
  • 浙江
  • 广东
  • 云南
  • 福建
  • 海南
  • 山西
  • 四川
  • 陕西
  • 贵州
  • 安徽
  • 广西
  • 内蒙
  • 西藏
  • 新疆
  • 宁夏
  • 兵团
手机号立即预约

请填写图片验证码后获取短信验证码

看不清楚,换张图片

免费获取短信验证码

SpringBoot实现全局异常处理方法总结

在项目开发中出现异常时很平常不过的事情,我们处理异常也有很多种方式,可能如下:

public int div(int a ,int b){
        int c=0;
        try{
           c=a/b;
        }catch (Exception ex){
            ex.printStackTrace();
        }
        return  c;
    }

如果我们这样处理异常,代码中就会出现特别多的异常处理模块,这样代码就会变得可读性非常差,而且业务模块逻辑会夹杂特别多的非业务逻辑。但是在项目开发的过程中我们应该将主要精力放在业务模块,除了必要的异常处理模块最好不要再包含其他无关紧要的代码。那么我们如何处理项目中无处不在的异常呢?这就引出了我们要介绍的全局异常处理方法,主要有两种种方式:

HandlerExceptionResolver。

@ControllerAdvice+@ExceptionHandler 今天我们主要介绍一下@ControllerAdvice+@ExceptionHandler模式处理全局异常。

全局异常处理

首先我们先介绍一下@ControllerAdvice和@ExceptionHandler

@ControllerAdvice注解: 他是一个比较特殊的@Component,用于定义全局异常处理类作用在所有的@Controller类型的接口上。

@ExceptionHandler注解: 用于声明处理异常的方法。

配置全局异常

@ControllerAdvice+@ExceptionHandler只要设计得当,就不用再在Controller使用trg-catch了!下面我们先写介绍一个Controller层全局异常处理类。

@ControllerAdvice
public class GlobalExceptionHandler {
   @ResponseBody
    @ExceptionHandler(Exception.class)
    public CommonResult exceptionHandler(HttpServletRequest request, Exception exception) throws Exception {    
        Map<String, Object> result = new HashMap<>(3);
        String message =exception.getMessage()+request.getRequestURL().toString();
        return CommonResult.failed(message);
    }
}

注:@ResponseBody的作用其实是将java对象转为json格式的数据。然后到这里为止,一个简单的全局异常处理解决方式就完成了,这只是一个简单的异常处理方式,远远不能达到完整项目中全局异常处理的方案。

全局异常处理的升级

我们项目中业务处理,可以通过自定义的异常知道哪一个模块发生异常,并且不同的业务模块也有不同的异常处理方式,这也方便我们做扩展

public class ServiceException extends RuntimeException {
    private IErrorCode errorCode;
    public ServiceException(IErrorCode errorCode) {
        super(errorCode.getMessage());
        this.errorCode = errorCode;
    }
    public ServiceException(String message) {
        super(message);
    }
    public ServiceException(Throwable cause) {
        super(cause);
    }
    public ServiceException(String message, Throwable cause) {
        super(message, cause);
    }
    public IErrorCode getErrorCode() {
        return errorCode;
    }
}

加入自定义异常处理

@ControllerAdvice
public class GlobalExceptionHandler {
    
    @ResponseBody
    @ExceptionHandler(value = ServiceException.class)
    public CommonResult handle(ServiceException e) {
        if (e.getErrorCode() != null) {
            return CommonResult.failed(e.getErrorCode());
        }
        return CommonResult.failed(e.getMessage());
    }
    
    @ResponseBody
    @ExceptionHandler(Exception.class)
    public CommonResult exceptionHandler(HttpServletRequest request, Exception exception) throws Exception {
     
        Map<String, Object> result = new HashMap<>(3);
        String message =exception.getMessage()+request.getRequestURL().toString();
        return CommonResult.failed(message);
    }
 
}

处理 Controller 数据绑定、数据校验的异常

在用户登录Model字段上注解数据校验规则。

@Data
@EqualsAndHashCode(callSuper = false)
public class UserLoginParam {
    @NotEmpty
    private String username;
    @NotEmpty
    private String password;
}

SpringBoot中可以使用@Validated + @RequestBody注解方式实现数据绑定和数据校验。例如登录方式为:

@ApiOperation(value = "登录以后返回token")
    @RequestMapping(value = "/login", method = RequestMethod.POST)
    @ResponseBody
    public CommonResult login(@Validated @RequestBody UmsAdminLoginParam umsAdminLoginParam) {
        String token = adminService.login(umsAdminLoginParam.getUsername(), umsAdminLoginParam.getPassword());
        if (token == null) {
            return CommonResult.validateFailed("用户名或密码错误");
        }
        Map<String, String> tokenMap = new HashMap<>();
        tokenMap.put("token", token);
        tokenMap.put("tokenHead", tokenHead);
        return CommonResult.success(tokenMap);
    }

如果数据校验不对数据抛出的异常为MethodArgumentNotValidException,所以我们可以在全局异常处理类中添加对MethodArgumentNotValidException异常的处理声明,就可以实现全局处理数据校验和绑定的异常了,实现如下:

@ResponseBody
    @ExceptionHandler(value = MethodArgumentNotValidException.class)
    public CommonResult handleValidException(MethodArgumentNotValidException e) {
        BindingResult bindingResult = e.getBindingResult();
        String message = null;
        if (bindingResult.hasErrors()) {
            FieldError fieldError = bindingResult.getFieldError();
            if (fieldError != null) {
                message = fieldError.getField()+fieldError.getDefaultMessage();
            }
        }
        return CommonResult.validateFailed(message);
    }

通过上面介绍的未知异常、数据校验和自定义全局异常所有的Controller层的异常处理方式全部都集中到了GlobalExceptionHandler类中,那么我们在Controller类中就不再需要收到记录错误了。

GlobalExceptionHandler全部代码

@ControllerAdvice
public class GlobalExceptionHandler {
    @ResponseBody
    @ExceptionHandler(value = ApiException.class)
    public CommonResult handle(ApiException e) {
        if (e.getErrorCode() != null) {
            return CommonResult.failed(e.getErrorCode());
        }
        return CommonResult.failed(e.getMessage());
    }
    @ResponseBody
    @ExceptionHandler(Exception.class)
    public CommonResult exceptionHandler(HttpServletRequest request, Exception exception) throws Exception {
        Map<String, Object> result = new HashMap<>(3);
        String message =exception.getMessage()+request.getRequestURL().toString();
        return CommonResult.failed(message);
       // return result;
    }
    @ResponseBody
    @ExceptionHandler(value = MethodArgumentNotValidException.class)
    public CommonResult handleValidException(MethodArgumentNotValidException e) {
        BindingResult bindingResult = e.getBindingResult();
        String message = null;
        if (bindingResult.hasErrors()) {
            FieldError fieldError = bindingResult.getFieldError();
            if (fieldError != null) {
                message = fieldError.getField()+fieldError.getDefaultMessage();
            }
        }
        return CommonResult.validateFailed(message);
    }
}

总结

今天主要讲解了@ControllerAdvice+@ExceptionHandler进行统一的在Controller层上的全局异常处理。

到此这篇关于SpringBoot实现全局异常处理方法总结的文章就介绍到这了,更多相关SpringBoot全局异常处理内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

SpringBoot实现全局异常处理方法总结

下载Word文档到电脑,方便收藏和打印~

下载Word文档

猜你喜欢

如何在SpringBoot中实现全局异常处理方式

如何在SpringBoot中实现全局异常处理方式?很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。springboot是什么springboot一种全新的编程规范,
2023-06-14

springboot全局异常处理的方法是什么

在Spring Boot中,可以使用`@ControllerAdvice`和`@ExceptionHandler`注解来实现全局异常处理。1. 创建一个全局异常处理类,使用`@ControllerAdvice`注解标记。该类可以捕获所有Co
2023-10-07

Java中如何实现Springboot全局异常处理

这篇文章主要为大家展示了“Java中如何实现Springboot全局异常处理”,内容简而易懂,条理清晰,希望能够帮助大家解决疑惑,下面让小编带领大家一起研究并学习一下“Java中如何实现Springboot全局异常处理”这篇文章吧。一、思路
2023-06-25

springboot全局异常处理详解

一、单个controller范围的异常处理package com.xxx.secondboot.web;import org.springframework.web.bind.annotation.ExceptionHandler;impo
2023-05-31

SpringBoot全局异常处理方式是什么

这篇文章主要讲解了“SpringBoot全局异常处理方式是什么”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“SpringBoot全局异常处理方式是什么”吧!SpringBoot全局异常处理为
2023-06-25

springboot如何实现全局异常处理及自定义异常类

这篇文章主要介绍springboot如何实现全局异常处理及自定义异常类,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!全局异常处理及自定义异常类全局异常处理定义一个处理类,使用@ControllerAdvice注解。@
2023-06-29

Python异常及处理方法总结

调试Python程序时,经常会报出一些异常,异常的原因一方面可能是写程序时由于疏忽或者考虑不全造成了错误,这时就需要根据异常Traceback到出错点,进行分析改正;另一方面,有些异常是不可避免的,但我们可以对异常进行捕获处理,防止程序终止
2023-01-31

go怎么实现全局异常处理

要实现Go语言的全局异常处理,可以使用defer和recover来捕获和处理panic异常。在Go语言中,defer语句会在函数结束之前执行,而recover函数用于捕获panic异常,并返回panic的值。结合这两个关键字,可以在顶层函
2023-10-20

编程热搜

  • Python 学习之路 - Python
    一、安装Python34Windows在Python官网(https://www.python.org/downloads/)下载安装包并安装。Python的默认安装路径是:C:\Python34配置环境变量:【右键计算机】--》【属性】-
    Python 学习之路 - Python
  • chatgpt的中文全称是什么
    chatgpt的中文全称是生成型预训练变换模型。ChatGPT是什么ChatGPT是美国人工智能研究实验室OpenAI开发的一种全新聊天机器人模型,它能够通过学习和理解人类的语言来进行对话,还能根据聊天的上下文进行互动,并协助人类完成一系列
    chatgpt的中文全称是什么
  • C/C++中extern函数使用详解
  • C/C++可变参数的使用
    可变参数的使用方法远远不止以下几种,不过在C,C++中使用可变参数时要小心,在使用printf()等函数时传入的参数个数一定不能比前面的格式化字符串中的’%’符号个数少,否则会产生访问越界,运气不好的话还会导致程序崩溃
    C/C++可变参数的使用
  • css样式文件该放在哪里
  • php中数组下标必须是连续的吗
  • Python 3 教程
    Python 3 教程 Python 的 3.0 版本,常被称为 Python 3000,或简称 Py3k。相对于 Python 的早期版本,这是一个较大的升级。为了不带入过多的累赘,Python 3.0 在设计的时候没有考虑向下兼容。 Python
    Python 3 教程
  • Python pip包管理
    一、前言    在Python中, 安装第三方模块是通过 setuptools 这个工具完成的。 Python有两个封装了 setuptools的包管理工具: easy_install  和  pip , 目前官方推荐使用 pip。    
    Python pip包管理
  • ubuntu如何重新编译内核
  • 改善Java代码之慎用java动态编译

目录