日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 前端技术 > javascript >内容正文

javascript

跨域之JSONP

發(fā)布時(shí)間:2025/3/21 javascript 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 跨域之JSONP 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

為什么80%的碼農(nóng)都做不了架構(gòu)師?>>> ??

1 跨域及同源策略

1.1 什么是跨域

一般來說,如果你在開發(fā)中需要進(jìn)行跨域操作(從一個(gè)非同源網(wǎng)站發(fā)送請(qǐng)求獲取數(shù)據(jù)),一般而言,你在瀏覽器控制臺(tái)看到的結(jié)果為:

XMLHttpRequest cannot load http://external-domain/service. No ‘Access-Control-Allow-Origin’ header is present on the requested resource. Origin ‘http://my-domain’ is therefore not allowed access.

像這樣發(fā)送ajax請(qǐng)求會(huì)在瀏覽器中得到如下訪問受限的提示

<html> <head> <meta charset="utf-8" /> <script> function success(text) { var textarea = document.getElementById('test-response-text'); textarea.innerHTML = text; }function fail(code) { var textarea = document.getElementById('test-response-text'); textarea.innerHTML = 'Error code: ' + code; }function helloAjax() { var request = new XMLHttpRequest(); // 新建XMLHttpRequest對(duì)象request.onreadystatechange = function () { // 狀態(tài)發(fā)生變化時(shí),函數(shù)被回調(diào) if (request.readyState === 4) { // 成功完成// 判斷響應(yīng)結(jié)果:if (request.status === 200) {// 成功,通過responseText拿到響應(yīng)的文本://alert('request.responseText');return success(request.responseText);} else {// 失敗,根據(jù)響應(yīng)碼判斷失敗原因://alert('request.status');return fail(request.status);} } else {console.log('continuing……'); } }// 發(fā)送請(qǐng)求: request.open('GET', 'http://api.money.126.net/data/feed/0000001,1399001,1399006?callback=refreshPrice'); request.send();alert('請(qǐng)求已發(fā)送,請(qǐng)等待響應(yīng)...'); }</script> </head> <body> <div> <p id="test-response-text"></p> <p><button type="button" onclick="helloAjax()">刷新</button></p> </div> </body> </html>

1.2 同源策略

????? 說到跨域就不得不提“同源策略”。同源策略是Web瀏覽器針對(duì)惡意的代碼所進(jìn)行的措施,為了防止世界被破壞,為了保護(hù)世界的和平,Web瀏覽器,采取了同源策略,只允許腳本讀取和所屬文檔來源相同的窗口和文檔的屬性。那么,怎么判斷文檔來源是否相同呢?很簡(jiǎn)單,看三個(gè)部分: 協(xié)議主機(jī)端口號(hào)。只要其中一個(gè)部分不同,則不同源。

1.3 跨域的應(yīng)用場(chǎng)景

  • 來自 home.example.com 的文檔里的腳本讀取 developer.example.com載入的文檔的屬性。

  • 來自 home.example.com 的文檔里的腳本讀取 text.segmentfault.com載入的文檔的屬性

  • 2 JSONP跨域

    實(shí)際應(yīng)用場(chǎng)景中不可避免地需要進(jìn)行跨域操作,這時(shí)候“同源策略”就顯得過于苛刻。JSONP跨域GET請(qǐng)求是一個(gè)常用的解決方案。

    2.1 概念介紹

    ?????? JSONP即JSON with Padding。由于同源策略的限制,XmlHttpRequest只允許請(qǐng)求當(dāng)前源(域名、協(xié)議、端口)的資源。如果要進(jìn)行跨域請(qǐng)求, 我們可以通過使用html的script標(biāo)記來進(jìn)行跨域請(qǐng)求(即利用在頁面中創(chuàng)建<script>節(jié)點(diǎn)的方法向不同域提交HTTP請(qǐng)求),并在響應(yīng)中返回要執(zhí)行的script代碼,其中可以直接使用JSON傳遞javascript對(duì)象。 這種跨域的通訊方式稱為JSONP。

    ?????? 假設(shè)在http://example1.com/index.php這個(gè)頁面中向http://example2.com/getinfo.php提交GET請(qǐng)求,我們可以將下面的JavaScript代碼放在http://example1.com/index.php這個(gè)頁面中來實(shí)現(xiàn):

    當(dāng)GET請(qǐng)求從http://example2.com/getinfo.php返回時(shí),可以返回一段JavaScript代碼,這段代碼會(huì)自動(dòng)執(zhí)行,可以用來負(fù)責(zé)調(diào)用http://example1.com/index.php頁面中的一個(gè)callback函數(shù)。

    2.2 原理及實(shí)例

    JSONP的最基本的原理是:

    動(dòng)態(tài)添加一個(gè)<script>標(biāo)簽,而script標(biāo)簽的src屬性是沒有跨域的限制的。這樣說來,這種跨域方式其實(shí)與ajax XmlHttpRequest協(xié)議無關(guān)了。

    這樣其實(shí)"jQuery AJAX跨域問題"就成了個(gè)偽命題,jquery $.ajax方法名有誤導(dǎo)人之嫌。如果設(shè)為dataType: 'jsonp',這個(gè)$.ajax方法就和ajax XmlHttpRequest沒什么關(guān)系了,取而代之的則是JSONP協(xié)議。JSONP是一個(gè)非官方的協(xié)議,它允許在服務(wù)器端集成Script tags返回至客戶端,通過javascript callback的形式實(shí)現(xiàn)跨域訪問。

    Jsonp的執(zhí)行過程如下:

    首先在客戶端注冊(cè)一個(gè)callback (如:'jsoncallback'), 然后把callback的名字(如:jsonp1236827957501)傳給服務(wù)器。注意:服務(wù)端得到callback的數(shù)值后,要用jsonp1236827957501(......)把將要輸出的json內(nèi)容包括起來,此時(shí),服務(wù)器生成 json 數(shù)據(jù)才能被客戶端正確接收。

    然后以 javascript 語法的方式,生成一個(gè)function, function 名字就是傳遞上來的參數(shù) 'jsoncallback'的值 jsonp1236827957501 .

    最后將 json 數(shù)據(jù)直接以入?yún)⒌姆绞?#xff0c;放置到 function 中,這樣就生成了一段 js 語法的文檔,返回給客戶端。

    例1:

    <html> <head> <meta charset="utf-8" /><script>function refreshPrice(data) {var p = document.getElementById('test-jsonp');p.innerHTML = '當(dāng)前價(jià)格:' +data['0000001'].name +': ' + data['0000001'].price + ';' +data['1399001'].name + ': ' +data['1399001'].price + ';' +data['1399006'].name + ': ' +data['1399006'].price; } function getPrice() {varjs = document.createElement('script'),head = document.getElementsByTagName('head')[0];js.src = 'http://api.money.126.net/data/feed/0000001,1399001,1399006?callback=refreshPrice';head.appendChild(js); }</script> </head> <body> <div><p id="test-jsonp">當(dāng)前價(jià)格:</p><p><button type="button" onclick="getPrice()">刷新</button></p> </div> </body> </html>

    通過參數(shù)callback定義回調(diào)函數(shù)名字為refreshPrice,服務(wù)端得到callback的數(shù)值為refreshPrice后,要用refreshPrice(......)把將要輸出的json內(nèi)容包括起來,此時(shí),服務(wù)器生成 json 數(shù)據(jù)才能被客戶端正確接收。

    例2:

    <html> <head> <meta charset="utf-8" /> <title>Test Jsonp</title> <script type="text/javascript"> function jsonpCallback(sb) { alert(sb['0000001'].name); } </script> <script type="text/javascript" src="http://api.money.126.net/data/feed/0000001,1399001,1399006?callback=jsonpCallback"></script> </head> <body> </body> </html>

    例3:

    <html> <head> <meta charset="utf-8" /> <title>Untitled Page</title><script type="text/javascript" src="http://cdn.bootcss.com/jquery/3.1.1/jquery.min.js"></script><script type="text/javascript">jQuery(document).ready(function(){$.ajax({type: "get",async: false,url: "http://api.money.126.net/data/feed/0000001,1399001,1399006",dataType: "jsonp",//jsonp: "zjg",//傳遞給請(qǐng)求處理程序或頁面的,用以獲得jsonp回調(diào)函數(shù)名的參數(shù)名(一般默認(rèn)為:callback)//jsonpCallback:"flightHandler",//自定義的jsonp回調(diào)函數(shù)名稱,默認(rèn)為jQuery自動(dòng)生成的隨機(jī)函數(shù)名,也可以寫"?",jQuery會(huì)自動(dòng)為你處理數(shù)據(jù)success: function(json){alert(json['0000001'].name);},error: function(){alert('fail');}});});</script></head><body></body></html>

    這里需重點(diǎn)說明下jquery中ajax的jsonp和jsonpCallback這兩個(gè)參數(shù)的含義

    3 JSONP優(yōu)缺點(diǎn)

    JSONP的優(yōu)點(diǎn)是:它不像XMLHttpRequest對(duì)象實(shí)現(xiàn)的Ajax請(qǐng)求那樣受到同源策略的限制;它的兼容性更好,在更加古老的瀏覽器中都可以運(yùn)行,不需要XMLHttpRequest或ActiveX的支持;并且在請(qǐng)求完畢后可以通過調(diào)用callback的方式回傳結(jié)果。

    JSONP的缺點(diǎn)則是:它只支持GET請(qǐng)求而不支持POST等其它類型的HTTP請(qǐng)求;它只支持跨域HTTP請(qǐng)求這種情況,不能解決不同域的兩個(gè)頁面之間如何進(jìn)行JavaScript調(diào)用的問題。

    ?

    參考:

    http://www.w3school.com.cn/jquery/ajax_ajax.asp

    https://segmentfault.com/a/1190000006908944?utm_source=tuicool&utm_medium=referral

    http://www.nowamagic.net/librarys/veda/detail/224/

    http://kb.cnblogs.com/page/139725/

    http://www.cnblogs.com/know/archive/2011/10/09/2204005.html

    http://www.liaoxuefeng.com/wiki/001434446689867b27157e896e74d51a89c25cc8b43bdb3000/001434499861493e7c35be5e0864769a2c06afb4754acc6000

    轉(zhuǎn)載于:https://my.oschina.net/zjg23/blog/794933

    總結(jié)

    以上是生活随笔為你收集整理的跨域之JSONP的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。