一般springBoot自带的全局异常捕获机制都是在业务层发生的异常来进行捕获的,因为过滤器的执行顺序是在全局异常机制启动之前执行的,所以一旦过滤器中发生异常,全局异常捕获机制无法使用

现在有一个围魏救赵的思路
在过滤器中try-catch掉需要捕获的异常,然后转发到controller在重新抛出,这样全局异常机制可以起作用,返回自定义信息

举个例子:
SpringSecurity使用过滤器链来实现用户校验,一旦签名出错,过滤器链中抛出响应的异常,我们不想抛出异常,而是返回相关错误信息。此时使用上述思路很容易做到

下面是真实代码:
这是一个过滤器,我们try-catch掉异常,然后转发给相应的controller

public class JWTAuthorizationFilter extends BasicAuthenticationFilter {private static final String LOGIN_URL = "/login";private static String token = null;public JWTAuthorizationFilter(AuthenticationManager authenticationManager) {super(authenticationManager);}@Overrideprotected void doFilterInternal(HttpServletRequest request,HttpServletResponse response,FilterChain chain) throws IOException, ServletException {String tokenHeader = request.getHeader(TokenEnum.TOKEN_HEADER.getValue());// 如果请求头中没有Authorization信息或者是登录接口直接放行了if (tokenHeader == null || !tokenHeader.startsWith(TokenEnum.TOKEN_PREFIX.getValue()) || request.getRequestURL().toString().contains(LOGIN_URL)) {chain.doFilter(request, response);return;}// 如果请求头中有token,则进行解析,并且设置认证信息try {if (JWTAuthorizationFilter.token != null) {refreshToken(token);SecurityContextHolder.getContext().setAuthentication(getAuthentication(token));} else {refreshToken(tokenHeader);SecurityContextHolder.getContext().setAuthentication(getAuthentication(tokenHeader));}} catch (RefreshTokenException | ExpiredJwtException e) {// 异常捕获,发送到expiredJwtExceptionrequest.setAttribute("expiredJwtException", e);//将异常分发到/expiredJwtException控制器request.getRequestDispatcher("/expiredJwtException").forward(request, response);} catch (AccessDeniedException | SignatureException e) {// 异常捕获,发送到signatureExceptionrequest.setAttribute("signatureException", e);//将异常分发到/signatureException控制器request.getRequestDispatcher("/signatureException").forward(request, response);}super.doFilterInternal(request, response, chain);}

异常controller

package com.hongseng.app.controller;import com.hongseng.app.config.exception.RefreshTokenException;
import io.jsonwebtoken.ExpiredJwtException;
import io.jsonwebtoken.security.SignatureException;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;import javax.servlet.http.HttpServletRequest;/*** @program: fire_control* @description:* @author: fbl* @create: 2021-01-18 07:54**/
@RestController
public class JwtExceptionController {/*** 重新抛出异常*/@RequestMapping("/expiredJwtException")public void expiredJwtException(HttpServletRequest request) throws ExpiredJwtException, RefreshTokenException {if (request.getAttribute("expiredJwtException") instanceof ExpiredJwtException) {throw ((ExpiredJwtException) request.getAttribute("expiredJwtException"));} else {throw new RefreshTokenException();}}@RequestMapping("/signatureException")public void signatureException(HttpServletRequest request) throws SignatureException {throw ((SignatureException) request.getAttribute("signatureException"));}}

然后在使用全局异常机制捕获并返回自定义信息即可

package com.hongseng.app.config.exception;import enums.ErrorCodeEnum;
import io.jsonwebtoken.ExpiredJwtException;
import io.jsonwebtoken.security.SignatureException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import result.Result;/*** @program: fire_control* @description: 处理自定义的业务异常* @author: fbl* @create: 2021-01-15 16:21**/
@ControllerAdvice
public class GlobalExceptionHandler {/*** token过期** @return*/@ExceptionHandler(value = {ExpiredJwtException.class, RefreshTokenException.class})@ResponseBodypublic Result expiredJwtException() {return Result.failure(ErrorCodeEnum.SYS_ERR_TOKEN_EXPIRED);}/*** token错误** @return*/@ExceptionHandler(value = SignatureException.class)@ResponseBodypublic Result signatureException() {return Result.failure(ErrorCodeEnum.SYS_ERR_TOKEN_SIGNATURE);}}

springBoot 在过滤器中如何捕获抛出的异常并自定义返回信息相关推荐

