本篇文章由:http://xinpure.com/solutions-for-cross-domain-ajax-cors/
兩種跨域方法
在 Javascript 中跨域訪問是比較常見的事情
就像現在比較流行寫單頁應用,而單頁應用在訪問 API 的時候就會有跨域的問題
要解決跨域的問題,其實也並不復雜,有兩種方案可以選擇
- Jsonp 跨域
Jsonp 的實現原理就是:創建一個回調函數,然后在遠程服務上調用這個函數並且將 JSON 數據形式作為參數傳遞,完成回調。
- CORS(跨域資源共享)
跨源資源共享標准通過新增一系列 HTTP 頭,讓服務器能聲明哪些來源可以通過瀏覽器訪問該服務器上的資源。
對於 GET 以外的 HTTP 方法,或者搭配某些 MIME 類型的 POST 請求,如:PUT 或者 DELETE 等,
以及如果自定義了請求頭的話,瀏覽器必須先以 OPTIONS 請求方式發送一個預請求 (Preflight Request),
從而獲知服務器端對跨域請求所支持的 HTTP 方法,確認了服務器端允許該跨域請求的情況下,以實際的 HTTP 請求方法發送真正的請求。
跨域方法的選擇
Jsonp 跨域方式,兼容性更好,如果需要兼容舊瀏覽器的話,可以考慮使用,但是這種方法不支持自定義請求頭 (Request Headers)
不過,對於訪問 API ,通常都是需要驗證 Token 的,而 Token 都是需要放到請求頭上的
所以對於正在寫的一個單頁應用,我選擇了 CORS
CORS 跨域方式,兼容性其實也不差,至少可以兼容到 IE8 IE9,
兼容 IE8 IE9,需要使用 XDomainRequest 代替 XMLHttpRequests
這個是完全可以接受的
跨域的具體應用
使用 CORS,其實主要都是服務器端的配置,都是設置一系列的響應頭 (Response Headers)
```
Access-Control-Allow-Origin: http://www.YOURDOMAIN.com // 設置允許請求的域名,多個域名以逗號分隔
Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS // 設置允許請求的方法,多個方法以逗號分隔
Access-Control-Allow-Headers: Authorization // 設置允許請求自定義的請求頭字段,多個字段以逗號分隔
Access-Control-Allow-Credentials: true // 設置是否允許發送 Cookies
```
服務端以 PHP 為例:
```
<?php
header('Access-Control-Allow-Origin: http://www.YOURDOMAIN.com');
header('Access-Control-Allow-Credentials: true'); //可選
header('Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS');
header('Access-Control-Allow-Headers: Authorization');
// 判斷如果是 OPTIONS 請求,直接退出即可
if ($_SERVER['REQUEST_METHOD'] == 'OPTIONS') {
exit;
}
echo json_encode(array('status' => '1', 'data' => ''));
?>
```
Javascript 代碼直接使用 Ajax 即可:
```
$.ajax({
url: aURL,
type: aMethod,
data: aParams,
dataType: 'json',
timeout: 1000 * 120,
beforeSend: function (xhr) {
var token = $.cookie('token');
if (token) {
xhr.setRequestHeader('Authorization', 'Bearer ' + token);
}
},
success: function (response) {
if (response.code == 200) {
typeof aSuccess == 'function' && aSuccess(response.data);
} else {
typeof aError == 'function' && aError(response.message);
}
},
error: function(xhr, type){
typeof aError == 'function' && aError(xhr.status + ' ' + xhr.statusText);
}
});
```
參考鏈接
https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Access_control_CORS