最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Cordova cross-domain file: iframe contentwindow communication - Stack Overflow

programmeradmin0浏览0评论

I found that i can do cross-domain munication from a page on file:// and an iframe hosted on a remote host with the contentWindow property of the iframe.

For example on the device I have an html page at the url file://.../index.html that loads cordova and contains an iframe:

<script type="text/javascript" src="cordova.js"></script>
<iframe id="appframe"></iframe>

On this page I can execute a javascript that loads the iframe and save a reference of an object in the iframed page like this:

var iframe = document.getElementById("appframe");
iframe.onload = function(){
    iframe.contentWindow.cordova = window.cordova;
}
iframe.src = ".html";

Now on the page inside the iframe, .html, i can execute a cordova call, for example:

cordova.exec(null, null, "StatusBar", "hide", []);

and this unexpectedly works, calling the native layer of the StatusBar cordova plugin and hiding the statusbar.

My question is:

Is this safe to use or is an hack that won't work in future version of the browsers?

I tested it on iOS 9 and Android 5 devices.

I found that i can do cross-domain munication from a page on file:// and an iframe hosted on a remote host with the contentWindow property of the iframe.

For example on the device I have an html page at the url file://.../index.html that loads cordova and contains an iframe:

<script type="text/javascript" src="cordova.js"></script>
<iframe id="appframe"></iframe>

On this page I can execute a javascript that loads the iframe and save a reference of an object in the iframed page like this:

var iframe = document.getElementById("appframe");
iframe.onload = function(){
    iframe.contentWindow.cordova = window.cordova;
}
iframe.src = "http://www.example./appframe.html";

Now on the page inside the iframe, http://www.example./appframe.html, i can execute a cordova call, for example:

cordova.exec(null, null, "StatusBar", "hide", []);

and this unexpectedly works, calling the native layer of the StatusBar cordova plugin and hiding the statusbar.

My question is:

Is this safe to use or is an hack that won't work in future version of the browsers?

I tested it on iOS 9 and Android 5 devices.

Share Improve this question edited Dec 20, 2016 at 16:27 Beat 4,4122 gold badges37 silver badges53 bronze badges asked Nov 2, 2015 at 9:47 mircocmircoc 1592 silver badges8 bronze badges 3
  • does this work if the appframe is served from file:/// ? – Lorenzo Boccaccia Commented Mar 17, 2016 at 8:41
  • Interesting. IMO it's very unsafe to do it, if you don't control the remote website - when they learn that you embed their code in your app, they can adjust their code and cordova.exec anything that your app supports via a plugin, and maybe with conjuction with some other bug, get really big privilege escalation. Having said that, you need to explicitly inject the reference to cordova into the iframe for this to work, so it's not a security hole unless you let it be. – jakub.g Commented May 19, 2016 at 9:43
  • @mircoc Like you I am also trying to load html pages(size of pages goes from 5Mb to 100Mb) in iframe but many times app crashes with error 'Out of memory'. Did you face this type of problem? if yes, can you guide me how to resolve this? – Deepika Commented Jul 17, 2017 at 5:05
Add a ment  | 

3 Answers 3

Reset to default 1

I Believe that the safer way to municate between frames is postMessage as described in MDN, do it in a different way could cause inconsistency between devices (Remember how fragmented is android and how painful could be the backward patibility with 4.3 and below)

So, you could get the iFrame element and then post a msg like

otherWindow.postMessage(InfoToSend, "*");

In the same way you could listen to that event inside the frame:

window.addEventListener("message", receiveMessage, false);

This will no cause cross-frame issues and it will be the safer way to pass information, the bad news is that you will not be able to pass the window.cordova instance, so you will need to establish a conversation between the iFrame and the window.top frame.

I think that probably you have in your config.xml the following tag.

<access origin="*" />

as described here https://cordova.apache/docs/en/latest/guide/appdev/whitelist/ you could restrict the cross domain policy to specified domains used as value of the property "origin" instead of using a wildcard.

So if you are using the wildcard value, this should be the desired behaviour.

With this PR you can fall back to using files instead of https://localhost with this preference:

<preference name="AndroidInsecureFileModeEnabled" value="true" />
发布评论

评论列表(0)

  1. 暂无评论