跨來源資源共享 (CORS) 是 Web 瀏覽器實作的重要安全機制,用於保護使用者免受潛在惡意腳本的侵害。然而,這也是開發人員(尤其是剛接觸 Web 開發的開發人員)感到沮喪的常見原因。本文旨在揭開 CORS 的神秘面紗,解釋其存在的原因,並提供處理 CORS 相關問題的策略。
CORS 是由 Web 瀏覽器實現的安全功能,用於控制從資源來源網域之外的另一個網域對網頁上的資源(例如 API 或字體)的存取。
要了解CORS,我們首先需要了解同源策略。此策略是 Web 瀏覽器中的一項基本安全措施,它限制從一個來源載入的文件或腳本如何與另一個來源的資源互動。來源由協定、域和連接埠的組合定義。
例如:
https://example.com/page1
和https://example.com/page2
有相同的來源。
https://example.com
和http://example.com
有不同的來源(不同的協定)。
https://example.com
和https://api.example.com
有不同的來源(不同的子網域)。
引入 CORS 是為了允許伺服器指定允許哪些來源存取其資源,從而以受控方式放寬同源策略。這對於經常需要向不同網域上託管的 API 發出請求的現代 Web 應用程式至關重要。
開發人員在嘗試從 Web 應用程式向不同網域上的 API 發出請求時經常會遇到 CORS 錯誤。典型的 CORS 錯誤可能如下所示:
Access to fetch at 'https://api.example.com/data' from origin 'https://myapp.com'
has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present
on the requested resource.
當Web應用程式發出跨來源請求時:
瀏覽器發送帶有Origin
標頭的請求,指定請求頁面的來源。
然後伺服器可以回應:
Access-Control-Allow-Origin
標頭指定允許哪些來源。
其他 CORS 標頭控制允許的方法、標頭等。
解決 CORS 問題最正確的方法是設定伺服器發送正確的 CORS 標頭。這通常涉及:
設定Access-Control-Allow-Origin
標頭以指定允許的來源。
依需求配置其他 CORS 標頭(例如Access-Control-Allow-Methods
、 Access-Control-Allow-Headers
)。
Node.js 中使用 Express 的範例:
const express = require('express');
const cors = require('cors');
const app = express();
app.use(cors({
origin: 'https://myapp.com'
}));
// Your routes here
如果您無法控制伺服器,則可以設定代理伺服器來新增必要的 CORS 標頭。這通常在開發環境中完成。
使用 Create React App 的代理程式功能的範例:
在package.json
中:
{
"proxy": "https://api.example.com"
}
JSONP(帶填充的 JSON)是一種較舊的技術,可以透過使用不受同源策略約束的腳本標籤來繞過 GET 請求的 CORS。
function handleResponse(data) {
console.log(data);
}
const script = document.createElement('script');
script.src = 'https://api.example.com/data?callback=handleResponse';
document.body.appendChild(script);
注意:JSONP 被認為已經過時,且安全性低於正確的 CORS 實作。
了解安全隱患:不要盲目繞過 CORS。它的存在是有原因的。
使用特定來源:避免在生產中的Access-Control-Allow-Origin
中使用*
。指定確切的允許來源。
使用特定於環境的配置:針對開發和生產環境具有不同的 CORS 設定。
處理預檢請求:對於非簡單請求,正確處理OPTIONS請求。
牢記安全性:請記住 CORS 是由瀏覽器強制執行的。伺服器端的安全措施仍然是必要的。
雖然 CORS 可能令人沮喪,但它是一項重要的安全功能。透過了解其工作原理並實施適當的解決方案,開發人員可以建立安全且功能齊全的 Web 應用程式,與跨不同領域的資源互動。
請記住,如果您遇到 CORS 問題,第一步是確定您是否可以控制伺服器。如果這樣做,實現正確的 CORS 標頭是最好的解決方案。如果沒有,請考慮使用代理,或作為簡單 GET 請求的最後手段,JSONP。
原文出處:https://dev.to/shanu001x/how-cors-actually-works-behind-the-scenes-5304