跨域服务调用基本概念及解决方法
综述
出于防范跨站脚本攻击的同源安全策略,浏览器禁止客户端脚本(如Javascript)对不同域名的服务进行跨域调用。
同源策略(Same Origin)中的源有着严格的定义,参见RFC6454,第4章节。一般而言,Origin由{protocol, host, port}三部分组成。
下面是同源检查的一些实例:
可能有点意外的是,一般我们会认为不同的子域名应该被当做同域名,是安全的调用,但实际上浏览器同源策略甚至禁止了不同子域名和端口的服务之间的调用。
有时候上述限制过于严格,为了在两个不同Origin的网页(服务)之间进行通讯,我们可以采用如下的一些技术方法:
1、服务代理模式即在web服务器上封装第三方服务,然后给自己同源的web页面调用。
2、跨子域名的调用如果想从www.example.com调用api.example.com的html/xml数据服务,那么可以通过使用iframe,并在document和iframe中均设置相同的document.domain属性,那么document和iframe所对应的页面直接就可以通信而不会有任何安全冲突(security violation),注意必须设置相同的一级域名(document.domain="example.com"),不要设置子域名。代码示例如下:
t.html
Access-Control-Allow-Origin响应头(一般回填$_SERVER['HTTP_ORIGIN']),header('Access-Control-Allow-Origin: '.$_SERVER['HTTP_ORIGIN']);
来告诉浏览器该服务允许来自特定源的访问或者允许所有人访问。
尽管该规范支持使用origin list的形式,但实际浏览器实现只支持了单个origin、*、null,如果要配置多个访问源,可以在代码中处理如下(PHP):
$.ajax({dataType: 'jsonp',data: 'id=10',jsonp: 'jsonp_callback',url: 'http://api.example.com/getdata',success: function () {// do stuff},});
5、跨文档消息(Cross-document Messaging)这个是HTML5引入的一个在跨域页面之间通讯的方法,参见W3规范 http://dev.w3.org/html5/postmsg/
postMessage API应用范围主要有2个,1是文档和内嵌frame之间的消息通信,2是文档和自身通过脚本打开的windows之间的消息通信
by iefreer