Cors實現(xiàn)跨域ajax,基本原理:客戶端不變,服務(wù)器端在返回響應(yīng)數(shù)據(jù)時,添加響應(yīng)頭讓瀏覽器允許其通過,
Cors實現(xiàn)跨域ajax很簡便,但不是所有瀏覽器都支持;jsonp實現(xiàn)跨域,只能get請求;
一、瀏覽器發(fā)送簡單請求:服務(wù)器直接添加響應(yīng)頭實現(xiàn)跨域
問:什么是簡單請求?
答:請求方式為head、get、post,且請求頭信息滿足條件
(1) 請求方法是以下三種方法之一:
HEAD
GET
POST
(2)HTTP的頭信息不超出以下幾種字段:
Accept
Accept-Language
Content-Language
Last-Event-ID
Content-Type:只限于三個值application/x-www-form-urlencoded、multipart/form-data、text/plain
凡是不同時滿足上面兩個條件,就屬于非簡單請求。
注意:允許攜帶cookie時,必須制定域名,不能用*,
另外:jsonp方式跨域,默認(rèn)傳遞cookie,
實際上getJson方式的根本原理和ajax使用jsonp的方式是一樣的。
在請求頁面上使用Access-Control-Allow-Origin標(biāo)頭。
使用如下標(biāo)頭可以接受全部網(wǎng)站請求:
header('Access-Control-Allow-Origin:*')
使用如下標(biāo)頭可以接受指定網(wǎng)站請求:
header('Access-Control-Allow-Origin:http://www.abc.com')
所以,服務(wù)器寫法:
header('Access-Control-Allow-Origin:*'); die( json_encode(array('msg'=>'msg....')) );
ajax寫法和平常一樣:
<!DOCTYPE html> <html class=""> <head> <meta charset="utf-8" /> <title>測試</title> <script src="http://theartemis.cn/templets/axskin/js/jquery.js"></script> <body> <script> $.ajax({ url:'http://192.168.1.124/homekoo.com/zde/cors_1.php', dataType:'json', success:function(data){ alert(data.msg); } }); </script> </body> </html>
jquery中常用getJson來調(diào)用獲取遠(yuǎn)程的數(shù)據(jù),并通過json格式返回。函數(shù)的原型如下:
1 jQuery.getJSON(url,data,success(data,status,xhr))
參數(shù)
描述
url
必需。規(guī)定將請求發(fā)送的哪個 URL。
data
可選。規(guī)定連同請求發(fā)送到服務(wù)器的數(shù)據(jù)。
success(data,status,xhr)
可選。規(guī)定當(dāng)請求成功時運行的函數(shù)。
額外的參數(shù):
response - 包含來自請求的結(jié)果數(shù)據(jù)
status - 包含請求的狀態(tài)
xhr - 包含 XMLHttpRequest 對象
該函數(shù)是簡寫的ajax函數(shù),實際上等價于:
1 jQuery.getJSON(url,data,success(data,status,xhr))
下面我們來看如何使用getJson跨域獲取數(shù)據(jù)。
html頁面示例代碼:
$(function(){ $("#ww").click(function(){ $.getJSON("http://zenphoto.1youku.org/zp-core/getimg1.php?&cid=257&square=9&jsoncallback=?", function (result) { alert(result.img_url); } ); }); });
執(zhí)行原理:
發(fā)送請求時需要傳一個callback的回調(diào)函數(shù)名到服務(wù)器端,服務(wù)器端拿到這個回調(diào)函數(shù)名,再將返回數(shù)據(jù)用參數(shù)的形式反回到客戶端,這樣客戶端就能夠調(diào)到。
所以發(fā)送請求URL的地址后面一定要上jsoncallback=?這樣的參數(shù),jquery會將?號自動替換成自動生成的回調(diào)函數(shù)的名稱。
所以最終的實際請求為:http://api.taobao.com/apitools/ajax_props.do&jsoncallback=jsonp1322444422697
所以和ajax的方式想比較,也就是callback函數(shù)一個是自動生成的函數(shù)名,一個是手工指定的函數(shù)名。
通過jQuery的ajax進(jìn)行跨域,這其實是采用的jsonp的方式來實現(xiàn)的。
jsonp是英文json with padding的縮寫。它允許在服務(wù)器端生成script tags至返回至客戶端,也就是動態(tài)生成javascript標(biāo)簽,通過javascript callback的形式實現(xiàn)數(shù)據(jù)讀取.
html代碼:
//首先要引入jquery的js包
jQuery(document).ready(function(){ $.ajax({ type : "get", //jquey是不支持post方式跨域的 async:false, url : "http://api.taobao.com/apitools/ajax_props.do", //跨域請求的URL dataType : "jsonp", //傳遞給請求處理程序,用以獲得jsonp回調(diào)函數(shù)名的參數(shù)名(默認(rèn)為:callback) jsonp: "jsoncallback", //自定義的jsonp回調(diào)函數(shù)名稱,默認(rèn)為jQuery自動生成的隨機函數(shù)名 jsonpCallback:"success_jsonpCallback", //成功獲取跨域服務(wù)器上的json數(shù)據(jù)后,會動態(tài)執(zhí)行這個callback函數(shù) success : function(json){ //do something when sucess } }); });
服務(wù)端php:
$jsonp=$_GET['callback']; $output=$jsonp.'({"name":"value",.....})'; exit($output);
jsonp的原理:
首先在客戶端注冊一個callback (如:'jsoncallback'), 然后把callback的名字(如:success_jsonpCallback)傳給服務(wù)器端對應(yīng)的處理函數(shù)。
服務(wù)器先生成需要返回給客戶端的 json 數(shù)據(jù)。然后以 javascript 語法的方式,生成一個function , function 名字就是傳遞上來的參數(shù)(jsoncallback)的值(success_jsonpCallback) 。
最后將 json 數(shù)據(jù)直接以入?yún)⒌姆绞?,放置?function 中,這樣就生成了一段 js 語法的文檔,返回給客戶端。
客戶端瀏覽器,解析script標(biāo)簽,并將服務(wù)器端返回的數(shù)據(jù),作為參數(shù),
傳入到了客戶端預(yù)先定義好的 callback 函數(shù)(如上例中jquery $.ajax()方法封裝的的success: function (json))里。
實際上跨域是通過動態(tài)增加script來加載數(shù)據(jù),無法直接獲得數(shù)據(jù),所以需要使用回調(diào)函數(shù)。
如對本文有疑問,請?zhí)峤坏浇涣髡搲?,廣大熱心網(wǎng)友會為你解答!! 點擊進(jìn)入論壇