成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

跨域

keelii / 1220人閱讀

摘要:一同源策略瀏覽器出于安全方面的考慮,只允許與本域下的接口交互。包括發(fā)送信息的內(nèi)容,發(fā)送信息的域名等等同樣的,在內(nèi)添加一個(gè)事件監(jiān)聽(tīng)綁定事件,在內(nèi)通過(guò)方法發(fā)送信息給一樣可以進(jìn)行跨域通信

一、同源策略(Same origin Policy)

瀏覽器出于安全方面的考慮,只允許與本域下的接口交互。不同源的客戶端腳本在沒(méi)有明確授權(quán)的情況下,不能讀寫(xiě)對(duì)方的資源。

1、同源(本域)

所謂“同源”指的是”三個(gè)相同“。相同的域名、端口和協(xié)議,這三個(gè)相同的話就視為同一個(gè)域,本域下的JS腳本只能讀寫(xiě)本域下的數(shù)據(jù)資源,無(wú)法訪問(wèn)其它域的資源。

協(xié)議相同 (都是http或者h(yuǎn)ttps)

域名相同 (都是http://jirengu.com/a> 和 和...

不同源情況:

http://jirengu.com/main.js> 和 https://jirengu.com/a.php (協(xié)議不同)

http://jirengu.com/main.js> 和 http://bbs.jirengu.com/a.php (域名不同,域名必須完全相同才可以)

http://jiengu.com/main.js> 和... (端口不同,第一個(gè)是80)

2、Ajax 跨域報(bào)錯(cuò)實(shí)例

(1)修改host文件:給host文件里添加兩條記錄,方便跨域操作

上圖意思是訪問(wèn) a.com 或是 b.com 相當(dāng)于訪問(wèn)本機(jī), 可以實(shí)現(xiàn)一個(gè)場(chǎng)景:瀏覽器是a.com,而接口是b.com,雖說(shuō)最終對(duì)應(yīng)的是本機(jī),但是域名不一樣

(2)建一個(gè)index.html文件,獲取數(shù)據(jù)

hello world

(3)建一個(gè)server.js文件,實(shí)現(xiàn)靜態(tài)文件、動(dòng)態(tài)路由功能

var http = require("http")
var fs = require("fs")
var path = require("path")
var url = require("url")

http.createServer(function(req, res){

  var pathObj = url.parse(req.url, true)

  switch (pathObj.pathname) {
    case "/getWeather":
      res.end(JSON.stringify({beijing: "sunny"}))
      break;

    default:
      fs.readFile(path.join(__dirname, pathObj.pathname), function(e, data){
        if(e){
          res.writeHead(404, "not found")
          res.end("

404 Not Found

") }else{ res.end(data) } }) } }).listen(8080)

(4)執(zhí)行結(jié)果

打開(kāi)終端,cd 到當(dāng)前文件夾,然后輸入node server.js,啟動(dòng)靜態(tài)服務(wù)器

A、瀏覽器地址欄輸入localhost:8080/index.html ,獲取到了數(shù)據(jù)

B、瀏覽器地址改為127.0.0.1:8080/index.html,就報(bào)錯(cuò)啦,因?yàn)楫?dāng)前域名和請(qǐng)求域名不一樣

C、如果瀏覽器改成a.com或是b.com 也是會(huì)報(bào)錯(cuò)的,就算它們都是指向同一個(gè)本機(jī)

總結(jié)一下:只有在請(qǐng)求域名和當(dāng)前域名相同的情況下,才能獲取數(shù)據(jù),才不會(huì)報(bào)錯(cuò)。

注:跨域的資源內(nèi)嵌是被允許的,對(duì)于當(dāng)前頁(yè)面來(lái)說(shuō)頁(yè)面存放的 JS 文件的域不重要,重要的是加載該 JS 頁(yè)面所在什么域

二、跨域

解決同源策略帶來(lái)的不便,突破同源策略的限制去獲取不同源之間的數(shù)據(jù)信息或者進(jìn)行不同源之間的信息傳遞。

解決辦法 1? JSONP

HTML 中 script 標(biāo)簽可以加載其他域下的js,比如我們經(jīng)常引入一個(gè)其他域下線上cdn的jQuery。

可以這樣子實(shí)現(xiàn)從其他域下獲取數(shù)據(jù)

這時(shí)候會(huì)向天氣接口發(fā)送請(qǐng)求獲取數(shù)據(jù),獲取數(shù)據(jù)后做為 js 來(lái)執(zhí)行。 但這里有個(gè)問(wèn)題, 數(shù)據(jù)是 JSON 格式的數(shù)據(jù),直接作為 JS 運(yùn)行的話,如何去得到這個(gè)數(shù)據(jù)來(lái)操作呢?

此時(shí)需要后端的配合,因?yàn)楹蠖说慕涌谛枰鶕?jù)約定的參數(shù)獲取回調(diào)函數(shù)名,然后跟返回?cái)?shù)據(jù)進(jìn)行拼接,最后進(jìn)行響應(yīng)

這個(gè)請(qǐng)求到達(dá)后端后,后端會(huì)去解析callback這個(gè)參數(shù)獲取到字符串showData,在發(fā)送數(shù)據(jù)做如下處理:

之前后端返回?cái)?shù)據(jù): {"city": "hangzhou", "weather": "晴天"}

