介紹什麼是同源和什麼是跨域,以及三種解決跨域問題的路徑
什麼是同源?什麼是跨域?
客戶端向伺服器傳送請求的時候,如果協議,域名(IP)和埠都一樣,則稱為同源,但凡有一個不一樣則跨域,跨域請求預設受到瀏覽器的安全策略的限制,瀏覽器會給出相應的錯誤資訊,對於客戶端而言意味著請求失敗
-
同源和跨域是瀏覽器的行為--瀏覽器安全機制
-
請求要麼同源要麼跨域:不同源則跨域
-
所謂同源就是指請求的源和對應的響應伺服器:協議一致,IP(域名)一致,埠一致
-
影響範圍
ajax 請求資料會受到影響,但是 html 程式碼中,二次請求檔案,比如圖片 img src, 或者 script src 這些不會受到限制
客戶端跨域
-
我想通過遠端介面獲取天氣資訊
-
找到介面:http://api.map.baidu.com/telematics/v3/weather?location=北京&output=json&ak=E4805d16520de693a3fe707cdc962045
-
傳送請求,獲取到天氣資料
$.ajax({ type: 'get', url: 'http://api.map.baidu.com/telematics/v3/weather', data: { ak: 'zVo5SStav7IUiVON0kuCogecm87lonOj', location: '廣州', output: 'json' }, success: function (result) { console.log(result.results[0].weather_data) } })
-
跨域錯誤資訊
-
錯誤資訊說明: 通過非同步方式,從源http://127.0.0.1:5500向http://api.baidu...傳送請求被CORS策略阻止了,不允許進行跨域請求
解決跨域
1.第一種 在伺服器設定 ( Access-Control-Allow-Origin: *)(常用)
- CROS 資料伺服器新增響應頭 Access-Control-Allow-Origin: *
- 星號表示所有域名,也可用指定域名代替星號
2.第二種 Proxy 代理 (常用)
Proxy 代理,網頁伺服器,同時負責轉發不同伺服器的資料
只從網頁伺服器請求資料,那麼網頁和資料來自同一伺服器,就不是跨域了
開發伺服器轉發代理配置步驟:
配置 vue.config.js
-
如何分辨哪些是資料請求?
proxy 是一個物件
物件裡面是鍵值對, 其中 key 是用來匹配資料請求的
我們希望所有資料請求都能統一處理,無需重複宣告
-
在所有資料請求的前面新增 /api 標識
-
然後就可以被 '/api' 攔截
-
-
將請求轉向真實資料伺服器
target 配置
代理解決跨域的根本在於伺服器之間通訊受跨域影響, 可以用跟頁面同域的伺服器作為中轉轉發, 避免跨域問題.
3.第一種jsonp解決方式(但是在現在的前端領域並不常見了)
-
jsonp 利用 script 標籤不受跨域限制的特性,使用 script 標籤向資料伺服器請求一個 js檔案,資料伺服器會將資料動態生成一個 js 檔案響應
-
在ajax中實現跨域請求
在客戶端實現跨域請求就稱為
客戶端跨域
ajax中通過設定dataType為jsonp就可以實現客戶端跨域
// 關鍵程式碼:第11行 $.ajax({ type: 'get', url: 'http://api.map.baidu.com/telematics/v3/weather', data: { ak: 'zVo5SStav7IUiVON0kuCogecm87lonOj', location: '廣州', output: 'json' }, // 開戶跨域請求 dataType: 'jsonp', success: function (result) { console.log(result.results[0].weather_data) } })
jsonp客戶端跨域的原理
1.客戶端跨域的本質是利用了script標籤的src屬性的天然跨域特性來實現
2.客戶端傳送請求的時候,傳遞一個客戶端存在的函式名稱到伺服器,如<script src='http://127.0.0.1:3000/getData?callback=fn' ></script>
3.伺服器中獲取資料,根據接收的函式名稱拼接成函式呼叫形式,如 res.end('fn({ "a": 1, "b" : 2 })')
4.通過script傳送的請求,返回值預設會以js語法進行解析,客戶端接收從伺服器返回的資料(如:fn({ "aa": 11, "bb" : 22 })),以js語法解析,恰巧客戶端有一個fn函式,完美
5.客戶端獲取到資料
客戶端
<script>
function fun(data){
console.log("data:",data)
}
</script>
// 傳送請求,傳入客戶端定義好的函式
<script src="http://127.0.0.1:3000/getUserList?callback=fun"></script>
伺服器端
// 1.引入http模組
const http = require('http')
// 讀取檔案需要fs模組
const fs = require('fs')
// 2.建立伺服器
const server = http.createServer()
// 3.新增伺服器的埠監聽
server.listen(3000, function () {
console.log('伺服器開好了: http://127.0.0.1:3000')
})
server.on('request', function (req, res) {
let url = req.url
let fun = req.url.split('=')[1]
console.log(fun)
let data = [{id:1,name:'jack'},{id:2,name:rose},{id:3,name:'tom'}]
if (url.indexOf('/getUserList?') === 0) {
fs.readFile(__dirname + "/data/users.json",'utf-8', function (err, data) {
if (err) {
res.end(`${fun}("404")`)
} else {
// 關鍵程式碼:伺服器獲取資料後,拼接資料和函式名稱,返回函式的呼叫形式
res.end(`${fun}(${data})`)
}
})
}else{
res.end(`${fun}("404")`)
}
})
結果
總結:
所謂jsonp跨域就是利用了script標籤的src屬性的天然跨域特性,
在傳送請求的時候,傳遞一個客戶端的函式名稱到伺服器端,
伺服器端獲取資料,根據接收的函式名稱拼接為函式呼叫的形式,
並返回到客戶端,客戶端獲取返回資料的之後,按js語法進行解析,客戶端就順利的獲取到資料了
只能發起get請求
可以理解的是,jsonp跨域嚴重的需要伺服器端的配合,在現在的前端領域並不常見了
相關文章
- 什麼是跨域,什麼是同源跨域
- 跨域訪問是什麼!怎麼解決?跨域
- 什麼是跨域跨域
- JavaScript跨域(1):什麼是跨域,如何跨域JavaScript跨域
- 什麼是跨域?解決方案有哪些?跨域
- 一文搞懂│什麼是跨域?如何解決跨域?跨域
- 什麼是跨域請求?跨域
- 24.什麼是跨域?解決方案有哪些?跨域
- 跨域是什麼?跨域請求資源有哪些方法?跨域
- 跨域資源共享(CORS)是什麼?跨域CORS
- 什麼是跨域,後端工程師如何處理跨域跨域後端工程師
- 前端怎麼解決跨域問題前端跨域
- 同源策略和跨域訪問跨域
- 同源策略和跨域跨域
- 跨域原理以及跨域解決方案跨域
- 也談談同源策略和跨域問題跨域
- 搞懂:前端跨域問題JS解決跨域問題VUE代理解決跨域問題原理前端跨域JSVue
- 解決跨域問題跨域
- 跨域問題(普通跨域和springsecurity跨域)跨域SpringGse
- Nginx解決前端跨域問題 CORS跨域配置Nginx前端跨域CORS
- 深入跨域問題(2) - 利用 CORS 解決跨域跨域CORS
- 什麼是瀏覽器跨域訪問操作?JS如何實現?瀏覽器跨域JS
- 跨域?如何解決?同源策略?跨域
- 解決ajax跨域問題的多種方法跨域
- 前端解決跨域問題的8種方案前端跨域
- 深入跨域問題(3) – 利用 JSONP 解決跨域跨域JSON
- 深入跨域問題(3) - 利用 JSONP 解決跨域跨域JSON
- CROS 解決跨域問題ROS跨域
- cors解決跨域問題CORS跨域
- WebSocket跨域問題解決Web跨域
- Flask解決跨域問題Flask跨域
- Luffy - 解決跨域問題跨域
- 跨域問題,解決之道跨域
- Java解決跨域問題Java跨域
- 10.13面試:什麼是跨域?如何解決跨域問題+springMVC如何處理檔案上傳和下載+ssm整合思路 (待完善)面試跨域SpringMVCSSM
- 【SpringMVC】解決跨域問題的兩種方式SpringMVC跨域
- Vue 跨域問題解決辦法 Vue 配置防止跨域 nginx 重定向防止跨域Vue跨域Nginx
- 輕鬆解決跨域問題跨域