原创文章,转载请注明
之前调整架构,一直忘了解决跨域问题。趁此机会,总结一下跨域的解决方案。
跨域的解决方案可大致分为客户端,服务端。客户端之间的跨域可以通过写脚本,客户端与服务端的跨域,比如ajax请求的跨域,最好是通过服务端的解决方案。这样对客户端透明。不需要额外的编码,而且这种方式是合理的,因为客户端的解决方案说的不好听一点都是通过漏洞进行解决的。
一、客户端
1、window.name
该属性很特别,通过iframe加载其他页面时,该值为被加载页面的值。比如页面A通过iframe加载页面B,页面B中window.name={page:b},那么我们在A页面的iframe中获得的值iframe.contentWindow.name为{page:b}。
需要注意一点,该属性需要域名相同才能访问,因此在远程页面被加载后需要代理会原始域iframe.contentWindow.location=页面A
如果只是客户端对客户端进行跨域,那么该方法还是可以的。简单,安全。
2、利用src标签
src是可以跨域的,不然你如何从其他域加载js,那么我们也可以利用src标签进行数据传递
方法一:动态创建script
利用js动态创建script,数据存在script之中。
如果只是客户端对客户端,并且数据为静态数据,那么该方法也是可以的。
方法二:jsonp
可能很多人喜欢用jsonp,其实jsonp的原理就是通过src标签,并不是xhr方式。
如果只是客户端对客户端,并且数据为静态数据,那么该方法也是可以的。
如果想用它来解决客户端对服务端的跨域,绝对不要用。
有几个问题:1、jsonp和json的结构是有略微差异的,因此服务端的代码需要修改。
2、jsonp是利用src标签实现,因此不能设置request头信息。因此无法通过request头信息进行一些验证。
3、jsonp是利用src标签实现,因此不支持post,put,delete,只支持get
二、服务端
其实服务端的解决方案是最合理的,方法是合理的设置response头信息。主要的有Access-Control-Allow-Origin,Access-Control-Allow-Methods
Access-Control-Allow-Origin表示允许的请求方域名
Access-Control-Allow-Methods表示允许的请求方式
1、filter
在filter中进行合理的response头信息配置
2、spring4
加上@CrossOrigin注解
三、例子
最后举一个例子,在spring-boot中,通过filter进行跨域设置。推荐一个第三方的filter实现,可以直接用
<dependency>
<groupId>com.thetransactioncompany</groupId>
<artifactId>java-property-utils</artifactId>
<version>1.9</version>
</dependency>
<dependency>
<groupId>com.thetransactioncompany</groupId>
<artifactId>cors-filter</artifactId>
<version>1.7</version>
</dependency>
然后配置该filter即可
@Bean
public FilterRegistrationBean filterRegistrationBean() {
FilterRegistrationBean registrationBean = new FilterRegistrationBean();
CORSFilter corsFilter = new CORSFilter ();
registrationBean.setFilter(corsFilter);
//相当于response的头文件属性Access-Control-Allow-Origin
registrationBean.addInitParameter("cors.allowOrigin", "*");
//相当于response的头文件属性Access-Control-Allow-Methods
registrationBean.addInitParameter("cors.supportedMethods", "GET, POST, HEAD, PUT, DELETE");
List<String> urlPatterns = new ArrayList<String>();
urlPatterns.add("/*");
registrationBean.setUrlPatterns(urlPatterns);
return registrationBean;
}