現(xiàn)在后端返回?cái)?shù)據(jù): showData({"city": "hangzhou", "weather": "晴天"})

前端script標(biāo)簽在加載數(shù)據(jù)后會(huì)把 「showData({“city”: “hangzhou”, “weather”: “晴天”})」做為 js 來(lái)執(zhí)行。

這實(shí)際上就是調(diào)用showData這個(gè)函數(shù),同時(shí)參數(shù)是 {“city”: “hangzhou”, “weather”: “晴天”}。

當(dāng)然前端提前在頁(yè)面定義好showData這個(gè)全局函數(shù),在函數(shù)內(nèi)部處理參數(shù)即可。


總結(jié)一下:

(1)JSONP是通過(guò) script 標(biāo)簽加載數(shù)據(jù)的方式去獲取數(shù)據(jù)當(dāng)做 JS 代碼來(lái)執(zhí)行

(2)提前在頁(yè)面上聲明一個(gè)函數(shù),函數(shù)名通過(guò)接口傳參的方式傳給后臺(tái),后臺(tái)解析到函數(shù)名后在原始數(shù)據(jù)上「包裹」這個(gè)函數(shù)名,發(fā)送給前端。

換句話說(shuō),JSONP 需要對(duì)應(yīng)接口的后端的配合才能實(shí)現(xiàn)

舉個(gè)例子

server.js 文件

var http = require("http")
var fs = require("fs")
var path = require("path")
var url = require("url")

