对于web框架中的跨域问题是一个很是广泛的问题,常见的解决方案也有不少,如:jsonp、cros、websocket等。下面是最近处理springmvc中使用cors解决跨域问题的一些总结。web
具体实现不在详细描述,基本原理利用filter拦截到全部请求,而后进行跨域设置。spring
实现代码json
public class WeCrosInterceptor implements HandlerInterceptor { public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { if (request.getHeader(HttpHeaders.ORIGIN) != null) { response.addHeader("Access-Control-Allow-Origin", "*"); response.addHeader("Access-Control-Allow-Credentials", "true"); response.addHeader("Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE, PUT, HEAD"); response.addHeader("Access-Control-Allow-Headers", "Content-Type"); response.addHeader("Access-Control-Max-Age", "3600"); } return true; } public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception { } public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception { } }
配置api
<mvc:interceptors> <mvc:interceptor> <mvc:mapping path="/**/*"/> <bean class="com.***.interceptor.WeCrosInterceptor" /> </mvc:interceptor> </mvc:interceptors>
注意:若是系统中有其余拦截器,要将该拦截器放在第一个。跨域
可注解在方法上,也可注解在类上websocket
示例mvc
@CrossOrigin(origins = "http://www.zhihu.com") @RequestMapping(value = "/allProductions", method = RequestMethod.GET) public Result getAllOldProductions() { }
全部跨域请求均可以访问app
<mvc:cors> <mvc:mapping path="/**" /> </mvc:cors>
细粒度的配置cors
<mvc:cors> <mvc:mapping path="/api/**" allowed-origins="http://domain1.com, http://domain2.com" allowed-methods="GET, PUT" allowed-headers="header1, header2, header3" exposed-headers="header1, header2" allow-credentials="false" max-age="123" /> <mvc:mapping path="/resources/**" allowed-origins="http://domain1.com" /> </mvc:cors>
以上两种方式在正常使用<mvc:annotation-driven 加载状况下彻底能够知足需求。框架
若是重写了RequestMappingHandlerMapping,就须要单独配置,此时会发现全局的xml配置没有做用了,具体缘由是没有使用springmvc框架解析的跨域配置最终是注入给RequestMappingHandlerMapping这个类的对象的,重写后的mapping对象不会被注入,怎么解决这个问题呢?filter
、拦截器均可以解决,可是都用了4.2的版本还要额外配置是否是太low了,通过查看源码,发现AbstractHandlerMapping有个setCorsConfigurations方法是用来设置跨域配置的,下面最终配置:
<bean name='handlerMapping' class="com.we.core.web.view.WeRequestMappingHandlerMapping"> <property name="corsConfigurations"> <map> <entry key="/**"> <bean class="org.springframework.web.cors.CorsConfiguration"> <property name="allowedMethods" value="GET,POST,OPTIONS"/> <property name="allowedOrigins" value="*"/> <property name="allowedHeaders" value="*"/> <property name="allowCredentials" value="true"/> <property name="maxAge" value="1800"/> </bean> </entry> </map> </property> </bean>
无需增长多余配置类,完美解决问题。