跨域的解決方式

JSONP

JSONPJSON with Padding)是資料格式JSON的一種“使用模式”,可以讓網(wǎng)頁從別的網(wǎng)域要資料蟋软。
由于同源策略踢代,一般來說位于server1.example.com的網(wǎng)頁無法與不是 server1.example.com的伺服器溝通钦扭,而HTML<script>元素是一個例外。利用 <script>元素的這個開放策略君纫,網(wǎng)頁可以得到從其他來源動態(tài)產(chǎn)生的JSON資料驯遇,而這種使用模式就是所謂的 JSONP。用JSONP抓到的資料并不是JSON蓄髓,而是任意的JavaScript叉庐,用 JavaScript直譯器執(zhí)行而不是用JSON解析器解析。

index.html

 <div class="container">
        <ul class="news">
            <li>習(xí)近平:堅(jiān)持中國特色社會主義社會治理之路</li>
            <li>在組織生活會上普通黨員習(xí)近平說了啥  喜迎十九大</li>
            <li>重訪習(xí)近平十八大以來國內(nèi)考察地  《輝煌中國》</li>
        </ul>
        <button id="btn">換一組</button>
    </div>
<script>
    $('#btn').addEventListener('click',function(){
      // 為按鈕添加點(diǎn)擊事件
        var script = document.createElement('script');
      // 創(chuàng)建一個script標(biāo)簽
        script.src='http://localhost:8080/getNews?callback=appendHtml'
      // 為script標(biāo)簽設(shè)置地址
        document.head.appendChild(script)
      //在head里添加script標(biāo)簽
        document.head.removeChild(script)
      //移除head里的script標(biāo)簽
    })


    // 處理返回的數(shù)據(jù)appendHtml(["xxx","xxx","xxx"])
    function appendHtml(news){
        var html = ''
        for(var i = 0;i<news.length;i++){
            html += '<li>'+news[i]+'</li>'
            // 把后臺傳遞過來的數(shù)據(jù)会喝,拆開加在<li></li>內(nèi)
        }
        $('.news').innerHTML = html;
        //把<ul class="news"></ul>中的內(nèi)容替換為處理好的數(shù)據(jù)
    }
    function $(id){
        return document.querySelector(id)
    }
</script>

router.js

app.get('/getNews',function(req,res){
    var news = [
        "<strong>習(xí)近平:堅(jiān)持中國特色社會主義社會治理之路</strong>",
        "在組織生活會上普通黨員習(xí)近平說了啥  喜迎十九大",
        "重訪習(xí)近平十八大以來國內(nèi)考察地  《輝煌中國》",
        "李克強(qiáng)同李顯龍會談  張德江主持會議  劉云山訪越",
        "大國網(wǎng)信安全護(hù)航  2017年國家網(wǎng)絡(luò)安全宣傳周",
        "俠客島:李顯龍時隔近4年為何“突然”訪華?",
        "<strong>墨西哥地震致一學(xué)校教學(xué)樓倒塌 約百名學(xué)生失蹤<stong>",
        "深圳一小學(xué)65名學(xué)生現(xiàn)身體不適 官方:已停用操場",
        "媒體:想知道中國海軍有多強(qiáng)陡叠?僅需一個細(xì)節(jié)",
        "特朗普演講:朝鮮半島無核化是唯一可接受的未來",
        "外媒:中國高鐵網(wǎng)絡(luò)預(yù)示著“高流動性時代”的到來",
        "外國專家:北斗已超越歐盟、俄羅斯衛(wèi)星導(dǎo)航系統(tǒng)"
    ]
    // 內(nèi)容庫

    var data = []
    for(var i = 0;i<3;i++){
        var index = parseInt(Math.random()*news.length)
        // parseInt取整肢执,抽取內(nèi)容庫的隨機(jī)數(shù)字
        data.push(news[index])
        // 把這條隨機(jī)的新聞枉阵,傳給data數(shù)組
        news.splice(index,1)
        //移除這條新聞,避免重復(fù)
    }

    var cb = req.query.callback;
    // 獲取傳遞的callback值
    if(cb){
        res.send(cb+'('+JSON.stringify(data)+')');
    //JSON.stringify 將JavaScript的值轉(zhuǎn)化為JSON
    //如果有callback的值预茄,返回callback值+(["xxx","xxx","xxx"])
    }else{
        res.send(data);        
    //如果沒有兴溜,返回["xxx","xxx","xxx"]
    }
})

