跨域,指的是欣賞器不能執行其他網站的劇本。它是由欣賞器的同源計策造成的,是欣賞器對javascript施加的安詳限制。
所謂同源是指,域名,協議,端口溝通。欣賞器執行javascript劇本時,會查抄這個劇本屬于誰人頁面,假如不是同源頁面,就不會被執行。
同源計策的目標,是防備黑客做一些做奸不法的運動。好比說,假如一個銀行的一個應用答允用戶上傳網頁,假如沒有同源計策,黑客可以編寫一個登岸表單提交到本身的處事器上,獲得一個看上去相當高峻上的頁面。黑客把這個頁面通過郵件等發給用戶,用戶誤認為這是某銀行的主網頁舉辦登岸,就會泄露本身的用戶數據。而因為欣賞器的同源計策,黑客無法收到表單數據。
此刻跟著RESTFUL的風行,許多應用提供http/https接口的API,通過xml/json名目對外提供處事,實現開放架構。如,微博、微信、天氣預報、openstack等網站和應用都提供restful接口。
Web應用也在向單頁面偏向成長。
越來越多的web應用此刻是這樣的架構:
靜態單個web頁面
ajax挪用
RESTFUL處事
我們本可以操作各個網站提供的API,做出許多出色的Web應用。但欣賞器執行javascript時的跨域限制,就成為了這類開放架構的攔路虎。
本文提出了一種簡樸有效的方法辦理跨域問題。
常用的跨域要領有這樣一些:
1,利用iFrame會見另一個域。 然后再從另一個頁面讀取iFrame的內容。jquery等有一些封裝。
聽說Firefox等大概不支持讀取另一個iFrame的內容。
2,jsonp。需要處事器支持。利用script src動態獲得一段java代碼。是回調頁面上的js函數,參數是一個json工具。
jquery也有封裝。
3,配置http頭,Access-Control-Allow-Origin:*
但聽說IE有一些版本不識別這個http頭。
4,處事器署理。如,處事器寫一個url的處理懲罰action。其參數是一個url。這個處事器會用參數拼湊一個url,用httpclient庫去執行url,然后把讀取的內容再輸出到http客戶端。
上面提到的這些跨域要領,都有一些問題。有的不能支持所有欣賞器,有的需要修改javascript代碼,有的需要重寫處事器端代碼。有的在session等場景下會有問題。
其實,用nginx反向署理實現跨域,是最簡樸的跨域方法。只需要修改nginx的設置即可辦理跨域問題,支持所有欣賞器,支持session,不需要修改任何代碼,而且不會影響處事器機能。
我們只需要設置nginx,在一個處事器上設置多個前綴來轉發http/https請求到多個真實的處事器即可。這樣,這個處事器上所有url都是溝通的域名、協議和端口。因此,對付欣賞器來說,這些url都是同源的,沒有跨域限制。而實際上,,這些url實際上由物理處事器提供處事。這些處事器內的javascript可以跨域挪用所有這些處事器上的url。
下面,給出一個nginx支持跨域的例子,舉辦詳細說明。
如,我們有兩個pythonflask開拓的項目:testFlask1和testFlask2。
testFlask2項目上的javascript劇本要通過ajax方法挪用testFlask1的一個url,獲取一些數據。
正常環境下陳設,就會有跨域問題,欣賞器拒絕執行如下這樣的挪用。
$("button").click(function () {
$.get("127.0.0.1:8081/partners/json", function (result) {
$("div").html(result);
});
});
$("button").click(function () { $.get("127.0.0.1:8081/partners/json", function (result) { $("div").html(result); }); }); |
下面把testFlask2項目標javascrip文件修改一下。這樣會見同源的url,就不會有跨域問題。
$("button").click(function () {
$.get("partners/json", function (result) {
$("div").html(result);
});
});
$("button").click(function () { $.get("partners/json", function (result) { $("div").html(result); }); }); |
可是,我們testFlask2項目實際上沒有partners/json這樣的url,那怎么處理懲罰呢?
我們這樣編寫nginx的設置文件: