【发布时间】:2017-02-21 21:52:55
【问题描述】:
我有一个非常简单的例子,我无法开始工作。
我有我的域来模拟我的数据库和我的存储库。
public interface MyTestRepository extends CrudRepository<MyTest, Integer> {
}
我用http://resttesttest.com/ 来测试它。对于 GET 方法,它会毫无问题地返回我的 JSON REST 信息。
我可以查询端点http://localhost:8080/mytest/1 并从数据库中取回 id=1 的信息。
但是,当我尝试使用 DELETE 选项时,问题就出现了。如果我在 http://localhost:8080/mytest/1 上运行 DELETE,我会得到 p>
对预检请求的响应未通过访问控制检查:否 请求中存在“Access-Control-Allow-Origin”标头 资源。因此不允许使用原点“http://resttesttest.com” 使用权。响应的 HTTP 状态代码为 403。
我最初尝试了以下,但发现我无法使用它,因为我使用的是 Spring-data-Rest。 https://jira.spring.io/browse/DATAREST-573
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/**")
.allowedOrigins("*")
.allowedMethods("*")
.allowedHeaders("*")
.allowCredentials(true).maxAge(3600);
}
我搜索了一下,发现了这个。
How to configure CORS in a Spring Boot + Spring Security application?
所以我加了
@Bean
public FilterRegistrationBean corsFilter() {
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
CorsConfiguration config = new CorsConfiguration();
config.setAllowCredentials(true);
config.addAllowedOrigin("*");
config.addAllowedHeader("*");
config.addAllowedMethod("*");
source.registerCorsConfiguration("/**", config);
FilterRegistrationBean bean = new FilterRegistrationBean(new CorsFilter(source));
bean.setOrder(0);
return bean;
}
我也找到了这个帖子。
也尝试了以下代码,但没有成功。
@Bean
public FilterRegistrationBean corsFilter() {
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
CorsConfiguration config = new CorsConfiguration();
config.setAllowCredentials(true);
config.addAllowedOrigin("*");
config.addAllowedHeader("*");
config.addAllowedMethod("OPTIONS");
config.addAllowedMethod("HEAD");
config.addAllowedMethod("GET");
config.addAllowedMethod("PUT");
config.addAllowedMethod("POST");
config.addAllowedMethod("DELETE");
config.addAllowedMethod("PATCH");
source.registerCorsConfiguration("/**", config);
// return new CorsFilter(source);
final FilterRegistrationBean bean = new FilterRegistrationBean(new CorsFilter(source));
bean.setOrder(0);
return bean;
}
我添加了一个 catch all 来测试,它应该允许所有 CORS 明智地通过,但是即使我有“*”,我仍然会不断收到 No 'Access-Control-Allow-Origin'。
此时,我不知道为什么预检请求未通过访问控制检查我缺少什么。
curl 发出删除没有问题。
编辑:
最终找到了确切的解决方案。我不确定我所拥有的和这种方法之间的区别,但这似乎有效。
import org.springframework.stereotype.Component;
import javax.servlet.*;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/**
* Note this is a very simple CORS filter that is wide open.
* This would need to be locked down.
* Source: https://stackoverflow.com/questions/39565438/no-access-control-allow-origin-error-with-spring-restful-hosted-in-pivotal-web
*/
@Component
public class CORSFilter implements Filter {
public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException {
HttpServletResponse response = (HttpServletResponse) res;
response.setHeader("Access-Control-Allow-Origin", "*");
response.setHeader("Access-Control-Allow-Methods", "POST, GET, PUT, OPTIONS, DELETE");
response.setHeader("Access-Control-Max-Age", "3600");
response.setHeader("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
chain.doFilter(req, res);
}
public void init(FilterConfig filterConfig) {}
public void destroy() {}
}
【问题讨论】:
-
在不使用 spring-boot-starter-security 的情况下直接使用 Spring Boot MVC/Rest 时,我必须使用上面的 CORSFIlter 来允许预检 OPTIONS 工作。当我使用 Postman 发送带有 Origin 标头的 OPTIONS 请求时,如果没有过滤器,我会收到 403 Forbidden(如果我关闭 Origin,OPTIONS 会正常工作)。我需要“公共类 CORSFilter 实现过滤器”和“公共类 CORSconfiguration 实现 WebMvcConfigurer”才能使 OPTIONS 正常工作
标签: java spring rest spring-mvc spring-data-rest