springboot 使用过滤器解决跨域问题和无法获取到 header 中值的问题

最近项目后台当中会被微信小程序端和 web 端同时请求,web 端是前后分离的,所以可能存在跨域问题,而微信小程序端则不存在跨域问题。所以就要求两端请求后台时,header 同时放入一个来源 source,后端过滤器中再去区分进行相关配置。

一、过滤器解决跨域问题代码


package com.wxw.upload.filter;

import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * @author wuxiongwei
 * @date 2020/6/5 14:59
 * @Description
 */
 @Component
public class Filter implements javax.servlet.Filter {
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {

    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;

        String source = request.getHeader("source");// 从 http 请求头中取出来源

       
        //小程序端
        if("1".equals(source)){
            //todo
        }
        //web 端
        if("2".equals(source)){
            response.setHeader("Access-Control-Allow-Origin","*");
            response.setHeader("Access-Control-Allow-Credentials", "true");
            response.setHeader("Access-Control-Allow-Methods", "POST, GET, PATCH, DELETE, PUT");
            response.setHeader("Access-Control-Max-Age", "3600");
            response.setHeader("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
        }
        
		filterChain.doFilter(request, servletResponse);
    }

    @Override
    public void destroy() {

    }
}


加了过滤器这段代码之后,我们的跨域问题还是无法解决,请继续往下看

二、解决 web 端处理跨域请求时,无法获取到 header 中值的问题

原因是这样的,对于【复杂的】跨域ajax请求,请求方思路是这样的:先发送一个 OPTIONS 请求,确认是可以请求的,之后才发送我们真正的 get 或者 post 等我们在 ajax 中定义的请求;第一次 OPTIONS 请求,headers 是不会带过来的,所以过滤器中是要跳过这种请求的。处理方式如下

		  //放行 options 的请求
        if ("OPTIONS".equals(request.getMethod())) {
            filterChain.doFilter(request, servletResponse);
        }

当我们如果没有加上面这段代码的时候,下面这行代码获取出来的值就是 null , 我们也就无法为 web 端设置跨域了

String source = request.getHeader("source");// 从 http 请求头中取出 token 来源

关注公众号查看更多资源
在这里插入图片描述
在这里插入图片描述

在Spring Boot框架中,解决跨域问题可以通过自定义过滤器来实现。下面是一个简单的示例: ```java @Component public class CorsFilter implements Filter { @Override public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException { HttpServletResponse response = (HttpServletResponse) res; HttpServletRequest request = (HttpServletRequest) req; response.setHeader("Access-Control-Allow-Origin", "*"); response.setHeader("Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE, PUT"); response.setHeader("Access-Control-Max-Age", "3600"); response.setHeader("Access-Control-Allow-Headers", "Content-Type, Authorization, Content-Length, X-Requested-With"); if ("OPTIONS".equalsIgnoreCase(request.getMethod())) { response.setStatus(HttpServletResponse.SC_OK); } else { chain.doFilter(req, res); } } @Override public void init(FilterConfig filterConfig) {} @Override public void destroy() {} } ``` 在上面的代码中,我们创建了一个名为"CorsFilter"的过滤器。该过滤器实现了javax.servlet.Filter接口,并覆盖了doFilter方法,用于处理跨域请求。 在doFilter方法中,我们首先将ServletResponse类型的res转换为HttpServletResponse类型的response,将ServletRequest类型的req转换为HttpServletRequest类型的request。然后,我们设置了Access-Control-Allow-Origin、Access-Control-Allow-Methods、Access-Control-Max-Age和Access-Control-Allow-Headers等响应头信息,以允许跨域请求。 最后,我们判断当前请求是否为OPTIONS请求,如果是,我们设置响应状态码为HttpServletResponse.SC_OK,否则我们继续执行过滤器链中的下一个过滤器。 在上面的示例中,我们将"Access-Control-Allow-Origin"设置为"*",表示接受来自任何域名的跨域请求。如果你希望限制跨域请求来源,可以将该值设置为具体的域名。 然后,我们将"Access-Control-Allow-Methods"设置为"POST, GET, OPTIONS, DELETE, PUT",表示接受这些HTTP方法的跨域请求。如果你希望限制跨域请求使用的HTTP方法,可以将该值设置为具体的HTTP方法。 最后,我们设置了"Access-Control-Allow-Headers",表示接受这些自定义请求头的跨域请求。如果你希望限制跨域请求使用的自定义请求头,可以将该值设置为具体的请求头。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值