如何使用Javascript从Iframe实现跨域URL访问?

时间:2022-08-23 10:06:53

I need to access the Parent Domain URL from my Iframe which is in another domain.

我需要从我在另一个域中的Iframe访问父域URL。

For example, "example.com" is my website which has an Iframe from another parent domain, such as "google.com". Here I need to access the parent domain URL from my example.com. That is, I need to get the URL "google.com" in my "example.com" domain. Moreover, the Parent domain cannot be hard coded.

例如,“example.com”是我的网站,其中包含来自其他父域的Iframe,例如“google.com”。在这里,我需要从example.com访问父域URL。也就是说,我需要在“example.com”域中获取URL“google.com”。而且,父域不能被硬编码。

What I tried was using the following code:

我尝试的是使用以下代码:

window.parent.location.href()

but this results in Access denied error. How do I implement this properly in order to achieve this?

但这会导致访问被拒绝错误。为了实现这一目标,我该如何正确实现?

6 个解决方案

#1


33  

You can try and check for the referer, which should be the parent site if you're an iframe

您可以尝试检查引用,如果您是iframe,则应该是父网站

you can do that like this:

你可以这样做:

var href = document.referrer;

#2


13  

You might want to take a look at these questions/answers ; they could give you some informations concerning your problem :

你可能想看看这些问题/答案;他们可以给你一些关于你的问题的信息:

To make things short : accessing iframe from another domain is not possible, for security reasons -- which explains the error message you are getting.

简而言之:出于安全原因,无法从其他域访问iframe - 这解释了您收到的错误消息。


The Same origin policy page on wikipedia brings some informations about that security measure :

*上的同源策略页面提供了有关该安全措施的一些信息:

In a nutshell, the policy permits scripts running on pages originating from the same site to access each other's methods and properties with no specific restrictions — but prevents access to most methods and properties across pages on different sites.

简而言之,该策略允许在源自同一站点的页面上运行的脚本访问彼此的方法和属性,没有任何特定限制 - 但阻止访问不同站点上的页面上的大多数方法和属性。

A strict separation between content provided by unrelated sites must be maintained on client side to prevent the loss of data confidentiality or integrity.

必须在客户端维护不相关站点提供的内容之间的严格分离,以防止数据机密性或完整性的丢失。

#3


6  

Instead of using the referrer, you can implement window.postMessage to communicate accross iframes/windows across domains.
You post to window.parent, and then parent returns the URL.
This works, but it requires asynchronous communication.
You will have to write a synchronous wrapper around the asynchronous methods, if you need it synchronous.

您可以实现window.postMessage来跨域传递iframes / windows,而不是使用引用者。您发布到window.parent,然后父级返回URL。这可行,但它需要异步通信。如果需要同步,则必须围绕异步方法编写同步包装器。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta http-equiv="content-type" content="text/html; charset=utf-8" />
    <title></title>

    <!--
    <link rel="shortcut icon" href="/favicon.ico">


    <link rel="start" href="http://benalman.com/" title="Home">

    <link rel="stylesheet" type="text/css" href="/code/php/multi_file.php?m=benalman_css">

    <script type="text/javascript" src="/js/mt.js"></script>
    -->
    <script type="text/javascript">
        // What browsers support the window.postMessage call now?
        // IE8 does not allow postMessage across windows/tabs
        // FF3+, IE8+, Chrome, Safari(5?), Opera10+

        function SendMessage()
        {
            var win = document.getElementById("ifrmChild").contentWindow;

            // http://robertnyman.com/2010/03/18/postmessage-in-html5-to-send-messages-between-windows-and-iframes/


            // http://*.com/questions/16072902/dom-exception-12-for-window-postmessage
            // Specify origin. Should be a domain or a wildcard "*"

            if (win == null || !window['postMessage'])
                alert("oh crap");
            else
                win.postMessage("hello", "*");
            //alert("lol");
        }



        function ReceiveMessage(evt) {
            var message;
            //if (evt.origin !== "http://robertnyman.com")
            if (false) {
                message = 'You ("' + evt.origin + '") are not worthy';
            }
            else {
                message = 'I got "' + evt.data + '" from "' + evt.origin + '"';
            }

            var ta = document.getElementById("taRecvMessage");
            if (ta == null)
                alert(message);
            else
                document.getElementById("taRecvMessage").innerHTML = message;

            //evt.source.postMessage("thanks, got it ;)", event.origin);
        } // End Function ReceiveMessage




        if (!window['postMessage'])
            alert("oh crap");
        else {
            if (window.addEventListener) {
                //alert("standards-compliant");
                // For standards-compliant web browsers (ie9+)
                window.addEventListener("message", ReceiveMessage, false);
            }
            else {
                //alert("not standards-compliant (ie8)");
                window.attachEvent("onmessage", ReceiveMessage);
            }
        }
    </script>


</head>
<body>

    <iframe id="ifrmChild" src="child.htm" frameborder="0" width="500" height="200" ></iframe>
    <br />


    <input type="button" value="Test" onclick="SendMessage();" />

</body>
</html>

Child.htm

<!DOCTYPE html>
<html lang="en">
<head>
    <meta http-equiv="content-type" content="text/html; charset=utf-8" />
    <title></title>

    <!--
    <link rel="shortcut icon" href="/favicon.ico">


    <link rel="start" href="http://benalman.com/" title="Home">

    <link rel="stylesheet" type="text/css" href="/code/php/multi_file.php?m=benalman_css">

    <script type="text/javascript" src="/js/mt.js"></script>
    -->

    <script type="text/javascript">
        /*
        // Opera 9 supports document.postMessage() 
        // document is wrong
        window.addEventListener("message", function (e) {
            //document.getElementById("test").textContent = ;
            alert(
                e.domain + " said: " + e.data
                );
        }, false);
        */

        // https://developer.mozilla.org/en-US/docs/Web/API/window.postMessage
        // http://ejohn.org/blog/cross-window-messaging/
        // http://benalman.com/projects/jquery-postmessage-plugin/
        // http://benalman.com/code/projects/jquery-postmessage/docs/files/jquery-ba-postmessage-js.html

        // .data – A string holding the message passed from the other window.
        // .domain (origin?) – The domain name of the window that sent the message.
        // .uri – The full URI for the window that sent the message.
        // .source – A reference to the window object of the window that sent the message.
        function ReceiveMessage(evt) {
            var message;
            //if (evt.origin !== "http://robertnyman.com")
            if(false)
            {
                message = 'You ("' + evt.origin + '") are not worthy';
            }
            else
            {
                message = 'I got "' + evt.data + '" from "' + evt.origin + '"';
            }

            //alert(evt.source.location.href)

            var ta = document.getElementById("taRecvMessage");
            if(ta == null)
                alert(message);
            else
                document.getElementById("taRecvMessage").innerHTML = message;

            // http://javascript.info/tutorial/cross-window-messaging-with-postmessage
            //evt.source.postMessage("thanks, got it", evt.origin);
            evt.source.postMessage("thanks, got it", "*");
        } // End Function ReceiveMessage




        if (!window['postMessage'])
            alert("oh crap");
        else {
            if (window.addEventListener) {
                //alert("standards-compliant");
                // For standards-compliant web browsers (ie9+)
                window.addEventListener("message", ReceiveMessage, false);
            }
            else {
                //alert("not standards-compliant (ie8)");
                window.attachEvent("onmessage", ReceiveMessage);
            }
        }
    </script>


</head>
<body style="background-color: gray;">
    <h1>Test</h1>

    <textarea id="taRecvMessage" rows="20" cols="20" ></textarea>

</body>
</html>

#4


1  

You have a couple of options:

你有几个选择:

  1. Scope the domain down (see document.domain) in both the containing page and the iframe to the same thing. Then they will not be bound by 'same origin' constraints.

    将域中的域(请参阅document.domain)放在包含页面和iframe中的同一事物中。然后他们将不受“同源”约束。

  2. Use postMessage which is supported by all HTML5 browsers for cross-domain communication.

    使用所有HTML5浏览器支持的postMessage进行跨域通信。

#5


0  

Good article here: Cross-domain communication with iframes

这里的好文章:与iframe的跨域通信

Also you can directly set document.domain the same in both frames (even

您也可以直接在两个框架中设置document.domain相同(甚至

document.domain = document.domain;

code has sense because resets port to null), but this trick is not general-purpose.

代码有意义,因为将端口重置为null),但这个技巧不是通用的。

#6


-2  

try

window.frameElement.ownerDocument.domain

#1


33  

You can try and check for the referer, which should be the parent site if you're an iframe

您可以尝试检查引用,如果您是iframe,则应该是父网站

you can do that like this:

你可以这样做:

var href = document.referrer;

#2


13  

You might want to take a look at these questions/answers ; they could give you some informations concerning your problem :

你可能想看看这些问题/答案;他们可以给你一些关于你的问题的信息:

To make things short : accessing iframe from another domain is not possible, for security reasons -- which explains the error message you are getting.

简而言之:出于安全原因,无法从其他域访问iframe - 这解释了您收到的错误消息。


The Same origin policy page on wikipedia brings some informations about that security measure :

*上的同源策略页面提供了有关该安全措施的一些信息:

In a nutshell, the policy permits scripts running on pages originating from the same site to access each other's methods and properties with no specific restrictions — but prevents access to most methods and properties across pages on different sites.

简而言之,该策略允许在源自同一站点的页面上运行的脚本访问彼此的方法和属性,没有任何特定限制 - 但阻止访问不同站点上的页面上的大多数方法和属性。

A strict separation between content provided by unrelated sites must be maintained on client side to prevent the loss of data confidentiality or integrity.

必须在客户端维护不相关站点提供的内容之间的严格分离,以防止数据机密性或完整性的丢失。

#3


6  

Instead of using the referrer, you can implement window.postMessage to communicate accross iframes/windows across domains.
You post to window.parent, and then parent returns the URL.
This works, but it requires asynchronous communication.
You will have to write a synchronous wrapper around the asynchronous methods, if you need it synchronous.

您可以实现window.postMessage来跨域传递iframes / windows,而不是使用引用者。您发布到window.parent,然后父级返回URL。这可行,但它需要异步通信。如果需要同步,则必须围绕异步方法编写同步包装器。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta http-equiv="content-type" content="text/html; charset=utf-8" />
    <title></title>

    <!--
    <link rel="shortcut icon" href="/favicon.ico">


    <link rel="start" href="http://benalman.com/" title="Home">

    <link rel="stylesheet" type="text/css" href="/code/php/multi_file.php?m=benalman_css">

    <script type="text/javascript" src="/js/mt.js"></script>
    -->
    <script type="text/javascript">
        // What browsers support the window.postMessage call now?
        // IE8 does not allow postMessage across windows/tabs
        // FF3+, IE8+, Chrome, Safari(5?), Opera10+

        function SendMessage()
        {
            var win = document.getElementById("ifrmChild").contentWindow;

            // http://robertnyman.com/2010/03/18/postmessage-in-html5-to-send-messages-between-windows-and-iframes/


            // http://*.com/questions/16072902/dom-exception-12-for-window-postmessage
            // Specify origin. Should be a domain or a wildcard "*"

            if (win == null || !window['postMessage'])
                alert("oh crap");
            else
                win.postMessage("hello", "*");
            //alert("lol");
        }



        function ReceiveMessage(evt) {
            var message;
            //if (evt.origin !== "http://robertnyman.com")
            if (false) {
                message = 'You ("' + evt.origin + '") are not worthy';
            }
            else {
                message = 'I got "' + evt.data + '" from "' + evt.origin + '"';
            }

            var ta = document.getElementById("taRecvMessage");
            if (ta == null)
                alert(message);
            else
                document.getElementById("taRecvMessage").innerHTML = message;

            //evt.source.postMessage("thanks, got it ;)", event.origin);
        } // End Function ReceiveMessage




        if (!window['postMessage'])
            alert("oh crap");
        else {
            if (window.addEventListener) {
                //alert("standards-compliant");
                // For standards-compliant web browsers (ie9+)
                window.addEventListener("message", ReceiveMessage, false);
            }
            else {
                //alert("not standards-compliant (ie8)");
                window.attachEvent("onmessage", ReceiveMessage);
            }
        }
    </script>


</head>
<body>

    <iframe id="ifrmChild" src="child.htm" frameborder="0" width="500" height="200" ></iframe>
    <br />


    <input type="button" value="Test" onclick="SendMessage();" />

</body>
</html>

Child.htm

<!DOCTYPE html>
<html lang="en">
<head>
    <meta http-equiv="content-type" content="text/html; charset=utf-8" />
    <title></title>

    <!--
    <link rel="shortcut icon" href="/favicon.ico">


    <link rel="start" href="http://benalman.com/" title="Home">

    <link rel="stylesheet" type="text/css" href="/code/php/multi_file.php?m=benalman_css">

    <script type="text/javascript" src="/js/mt.js"></script>
    -->

    <script type="text/javascript">
        /*
        // Opera 9 supports document.postMessage() 
        // document is wrong
        window.addEventListener("message", function (e) {
            //document.getElementById("test").textContent = ;
            alert(
                e.domain + " said: " + e.data
                );
        }, false);
        */

        // https://developer.mozilla.org/en-US/docs/Web/API/window.postMessage
        // http://ejohn.org/blog/cross-window-messaging/
        // http://benalman.com/projects/jquery-postmessage-plugin/
        // http://benalman.com/code/projects/jquery-postmessage/docs/files/jquery-ba-postmessage-js.html

        // .data – A string holding the message passed from the other window.
        // .domain (origin?) – The domain name of the window that sent the message.
        // .uri – The full URI for the window that sent the message.
        // .source – A reference to the window object of the window that sent the message.
        function ReceiveMessage(evt) {
            var message;
            //if (evt.origin !== "http://robertnyman.com")
            if(false)
            {
                message = 'You ("' + evt.origin + '") are not worthy';
            }
            else
            {
                message = 'I got "' + evt.data + '" from "' + evt.origin + '"';
            }

            //alert(evt.source.location.href)

            var ta = document.getElementById("taRecvMessage");
            if(ta == null)
                alert(message);
            else
                document.getElementById("taRecvMessage").innerHTML = message;

            // http://javascript.info/tutorial/cross-window-messaging-with-postmessage
            //evt.source.postMessage("thanks, got it", evt.origin);
            evt.source.postMessage("thanks, got it", "*");
        } // End Function ReceiveMessage




        if (!window['postMessage'])
            alert("oh crap");
        else {
            if (window.addEventListener) {
                //alert("standards-compliant");
                // For standards-compliant web browsers (ie9+)
                window.addEventListener("message", ReceiveMessage, false);
            }
            else {
                //alert("not standards-compliant (ie8)");
                window.attachEvent("onmessage", ReceiveMessage);
            }
        }
    </script>


</head>
<body style="background-color: gray;">
    <h1>Test</h1>

    <textarea id="taRecvMessage" rows="20" cols="20" ></textarea>

</body>
</html>

#4


1  

You have a couple of options:

你有几个选择:

  1. Scope the domain down (see document.domain) in both the containing page and the iframe to the same thing. Then they will not be bound by 'same origin' constraints.

    将域中的域(请参阅document.domain)放在包含页面和iframe中的同一事物中。然后他们将不受“同源”约束。

  2. Use postMessage which is supported by all HTML5 browsers for cross-domain communication.

    使用所有HTML5浏览器支持的postMessage进行跨域通信。

#5


0  

Good article here: Cross-domain communication with iframes

这里的好文章:与iframe的跨域通信

Also you can directly set document.domain the same in both frames (even

您也可以直接在两个框架中设置document.domain相同(甚至

document.domain = document.domain;

code has sense because resets port to null), but this trick is not general-purpose.

代码有意义,因为将端口重置为null),但这个技巧不是通用的。

#6


-2  

try

window.frameElement.ownerDocument.domain