Заблокировано фрейм с именем origin & ldquo; http: //example.com” от доступа к кадру кросс-начала [дубликат]

Мы не можем привязать это к setTimeout(), поскольку он всегда выполняется с глобальным объектом (Window), если вы хотите получить доступ к контексту this в функции обратного вызова, а затем с помощью bind() к функции обратного вызова, которую мы можем достичь как:

setTimeout(function(){
    this.methodName();
}.bind(this), 2000);
357
задан Marco Bonelli 7 December 2015 в 15:30
поделиться

6 ответов

Политика одного и того же происхождения

Не путать с CORS !

Вы не можете получить доступ к <iframe> с разным началом с использованием JavaScript, это было бы огромным недостатком безопасности, если бы вы могли это сделать. Для браузеров того же происхождения блокируют сценарии, пытающиеся получить доступ к кадру с другим происхождением.

Происхождение считается другим, если не поддерживается хотя бы одна из следующих частей адреса:

<protocol>://<hostname>:<port>/path/to/page.html 

Протокол, имя хоста и порт должны быть одинаковыми для вашего домена, если вы хотите получить доступ к кадру.

Примеры

Вот что произойдет, пытаясь получить доступ к следующим URL-адресам из http://www.example.com/home/index.html

URL                                             RESULT 
http://www.example.com/home/other.html       -> Success 
http://www.example.com/dir/inner/another.php -> Success 
http://www.example.com:80                    -> Success (default port for HTTP) 
http://www.example.com:2251                  -> Failure: different port 
http://data.example.com/dir/other.html       -> Failure: different hostname 
https://www.example.com/home/index.html.html -> Failure: different protocol 
ftp://www.example.com:21                     -> Failure: different protocol & port 
https://google.com/search?q=james+bond       -> Failure: different hostname & protocol 

Обходное решение

-origin блокирует скрипты от доступа к содержимому сайтов с другим происхождением, если у вас есть обе страницы, вы можете обойти эту проблему, используя window.postMessage и ее относительное message событие для отправки сообщений между двумя страницами, например:

  • На главной странице:
    var frame = document.getElementById('your-frame-id'); 
    
    frame.contentWindow.postMessage(/*any variable or object here*/, '*'); 
    
  • На вашем <iframe> (см. основную страницу):
    window.addEventListener('message', function(event) { 
    
        // IMPORTANT: Check the origin of the data! 
        if (~event.origin.indexOf('http://yoursite.com')) { 
            // The data has been sent from your site 
    
            // The data sent with postMessage is stored in event.data 
            console.log(event.data); 
        } else { 
            // The data hasn't been sent from your site! 
            // Be careful! Do not use it. 
            return; 
        } 
    }); 
    

Этот метод может применяться в обоих направлениях, создавая слушателя на главной странице и получая ответы от фрейма. Та же логика также может быть реализована во всплывающих окнах и в основном в любом новом окне, создаваемом главной страницей (например, с использованием window.open() ), без какой-либо разницы.

Отключение политика того же происхождения в браузере

Уже есть некоторые хорошие ответы на эту тему (я просто нашел их googling), поэтому для браузеров, где это возможно, ll ссылку относительный ответ. Однако помните, что отключение политики одного и того же происхождения (или CORS) повлияет только на на ваш браузер . Кроме того, при запуске браузера с настройками безопасности с одинаковым исходным кодом отключены доступ к веб-сайту для ресурсов с перекрестными источниками, поэтому он очень опасен и должен выполняться только для целей разработки.

521
ответ дан Marco Bonelli 21 August 2018 в 20:11
поделиться
  • 1
    Любой другой ответ, который я нашел 1 , 2 , предполагает, что CORS / Access-Control-Allow-Origin не применяется к iFrames, только к XHR, Fonts, WebGL и canvas.drawImage . Я считаю, что postMessage - единственный вариант. – snappieT 14 January 2015 в 13:12
  • 2
    я просто оставлю это здесь github.com/ternarylabs/porthole – parliament 20 February 2015 в 23:11
  • 3
    В первый раз я увидел тильду "~" оператор в javascript. Для кого-то еще, кто также не знал, что он делает: он преобразует -1 в 0, что избавляет вас от необходимости делать & quot;! = -1 & quot; на результат индекса Of. Лично я думаю, что продолжу использование & quot;! = -1 & quot; так как другим программистам легче понять и избежать ошибок, которые могут возникнуть из-за забывания поместить тильду. (Но всегда приятно узнать что-то новое). – Redzarf 5 June 2015 в 16:32
  • 4
    @SabaAhang просто проверьте на iframe.src, и если сайт отличается от имени хоста вашего домена, вы не сможете получить доступ к этому фрейму. – Marco Bonelli 17 October 2015 в 09:34
  • 5
    @Snuggs полностью неверно, ~ возвращает дополнение 2 к числу, поэтому n становится -n-1, а это означает, что только -1 станет 0 (который интерпретируется как false), и любое другое значение пройдет тест. И.Е. 0 = -(-1)-1, а не -(-1+1). – Marco Bonelli 8 November 2016 в 07:18

Проверьте веб-сервер домена для конфигурации http://www.<domain>.com для X-Frame-Options. Это функция безопасности, предназначенная для предотвращения атак типа clickJacking,

. Как работает clickJacking?

  1. Страница зла выглядит точно так же, как страница жертвы.
  2. Затем она обманула пользователей, указав их имя пользователя и пароль.

