1. 程式人生 > >JavaScript:使用原生JS實現Jsonp跨域,呼叫百度搜索介面完成聯想詞功能

JavaScript:使用原生JS實現Jsonp跨域,呼叫百度搜索介面完成聯想詞功能

Jsonp解釋

Jsonp這個術語聽起來很高大上,其實它的原理非常簡單,就是利用src不受同源策略限制這一點來實現的,很多標籤都有src特性。

你們可以想想為什麼img標籤能將不同源的百度logo拿過來?

<img src="https://www.baidu.com/img/bd_logo1.png" alt="">

Jsonp原理

一、src不受同源策略的限制,不受跨域的影響,所以可以藉助script中的src屬性進行跨域獲取資料。

二、所以將資料放到伺服器上,並且資料為json形式,因為js可以輕鬆處理json資料。

三、由於我們動態建立的script標籤是一個非同步載入的過程,不確定資料什麼時候回來,所以要做個處理,在前端寫好一個function並將函式名傳給伺服器,後端拿到函式名,完成一個拼接 functionName(parameter),將json資料以入參的方式放置在function中,生成js語法的文件,返回給客戶端。此時客戶端繼續解析,將json資料作為引數,傳入之前定義好的callback函式中。

四、所以根據第三步,需要先寫好函式來處理跨域獲取的資料。

五、用src獲取資料的時候,在url後邊新增一個引數,例如cb = xxx,服務端會將cb的值,對應為一個函式,將引數插入到其中,例如 xxx(parameter)

注意

基於JSONP的實現原理,所以JSONP只能是“GET”請求,不能進行較為複雜的POST和其它請求,所以遇到那種情況,就得參考CORS解決跨域了(所以如今它也基本被淘汰了)。

下面程式碼演示如何使用Jsonp來實現跨域請求百度搜索介面,完成聯想詞功能,這裡先用原生JS來實現,能更好理解實現原理。在jQuery的ajax裡封裝了Jsonp和CORS跨域解決辦法,後期會進行講解。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>百度搜索框</title>
    <style>
        *{
            padding: 0;
            margin: 0;
            list-style: none;
        }
        input{
            width: 400px;
            height
: 34px; } ul{ display: none; width: 400px; border: 1px solid #ccc; } li{ margin-left: 10px; margin-top: 3px; } .wrapper{ margin: 100px; } a{ text-decoration: none; color: #666; font-size: 14px; }
</style> </head> <body> <div class="wrapper"> <input type="text"> <ul> </ul> </div> <script src="jquery.js"></script> <script> function ds(data) { console.log(data) } /*通過jsonp訪問百度伺服器,獲取搜尋聯想詞*/ var oInput = document.getElementsByTagName("input")[0]; oInput.oninput = function () { var value = this.value; var oScript = document.createElement("script"); //wd=關鍵字,doJson=執行函式名,這裡要保證傳的是函式名的字串!!! oScript.src = "https://sp0.baidu.com/5a1Fazu8AA54nxGko9WTAnF6hhy/su?wd="+ value +"&cb=doJson&_=1544270132010"; //這裡將插入以聯想詞陣列為引數的名為doJson的js檔案,馬上執行 document.body.appendChild(oScript); //執行完以後又馬上移除掉 document.body.removeChild(oScript); }; function doJson(data) { var s = data.s; $("ul").empty(); //當輸入值過多時,s的聯想詞會匹配不到 if(s.length > 0){ s.forEach(function (ele,index) { var a = $("<a></a>").attr("href","https://www.baidu.com/s?wd=" + ele); a.text(ele); $("<li></li>").append(a).appendTo($("ul")); }); $("ul").css("display","block"); }else{ $("ul").css("display","none"); } } </script> </body> </html>