CORS

CORS 全稱是跨域資源共享(Cross-Origin Resource Sharing)侦厚,是一種ajax 跨域請求資源的方式支持現(xiàn)代瀏覽器拙徽,IE支持10以上刨沦。 實(shí)現(xiàn)方式很簡單,當(dāng)你使用 XMLHttpRequest 發(fā)送請求時膘怕,瀏覽器發(fā)現(xiàn)該請求不符合同源策略想诅,會給該請求加一個請求頭:Origin,后臺進(jìn)行一系列處理岛心,如果確定接受請求則在返回結(jié)果中加入一個響應(yīng)頭:Access-Control-Allow-Origin; 瀏覽器判斷該相應(yīng)頭中是否包含 Origin 的值来破,如果有則瀏覽器會處理響應(yīng),我們就可以拿到響應(yīng)數(shù)據(jù)忘古,如果不包含瀏覽器直接駁回徘禁,這時我們無法拿到響應(yīng)數(shù)據(jù)。所以 CORS 的表象是讓你覺得它與同源的 ajax 請求沒啥區(qū)別存皂,代碼完全一樣晌坤。

例:http://a.jrg.com:8080網(wǎng)站向http://b.jrg.com:8080/getNews獲取數(shù)據(jù)

html

    <div class="container">
        <ul class="news">
            <li>習(xí)近平:堅(jiān)持中國特色社會主義社會治理之路</li>
            <li>在組織生活會上普通黨員習(xí)近平說了啥  喜迎十九大</li>
            <li>重訪習(xí)近平十八大以來國內(nèi)考察地  《輝煌中國》</li>
        </ul>
        <button id="btn">換一組</button>
    </div>

script

    $('#btn').addEventListener('click',function(){
    var xhr = new XMLHttpRequest();
    xhr.open('get','http://b.jrg.com:8080/getNews',true)
    xhr.send()
    xhr.onreadystatechange = function(){
        if(xhr.readyState===4 && xhr.status===200){
            appendHtml( JSON.parse(xhr.responseText) )
        }
    }
    })

    function appendHtml(news){
        var html = '';
        for(var i = 0;i<news.length;i++){
            html += '<li>'+news[i]+'</li>'        
        }
        $('.news').innerHTML = html;
    }
    
    function $(id){
        return document.querySelector(id);
    }

router.js

app.get('/getNews',function(req,res){
    var news = [
        "<strong>習(xí)近平:堅(jiān)持中國特色社會主義社會治理之路</strong>",
        "在組織生活會上普通黨員習(xí)近平說了啥  喜迎十九大",
        "重訪習(xí)近平十八大以來國內(nèi)考察地  《輝煌中國》",
        "李克強(qiáng)同李顯龍會談  張德江主持會議  劉云山訪越",
        "大國網(wǎng)信安全護(hù)航  2017年國家網(wǎng)絡(luò)安全宣傳周",
        "俠客島:李顯龍時隔近4年為何“突然”訪華?",
        "<strong>墨西哥地震致一學(xué)校教學(xué)樓倒塌 約百名學(xué)生失蹤<stong>",
        "深圳一小學(xué)65名學(xué)生現(xiàn)身體不適 官方:已停用操場",
        "媒體:想知道中國海軍有多強(qiáng)逢艘?僅需一個細(xì)節(jié)",
        "特朗普演講:朝鮮半島無核化是唯一可接受的未來",
        "外媒:中國高鐵網(wǎng)絡(luò)預(yù)示著“高流動性時代”的到來",
        "外國專家:北斗已超越歐盟旦袋、俄羅斯衛(wèi)星導(dǎo)航系統(tǒng)"
    ]

    var data = []
    for(var i = 0;i<3;i++){
        var index = parseInt(Math.random()*news.length)
        data.push(news[index])
        news.splice(index,1)
    }

    res.header("Access-Control-Allow-Origin","http://a.jrg.com:8080")
    // 返回來自http://a.jrg.com:8080的數(shù)據(jù)請求

    //res.header("Access-Control-Allow-Origin","*")
    //返回所有網(wǎng)站的數(shù)據(jù)請求

    res.send(data);
})

