探秘ajax跨域請(qǐng)求
前言
ajax,用蒼白的話贊揚(yáng):很好。
我們可以使用ajax實(shí)現(xiàn)異步獲取數(shù)據(jù),減少服務(wù)器運(yùn)算時(shí)間,大大地改善用戶體驗(yàn);我們可以使用ajax實(shí)現(xiàn)小系統(tǒng)組合大系統(tǒng);我們還可以使用ajax實(shí)現(xiàn)前端的優(yōu)化。(好一個(gè)排比)
雖然ajax很好,但在使用起來也會(huì)有一定的限制,出于安全考慮,不允許跨域通信。如果嘗試從不同的域請(qǐng)求數(shù)據(jù),會(huì)出現(xiàn)安全錯(cuò)誤。(下面例子1可以直觀看出)
同源策略限制
同源策略阻止從一個(gè)域上加載的腳本獲取或操作另一個(gè)域上的文檔屬性。也就是說,受到請(qǐng)求的 URL 的域必須與當(dāng)前 Web 頁面的域相同。這意味著瀏覽器隔離來自不同源的內(nèi)容,以防止它們之間的操作。這個(gè)瀏覽器策略很舊,從 Netscape Navigator 2.0 版本開始就存在?!詃eveloperWorks
所謂同源是指,域名,協(xié)議,端口相同。
平地一聲吼
本文講解的是怎么利用ajax實(shí)現(xiàn)跨域請(qǐng)求,那么知道“同源策略”,就可以解決很多疑問:“為毛我的ajax加載不了數(shù)據(jù)!”“為毛瀏覽器控制臺(tái)會(huì)對(duì)我如此漂亮的代碼報(bào)錯(cuò)!”
例子1
先上一個(gè)錯(cuò)誤示范
客戶端代碼:
<script>
// 客戶端使用getJSON方法請(qǐng)求另一臺(tái)機(jī)子上的腳本
$.getJSON("){
alert(json.website);
});
</script>
服務(wù)端PHP腳本代碼:
<?php
// ajax.php
header('Content-type: application/json');
echo json_encode(array('website'=>'hcoding'));
?>
firefox下的錯(cuò)誤提示:
根據(jù)同源策略的概念,localhost和172.22.22.120是出于不同的域名下的,所以跨域請(qǐng)求理所當(dāng)然地被瀏覽器拒絕了。
JSONP
JSONP(JSON with Padding)是資料格式 JSON 的一種“使用模式”,可以讓網(wǎng)頁從別的網(wǎng)域要資料。另一個(gè)解決這個(gè)問題的新方法是跨來源資源共享。由于同源策略,一般來說位于 server1.example.com 的網(wǎng)頁無法與不是 server1.example.com 的服務(wù)器溝通,而 HTML 的 <script> 元素是一個(gè)例外。利用 <script> 元素的這個(gè)開放策略,網(wǎng)頁可以得到從其他來源動(dòng)態(tài)產(chǎn)生的 JSON 資料,而這種使用模式就是所謂的 JSONP。用 JSONP 抓到的資料并不是 JSON,而是任意的 JavaScript,用 JavaScript 直譯器執(zhí)行而不是用 JSON 解析器解析?!跃S基百科
這話該怎么理解呢!我個(gè)人是這樣認(rèn)為的,用<script>跨域的請(qǐng)求數(shù)據(jù),跨域的服務(wù)器返回一段【JavaScript代碼】,是 的,你沒看錯(cuò),不是json格式數(shù)據(jù),是JavaScript代碼,這樣,這段代碼就由JavaScript 直譯器執(zhí)行。上例子更直觀:
例子2
客戶端代碼:
<script>
// 這是回調(diào)方法
function cb(data){
alert(data.website);
}
</script>
<!--這是跨域請(qǐng)求的代碼,切記,這段代碼要在回調(diào)函數(shù)之后-->
<script src=">
服務(wù)端PHP腳本代碼:
<?php
$cb = htmlspecialchars($_GET['callback']); // 注意了,這里要做好過濾,防止xss攻擊
echo $cb,'(',json_encode(array('website'=>'hcoding')),')'; // 返回客戶端的數(shù)據(jù)為:cb({"name":"hcoding"}) 這是一段js代碼
?>
瀏覽器會(huì)發(fā)生什么事呢,我就不說了,當(dāng)然是cb方法被調(diào)用啦:
所以,再說jsonp的概念,利用<script>不受同源策略的限制,跨域的服務(wù)器把要返回的json數(shù)據(jù)作為參數(shù)和回調(diào)函數(shù)一起返回客戶端。
JQuery對(duì)JSONP的支持
本文要講ajax的跨域請(qǐng)求,前面說了那么多,下面當(dāng)然要講主題啦。
從 1.2 版本開始,jQuery 擁有對(duì) JSONP 回調(diào)的本地支持。如果指定了 JSONP 回調(diào),就可以加載位于另一個(gè)域的 JSON 數(shù)據(jù),回調(diào)的語法為:url?callback=?。jQuery 自動(dòng)將 ? 替換為要調(diào)用的生成函數(shù)名。
例子3:$.getJSON方法跨域請(qǐng)求
例子4:$.ajax方法自定義回調(diào)方法
例子3
客戶端代碼:
<script>
// 客戶端使用getJSON方法請(qǐng)求另一臺(tái)機(jī)子上的腳本
// 瀏覽器會(huì)生成一個(gè)隨機(jī)的callback參數(shù)
$.getJSON("){
alert(json.website);
});
</script>
服務(wù)端PHP腳本代碼:
<?php
$cb = htmlspecialchars($_GET['callback']); // 注意了,這里要做好過濾,防止xss攻擊
echo $cb,'(',json_encode(array('website'=>'hcoding')),')'; // 返回客戶端的數(shù)據(jù),這是一段js代碼
?>
$.getJSON簡(jiǎn)單易用,但就是不能指定回調(diào)函數(shù)。
例子4
客戶端代碼:
<script>
$.ajax({
type : "GET",
url : " dataType : "jsonp", // 數(shù)據(jù)格式指定為jsonp
jsonp: "callback", // 服務(wù)點(diǎn)通過這個(gè)鍵值獲取回調(diào)方法
jsonpCallback:"cb", // 指定回調(diào)方法
success : function(json){
},
});
// 回調(diào)方法
function cb(data){
alert(data.website);
}
</script>
服務(wù)端PHP腳本代碼和例子3的相同。
總結(jié)
正所謂無規(guī)矩不成方圓,以安全為出發(fā)點(diǎn),遵循同源策略是一個(gè)好品德。但我們也有跨域請(qǐng)求的需求,jsonp就能滿足我們的需求。當(dāng)然跨域請(qǐng)求還有很多的方法,不單止jsonp。
以上所述就是本文的全部?jī)?nèi)容了,希望大家能夠喜歡。
相關(guān)文章
Ajax實(shí)現(xiàn)異步加載數(shù)據(jù)
這篇文章主要為大家詳細(xì)介紹了Ajax實(shí)現(xiàn)異步加載數(shù)據(jù),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2021-11-11AJAX開發(fā)技術(shù)在PHP開發(fā)中的簡(jiǎn)單應(yīng)用技巧
AJAX無疑是2005年炒的最熱的Web開發(fā)技術(shù)之一,當(dāng)然,這個(gè)功勞離不開Google。我只是一個(gè)普通開發(fā)者,使用AJAX的地方不是特別多,我就簡(jiǎn)單的把我使用的心得說一下。(本文假設(shè)用戶已經(jīng)具有JavaScript、HTML、CSS等基本的Web開發(fā)能力)2010-04-04ajax三級(jí)聯(lián)動(dòng)下拉菜單效果
這篇文章主要為大家詳細(xì)介紹了ajax三級(jí)聯(lián)動(dòng)下拉菜單的相關(guān)資料,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-03-03React+ajax+java實(shí)現(xiàn)上傳圖片并預(yù)覽功能
這篇文章主要介紹了React+ajax+java實(shí)現(xiàn)上傳圖片并預(yù)覽功能,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-05-05ajax獲得json對(duì)象數(shù)組 循環(huán)輸出數(shù)據(jù)的方法
今天小編就為大家分享一篇ajax獲得json對(duì)象數(shù)組 循環(huán)輸出數(shù)據(jù)的方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2018-08-08PHP Ajax實(shí)現(xiàn)頁面無刷新發(fā)表評(píng)論
PHP Ajax實(shí)現(xiàn)頁面無刷新發(fā)表評(píng)論...2006-12-12JQuery ajax中error返回錯(cuò)誤及一直返回error的解答
本文由腳本之家小編給大家分享有關(guān) JQuery ajax中error返回錯(cuò)誤及一直返回error的解答總結(jié),需要的朋友可以參考下2015-09-09jQuery AJAX中readyState與status的區(qū)別與聯(lián)系
這篇文章主要介紹了 jQuery AJAX中readyState與status的區(qū)別與聯(lián)系,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友可以參考下2017-03-03