首页 > 解决方案 > Spring:CrossOrigin 不与 ResponseEntity 一起使用

问题描述

关于在春季启用有很多问题,CORS但似乎并非所有这些问题都有有效的答案,或者接受的答案对我的情况不起作用。所以我正在创建这个问题,看看是否有人可以帮助我。

我一直在尝试启用CORS对我的 API 响应的响应,我尝试向@CrossOrigin方法添加注释,甚至添加到类控制器以使其工作,但是这两种方法都不起作用。我还尝试Bean在应用程序引导配置或实现的类配置上创建一个,WebMvcConfigurer但最终结果仍然相同。

起初我认为这可能是因为我正在返回带有ResponseEntity实例的响应,而不是像大多数示例显示的那样仅返回实际值,但即使替换了我返回值的方式,结果也是一样的。CORS响应中没有附加任何标头,即使在OPTIONS请求它时在 http 方法中也没有,它只响应没有Cross Origin Allow.

因此,为了展示我一直在努力实现的目标CORS,这是我的一RestController堂课:

package com.vod.cloudservice.controller;

import com.vod.cloudservice.entity.Series;
import com.vod.cloudservice.service.SeriesService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

import javax.validation.Valid;
import java.util.List;

@RestController
@RequestMapping("/series")
public class SeriesController {
    @Autowired
    SeriesService seriesService;

    @CrossOrigin
    @GetMapping
    public ResponseEntity<List<Series>> getSeriesList() {
        List<Series> seriesList = this.seriesService.findAll();

        return new ResponseEntity<>(seriesList, HttpStatus.OK);
    }

    // More resources ahead.
}

单独这样做是行不通的。所以我创建了一个这样的配置类:

package com.vod.cloudservice.config;

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@Configuration
@EnableWebMvc
public class WebConfig implements WebMvcConfigurer {
    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry.addMapping("/**")
            .allowedOrigins("*")
            .allowedMethods("GET", "POST", "PUT", "DELETE", "OPTIONS")
            .allowedHeaders("Content-Type")
            .maxAge(3600);
    }
}

即使这样,响应仍然相同。如果它有助于了解对我想要CORS启用的控制器的完整请求,请求是这样完成的:

GET: http://localhost:8080/series

我可能通过拦截响应并手动添加标头来解决此问题,但我希望更好地控制响应,例如我想在一个类上处理 X 数量的允许方法。

标签: javaspringcors

解决方案


我对此事进行了更多研究,我发现RestController注释使响应标头在CORS处理注释时已经写入,就好像CORS处理程序无法写入已经发送的内容一样。

所以在我的例子中,我创建了一个过滤器类,它将CORS在响应中添加标题,如下所示:

public class HttpFilter extends OncePerRequestFilter {
    @Override
    protected void doFilterInternal(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, FilterChain filterChain) throws ServletException, IOException {
        httpServletResponse.setHeader("Access-Control-Allow-Origin", "*");
        httpServletResponse.setHeader("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
        httpServletResponse.setHeader("Access-Control-Allow-Headers", "Content-Type");
        httpServletResponse.setHeader("Access-Control-Max-Age", "3600");

        filterChain.doFilter(httpServletRequest, httpServletResponse);
    }
}

在此之后,我只需要将过滤器注册为 aFilterBean然后它就可以工作了,虽然不是我最初想要的方式,但它至少给了我工作所需的结果。


推荐阅读