降域


a.html

  <div class="ct">
    <h1>降域</h1>
    <div class="main">
    <input type="text" placeholder="http://a.jrg.com:8080/a.html">
  </div>
  <iframe src="http://b.jrg.com:8080/b.html" frameborder="0"></iframe>
  </div>
  <script>
    document.querySelector('.main input').addEventListener('input',function(){
    //給當(dāng)前窗口的input綁定一個輸入事件
      window.frames[0].document.querySelector('input').value = this.value;
      //把當(dāng)前輸入input的值,賦給第一個frames的input的值
  })

    document.domain = "jrg.com"
    //降域
  </script>

b.html

  <input id="input" type="text" placeholder="http://b.jrg.com:8080/b.html">
  <script>
    document.querySelector('#input').addEventListener('input',function(){
    //獲取頁面上的input它改,添加輸入事件
      window.parent.document.querySelector('input').value = this.value;
      //把當(dāng)前frame的input的值疤孕,賦給父級頁面的input的值
  })
  document.domain = "jrg.com"
  //降域
  </script>

postMessage

postMessage對于不同的域下,可以向他發(fā)送一個數(shù)據(jù)央拖,如果對方接受認(rèn)可這個數(shù)據(jù)祭阀,那就可以去使用,如果對象沒有去監(jiān)控這個數(shù)據(jù)鲜戒,就沒有任何作用专控。


a.html

  <div class="ct">
    <h1>postMessage</h1>
    <div class="main">
    <input type="text" placeholder="http://a.jrg.com:8080/a.html">
  <iframe src="http://b.jrg.com:8080/b.html" frameborder="0"></iframe>
  </div>
  <script>
    $('.main input').addEventListener('input',function(){
      window.frames[0].postMessage(this.value,"*");
    })

    window.addEventListener('message',function(e){
      $('.main input').value = e.data
    })

    function $(id){
      return document.querySelector(id)
    }
  </script>

b.html

  <input id="input" type="text" placeholder="http://b.jrg.com:8080/b.html">
  <script>
    $('#input').addEventListener('input',function(){
      window.parent.postMessage(this.value,"*")
    })

    window.addEventListener('message',function(e){
      $('#input').value = e.data
    })

    function $(id){
      return document.querySelector(id)
    }
  </script>

其他跨域方式

js中幾種實(shí)用的跨域方法原理詳解

用到的函數(shù)
  • JSON.stringify()方法將一個 JavaScript 值轉(zhuǎn)換為一個 JSON 字符串,如果指定了一個 replacer 函數(shù)遏餐,則可以替換值伦腐,或者如果指定了一個 replacer 數(shù)組,可選地僅包括指定的屬性失都。
  • parseInt() 函數(shù)可解析一個字符串柏蘑,并返回一個整數(shù)。
  • JSON.parse()方法用于將一個 JSON 字符串轉(zhuǎn)換為對象粹庞。

參考文章

