一.关于跨域需要设置的响应头消息
Access-Control-Allow-Origin:*#允许所有主机 Access-Control-Allow-Origin:http://hello-world.example#允许特定主机 Access-Control-Allow-Methods:POST,GET,OPTIONS#允许跨域执行的方法 Access-Control-Allow-Headers:X-PINGOTHER,Content-Type,MyHeader#允许跨域设置的头信息(如果不设置,那么无法获取该值,甚至数据无法获取) Access-Control-Max-Age:1728000
二.关于IE8和IE9浏览器差异性说明
IE8和IE9使用新的API XDomainRequest(IE又淘气了一次,但还好IE7上可以通过ajax跨域)
varxdr=newXDomainRequest(); xdr.onload=function(e){//当收到服务器响应的回调函数 vardata=$.parseJSON(xdr.responseText); if(data==null||typeof(data)=='undefined'){ data=$.parseJSON(data.firstChild.textContent); } //success }; xdr.onerror=function(e){ //error } xdr.open("GET",url);//目前只支持IE8和IE9 xdr.send();
对于webkit阵营的浏览器而言,需要使用ajax,这里我们不在多演示,我们将在下面做一个兼容性的例子。
三.为了达到兼容性的指标,我们进行如下改造
设立一站点 www.a.com,作为请求的client
<!doctypehtml> <html> <head> <Metacharset="utf-8"/> <title>Cross-Domain</title> <Metahttp-equiv="X-UA-Compatible"content="IE=EmulateIE7"/> </head> <body> <scripttype="text/javascript"charset="utf-8"> varxdr=null; if(!!window.XMLHttpRequest) { xdr=newXMLHttpRequest(); } elseif(window.ActiveXObject) { try {//IE7+ xdr=newActiveXObject("Msxml2.XMLHTTP"); } catch(e) { //IE6- try{xdr=newActiveXObject("Microsoft.XMLHTTP");}catch(e){} } } if(xdr) { if(!("withCredentials"inxdr)&&window.XDomainRequest) { xdr=newXDomainRequest(); }else{ xdr['withCredentials']=true; } if(window.XMLHttpRequest&&(xdrinstanceofXMLHttpRequest))//如果是IE6,IE7,chrome,firefox,IE10,IE11 { xdr.open('OPTIONS','http://www.b.com/html5/crossdomain-server.PHP',true); } elseif(window.ActiveXObject&&(xdrinstanceofXDomainRequest))//如果是IE8,IE9 { xdr.open("POST","http://www.b.com/html5/crossdomain-server.PHP"); } xdr.onload=function(e) { xdr.onReadyStateChange(arguments); }; xdr.onReadyStateChange=function(e) { if(window.console) { console.dir(xdr.responseText); }else{ alert(xdr.responseText); } } xdr.send(null); } else { alert('NotSupported!'); } </script> </body> </html>
设立服务器站点 www.b.com/html5/crossdomain-server.PHP
<?PHP header('Content-Type:application/json;charset=utf-8'); header('Pragma:no-cache,no-store'); header('Cache-Control:no-cache,private'); header('Date:'+date('r')); header('Connection:Keep-Alive'); header('Access-Control-Allow-Origin:http://www.a.com'); header('Access-Control-Allow-Methods:POST,OPTIONS,PUT,DELETE,HEAD'); header('Access-Control-Allow-Headers:X-PINGOTHER,Content-Type,Accept,Range'); header('Access-Control-Max-Age:1728000'); header('Access-Control-Allow-Credentials:true'); date_default_timezone_set('Asia/Chongqing'); $data=array( 'id'=>'ZF1024','name'=>'zhangsan','token'=>uniqid() ); echojson_encode($data); ?>
请求结果
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
三.html5 postMessage进行跨域
a.com/index.html中的代码: <iframeid="ifr"src="b.com/index.html"></iframe> <scripttype="text/javascript"> window.onload=function(){ varifr=document.getElementById('ifr'); vartargetOrigin='http://b.com';//若写成'http://b.com/c/proxy.html'效果一样 //若写成'http://c.com'就不会执行postMessage了 ifr.contentWindow.postMessage('Iwasthere!',targetOrigin);//通过这句穿透域名限制 }; </script>
b.com/index.html中的代码: <scripttype="text/javascript"> window.addEventListener('message',function(event){ //通过origin属性判断消息来源地址 if(event.origin=='http://a.com'){ alert(event.data);//弹出"Iwasthere!" alert(event.source);//对a.com、index.html中window对象的引用 //但由于同源策略,这里event.source不可以访问window对象 } },false);
最后,你还可以通过apache服务器设置跨域
<IfModule mod_setenvif.c> <IfModule mod_headers.c> <FilesMatch "\.(cur|gif|ico|jpe?g|png|svgz?|webp)$"> SetEnvIf Origin ":" IS_CORS Header set Access-Control-Allow-Origin "*" env=IS_CORS </FilesMatch> </IfModule> </IfModule>
参考:http://www.cnblogs.com/rainman/archive/2011/02/20/1959325.html#m2
http://msdn.microsoft.com/zh-cn/library/gg589525(v=vs.85).aspx