spring boot 项目在自定义Filter中抛出异常捕获不到的处理方法

5 篇文章 0 订阅
4 篇文章 0 订阅

一、序言

全局异常处理@RestControllerAdvice并非可以解决所有异常返回信息,
像是在Filter中的异常,Advice就失效了,就需要从别的方面进行入手

二、解决问题

1、代码实现

添加下方这个类,即可完美解决问题,其中ResponseEntity为spring自带类,Result为自定义返回前端实体类
请重点注意,我这里是采用@Override,也就是重写了error方法,也只有这样才能实现效果

import com.dely.common.entity.Result;
import org.springframework.boot.autoconfigure.web.ErrorProperties;
import org.springframework.boot.autoconfigure.web.servlet.error.BasicErrorController;
import org.springframework.boot.web.servlet.error.DefaultErrorAttributes;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.servlet.http.HttpServletRequest;
import java.util.Map;

/**
 * @author ruiMin
 * @date 2020/2/20 21:55
 */
@RestController
public class ErrorController extends BasicErrorController {

	/**
	* 必须实现的一个构造方法
	**/
    public ErrorController() {
        super(new DefaultErrorAttributes(), new ErrorProperties());
    }

    /**
     * produces 设置返回的数据类型:application/json
     *
     * @param request 请求
     * @return 自定义的返回实体类
     */
    @Override
    @RequestMapping(produces = {MediaType.APPLICATION_JSON_VALUE})
    public ResponseEntity<Map<String, Object>> error(HttpServletRequest request) {
        Map<String, Object> body = getErrorAttributes(request, isIncludeStackTrace(request, MediaType.ALL));
        HttpStatus status = getStatus(request);
        // 获取错误信息
        String message = body.get("message").toString();

        return new ResponseEntity<>(Result.error(message), status);
    }
}

2、效果

这里就实现了按我自定义的格式发送消息,原效果请看下方原理解析图片
在这里插入图片描述

3、原理解析

其实原理也不复杂,就是,springboot在遇到错误的时候,是由自己的一套错误提示逻辑的,如以下图两种情况,由于我的项目是前后端分离项目,故这里只针对第二种进行重写,我们做的方法,就是继承BasicErrorController,然后重写关于ajax请求的实体信息返回

1)页面访问的形式
在这里插入图片描述
2)ajax接口访问形式
在这里插入图片描述

4、Result类


import com.dely.common.constant.HttpStatus;
import java.util.HashMap;

/**
 * 用于返回成功失败错误的结果信息及状态
 *
 * @author ruiMin
 * @date 2019-09-20 20:18
 */
public class Result extends HashMap<String, Object> {

    /**
     * 状态码
     */
    private String status = "status";
    /**
     * 返回内容
     */
    private String message = "message";
    /**
     * 数据对象
     */
    private String data = "data";


    public Result() {
    }

    /**
     * 初始化一个新创建的 Result 对象
     *
     * @param status
     * @param message
     */
    public Result(Integer status, Object message) {
        this.put(this.status, status);
        this.put(this.message, message);
    }

    /**
     * 初始化一个新创建的 Result 对象
     *
     * @param message
     * @param data
     */
    public Result(Integer status, Object message, Object data) {
        this.put(this.status, status);
        this.put(this.message, message);
        this.put(this.data, data);
    }

    /**
     * 自定义拓展状态消息
     */
    public static Result msg(Integer status, Object msg) {
        return new Result(status, msg, null);
    }

    /**
     * 返回成功消息
     *
     * @return 成功消息
     */
    public static Result success() {
        return Result.success("操作成功");
    }

    /**
     * 返回成功数据
     *
     * @return 成功消息
     */
    public static Result success(Object data) {
        return Result.success("操作成功", data);
    }

    /**
     * 返回成功消息
     *
     * @param msg 返回内容
     * @return 成功消息
     */
    public static Result success(String msg) {
        return Result.success(msg, null);
    }

    /**
     * 返回成功消息
     *
     * @param msg  返回内容
     * @param data 数据对象
     * @return 成功消息
     */
    public static Result success(String msg, Object data) {
        return new Result(HttpStatus.SUCCESS, msg, data);
    }

    /**
     * 返回失败消息
     *
     * @return 失败消息
     */
    public static Result fail() {
        return Result.fail("操作失败");
    }

    /**
     * 返回失败消息
     *
     * @param msg 返回内容
     * @return 失败消息
     */
    public static Result fail(String msg) {
        return Result.fail(msg, null);
    }

    /**
     * 返回失败消息
     *
     * @param msg  返回内容
     * @param data 数据对象
     * @return 失败消息
     */
    public static Result fail(String msg, Object data) {
        return new Result(HttpStatus.FAIL, msg, data);
    }

    /**
     * 特定状态码返回失败信息
     *
     * @param status 状态
     * @param msg    信息
     * @return
     */
    public static Result fail(Integer status, String msg) {
        return new Result(status, msg, null);
    }

    /**
     * 返回错误消息
     *
     * @return 错误消息
     */
    public static Result error() {
        return Result.error("未知异常,请联系管理员");
    }

    /**
     * 返回错误消息
     *
     * @param msg 返回内容
     * @return 错误消息
     */
    public static Result error(String msg) {
        return Result.error(msg, null);
    }

    /**
     * 返回错误消息
     *
     * @param msg  返回内容
     * @param data 数据对象
     * @return 错误消息
     */
    public static Result error(String msg, Object data) {
        return new Result(HttpStatus.ERROR, msg, data);
    }

    /**
     * 特定状态码返回错误信息
     *
     * @param status 状态
     * @param msg    信息
     * @return
     */
    public static Result error(Integer status, String msg) {
        return new Result(status, msg, null);
    }

    @Override
    public Result put(String key, Object value) {
        super.put(key, value);
        return this;
    }

}

  • 5
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
Spring Boot 自定义 Filter 主要分为以下几个步骤: 1. 创建一个类并实现 javax.servlet.Filter 接口; 2. 在类上添加 @Component 注解将其注册为一个 Spring Bean; 3. 重写 Filter 接口的 doFilter 方法,并在其编写过滤逻辑; 4. 在配置类通过 FilterRegistrationBean 对象将自定义 Filter 注册到 Spring Boot 应用。 下面是一个示例代码: ```java @Component public class CustomFilter implements Filter { @Override public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { // 过滤逻辑 chain.doFilter(request, response); } } ``` 在上述代码,我们创建了一个名为 CustomFilter 的类并实现了 Filter 接口。在 doFilter 方法,我们可以编写自己的过滤逻辑。 接下来,在 Spring Boot 的配置类注册自定义 Filter: ```java @Configuration public class WebConfig { @Bean public FilterRegistrationBean<CustomFilter> filterRegistrationBean() { FilterRegistrationBean<CustomFilter> registrationBean = new FilterRegistrationBean<>(); registrationBean.setFilter(new CustomFilter()); registrationBean.addUrlPatterns("/*"); // 设置过滤路径 registrationBean.setName("CustomFilter"); // 设置 Filter 名称 registrationBean.setOrder(1); // 设置 Filter 执行顺序 return registrationBean; } } ``` 在上述代码,我们创建了一个名为 WebConfig 的配置类,并在其创建了一个名为 filterRegistrationBean 的方法,并使用 @Bean 注解将其声明为一个 Spring Bean。在该方法,我们通过 FilterRegistrationBean 对象将自定义 Filter 注册到 Spring Boot 应用,并设置了过滤路径、Filter 名称以及执行顺序。 最后,启动 Spring Boot 应用程序并访问注册了自定义 Filter 的路径,即可看到自定义 Filter 生效的效果。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值