laurentj / slimerjs

A scriptable browser like PhantomJS, based on Firefox
http://slimerjs.org
Other
3k stars 258 forks source link

cannot get the outerHTML for a cross origin iframe from page.evaluate of parent window #699

Open andynuss opened 6 years ago

andynuss commented 6 years ago

versions

Steps to reproduce the issue

Create a simple webpage that holds nothing but an iframe in a different origin/domain.

Verify that in chrome and firefox devtools, though the iframe displays the content of the cross-origin src, devtools cannot see anything on frames[0] of the root page relating to the framewin.document.

Run this page thru slimer and use page.evaluate to console.log() the following: var win = frames[0]; var content = win.contentDocument.documentElement.outerHTML; console.log(content);

Get a Script Error logged in the console output of slimer: Script Error: Error: Permission denied to access property "contentDocument" on cross-origin object Stack: -> phantomjs://webpage.evaluate(): 3 -> phantomjs://webpage.evaluate(): 1

Although this is not surprising, phantom allows you to do this! Is there any way to relax cors issues in page.evaluate in slimerjs?

laurentj commented 6 years ago

phantom allows you to do this because

  1. it is based on an older web engine in which there are less security features
  2. it probably disables some security features, which is bad because it does not match the reality. And it is dangerous in fact.

Disabling security features means that content in the frame can access to the host page and vice-versa, and this is really dangerous. Most of time, you don't know what these pages are doing, except if you are the author of both sites.

Did you try to evaluate the javascript directly into the frame, by using API related to frames?

andynuss commented 6 years ago

I'll give your suggestion a try and see if that works.

Paxa commented 6 years ago

It used to work like this, but now sometimes not working, I think it fails before iframe is completely loaded. Will try to make some example

andynuss commented 6 years ago

I tried it as follows in the page.onLoadFinished hook:

page.switchToFrame('0');     // use an index of zero as name since frame has no name
page.evaluate(function () {
    console.log(document.documentElement.outerHTML);
});

And it just gave me the outerHTML of the root page. Am I doing something wrong?

andynuss commented 6 years ago

Any ideas on whether this is a limitation of slimer and if so, are there plans to fix?