關于JSONP跨域請求原理的深入解析
什么是同源策略
同源策略,它是由Netscape提出的一個著名的安全策略?,F在所有支持JavaScript 的瀏覽器都會使用這個策略。
簡單來講,域名,協(xié)議,端口相同。當一個瀏覽器的兩個tab頁中分別打開來 百度和谷歌的頁面。當瀏覽器的百度tab頁執(zhí)行一個腳本的時候會檢查這個腳本是屬于哪個頁面的,即檢查是否同源,只有和百度同源的腳本才會被執(zhí)行。如果非同源,那么在請求數據時,瀏覽器會在控制臺中報一個異常,提示拒絕訪問。
什么是JSONP
JSONP是JSON with Padding的略稱。它是一個非官方的協(xié)議,它允許在服務器端集成Script tags返回至客戶端,通過javascript callback的形式實現跨域訪問(這僅僅是JSONP簡單的實現形式)
如何理解上面那句話
我們知道標簽中的src屬性既可以請求本地圖片,也可以請求網上資源。也就是說html中的src屬性是支持跨域的。同理jsonp跨域請求也是利用src屬性,只不過用的是標簽。
那么我們來舉例看一下:
先寫一個html文件
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<title>jsonp請求資源</title>
<script type="text/javascript" src="./t10.js"></script>
</body>
</html>
在寫一個js文件:
console.log("我被請求了!");
打開控制臺可以看到:

jsonp實現了本地數據的請求,在這里我們模擬了一下本地請求是怎么實現的。
如果請求服務器的數據該是怎樣去實現呢?
了解跨域請求模式:
我們先打開百度的搜索頁面,打開控制臺,點擊Network如下:

然后在頁面輸入一個b:

https://www.baidu.com/sugrec?pre=1&p=3&ie=utf-8&json=1&prod=pc&from=pc_web&sugsid=35105,31660,35239,35457,34584,35245,35480,35499,35329,35316,26350,35475&wd=b&req=2&csor=1&cb=jQuery11020022466709590333256_1639545101298&_=1639545101299
關鍵字:wd=b
這是回調函數:
cb=jQuery11020022466709590333256_1639545101298&_=1639545101299
可以看到他的請求方式是GET方式,Jsonp的請求方式默認也是GET請求。通過get方式請求服務器,服務器返回的數據若是json字符串將自動轉化為js對象。所以jsonp是需要服務器端和客戶端相互配合的。

紅色方框是返回的關鍵字:

可以發(fā)現,我們并沒有寫callback方法,jQuery自動幫我們封裝了一個callback方法。我們修改CD為001后發(fā)現它的名字變成了001。
https://www.baidu.com/sugrec?pre=1&p=3&ie=utf-8&json=1&prod=pc&from=pc_web&sugsid=35105,31660,35239,35457,34584,35245,35480,35499,35329,35316,26350,35475&wd=b&req=2&csor=1&cb=001

練習
獲取請求到的數據,并將它們顯示出來(百度搜索框)。
做法如下:
可以根據我們輸入的東西動態(tài)的創(chuàng)建腳本,然后獲取回調函數里面的值的函數,然后頁面添加一個列表把它們顯示出來。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<script src="../12-5/js/jquery.js"></script>
<style>
input {
width: 540px;
height: 40px;
border: 2px solid #4E6EF2;
}
li{
height: 40px;
width: 411px;
line-height: 40px;
font-size: 16px;
list-style: none;
}
</style>
</head>
<body>
<img src="https://ss0.bdstatic.com/5aV1bjqh_Q23odCf/static/superman/img/logo/bd_logo1_31bdc765.png">
<div>
<input type="text" value =''>
</div>
<ul></ul>
<script>
//
function getData(data){
var script = document.querySelector('#jsonp');
script.parentNode.removeChild(script);
$('ul').html('');
for(var i =0;i<data.g.length;i++){
$('<li>'+data.g[i].q +'</li>').appendTo('ul');//將獲取到的數據加入列表
}
}
//動態(tài)生成script腳本
function getList(wd){
var script = document.createElement('script');
script.id = 'jsonp';
script.src = 'https://www.baidu.com/sugrec?pre=1&p=3&ie=utf-8&json=1&prod=pc&from=pc_web&sugsid=26350&req=2&csor=1&cb=getData&wd='+wd;
document.body.appendChild(script);
}
//給input設置鍵盤事件。
//實現輸入文本后調用腳本函數
var ipt = document.querySelector('input');
ipt.addEventListener('keyup',function(){
var wd = this.value;
getList(wd);
})
</script>
</body>
</html>

jsonp的缺點
- 只能發(fā)送get請求。因為script只能發(fā)送get請求
- 需要后臺配合。此種請求方式應該前后端配合,將返回結果包裝成callback(result)的形式。
總結
到此這篇關于JSONP跨域請求原理的文章就介紹到這了,更多相關JSONP跨域請求原理內容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!
相關文章
javascript中的event loop事件循環(huán)詳解
這篇文章主要給大家介紹了關于javascript中event loop事件循環(huán)的相關資料,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧2018-12-12

