前世今生
在WEB應用普及的今天,個人信息(賬號、COOKIE等)廣泛應用於網頁。瀏覽器同源策略保證了WEB環境的安全性。同源策略是說,在a.com域名下通過ajax或者XmlHttpRequest等方式訪問b.com的資源時,是不被允許的。
然而在很多時候,出於業務的的需要,我們經常有類似的跨域訪問 的需求。瀏覽器有一些支持跨域訪問的標籤,例如script,img等。有這樣的需求,自然就衍生了一些解決辦法。
比較普遍的是通過jsonp的方式來實現接口。
另外一個方式就是在服務器端配置,允許部分或者所有頁面進行跨域訪問。
JSONP方式
簡單來說,jsonp返回的不是json數據,而且一段通過函數將json數據包起來的js代碼。這樣,就可以通過script標籤來加載這段代碼,實現任意服務器的訪問。
對於如下一個返回json數據的接口:
http://www.test.com/jsonServerResponse
其對應的jsonp方式的用法如下,其中jsonpCallback是客戶端實現的處理json數據的函數。
<script>
var data;
function jsonpCallback(result) {
data = result;
}
</script>
<script src="http://www.test.com/jsonServerResponse?callback=jsonpCallback"></script>
前端頁面在調用接口時,需要以callback=jsonpCallback的形式,將本地實現的處理json數據的函數上傳到服務器。跨域服務器實現相應的jsonp接口
http://www.test.com/jsonServerResponse?callback=jsonpCallback
這個接口的返回數據如下
jsonpCallback({'msg':'this is json data'});
可以看出,關鍵得在服務器端實現jsonp方式的接口,有了這些,客戶端就可以自由的跨域了!
服務器端
另外一個辦法,直接在服務器端,允許某些來源、某些接口、某些方法以某些形式被跨域調用。
nodejs express配置
app.all('/test', function(req, res, next) {
res.header("Access-Control-Allow-Origin", "*");
res.header('Access-Control-Allow-Methods', 'PUT, GET, POST, DELETE, OPTIONS');
res.header("Access-Control-Allow-Headers", "X-Requested-With");
res.header('Access-Control-Allow-Headers', 'Content-Type');
next();
});
nginx配置
然而添加了這些之後,仍然不好使。查了查,可能是要在nginx上也作設置,在nginx相應路徑添加如下:
location ^~ /test {
add_header 'Access-Control-Allow-Origin' '*';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Methods' 'OPTION, POST, GET';
add_header 'Access-Control-Allow-Headers' 'X-Requested-With, Content-Type';
}
之後重新加載nginx配置即可,大功告成。
更多關於跨域的討論,歡迎留言!