Chính sách cùng nguồn gốc
Bạn không thể truy cập một <iframe>
nguồn gốc khác bằng JavaScript, đó sẽ là một lỗ hổng bảo mật rất lớn nếu bạn có thể làm điều đó. Đối với các trình duyệt chính sách cùng nguồn gốc, các tập lệnh chặn các tập lệnh đang cố truy cập vào một khung có nguồn gốc khác .
Nguồn gốc được coi là khác nhau nếu ít nhất một trong các phần sau của địa chỉ không được duy trì:
<protocol>://<hostname>:<port>/...
Giao thức , tên máy chủ và cổng phải giống nhau trong tên miền của bạn, nếu bạn muốn truy cập vào một khung.
LƯU Ý: Internet Explorer được biết là không tuân thủ nghiêm ngặt quy tắc này, xem tại đây để biết chi tiết.
Ví dụ
Đây là những gì sẽ xảy ra khi cố gắng truy cập các URL sau từ http://www.example.com/home/index.html
URL RESULT
http://www.example.com/home/other.html -> Success
http://www.example.com/dir/inner/another.php -> Success
http://www.example.com:80 -> Success (default port for HTTP)
http://www.example.com:2251 -> Failure: different port
http://data.example.com/dir/other.html -> Failure: different hostname
https://www.example.com/home/index.html:80 -> Failure: different protocol
ftp://www.example.com:21 -> Failure: different protocol & port
https://google.com/search?q=james+bond -> Failure: different protocol, port & hostname
Giải pháp thay thế
Mặc dù chính sách cùng nguồn gốc ngăn các tập lệnh truy cập nội dung của các trang web có nguồn gốc khác nhau, nếu bạn sở hữu cả hai trang, bạn có thể giải quyết vấn đề này bằng cách sử dụng window.postMessage
và message
sự kiện tương đối của nó để gửi tin nhắn giữa hai trang, như sau:
Trong trang chính của bạn:
let frame = document.getElementById('your-frame-id');
frame.contentWindow.postMessage(/*any variable or object here*/, 'http://your-second-site.com');
Đối số thứ hai postMessage()
có thể là '*'
chỉ ra không có ưu tiên nào về nguồn gốc của điểm đến. Nguồn gốc mục tiêu phải luôn được cung cấp khi có thể, để tránh tiết lộ dữ liệu bạn gửi đến bất kỳ trang web nào khác.
Trong của bạn <iframe>
(có trong trang chính):
window.addEventListener('message', event => {
// IMPORTANT: check the origin of the data!
if (event.origin.startsWith('http://your-first-site.com')) {
// The data was sent from your site.
// Data sent with postMessage is stored in event.data:
console.log(event.data);
} else {
// The data was NOT sent from your site!
// Be careful! Do not use it. This else branch is
// here just for clarity, you usually shouldn't need it.
return;
}
});
Phương pháp này có thể được áp dụng theo cả hai hướng , tạo cả người nghe trong trang chính và nhận phản hồi từ khung. Logic tương tự cũng có thể được triển khai trong cửa sổ bật lên và về cơ bản, bất kỳ cửa sổ mới nào được tạo bởi trang chính (ví dụ: sử dụng window.open()
) cũng không có sự khác biệt.
Vô hiệu hóa chính sách cùng nguồn gốc trong trình duyệt của bạn
Đã có một số câu trả lời hay về chủ đề này (tôi chỉ thấy chúng googling), vì vậy, đối với các trình duyệt có thể, tôi sẽ liên kết câu trả lời tương đối. Tuy nhiên, hãy nhớ rằng việc vô hiệu hóa chính sách cùng nguồn gốc sẽ chỉ ảnh hưởng đến trình duyệt của bạn . Ngoài ra, việc chạy trình duyệt có cài đặt bảo mật cùng nguồn gốc đã vô hiệu hóa cấp cho bất kỳ trang web nào truy cập tài nguyên nguồn gốc chéo, vì vậy nó rất không an toàn và KHÔNG BAO GIỜ nên được thực hiện nếu bạn không biết chính xác những gì bạn đang làm (ví dụ: mục đích phát triển) .
Access-Control-Allow-Origin
không áp dụng cho iFrames, chỉ áp dụng cho XHRs, Phông chữ, WebGL vàcanvas.drawImage
. Tôi tinpostMessage
là lựa chọn duy nhất.