【转载】Springboot 2.3.5 前后端分离项目中使用拦截器获取不到token或者token为空的问题(OPTION请求被拦截问题)

参考

  1. 前后端分离,SpringBoot拦截器中,获取的请求头token为NULL问题解决

  2. 为什么出现OPTIONS?SpringBoot接口跨域解决方案

前言

  • 项目是前后端分离的,并且springboot也配置了跨域功能。

  • 但是配置了JWT功能、以及验证器验证之后却出现了获取不到jwt的问题。获取参数为 null。并且全局异常拦截失效,前端响应为cors跨域问题获取不到数据。

  • 使用postman可以正常请求并获取数据,考虑到是不是因为自己header中的jwt字段不是标准的header字段,尝试放到Authorization中也是null,并且全局拦截也是失效的。

  • 又考虑到是不是因为cors配置加载于拦截器之后,又在拦截器里面配置响应以及header允许cors,一久无效。

  • 最后看到《前后端分离,SpringBoot拦截器中,获取的请求头token为NULL问题解决》这篇文章才得以解决,前端在请求的时候会发送一个OPTION请求来验证本次请求是否安全,但是springboot的拦截器会拦截所有请求。因为第一次是OPTION没有携带JWT,所以验证失败导致一连串的问题。

  • Edge、Google浏览器的开发者工具中不显示OPTION请求(可以通过配置显示)。

  • FireFox浏览器默认支持显示。FireFox YYDS

正文

  • 在JWT拦截器方法的最前端添加判断是否是OPTIONS请求,如果是就返回TRUE
if (HttpMethod.OPTIONS.toString().equals(request.getMethod())) {
		return true;
}
  • 完整拦截器代码

/**
 * @Author 夏秋初
 * @Date 2021/8/22 16:56
 *  * 异常有很多种,空指针异常也要单独捕获 https://blog.csdn.net/leilei1366615/article/details/104052919
 *  * 拦截器异常在全局异常加载器前面,所以拦截不到 https://blog.csdn.net/qq_40058629/article/details/112857305
 */
@Component
public class JWTAdminInterceptor extends HandlerInterceptorAdapter {

    @Value("${admin.login.account}")
    private String account;

    @Override
    public  boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws JwtAuthExceptionHandler {
        /**
         * 前后端分离有时候会有两次请求,第一次为OPTIONS请求,默认会拦截所有请求,但是第一次请求又获取不到jwt,所以会出错。
         * https://www.cnblogs.com/lyh233/p/14472245.html
         */
        if (HttpMethod.OPTIONS.toString().equals(request.getMethod())) {
            return true;
        }
        // 因为jwt还会有其他错误,不去详细拦截,统一的 Exception 处理
        try {
            String jwt = request.getHeader("Authorization");
            if("".equals(jwt) || jwt == null){
                throw new JwtAuthExceptionHandler();
            }
            DecodedJWT decodedJWT = JwtUtils.decodeJWT(jwt);
            if(!decodedJWT.getClaim("account").asString().equals(account)){
                throw new JwtAuthExceptionHandler();
            }
        }catch (JWTDecodeException e){
            throw new JwtAuthExceptionHandler();
        }
        return true;
    }
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) {
        //
//        System.out.println("JWT 执行完了");
    }


    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) {
//        System.out.println("我获取到了一个返回的结果:"+response);
//        System.out.println("请求结束了");
    }
}


posted @   夏秋初  阅读(3473)  评论(2编辑  收藏  举报
编辑推荐:
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
阅读排行:
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?
点击右上角即可分享
微信分享提示