跨域問題一般都在后臺(tái)程序解決,將自己的程序通過配置文件或者代碼將其允許跨域,

讓客戶滿意是我們工作的目標(biāo),不斷超越客戶的期望值來自于我們對(duì)這個(gè)行業(yè)的熱愛。我們立志把好的技術(shù)通過有效、簡單的方式提供給客戶,將通過不懈努力成為客戶在信息化領(lǐng)域值得信任、有價(jià)值的長期合作伙伴,公司提供的服務(wù)項(xiàng)目有:域名與空間、網(wǎng)站空間、營銷軟件、網(wǎng)站建設(shè)、馬山網(wǎng)站維護(hù)、網(wǎng)站推廣。
在有跨域安全的時(shí)候,所有前端post請(qǐng)求時(shí),會(huì)發(fā)送一個(gè)與其請(qǐng)求名字一樣的OPTIONS
此請(qǐng)求沒有任何參數(shù),此機(jī)制為post不知道是否有權(quán)限請(qǐng)求接口,發(fā)送了一個(gè)探知請(qǐng)求,探知
請(qǐng)求確認(rèn)后,允許訪問后調(diào)用正常Post接口。 不允許就會(huì)出現(xiàn)你現(xiàn)在的問題跨域異常。
萌新,java是開源的,比NET好多了,多看看底層
大家好,一直以來我都本著 用最通俗的話理解核心的知識(shí)點(diǎn), 我認(rèn)為所有的難點(diǎn)都離不開 「基礎(chǔ)知識(shí)」 的鋪墊
「大佬可以繞過 ~」
如果你是一路看過來的,很高興你能夠耐心看完。之前帶大家學(xué)了 Springboot 基礎(chǔ)部分,對(duì)基本的使用有了初步的認(rèn)識(shí), 接下來的幾期內(nèi)容將會(huì)帶大家進(jìn)階使用,會(huì)先講解基礎(chǔ) 中間件 的使用和一些場景的應(yīng)用,或許這些技術(shù)你聽說過,沒看過也沒關(guān)系,我會(huì)帶大家一步一步的入門,耐心看完你一定會(huì)有 收獲 ~
上期帶大家學(xué)習(xí)了 Springboot 中如何集成 MyBatis分頁插件PageHelper 以及它的一個(gè)基本使用, 本期將帶大家學(xué)習(xí) SpringBoot 中如何處理跨域問題的,同樣的,我們集成到 Springboot 中。最近github可能會(huì)被墻,所以我把源碼放到了國內(nèi)gitee上,本節(jié)我們依然使用上期的代碼
同樣的,為了照顧小白同學(xué),依然先說一下啥是跨域。說到跨域問題,如果你是 前端 同學(xué),肯定不會(huì)陌生, 你有可能調(diào)接口調(diào)著調(diào)著,發(fā)現(xiàn)請(qǐng)求發(fā)布出去,控制臺(tái)會(huì)報(bào) CORS 錯(cuò)誤, 這時(shí)候你會(huì)找后臺(tái)老大哥給你處理一下。然而現(xiàn)在前端工程中,一般都會(huì)有 proxy代理 ,這樣也能解決問題,這只是本地調(diào)試,但上線還會(huì)有問題, 除非你發(fā)布的時(shí)候你們是同一個(gè) 域 下。
好,說了這么多,大概明白跨域是如何產(chǎn)生了,就是說前端調(diào)用的后端接口不屬于同一個(gè) 域(域名或端口不同) ,就會(huì)產(chǎn)生跨域問題,也就是說你的應(yīng)用訪問了該應(yīng)用域名或端口之外的域名或端口,這里給大家總結(jié)一下,產(chǎn)生跨域的三個(gè)條件:
解決思路大致可以分為以下幾方面:
從源頭瀏覽器解決,解除跨域機(jī)制,用戶自己設(shè)置瀏覽器,這不大現(xiàn)實(shí),好, pass
發(fā)送 JSONP 請(qǐng)求替代XHR請(qǐng)求,并不能適用所有的請(qǐng)求方式, 不推薦
之前我們提到前端本地工程開啟 Proxy ,那么服務(wù)端可不可進(jìn)行代理呢?答案是可以的,怎么做?可以通過 nginx 進(jìn)行代理,給大家簡單演示一下:
nginx 是當(dāng)今比較火的 web 服務(wù)器,常用于服務(wù)代理, 等教大家部署的時(shí)候會(huì)講一下
這也是本節(jié)要講的內(nèi)容,我們先不直接的給大家展示代碼,先說一下它的原理。
一般我們下載的瀏覽器比如 Chrome ,它都是自行默認(rèn)開啟 跨域限制 的,那我們?nèi)绾闻袛辔覀儼l(fā)出去的請(qǐng)求是一個(gè) 跨域請(qǐng)求 呢,打開瀏覽器開發(fā)者工具,在請(qǐng)求的請(qǐng)求頭中就可以發(fā)現(xiàn),如果不是一個(gè)跨域請(qǐng)求,它只有 Host ,如果是一個(gè) 跨域請(qǐng)求 它會(huì)多一個(gè) Origin ,告訴瀏覽器我倆請(qǐng)求的地方不一樣
跨源資源共享(CORS) 是一種基于 HTTP頭 的機(jī)制,該機(jī)制通過允許服務(wù)器標(biāo)示除了它自己以外的其它 origin(域,協(xié)議和端口 ),這樣瀏覽器就可以訪問加載這些資源。跨源資源共享還通過一種機(jī)制來檢查服務(wù)器是否會(huì)允許要發(fā)送的真實(shí)請(qǐng)求,該機(jī)制通過瀏覽器發(fā)起一個(gè)到服務(wù)器托管的跨源資源的 預(yù)檢(OPTION) 請(qǐng)求。在預(yù)檢中,瀏覽器發(fā)送的頭中標(biāo)示有HTTP方法和真實(shí)請(qǐng)求中會(huì)用到的頭,那么具體是怎么設(shè)置 頭 的呢?
服務(wù)端通過設(shè)置如上,就可以進(jìn)行跨域訪問了。好,有了基本的理論之后,我們一起看一下在 Springboot 中如何解決的:
是不是很簡單~ 它的實(shí)現(xiàn)機(jī)制主要是通過請(qǐng)求 攔截器 實(shí)現(xiàn)的,你慢慢會(huì)發(fā)現(xiàn),隨著學(xué)習(xí)的深入,你會(huì)遇到各種 攔截器 技術(shù)
本期到這里就結(jié)束了,總結(jié)一下,本節(jié)主要帶大家認(rèn)識(shí)了什么是 跨域 ,以及解決思路,最后教大家 Sprinboot 中是如何配置跨域訪問的,源碼已更新,大家可以自行試一下
前言
相信大家在寫前端腳本的時(shí)候經(jīng)常會(huì)遇到發(fā)送數(shù)據(jù)到后臺(tái)的情況,但是由于瀏覽器的限制,不同域名之間的數(shù)據(jù)是不能互相訪問的,那前端怎么和后端如何進(jìn)行數(shù)據(jù)之間的交換呢?
JavaScript由于安全性方面的考慮,不允許頁面跨域調(diào)用其他頁面的對(duì)象,那么問題來了,什么是跨域問題?
答:這是由于瀏覽器同源策略的限制,現(xiàn)在所有支持JavaScript的瀏覽器都使用了這個(gè)策略。那么什么是同源呢?所謂的同源是指三個(gè)方面“相同”:
域名相同
協(xié)議相同
端口相同
下面就舉幾個(gè)例子來幫助更好的理解同源策略。
URL
說明
是否允許通信
同一域名 ? ?允許 ?
不同域名 ? ?不允許 ?
同一域名不同端口 ? ?不允許 ?
同一域名不同協(xié)議 ? ?不允許 ?
在JAVA中處理跨域問題,通常有以下兩種常用的解決方法。
第一種解決方法
后臺(tái)代碼在被請(qǐng)求的Servlet中添加Header設(shè)置:
response.setHeader("Access-Control-Allow-Origin", "*");
PrintWriter out =null;
try
{
out = response.getWriter();
} catch (IOException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
out.print("{'status':'ok'}");
out.flush();
out.close();
Access-Control-Allow-Origin這個(gè)Header在W3C標(biāo)準(zhǔn)里用來檢查該跨域請(qǐng)求是否可以被通過,如果值為*則表明當(dāng)前頁面可以跨域訪問。默認(rèn)的情況下是不允許的。
在前端JS中需要向Servlet發(fā)出請(qǐng)求,請(qǐng)求代碼如下所示:
$.ajax({
url: "your url",
type:"get or post",
dataType:"json",
data:{
....
},
success:function(data){
...
}
第二種解決方法
通過jsonp跨域請(qǐng)求的方式。JSONP和JSON雖然只有一個(gè)字母的區(qū)別,但是他們完全就是兩回事,很多人很容易把他們搞混。JSON是一種數(shù)據(jù)交換的格式,而JSONP則是一種非官方跨域數(shù)據(jù)交互協(xié)議。
首先來說一下前端JS是怎么發(fā)送請(qǐng)求。代碼如下所示:
$.ajax({
url:"your url",
type:"get or post",
async:false,
dataType : "jsonp",
//服務(wù)端用于接收callback調(diào)用的function名的參數(shù)
jsonp:"callbackparam",
//callback的function名稱
jsonpCallback:"success_jsonpCallback",
success:function(data){
console.log(data);
},
error:function(data){
console.log(data);
}
});
這里的callbackparam和success_jsonpCallback可以理解為發(fā)送的data數(shù)據(jù)的鍵值對(duì),可以自定義,但是callbackparam需要和后臺(tái)約定好參數(shù)名稱,因?yàn)楹笈_(tái)需要獲取到這個(gè)參數(shù)里面的值(即success_jsonpCallback)。
下面,最重要的來了,后臺(tái)怎么樣獲取和返回?cái)?shù)據(jù)呢。代碼如下所示:
PrintWriter out =null;
String callback=req.getParameter("callbackparam");
String json=callback+"({'status':'ok'})";
try
{
out = resp.getWriter();
} catch (IOException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
out.print(json);
out.flush();
out.close();
首先需要獲取參數(shù)名為callbackparam的值,這里獲取到的值就是“success_jsonpCallback”。然后將這個(gè)值加上一對(duì)小括號(hào)。小括號(hào)里放入你需要返回的數(shù)據(jù)內(nèi)容,比如這里我返回一個(gè)JSON對(duì)象。當(dāng)然你也可以返回其他對(duì)象,比如只返回一個(gè)字符串類型數(shù)據(jù)也可以。最后前端JS返回的數(shù)據(jù)就是這樣的:
success_jsonpCallback({'status':'ok'})
瀏覽器會(huì)自動(dòng)解析為json對(duì)象,這時(shí)候你只需要在success回調(diào)函數(shù)中直接用data.status就可以了。
1、CORS的原理:CORS定義一種跨域訪問的機(jī)制,可以讓AJAX實(shí)現(xiàn)跨域訪問。CORS 允許一個(gè)域上的網(wǎng)絡(luò)應(yīng)用向另一個(gè)域提交跨域 AJAX 請(qǐng)求。實(shí)現(xiàn)此功能非常簡單,只需由服務(wù)器發(fā)送一個(gè)響應(yīng)標(biāo)頭即可。
2、tomcat如何配置cors的跨域請(qǐng)求:?
在tomcat中,有一個(gè)和cors相關(guān)的攔截器:CORS Filter
該過濾器可以通過添加必需的訪問控制請(qǐng)求頭Access-Control-*對(duì)象來進(jìn)行跨域。同時(shí)還可以對(duì)一些請(qǐng)求進(jìn)行攔截。如果請(qǐng)求是無效的,或者是不被允許的,該請(qǐng)求被拒絕或者禁止。?
其在web.xml文件中的基本配置如下:
filter
filter-nameCorsFilter/filter-name
filter-classorg.apache.catalina.filters.CorsFilter/filter-class
init-param
param-namecors.allowed.origins/param-name
param-value
,
/param-value
/init-param
init-param
param-namecors.allowed.methods/param-name
param-value
GET,POST,HEAD,OPTIONS,PUT
/param-value
/init-param
init-param
param-namecors.allowed.headers/param-name
param-value
Content-Type,X-Requested-With,accept,Origin,Access-Control-Request-Method,Access-Control-Request-Headers,Access-Control-Allow-Origin
/param-value
/init-param
init-param
param-namecors.exposed.headers/param-name
param-value
Access-Control-Allow-Origin,Access-Control-Allow-Credentials
/param-value
/init-param
init-param
param-namecors.support.credentials/param-name
param-valuetrue/param-value
/init-param
init-param
param-namecors.preflight.maxage/param-name
param-value10/param-value
/init-param
/filter
filter-mapping
filter-nameCorsFilter/filter-name
url-pattern/wxrefund/*/url-pattern
/filter-mapping
3、cors.allowed.origins:允許訪問資源的源列表。*表示任何來源都可以訪問該資源。否則,只有配置的白名單的來源可以訪問該資源,其中白名單用逗號(hào)隔開,如。
4、cors.allowed.methods:允許訪問的http請(qǐng)求方法,如GET,POST,HEAD,OPTIONS,PUT等,方法名用逗號(hào)隔開。
5、cors.allowed.headers:在實(shí)際請(qǐng)求時(shí)可使用的請(qǐng)求頭列表,用逗號(hào)隔開。如Content-Type,X-Requested-With,accept,Origin,Access-Control-Request-Method,Access-Control-Request-Headers,Access-Control-Allow-Origin。這些頭也將返回作為訪問控制的一部分。
跨域是指跨域名的訪問,以下情況都屬于跨域:
如果 域名和端口都相同,但是請(qǐng)求路徑不同 ,不屬于跨域,如:
跨域不一定會(huì)有跨域問題。
因?yàn)榭缬騿栴}是瀏覽器對(duì)于ajax請(qǐng)求的一種安全限制: 一個(gè)頁面發(fā)起的ajax請(qǐng)求,只能是于當(dāng)前頁同域名的路徑 ,這能有效的阻止跨站攻擊。
因此: 跨域問題 是針對(duì)ajax的一種限制 。
但是這卻給我們的開發(fā)帶來了不變,而且在實(shí)際生成環(huán)境中,肯定會(huì)有很多臺(tái)服務(wù)器之間交互,地址和端口都可能不同,怎么辦?
目前比較常用的跨域解決方案有3種:
我們這里會(huì)采用cors的跨域方案。
CORS是一個(gè)W3C標(biāo)準(zhǔn),全稱是"跨域資源共享"(Cross-origin resource sharing)。
它允許瀏覽器向跨源服務(wù)器,發(fā)出 XMLHttpRequest 請(qǐng)求,從而克服了AJAX只能 同源 使用的限制。
CORS需要瀏覽器和服務(wù)器同時(shí)支持。目前,所有瀏覽器都支持該功能,IE瀏覽器不能低于IE10。
瀏覽器會(huì)將ajax請(qǐng)求分為兩類,其處理方案略有差異:簡單請(qǐng)求、特殊請(qǐng)求。
只要同時(shí)滿足以下兩大條件,就屬于簡單請(qǐng)求。:
(1) 請(qǐng)求方法是以下三種方法之一:
(2)HTTP的頭信息不超出以下幾種字段:
當(dāng)瀏覽器發(fā)現(xiàn)發(fā)現(xiàn)的ajax請(qǐng)求是簡單請(qǐng)求時(shí),會(huì)在請(qǐng)求頭中攜帶一個(gè)字段: Origin .
Origin中會(huì)指出當(dāng)前請(qǐng)求屬于哪個(gè)域(協(xié)議+域名+端口)。服務(wù)會(huì)根據(jù)這個(gè)值決定是否允許其跨域。
如果服務(wù)器允許跨域,需要在返回的響應(yīng)頭中攜帶下面信息:
注意:
如果跨域請(qǐng)求要想操作cookie,需要滿足3個(gè)條件:
不符合簡單請(qǐng)求的條件,會(huì)被瀏覽器判定為特殊請(qǐng)求,,例如請(qǐng)求方式為PUT。
特殊請(qǐng)求會(huì)在正式通信之前,增加一次HTTP查詢請(qǐng)求,稱為"預(yù)檢"請(qǐng)求(preflight)。
瀏覽器先詢問服務(wù)器,當(dāng)前網(wǎng)頁所在的域名是否在服務(wù)器的許可名單之中,以及可以使用哪些HTTP動(dòng)詞和頭信息字段。只有得到肯定答復(fù),瀏覽器才會(huì)發(fā)出正式的 XMLHttpRequest 請(qǐng)求,否則就報(bào)錯(cuò)。
一個(gè)“預(yù)檢”請(qǐng)求的樣板:
與簡單請(qǐng)求相比,除了Origin以外,多了兩個(gè)頭:
服務(wù)的收到預(yù)檢請(qǐng)求,如果許可跨域,會(huì)發(fā)出響應(yīng):
除了 Access-Control-Allow-Origin 和 Access-Control-Allow-Credentials 以外,這里又額外多出3個(gè)頭:
如果瀏覽器得到上述響應(yīng),則認(rèn)定為可以跨域,后續(xù)就跟簡單請(qǐng)求的處理是一樣的了。
雖然原理比較復(fù)雜,但是前面說過:
事實(shí)上,SpringMVC已經(jīng)幫我們寫好了CORS的跨域過濾器:CorsFilter ,內(nèi)部已經(jīng)實(shí)現(xiàn)了剛才所講的判定邏輯,我們直接用就好了。
在 Application 下編寫一個(gè)配置類,并且注冊(cè)CorsFilter:
結(jié)構(gòu):
放到Application下即可。
4.5.4.重啟測試:
訪問正常:
分享名稱:java代碼跨域cors,javascript跨域
當(dāng)前路徑:http://chinadenli.net/article39/dsidpph.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供網(wǎng)站設(shè)計(jì)、全網(wǎng)營銷推廣、動(dòng)態(tài)網(wǎng)站、軟件開發(fā)、云服務(wù)器、網(wǎng)站營銷
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場,如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)