  1. java中主函数抛出的异常怎么解决_java – 从递归函数中抛出异常

    我为一个更大的应用程序构建了一个库/模块,它从函数中抛出异常.如果找不到文件或文件包含错误格式,则抛出Exeption. 该方法看起来像: Shape parse(String path) throw ...

  2. java 异常 不抛_java中的不抛出的异常是什么

    RuntimeException与其子类和错误(Error)不是必须要捕获或抛出. Java异常Throwable分为两类:Error和Exception,Error类是错误,程序本身不能处理的. E ...

  3. JSqlParser4.3版本无法解析mysql中JSON_OBJECT函数抛出ParseException异常

    2022年3月31日,找了一下午的bug bug 已经提交issues,详情请看GitHub,地址:https://github.com/JSQLParser/JSqlParser/issues/15 ...

  4. java抛异常 代替返回_请问业务层方法是抛出一个异常好还是返回一个结果更好...

    @Override public Response checkUserToken(long uid, String accessToken, String deviceToken){ Response ...

  5. java 抛出指定异常信息_java 抛出异常处理的方法

    java 抛出异常处理的方法 为了避免调用的人不知道有异常,才抛出异常的,所以是谁掉用的久在哪里处理.说的对吗 对. 1.throws关键字通常被应用在声明方法时,用来指定可能抛出的异常.多个异常可以 ...

  6. Java中主线程如何捕获子线程抛出的异常

    Java中主线程如何捕获子线程抛出的异常 参考文章: (1)Java中主线程如何捕获子线程抛出的异常 (2)https://www.cnblogs.com/jpfss/p/10272885.html ...

  7. java 异常 不抛,java中不捕获或抛出的异常

    java中不捕获或抛出的异常 发布时间:2020-06-25 14:29:16 来源:亿速云 阅读:137 作者:Leah 这期内容当中小编将会给大家带来有关java中不捕获或抛出的异常,文章内容丰富 ...

  8. 【Java 多线程】Java中主线程如何捕获子线程抛出的异常

    首先明确线程代码的边界.其实很简单,Runnable接口的run方法所界定的边界就可以看作是线程代码的边界.Runnable接口中run方法原型如下: public void run(); 而所有的具 ...

  9. [转]Java中主线程如何捕获子线程抛出的异常

    这么来看待这个问题.首先明确线程代码的边界.其实很简单,Runnable接口的run方法所界定的边界就可以看作是线程代码的边界.Runnable接口中run方法原型如下:     <<   ...

最新文章

  1. 优化:梯度下降法、牛顿法、共轭梯度法
  2. 优化mysql服务器硬件包括_MySQL优化之一:服务器硬件和操作系统
  3. java redis设置过期时间_Redis的一些核心原理
  4. NOIP模拟题——dun
  5. 关于wcf三大工具的使用(wsdl.exe svcutil.exe disco.exe)
  6. Context node attribute expand trouble shooting guide
  7. java version 和javac版本不一致_解决linux下javac -version和java -version版本显示不一致...
  8. 页面访问的常见错误码解析
  9. 随机森林需要分训练集测试集吗_讨论记录用随机森林对生存数据降维,筛选signature...
  10. haproxy5-ssl
  11. 资深面试官解答:大厂月薪过20K的测试工程师,都需要满足哪些要求?
  12. 学习J2ME需要掌握的七种技术
  13. SCSA网络安全------数据传输安全-------广域网加速解决方案
  14. 算法竞赛入门经典经典例题及习题题解
  15. Context.getDir
  16. 京东静态网页设计案例(1)
  17. STM32基础11--模数转换(ADC)
  18. Linux下文件备份和同步的工具软件
  19. 网络系统高可用是几个9?
  20. ftp文件缓存服务器,ftp服务器上的缓存在哪

热门文章

  1. 人工智能中的图灵测试
  2. intoduction linux services
  3. Reids实战——优惠券秒杀(全局唯一ID生成策略)
  4. 【JS逆向】知乎请求头 _x-zes-96 webpack还原
  5. 半导体物理实验 06 - | PN结正向压降的温度特性
  6. 51单片机上连YL69土壤湿度传感器获取的数据在LCD上显示出来
  7. 一年期早过:Windows 10免费升级漏洞仍然敞开着
  8. Unicode编码的实现
  9. 栈和队列---算法题目
  10. 悟空CRM(基于jfinal+vue+ElementUI的前后端分离的开源CRM系统)