http.createServer(function(req, res){
  var pathObj = url.parse(req.url, true)

  switch (pathObj.pathname) {
    case "/getNews":
      var news = [
        "第11日前瞻:中國(guó)沖擊4金 博爾特再戰(zhàn)200米羽球",
        "正直播柴飚/洪煒出戰(zhàn) 男雙力爭(zhēng)會(huì)師決賽",
        "女排將死磕巴西!郎平安排男陪練模仿對(duì)方核心"
        ]
      res.setHeader("Content-Type","text/json; charset=utf-8")
      if(pathObj.query.callback){
        res.end(pathObj.query.callback + "(" + JSON.stringify(news) + ")")
      }else{
        res.end(JSON.stringify(news))
      }

      break;

    default:
      fs.readFile(path.join(__dirname, pathObj.pathname), function(e, data){
        if(e){
          res.writeHead(404, "not found")
          res.end("

404 Not Found

") }else{ res.end(data) } }) } }).listen(8080)

html文件




  

打開(kāi)終端,cd 到當(dāng)前文件夾,然后輸入node server.js,啟動(dòng)靜態(tài)服務(wù)器

顯示結(jié)果:

圖中Request URL :http://127.0.0.1:8080/getNews?callback=appendHtml 會(huì)向?yàn)g覽器發(fā)請(qǐng)求,得到數(shù)據(jù),然后當(dāng)成 js 去執(zhí)行,因?yàn)轫?yè)面上已經(jīng)有了appendHtml函數(shù),然后去執(zhí)行這個(gè)函數(shù),把a(bǔ)ppendHtml 括號(hào)里的內(nèi)容作為參數(shù)傳遞進(jìn)去

2、CORS

全稱是跨域資源共享(Cross-Origin Resource Sharing),是一種 ajax 跨域請(qǐng)求資源的方式,支持現(xiàn)代瀏覽器,IE支持10以上。

實(shí)現(xiàn)方式:

當(dāng)你使用 XMLHttpRequest 發(fā)送請(qǐng)求時(shí),瀏覽器發(fā)現(xiàn)該請(qǐng)求不符合同源策略,會(huì)給該請(qǐng)求加一個(gè)請(qǐng)求頭:Origin,后臺(tái)進(jìn)行一系列處理:

(1)如果確定接受請(qǐng)求則在返回結(jié)果中加入一個(gè)響應(yīng)頭:Access-Control-Allow-Origin; 瀏覽器判斷該相應(yīng)頭中是否包含 Origin 的值。

(2)如果有則瀏覽器會(huì)處理響應(yīng),我們就可以拿到響應(yīng)數(shù)據(jù)。

(3)如果不包含瀏覽器直接駁回,這時(shí)我們無(wú)法拿到響應(yīng)數(shù)據(jù)。

所以 CORS 的表象是讓你覺(jué)得它與同源的 ajax 請(qǐng)求沒(méi)啥區(qū)別,代碼完全一樣。

舉個(gè)例子

server.js文件

var http = require("http")
var fs = require("fs")
var path = require("path")
var url = require("url")

http.createServer(function(req, res){
  var pathObj = url.parse(req.url, true)

  switch (pathObj.pathname) {
    case "/getNews":
      var news = [
        "第11日前瞻:中國(guó)沖擊4金 博爾特再戰(zhàn)200米羽球",
        "正直播柴飚/洪煒出戰(zhàn) 男雙力爭(zhēng)會(huì)師決賽",
        "女排將死磕巴西!郎平安排男陪練模仿對(duì)方核心"
        ]

      res.setHeader("Access-Control-Allow-Origin","http://localhost:8080")
      //訪問(wèn)控制允許的域 http://localhost:8080
      //res.setHeader("Access-Control-Allow-Origin","*")
      res.end(JSON.stringify(news))
      break;
    default:
      fs.readFile(path.join(__dirname, pathObj.pathname), function(e, data){
        if(e){
          res.writeHead(404, "not found")
          res.end("

404 Not Found

") }else{ res.end(data) } }) } }).listen(8080)

index.html文件




  

顯示結(jié)果

(1)輸入http://127.0.0.1:8080/index.html 發(fā)送請(qǐng)求時(shí),不需要跨域,請(qǐng)求頭什么都沒(méi)有

(2)輸入http://localhost:8080/index.html,此時(shí)出現(xiàn)跨域

? 響應(yīng)頭有Access-Control-Allow-Origin: http://localhost:8080

? 請(qǐng)求頭有Origin: http://localhost:8080

? 表示兩者相同,可以獲取數(shù)據(jù)

(3)輸入http://a.com:8080/index.html 時(shí),就報(bào)錯(cuò)啦

因?yàn)榉?wù)端不允許a.com 獲取數(shù)據(jù)

響應(yīng)頭 Access-Control-Allow-Origin 設(shè)置為星號(hào),表示同意任意跨源請(qǐng)求

Access-Control-Allow-Origin: "*"

那么http://a.com:8080/index.html就能獲取數(shù)據(jù)啦!

3?降域
(1)iframe 不同源

iframe里面加載的頁(yè)面,它的域名,如果和我當(dāng)前的是屬于不同域,雖然iframe里面的東西可以加載,但外部的js無(wú)法去獲取或操作的。
也就是說(shuō),只有在相同域名下的iframe,才可以去訪問(wèn)里面的東西

舉個(gè)例子

a.html




    





使用降域?qū)崿F(xiàn)跨域

b.html




    







同樣先是host 文件添加兩條記錄

打開(kāi)終端,cd 到當(dāng)前文件夾,啟動(dòng)http-server

用a.com 打開(kāi)a.html, http://a.com:8080/a.html , 其中頁(yè)面iframe的地址是b.com,和網(wǎng)頁(yè)不同源的??梢钥吹皆揻rame可以正確加載,但我們不能用js操作它

用b.com 打開(kāi)a.html, http://b.com:8080/a.html , 其中frame 的地址是b.com,和網(wǎng)頁(yè)同源的,現(xiàn)在我們就可以用 js 獲取 iframe里面的內(nèi)容

(2)修改源 document.domain

當(dāng)兩個(gè)url的主域名不同,但子域名相同的情況下,我們可以通過(guò)

b.html

4?PostMessage

允許來(lái)自不同源的腳本采用異步方式進(jìn)行有限的通信,可以實(shí)現(xiàn)跨文本檔、多窗口、跨域消息傳遞。

舉個(gè)例子 (實(shí)現(xiàn)iframe跨域通信)

a.html




    





    

使用postMessage實(shí)現(xiàn)跨域

b.html




    







啟動(dòng)http-server,查看執(zhí)行結(jié)果

總結(jié)一下:

A、a.html 通過(guò) window.postMessage() 發(fā)送一個(gè)信息給b.html

B、b.html 在 window 上添加一個(gè)事件監(jiān)聽(tīng)綁定 message 事件,可以接收到來(lái)自任何不同域名通過(guò) postMessage 方法發(fā)送過(guò)來(lái)的信息

C、當(dāng) b.html 接收到 a.html 發(fā)送過(guò)來(lái)的信息時(shí)執(zhí)行監(jiān)聽(tīng)事件就 OK,在監(jiān)聽(tīng)事件的 event 參數(shù)中包含了所有 message 事件接收到的相關(guān)數(shù)據(jù)。包括發(fā)送信息的內(nèi)容 event.data,發(fā)送信息的域名 event.origin 等等

同樣的,在 a.html 內(nèi)添加一個(gè)事件監(jiān)聽(tīng)綁定 message 事件,在 b.html 內(nèi)通過(guò) postMessage方法發(fā)送信息給 a.html 一樣可以進(jìn)行跨域通信

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/99930.html

相關(guān)文章

  • ajax跨域,這應(yīng)該是最全的解決方案了

    摘要:關(guān)于,強(qiáng)烈推薦閱讀跨域資源共享詳解阮一峰另外,這里也整理了一個(gè)實(shí)現(xiàn)原理圖簡(jiǎn)化版如何判斷是否是簡(jiǎn)單請(qǐng)求瀏覽器將請(qǐng)求分成兩類簡(jiǎn)單請(qǐng)求和非簡(jiǎn)單請(qǐng)求。 前言 從剛接觸前端開(kāi)發(fā)起,跨域這個(gè)詞就一直以很高的頻率在身邊重復(fù)出現(xiàn),一直到現(xiàn)在,已經(jīng)調(diào)試過(guò)N個(gè)跨域相關(guān)的問(wèn)題了,16年時(shí)也整理過(guò)一篇相關(guān)文章,但是感覺(jué)還是差了點(diǎn)什么,于是現(xiàn)在重新梳理了一下。 個(gè)人見(jiàn)識(shí)有限,如有差錯(cuò),請(qǐng)多多見(jiàn)諒,歡迎提出iss...

    ytwman 評(píng)論0 收藏0
  • 大話javascript 5期:跨域

    摘要:同源策略所謂同源是指協(xié)議,域名,端口均相同。同源策略是瀏覽器的一個(gè)安全功能,不同源的客戶端腳本在沒(méi)有明確授權(quán)的情況下,不能讀寫(xiě)對(duì)方資源。需注意的是由于同源策略的限制,所讀取的為跨域請(qǐng)求接口所在域的,而非當(dāng)前頁(yè)。 一、什么是跨域 1.URL解析 URL (Uniform Resource Locator )統(tǒng)一資源定位符(URL)是用于完整地描述Internet上網(wǎng)頁(yè)和其他資源的地址的...

    jzzlee 評(píng)論0 收藏0
  • 用本地運(yùn)行的demo快速入門(mén)跨域

    摘要:學(xué)習(xí)建議在學(xué)習(xí)其中一種跨域方法的時(shí)候,建議邊運(yùn)行項(xiàng)目里的,邊在網(wǎng)上搜索博客文章學(xué)習(xí)這種跨域方法,這樣有助于快速并且深入理解跨域。鑒于網(wǎng)上有很多文章詳細(xì)講述跨域知識(shí),只是少了可以本地運(yùn)行的,所以這里就不再贅述跨域知識(shí)。 前言 因?yàn)閷W(xué)習(xí)跨域需要配置本地服務(wù)器,可能會(huì)比較麻煩,所以自己根據(jù)網(wǎng)上的博客寫(xiě)了大多數(shù)跨域的簡(jiǎn)單demo,可以自己在本地運(yùn)行,而且不用配置服務(wù)器。自己對(duì)于跨域的理解剛開(kāi)始...

    yy736044583 評(píng)論0 收藏0
  • 用本地運(yùn)行的demo快速入門(mén)跨域

    摘要:學(xué)習(xí)建議在學(xué)習(xí)其中一種跨域方法的時(shí)候,建議邊運(yùn)行項(xiàng)目里的,邊在網(wǎng)上搜索博客文章學(xué)習(xí)這種跨域方法,這樣有助于快速并且深入理解跨域。鑒于網(wǎng)上有很多文章詳細(xì)講述跨域知識(shí),只是少了可以本地運(yùn)行的,所以這里就不再贅述跨域知識(shí)。 前言 因?yàn)閷W(xué)習(xí)跨域需要配置本地服務(wù)器,可能會(huì)比較麻煩,所以自己根據(jù)網(wǎng)上的博客寫(xiě)了大多數(shù)跨域的簡(jiǎn)單demo,可以自己在本地運(yùn)行,而且不用配置服務(wù)器。自己對(duì)于跨域的理解剛開(kāi)始...

    GraphQuery 評(píng)論0 收藏0
  • 用本地運(yùn)行的demo快速入門(mén)跨域

    摘要:學(xué)習(xí)建議在學(xué)習(xí)其中一種跨域方法的時(shí)候,建議邊運(yùn)行項(xiàng)目里的,邊在網(wǎng)上搜索博客文章學(xué)習(xí)這種跨域方法,這樣有助于快速并且深入理解跨域。鑒于網(wǎng)上有很多文章詳細(xì)講述跨域知識(shí),只是少了可以本地運(yùn)行的,所以這里就不再贅述跨域知識(shí)。 前言 因?yàn)閷W(xué)習(xí)跨域需要配置本地服務(wù)器,可能會(huì)比較麻煩,所以自己根據(jù)網(wǎng)上的博客寫(xiě)了大多數(shù)跨域的簡(jiǎn)單demo,可以自己在本地運(yùn)行,而且不用配置服務(wù)器。自己對(duì)于跨域的理解剛開(kāi)始...

    Integ 評(píng)論0 收藏0
  • javascript跨域

    摘要:實(shí)現(xiàn)跨域的原理通過(guò)方式請(qǐng)求載入并執(zhí)行一個(gè)文件,相當(dāng)于通過(guò)的形式的導(dǎo)入一個(gè)外部的方法語(yǔ)法該函數(shù)是簡(jiǎn)寫(xiě)的函數(shù),等價(jià)于在中,您可以通過(guò)使用形式的回調(diào)函數(shù)來(lái)加載其他網(wǎng)域的數(shù)據(jù),如。將自動(dòng)替換為正確的函數(shù)名,以執(zhí)行回調(diào)函數(shù)。 更多詳情見(jiàn)http://blog.zhangbing.club/Ja... 最近在項(xiàng)目開(kāi)發(fā)的過(guò)程中遇到一些Javascript 跨域請(qǐng)求的問(wèn)題,今天抽空對(duì)其進(jìn)行總結(jié)一下,以...

    PingCAP 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看
<