Reputation: 481
I am trying to do cross-domain communication using postMessage between a page (on example1.com) and an iframe on the same page that is on example2.com
When the iframe is done loading, it sends a postMessage to the parent page using the following command:
parent.postMessage('hello parent', 'http://example1.com'); //this command works
In the event handler for postMessage in the parent page (on example1.com), I send a response back to the child page (example2.com) using the following function:
//this function is defined in example1.com:
function receiveMessage(event){
if (event.origin == "http://example2.com"){
console.log('Message Received from iframe'); //this line works
event.source.postMessage('hello to you too', event.origin); //this line does not work
}
}
For some reason, the event handler for postMessage in the iframe is not triggered.
//this function is defined in example2.com
function receiveMessage(event){
if (event.origin == "http://example1.com"){ // I even tried removing this check to no avail
console.log('Message Received from parent'); //this line works
}
}
When the parent tries to send a message to the iframe it simply returns undefined.
Any help is appreciated!
EDIT:
I tried changing the following line in example1.com's receiveMessage event:
event.source.postMessage('hello to you too', event.origin);
to this:
event.source.postMessage('hello to you too', 'http://example2.com');
But I get this following error:
Unable to post message to http://example2.com. Recipient has origin http://example1.com
Why is event.origin evaluating to http://example1.com when it is receiving a message from example2.com?
example1.com is trying to send itself a postMessage. This ought to be the source of the error
Upvotes: 2
Views: 7598
Reputation: 41
In my Vue project, i got same result as you, and finally i changed my origins to another host like 127.0.0.10
and then i got data object
here is my code
first origin : 127.0.0.10:8000
function sendMessage() {
document
.getElementById('frame')
.contentWindow
.postMessage('Hello world!', '*');
}
<iframe class="d-none" src="http://127.0.0.20:8080/login" onload="sendMessage()" id="frame"></iframe>
second origin : 127.0.0.10:8000
window.addEventListener(
"message",
function (event) {
if (event.origin.indexOf('127.0.0.10:8000') > 0)
{
console.log(event.data);
}
}
);
Upvotes: 0
Reputation: 1060
Sometimes postMessage can be very unclear in which frame sends and which one receives. For this reason I created a little script to help unravel communication between frames.
Add the following snippet to your page and watch your console to see what happens. Make sure you add it to your page before the inter frame communication with postMessage begins.
var listener = function (e) {
console.log('Caught ', e.type, ' event from ', e.source.self, ' to ', e.target, ' origin ', e.origin, ' with data ', e.data, '. Full details: ', e);
};
function addToFrame(el) {
var frames = el.querySelectorAll('iframe'), ifrm = 0;
for (var i = 0; i < frames.length; i++) {
frames[i].contentWindow.addEventListener("message", listener, true);
ifrm += addToFrame(frames[i].contentWindow.document);
}
return i + ifrm;
}
window.addEventListener("message", listener, true);
var c = addToFrame(document);
console.log('Recursively added listener to main window and', c, 'frames');
In your console it clearly states which frame sends what to which other frame. For more details, please see my blog post I've prepared for you on my site.
I hope this will help figuring out the iframe communication ;-)
p.s. If this does not help, please create a jsfiddle of your problem. This will make it easier for us to understand the problem you're having...
Upvotes: 3