Spring Data Rest 和 Cors [英] Spring Data Rest and Cors

查看:34
本文介绍了Spring Data Rest 和 Cors的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在开发一个带有 Rest 接口和 dart 前端的 Spring Boot 应用程序.

I am developing a Spring Boot application with a Rest interface and a dart fronted.

XMLHttpRequest 确实执行了一个完全正确处理的 OPTIONS 请求.在此之后,发出最终的 GET ("/products") 请求并失败:

The XMLHttpRequest does execute a OPTIONS request which is handled totally correct. After this, the final GET ("/products") request is issued and fails:

请求的资源上不存在Access-Control-Allow-Origin"标头.Origin 'http://localhost:63343' 因此不允许访问.

No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:63343' is therefore not allowed access.

经过一些调试后,我发现了以下内容:AbstractHandlerMapping.corsConfiguration 为除 RepositoryRestHandlerMapping 之外的所有子类填充.在 RepositoryRestHandlerMapping 中,在创建时不存在/设置 corsConfiguration,因此它不会被识别为 cors 路径/资源.
=> 没有附加 CORS 标头
这可能是问题吗?我该如何设置?

After some debugging I have found the following: The AbstractHandlerMapping.corsConfiguration is populated for all Subclasses except RepositoryRestHandlerMapping. In the RepositoryRestHandlerMapping no corsConfiguration is present / set at creation time and so it won't get recognized as cors path / resource.
=> No CORS headers attached
Could that be the problem? How can I set it?

配置类:

@Configuration
public class RestConfiguration extends RepositoryRestMvcConfiguration {

    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry.addMapping("/**").allowCredentials(false).allowedOrigins("*").allowedMethods("PUT", "POST", "GET", "OPTIONS", "DELETE").exposedHeaders("Authorization", "Content-Type");
    }

   ...
}

我什至尝试为每个注释设置 Cors:

I even tried to set the Cors per annotation:

@CrossOrigin( methods = RequestMethod.GET, allowCredentials = "false")
public interface ProductRepository extends CrudRepository<Product, String> {


}

原始请求标头:

GET /products HTTP/1.1
Host: localhost:8080
Connection: keep-alive
Cache-Control: max-age=0
authorization: Basic dXNlcjpwYXNzd29yZA==
User-Agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Ubuntu Chromium/43.0.2357.130 Chrome/43.0.2357.130 Safari/537.36
Content-Type: application/json
Accept: */*
Referer: http://localhost:63343/inventory-web/web/index.html
Accept-Encoding: gzip, deflate, sdch
Accept-Language: de-DE,de;q=0.8,en-US;q=0.6,en;q=0.4

原始响应头:

HTTP/1.1 200 OK
Server: Apache-Coyote/1.1
Content-Type: application/hal+json;charset=UTF-8
Transfer-Encoding: chunked
Date: Thu, 30 Jul 2015 15:58:03 GMT

使用的版本:弹簧靴 1.3.0.M2弹簧 4.2.0.RC2

Versions used: Spring Boot 1.3.0.M2 Spring 4.2.0.RC2

我想念什么?

推荐答案

确实,在 Spring Data REST 2.6 (Ingalls) 之前,只有 Spring MVC 创建的 HandlerMapping 实例 WebMvcConfigurationSupport 和使用 @CrossOrigin 注释的控制器可以识别 CORS.

Indeed, before Spring Data REST 2.6 (Ingalls) only HandlerMapping instances created by Spring MVC WebMvcConfigurationSupport and controllers annotated with @CrossOrigin were CORS aware.

但是现在 DATAREST-573 已经修复,RepositoryRestConfiguration 现在公开了一个 getCorsRegistry() 用于全局设置,并且还识别存储库上的 @CrossOrigin 注释,因此这是推荐的方法.有关具体示例,请参阅 https://stackoverflow.com/a/42403956/1092077 答案.

But now that DATAREST-573 has been fixed, RepositoryRestConfiguration now exposes a getCorsRegistry() for global setup and @CrossOrigin annotations on repositories are also recognized so this is the recommended approach. See https://stackoverflow.com/a/42403956/1092077 answer for concrete examples.

对于必须坚持使用 Spring Data REST 2.5 (Hopper) 或以前版本的人,我认为最好的解决方案是使用基于过滤器的方法.您显然可以使用 Tomcat、Jetty 或 这个,但请注意 Spring Framework 4.2 也提供了一个 CorsFilter 使用与 @CrossOriginaddCorsMappings(CorsRegistry registry) 方法相同的 CORS 处理逻辑.通过传递 UrlBasedCorsConfigurationSource 实例到 CorsFilter 构造函数参数,您可以轻松获得与 Spring 原生 CORS 全局支持一样强大的功能.

For people that have to stick to Spring Data REST 2.5 (Hopper) or previous versions, I think the best solution is to use a filter based approach. You could obviously use Tomcat, Jetty or this one, but be aware that Spring Framework 4.2 also provides a CorsFilter that use the same CORS processing logic that @CrossOrigin and addCorsMappings(CorsRegistry registry) approaches. By passing an UrlBasedCorsConfigurationSource instance to the CorsFilter constructor parameter, you could easily get something as powerful as Spring native CORS global support.

如果您使用的是 Spring Boot(支持 Filter bean),它可能是这样的:

If you are using Spring Boot (which supports Filter beans), it could be something like:

@Configuration
public class RestConfiguration {

    @Bean
    public FilterRegistrationBean corsFilter() {
        UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
        CorsConfiguration config = new CorsConfiguration().applyPermitDefaultValues();
        source.registerCorsConfiguration("/**", config);
        FilterRegistrationBean bean = new FilterRegistrationBean(new CorsFilter(source));
        bean.setOrder(0);
        return bean;
    }
}

这篇关于Spring Data Rest 和 Cors的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