Технически зло имеет iframe с источником на страницу жертвы.

<html>
    <iframe src='victim_domain.com'/>
    <input id="username" type="text" style="display: none;/>
    <input id="password" type="text" style="display: none;/>
    <script>
        //some JS code that click jacking the user username and input from inside the iframe...
    <script/>
<html>

Как работает функция безопасности

Если вы хотите, чтобы запрос веб-сервера отображался в iframe, добавьте x- frame-options

Параметры X-Frame DENY

Возможные варианты:

  1. SAMEORIGIN / / разрешить только моему собственному домену, сделать мой HTML внутри iframe.
  2. DENY // не разрешать отображение моего HTML внутри любого iframe
  3. "ALLOW-FROM https : //example.com/ "// разрешить определенному домену отображать мой HTML внутри iframe

Это пример конфигурации IIS:

   <httpProtocol>
       <customHeaders>
           <add name="X-Frame-Options" value="SAMEORIGIN" />
       </customHeaders>
   </httpProtocol>

Решение вопроса

Если веб-сервер активировал функцию безопасности, это может привести к безопасности на стороне клиента как следует.

7
ответ дан floydian 21 August 2018 в 20:11
поделиться

В дополнение к ответу Марко Бонелли: лучший текущий способ взаимодействия между фреймами / фреймами использует window.postMessage , , поддерживаемый всеми браузерами

42
ответ дан Geert 21 August 2018 в 20:11
поделиться
  • 1
    Хотя эта ссылка может ответить на вопрос, лучше включить здесь основные части ответа и предоставить ссылку для справки. Ответные ссылки могут стать недействительными, если связанная страница изменится. - Из обзора – Alessandro Cuttin 1 April 2016 в 15:30
  • 2
    Я не согласен, @AlessandroCuttin. Объясняя, как работает window.postMessage, будет только дублировать принятый ответ, который я уже упоминаю. Кроме того, существенное значение, которое добавляет мой ответ, - это именно ссылка на внешнюю документацию. – Geert 4 April 2016 в 12:42
  • 3
    Я думаю, что это лучше, если вы можете отредактировать принятый ответ и добавить его туда – Martin Massera 3 January 2017 в 05:17
  • 4
    window.postMessage мы можем использовать только в том случае, если мы сможем получить доступ как к родительскому (нашей HTML-странице), так и к дочернему элементу (другому домену iframe). В противном случае «НЕТ ВОЗМОЖНОСТИ» всегда будет выдаваться ошибка «Невозможно использовать DOMException: Blocked кадр с источником & lt; yourdomainname.com & gt; & quot; / g0]; от доступа к кадру с поперечным началом. & quot; – VVL 1 February 2017 в 19:35

Мое приложение разбилось с помощью SecurityError, если оно помещено внутри iframe. Проблема заключалась в том, что .animate({scrollTop: top}, 0) jQuery был применен непосредственно на window.

Удаление LOC устранило проблему для нас.

0
ответ дан Oorja 21 August 2018 в 20:11
поделиться

Для меня я хотел реализовать двухстороннее рукопожатие, то есть: - родительское окно будет загружаться быстрее iframe - iframe должен поговорить с родительским окном, как только он будет готов - родитель готов получить iframe message и replay

этот код используется для установки белой метки в iframe с использованием [CSS custom property] кода: iframe

$(function() {
    window.onload = function() {
        // create listener
        function receiveMessage(e) {
            document.documentElement.style.setProperty('--header_bg', e.data.wl.header_bg);
            document.documentElement.style.setProperty('--header_text', e.data.wl.header_text);
            document.documentElement.style.setProperty('--button_bg', e.data.wl.button_bg);
            //alert(e.data.data.header_bg);
        }
        window.addEventListener('message', receiveMessage);
        // call parent
        parent.postMessage("GetWhiteLabel","*");
    }
});

parent

$(function() {
    // create listener
    var eventMethod = window.addEventListener ? "addEventListener" : "attachEvent";
    var eventer = window[eventMethod];
    var messageEvent = eventMethod == "attachEvent" ? "onmessage" : "message";
    eventer(messageEvent, function (e) {
        // replay to child (iframe) 
        document.getElementById('wrapper-iframe').contentWindow.postMessage(
            {
                event_id: 'white_label_message',
                wl: {
                    header_bg: $('#Header').css('background-color'),
                    header_text: $('#Header .HoverMenu a').css('color'),
                    button_bg: $('#Header .HoverMenu a').css('background-color')
                }
            },
            '*'
        );
    }, false);
});

Естественно, вы можете ограничить исход и текст, это легко работать с кодом. Я нашел этот пример полезным: [Междоменные сообщения с postMessage]

5
ответ дан Yakir Manor 21 August 2018 в 20:11
поделиться
  • 1
    я имею дело с проблемой с сафари, где документ в iframe выполняет свою JS позже родительской страницы, которая заставляет сообщение отправляться раньше, чем документ в iframe слушает сообщения; что совершенно противоположно тому, что делают хром и firefox - вы проверили свой код на сафари на ios? btw postMessage со вторым параметром значения "*" не совсем безопасно, вы всегда должны указывать домен – sKopheK 22 March 2018 в 16:51
1
ответ дан Vineeth Sai 4 November 2018 в 17:21
поделиться
Другие вопросы по тегам:

Похожие вопросы: