I have an HTML and an iframe inside it. when I try to access iframe contents it shows error like this.
" Uncaught DOMException: Blocked a frame with origin "http://parattapayyan.surge.sh" from accessing a cross-origin frame.
at http://parattapayyan.surge.sh/test.html:14:24
(anonymous) # test.html:14 "
how some chat companies like "intercom" and etc, accessing iframe from external server and components inside iframe..?
When Site A tries to fetch content from Site B in a frame, by default, Site B's pages are not accessible due to security reasons(Read this :: https://developer.mozilla.org/en-US/docs/Web/Security/Same-origin_policy); But using the Access-Control-Allow-Origin header site B can give cross-origin access to specific requesting origins.
Site B can serve its pages to Site A with the following response header:
Access-Control-Allow-Origin: http://www.siteA.com
Without site B doing this, you won’t be able to access site A in a frame.
Related
While I was testing the SOP, i came to this scenario two documents has a relationship with the same domain as i would expected and it throws an error when i try to get the location.
To reproduce the problem:
Open https://www.google.com
from the console let opened = window.open("https://www.google.com")
from the same window do opened.location.toString() which will return the correct location
from the second tab's console do document.domain = "www.google.com"
from the first tab do opened.location.toString() and you will get an error
Uncaught DOMException: Blocked a frame with origin "https://www.google.com" from accessing a cross-origin frame.
at <anonymous>:1:12
Can anyone explain this strange behavior?
This error is not a bug. The same-origin policy is a security mechanism that ensures that window objects only have access to the informations they are authorized to get. In your case, this includes having access to opened.location.
Upon creation, both tabs have the same origin, which allows the first one to access opened.location. But after the call to document.domain='www.google.com', they don't anymore.
"What? But in both tabs, window.location.origin are identical"
Yes, but it is a little bit more complex. The origin is defined by the scheme/host/port tuple, see #TheUnknown's answer for more details. The scheme and host stay the same all along, and they're the one included in the string of window.location.origin.
The tricky thing to know is that any call to document.domain, including document.domain = document.domain, causes the port number to be overwritten with null, therefore causing a difference in the two tabs' origins, and preventing them from communicating informations like opened.location with one another, thus the error.
Informations extracted from MDN's guide on same-origin policy
First, I would recommend, you read Same-origin Policy.
The same-origin policy is a critical security mechanism that restricts
how a document or script loaded from one origin can interact with a
resource from another origin. It helps isolate potentially malicious
documents, reducing possible attack vectors.
Two URLs have the same origin if the protocol, port (if specified), and host are the same for both. You may see this referenced as the "scheme/host/port tuple", or just "tuple". (A "tuple" is a set of items that together comprise a whole — a generic form for double/triple/quadruple/quintuple/etc.)
In this particular case, you open a window with HTTPS protocol, however when you set the domain, the protocol is changed to HTTP, see image below:
As per 1, if the protocols are not the same, then its a violation of the principle and hence you get the error
Uncaught DOMException: Blocked a frame with origin
"https://www.google.com" from accessing a cross-origin frame.
cross-origin is the keyword here.
Also, check out this SecurityError: Blocked a frame with origin from accessing a cross-origin frame for more details.
This will be a bit uninformative (just states facts), nevertheless:
After you change domain in window B, window B stops accounting window A as opener.
Since window A is no longer considered an opener of window B, the access is prohibited.
This makes me think, that altering document.domain is considered potentially insecure and is "punished" by orphaning the child window.
I am trying to list the names of all the iframes in a page, so I can access them through Selenium.
The problem is that the name of the iframe changes each time, so I need to loop through all of them.
I am getting:
Uncaught DOMException: Blocked a frame with origin "http://localhost:8080" from accessing a cross-origin frame.
error when I try to loop over them using:
for (var f = 0; f < window.frames.length; f++) {
console.log(window.frames[f].name)
}
Is there a way to get the name of the iframe in a different way?
This error message...
Uncaught DOMException: Blocked a frame with origin "http://localhost:8080" from accessing a cross-origin frame.
...implies that the WebDriver instance blocked from accessing a cross-origin frame.
Same-origin policy
Same-origin policy : Same-origin policy restricts how a document or script loaded from one origin can interact with a resource from another origin. It is a critical security mechanism for isolating potentially malicious documents.
Cross-Origin Resource Sharing (CORS)
Cross-Origin Resource Sharing (CORS) : Cross-Origin Resource Sharing (CORS) is a mechanism that uses additional HTTP headers to tell a Browser Client to let the AUT (Application under Test) running at one origin (domain) have permission to access selected resources from a server at a different origin. A web application makes a cross-origin HTTP request when it requests a resource that has a different origin (domain, protocol, and port) than its own origin.
Example of an origin
Here is an example of origin comparisons to the URL http://store.company.com/dir/page.html
URL Outcome Reason
http://store.company.com/dir2/other.html Success
http://store.company.com/dir/inner/another.html Success
https://store.company.com/secure.html Failure Different protocol
http://store.company.com:81/dir/etc.html Failure Different port
http://news.company.com/dir/other.html Failure Different host
What went wrong
When you tried to loop through frames your script/program tried to access an <iframe> with different origin using JavaScript which would been a huge security flaw if you would have achieved it. As mentioned above the same-origin policy browsers block scripts trying to access a <iframe> with a different origin.
Two pages have the same origin if the protocol, port (if one is specified), and host are the same for both the webpages. You'll see this referred to as the "scheme/host/port tuple" at times (where a "tuple" is a set of three components that together comprise a whole). Perhaps the protocol, domain, hostname and port must be the same of your same domain when you want to access the desired frame.
Solution
The AUT may contain numerous frames / iframes and some of them may be loaded only after certain JavaScript / Ajax have completed where as some of them may be having style attribute set as display:none; or visiblity as hidden. Of-course won't require to interact with all of them. So it will be a better approach to identify the attributes of the <iframe> and switch accordingly. You can switch to an <iframe> through:
Frame Name
Frame ID
Frame Index
WebElement
As per best practices when you intent to switch to a frame induce WebDriverWait for frameToBeAvailableAndSwitchToIt as per the references below.
Here you can find a relevant discussion on Uncaught DOMException
References
Some references:
In this discussion you will find a detailed analysis on SecurityError: Blocked a frame with origin from accessing a cross-origin frame
In this discussion you will find the different approaches on Is it possible to switch to an element in a frame without using driver.switchTo().frame(“frameName”) in Selenium Webdriver Java?
In the A Better Approach to Switch Frames section of this discussion you will find the different approaches on How can I select a html element no matter what frame it is in in selenium?
You can try something like this : (Not sure about JavaScript)
var iframeElems = driver.findElements(webdriver.By.tagName("iframe"));
iterate this list to get the attribute.
for (var f = 0; f < iframeElems.length; f++) {
console.log(iframeElems.getAttribute("attribute name"))
}
Dirty solution:
for windows:
chrome.exe --user-data-dir="" --disable-web-security
for mac:
open -a Google\ Chrome --args --disable-web-security --user-data-dir=""
In this way you open the chrome and let it ignore the web security.
You can use selenium to get iframe tags like this:
var iframeElems = driver.findElements(webdriver.By.xpath("//iframe"));
Then loop on those elements and get the name attribute:
iframe.getAttribute('name')
I have 2 applications both hosted individually. Lets name them App A and App B.
In App A's iframe I am loading the url of App B to perform an action.(It is actually a form submit which contains file upload, but to not reload the page, I'm using an iframe to do that)
While the url is called and the action is performed in App B correctly, I'm unable to read the response in App A.
I'm getting the below JS Exception while reading the response.
Failed to read the 'contentDocument' property from 'HTMLIFrameElement': Blocked a frame with origin "App A URL" from accessing a cross-origin frame.
When the URL is loaded in App A, it is received by a Servlet in App B. The action is performed in App B and response is returned. In App B, I have set the following -
response.setContentType("application/json");
response.setHeader("Access-Control-Allow-Origin","*");
response.setHeader("Access-Control-Allow-Methods","POST,GET,OPTIONS,DELETE");
Even by setting Access-Control-Allow-Orgin to *, I'm unable to read the response.
How do I get the response in my iframe?
PS: I don't want to use any third party API.
I am currently attempting to wrap a web application (ConnectWise) for inclusion within my company's central intranet site. It's a fairly simple process for the most part; create a containing page, with an iframe, point the iframe at the ConnectWise url. This part works for almost all of the functionality.
The problem comes during certain select features of the app (in this case, part of the process of creating a timesheet entry), which simply fail to work. Chrome gives the following console output.
Uncaught SecurityError: Failed to read the 'frame' property from 'Window': Blocked a frame with origin "https://app.example.com" from accessing a frame with origin "https://host.example.com". Protocols, domains, and ports must match.
I am aware this is caused by the security options for cross-site and same-origin policies. Given the following points, is there a way to overcome this?
I have full control over https://host.example.com
I can change html, javascript, and file contents
I can change IIS settings and headers
I have partial control over https://app.example.com
I can not change html, javascript, and file contents
I can change IIS settings and headers.
I have tried setting the Access-Control-Allow-Origin on each server, which so far is the only method I've come across that does not involve being able to change the file contents for the app server. This does not appear to work when given the settings (and combinations of settings) of
* or https://app.example.com while on https://host.example.com
* or https://host.example.com while on https://app.example.com
Edit:
The solution to this "duplicate" question is not applicable here. I do not have access to change file contents (including javascript) of the iframed page (app.example.com). Additionally, the script requiring the permission to run is the page within the iframe, not the page hosting the iframe.
CORS headers such as Access-Control-Allow-Origin only affect AJAX requests, not DOM access.
However, If they are both on the same domain but different subdomains then you can include the following on each page:
document.domain = 'example.com';
From MDN:
One document is allowed to access another if they have both set
document.domain to the same value, indicating their intent to
cooperate
If app.example.com has any script includes to host.example.com then you could put the above code in those scripts to set the domain.
e.g.
<script src="https://host.example.com/setup.js"></script>
No, it is not possible.
Access-Control-Allow-Origin primarily affects getting raw data from HTTP requests, not live DOMs.
postMessage can let frames on different origins communicate, but it requires JS to be included on both pages.
Hi I am having a problem with this message.
the url from my MAIN page is:
page1.mydomain.com/page1.html
this page have a Iframe to:
frame.mydomain.com/iframe.html
and from the main page I open a window from a another page like that:
mywindow = window.open("http://page1.mydomain.com/page3.html", 'page3', 'status=1,height=768,width=1280,scrollbars=1');
all the 3 pages have set the javascript:
document.domain = "mydomain.com";
I can interact from the main page to the iframe without a problem.
I only have problem to access the window.open properties.
Like:
mywindow.document.getElementById("something")
I got that error message.
blocked a frame with origin from accessing a cross-origin frame
if I try from the page3:
window.opener.document.getElementById("somethingPage1")
I got the same error:
blocked a frame with origin from accessing a cross-origin frame
Why I can interact with the iframe and can't interact with the window.open and the window.opener ?
In my case domain names were different and I solved it by replacing client's domain with the parent's domain name. You can try that if domain name is not matter in child(popup) windows.
What you are trying to access window.opener.document.getElementById() won't work.
It will raise security error as you posted. Best way to do is make both the URLs under the same Domain Name if it's possible. Or just for the development you can install extension
"Allow-Control-Allow-Origin:" in Chrome it will work.