JSON.stringify()
parseInt() 函數(shù)
JSON.parse()

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末咳焚,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子庞溜,更是在濱河造成了極大的恐慌革半,老刑警劉巖,帶你破解...
    沈念sama閱讀 218,451評論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異又官,居然都是意外死亡不傅,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,172評論 3 394
  • 文/潘曉璐 我一進(jìn)店門赏胚,熙熙樓的掌柜王于貴愁眉苦臉地迎上來访娶,“玉大人,你說我怎么就攤上這事觉阅⊙掳蹋” “怎么了?”我有些...
    開封第一講書人閱讀 164,782評論 0 354
  • 文/不壞的土叔 我叫張陵典勇,是天一觀的道長劫哼。 經(jīng)常有香客問我,道長割笙,這世上最難降的妖魔是什么权烧? 我笑而不...
    開封第一講書人閱讀 58,709評論 1 294
  • 正文 為了忘掉前任,我火速辦了婚禮伤溉,結(jié)果婚禮上般码,老公的妹妹穿的比我還像新娘。我一直安慰自己乱顾,他們只是感情好板祝,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,733評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著走净,像睡著了一般券时。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上伏伯,一...
    開封第一講書人閱讀 51,578評論 1 305
  • 那天橘洞,我揣著相機(jī)與錄音,去河邊找鬼说搅。 笑死炸枣,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的蜓堕。 我是一名探鬼主播抛虏,決...
    沈念sama閱讀 40,320評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼套才!你這毒婦竟也來了迂猴?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,241評論 0 276
  • 序言:老撾萬榮一對情侶失蹤背伴,失蹤者是張志新(化名)和其女友劉穎沸毁,沒想到半個月后峰髓,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,686評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡息尺,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,878評論 3 336
  • 正文 我和宋清朗相戀三年携兵,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片搂誉。...
    茶點(diǎn)故事閱讀 39,992評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡徐紧,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出炭懊,到底是詐尸還是另有隱情并级,我是刑警寧澤,帶...
    沈念sama閱讀 35,715評論 5 346
  • 正文 年R本政府宣布侮腹,位于F島的核電站嘲碧,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏父阻。R本人自食惡果不足惜愈涩,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,336評論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望加矛。 院中可真熱鬧履婉,春花似錦、人聲如沸荒椭。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,912評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽趣惠。三九已至,卻和暖如春身害,著一層夾襖步出監(jiān)牢的瞬間味悄,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,040評論 1 270
  • 我被黑心中介騙來泰國打工塌鸯, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留侍瑟,地道東北人。 一個月前我還...
    沈念sama閱讀 48,173評論 3 370
  • 正文 我出身青樓丙猬,卻偏偏與公主長得像涨颜,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子茧球,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,947評論 2 355

推薦閱讀更多精彩內(nèi)容

  • 瀏覽器安全的基石是"同源政策"庭瑰。所謂"同源"指的是"三個相同"。 協(xié)議相同 域名相同 端口相同 同源政策的目的抢埋,是...
    cce117b0a0ce閱讀 287評論 0 1
  • 跨域有很多種方式弹灭,下面就簡單說說跨域最常見的幾種解決方式1督暂、JSONPJSONP是服務(wù)器與客戶端跨源通信的常用方法...
    小囧兔閱讀 388評論 0 0
  • 1.JSONP(JSON with Padding)可用于解決主流瀏覽器的跨域數(shù)據(jù)訪問的問題。由于Web 頁面上調(diào)...
    大主教小豪閱讀 254評論 0 0
  • 新年的鐘聲敲響了八回,2016年又TM的過去了。忙忙碌碌的這一年我收獲了些什么呢驾诈?嗯……怎么感覺只有年齡和體重呢辽社。那些...
    邱小貓閱讀 3,938評論 3 2
  • 夜至深處,四處無聲翘鸭,碾轉(zhuǎn)翻身無眠滴铅,仔細(xì)思來,原是前幾夜打游戲睡的太晚就乓,形成了壞習(xí)慣導(dǎo)致的汉匙。 想到壞習(xí)慣,那么這一...
    游鯽閱讀 458評論 0 0