I've got an extremely simple example that I can't get to work.
I have my domain that models my database, and my Repository.
public interface MyTestRepository extends CrudRepository<MyTest, Integer> {
}
I used http://resttesttest.com/ to test it. For GET Method's it returns me the JSON REST information without any issue.
I can query the endpoint http://localhost:8080/mytest/1 and I get back the information for id=1 from the database.
However, the problem comes in when I try to use the DELETE option. If I run a DELETE on http://localhost:8080/mytest/1 I get
Response to preflight request doesn't pass access control check: No
'Access-Control-Allow-Origin' header is present on the requested
resource. Origin 'http://resttesttest.com' is therefore not allowed
access. The response had HTTP status code 403.
I initially tried the following, but found out that I can't use it because I'm using 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);
}
I googled around and found this.
How to configure CORS in a Spring Boot + Spring Security application?
So I added
@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;
}
I also found this thread.
Spring Data Rest and Cors
and tried the following code as well, but no luck.
@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;
}
I added a catch all to test which should allow everything CORS wise to pass, however I still keep getting the No 'Access-Control-Allow-Origin' even though I have "*".
At this point I have no idea what I am missing on why the preflight request doesn't pass access control check.
curl has no problem issuing the delete.
Edit:
Ended up finding the exact solution. I'm not sure of the differences between what I have and this method, but this seems to work.
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() {}
}
See Question&Answers more detail:
os