之前的跨域 都是 写在一个 filter 中:
@Order(2)
@WebFilter(filterName = "CrossDomainFilter",urlPatterns = "*/
/*")
public class CrossDomainFilter extends OncePerRequestFilter {
@Override
protected void doFilterInternal(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, FilterChain filterChain) throws ServletException, IOException {
setOrigin(httpServletRequest,httpServletResponse,filterChain);
filterChain.doFilter(httpServletRequest, httpServletResponse);
}
*/
/**
* 设置Access-Control-Allow-Origin消息头
* @param request
* @param response
* @param filterChain
* @throws ServletException
* @throws IOException
*//*
public static void setOrigin(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException{
System.out.println("----------");
System.out.println("Origin:"+request.getHeader("Origin"));
System.out.println("----------");
String headerOrigin = request.getHeader("origin");
// response.setContentType("application/json;charset=UTF-8");
response.setHeader("Content-type", "application/json;charset=UTF-8");
if(headerOrigin != null){
response.setHeader("Access-Control-Allow-Origin",headerOrigin);
}
response.setHeader("Access-Control-Expose-Headers","page, per_page,status,total_count");
response.setHeader("Access-Control-Allow-Credentials", "true");
response.setHeader("Access-Control-Allow-Headers",request.getHeader("Access-Control-Request-Headers"));
System.out.println(request.getHeader("Access-Control-Request-Headers"));
response.setHeader("Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE,PUT");
response.setHeader("XDomainRequestAllowed","1");
}
}
然后发现这样写 ,当前端传的content-type是 application/json 的时候,会出现 options method 400 错误 。然后 接口调用不了。
去官网看了下 发现 spring 官网的推荐 是这样写:
@Configuration
@EnableWebMvc
//@EnableAspectJAutoProxy(proxyTargetClass = true)
public class WebConfig implements WebMvcConfigurer {
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/**").allowedOrigins("*")
.allowedMethods("*").allowCredentials(false).exposedHeaders("status")
.maxAge(30*1000);
}
@Bean
public RequestMappingHandlerAdapter requestMappingHandlerAdapter() {
RequestMappingHandlerAdapter adapter = new RequestMappingHandlerAdapter();
// @ResponseBody注解靠HttpMessageConverter解析
List<HttpMessageConverter<?>> converters = adapter.getMessageConverters();
Iterator<HttpMessageConverter<?>> iterator = converters.iterator();
while (iterator.hasNext()) {
HttpMessageConverter<?> converter = iterator.next();
if (converter instanceof StringHttpMessageConverter) { // 移除默认编码为ISO8859-1的字符串解析器
iterator.remove();
}
}
converters.add(new StringHttpMessageConverter(Charset.forName("UTF-8"))); // 字符串才使用UTF-8解析
converters.add(new MappingJackson2HttpMessageConverter()); // 解析json
adapter.setMessageConverters(converters);
return adapter;
}
@Bean
public static PropertySourcesPlaceholderConfigurer propertyConfigIn() {
return new PropertySourcesPlaceholderConfigurer();
}
}
然后 琢磨了一下 发现 在原来的 filter 的 基础上也可以这样加上一个判断实现:
if ("OPTIONS".equals(httpServletRequest.getMethod())) {
try {
httpServletResponse.getWriter().print("OK");
httpServletResponse.getWriter().flush();
} catch (IOException e) {
e.printStackTrace();
}
} else {
filterChain.doFilter(httpServletRequest, httpServletResponse);
}
PS:参考文档 https://spring.io/blog/2015/06/08/cors-support-in-spring-framework#global-cors-configuration