Politica della stessa origine
Non puoi accedere a un <iframe>
origine diversa utilizzando JavaScript, sarebbe un enorme difetto di sicurezza se potessi farlo. Per i criteri della stessa origine i browser bloccano gli script tentando di accedere a un frame con un'origine diversa .
L'origine è considerata diversa se almeno una delle seguenti parti dell'indirizzo non è mantenuta:
<protocol>://<hostname>:<port>/...
Il protocollo , il nome host e la porta devono essere gli stessi del tuo dominio, se vuoi accedere a un frame.
NOTA: Internet Explorer è noto per non seguire rigorosamente questa regola, vedere qui per i dettagli.
Esempi
Ecco cosa succederebbe provando ad accedere ai seguenti URL da 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
Soluzione
Anche se la politica della stessa origine impedisce agli script di accedere al contenuto dei siti con un'origine diversa, se si possiede entrambe le pagine, è possibile aggirare questo problema utilizzando window.postMessage
e il relativo message
evento relativo all'invio di messaggi tra le due pagine, in questo modo:
Nella tua pagina principale:
let frame = document.getElementById('your-frame-id');
frame.contentWindow.postMessage(/*any variable or object here*/, 'http://your-second-site.com');
Il secondo argomento postMessage()
può essere '*'
quello di non indicare alcuna preferenza sull'origine della destinazione. Se possibile, è necessario fornire sempre un'origine target, per evitare di divulgare i dati inviati a qualsiasi altro sito.
Nel tuo <iframe>
(contenuto nella pagina principale):
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;
}
});
Questo metodo può essere applicato in entrambe le direzioni , creando anche un listener nella pagina principale e ricevendo risposte dal frame. La stessa logica può essere implementata anche nei pop-up e praticamente in qualsiasi nuova finestra generata dalla pagina principale (ad es. Utilizzo window.open()
), senza alcuna differenza.
Disattivazione criterio dell'origine nel tuo navigatore
Ci sono già alcune buone risposte su questo argomento (le ho appena trovate su Google), quindi, per i browser in cui ciò è possibile, collegherò la risposta relativa. Tuttavia, tieni presente che la disabilitazione della politica della stessa origine influirà solo sul tuo browser . Inoltre, l'esecuzione di un browser con le impostazioni di sicurezza della stessa origine disabilitate garantisce a qualsiasi sito Web l'accesso alle risorse di origine incrociata, quindi è molto pericoloso e non dovrebbe MAI essere fatto se non si sa esattamente cosa si sta facendo (ad es. Scopi di sviluppo) .
Access-Control-Allow-Origin
non si applica a iFrame, ma solo a XHR, Fonts, WebGL ecanvas.drawImage
. CredopostMessage
sia l'unica opzione.