【広告クリエイティブにおける技術】iframeクロスドメイン対応

e0797971d059fa3cda8da11bb40f358e_s

Webブラウザにはセキュリティのための機能がいくつかあり、その一つにクロスドメイン制約があります。
クロスドメイン制約は様々なパターンがありますが、本稿では、広告表示の際によく発生するiframeのクロスドメイン制約とその対策について取り上げます。

クロスドメイン制約とは?

クロスドメイン制約とは
「あるドメイン上で、異なるドメインのコンテンツ操作をしてはいけない」
というブラウザの制約のことです。

広告では良くiframeを用いて表示を行うことが多いのですが、Webサイトのドメインと広告のドメインは異なるので、広告側からWebサイトの情報を読み取ろうとするとブラウザエラーが出てアクセスできなくなってしまう、という問題があります。
これができないと、ユーザーのスクロール情報を読み取ってスマートフォンの画面内に入った時に広告アニメーションを開始したり、広告をタップした時にエクスパンドさせて大きい画面で表示したりすることができなくなってしまいます。

クロスドメイン対策

今回はクロスドメインのiframe内からiframe外の情報を取得する方法を解説します。

想定するシチュエーション

iframe外 【aaa.com】

<iframe id="ifr" src="http://bbb.com">
</iframe>




<div id="test">
 CrossDomain
</div>

シチュエーションとして、aaa.comというWebサイト上でbbb.comのiframeが呼ばれていて、bbb.comからaaa.com上の「CrossDomain」という文字を取得することを想定します。

良くない例

iframe内 【bbb.com】

window.parent.document.getElementById("test").innerHTML

window.parentで親、つまりaaa.comのwindowを取得することができるので、そのwindow配下にあるidがtestのdivを取得する手法です。
クロスドメインではない場合、この方法で問題ないのですが、今回はiframe内外で異なるドメインのため、ブラウザがエラーを出してしまいます。

postMessageを用いる例

iframe内と外でドメインは違うがお互いに情報のやり取りを行いたい場合はpostMessageを使います。
テキストデータをクロスドメイン環境下のiframe内外でお互いに送信できる機能になります。

具体例

iframe内 【bbb.com】

window.parent.postMessage("getHTML:test", “*”);

このようにすると、window.parent、つまりaaa.comに対して「getHTML:test」という文字列を送信することができます。

iframe外 【aaa.com】

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

function receiveMessage(event) {
  var message = event.data;
  if(message.split(":")[0]=="getHTML"){
    var response = document.getElementById(message.split(":")[1]).innerHTML;
    document.getElementById("ifr").contentWindow.postMessage(response,"*");
  }
}

また、javascriptには、postMessageが送信された時に受け取れる「message」というイベントが用意されているので、addEventListenerで設定しておきます。
iframe内からpostMessageが送られてきた時にreceiveMessageが実行されます。

postMessageで送られてきたテキストはevent.dataで取り出すことができます。
テキストの中に「getHTML」という文字列があったら「:」で分割し、その2つ目、つまり「test」というidのdivの中身を取得し、「response」に入れます。
その後、iframeに向けて「response」を送信する形になります。

iframe内(受け取り時) 【bbb.com】

window.addEventListener("message", receiveMessage, false);
function receiveMessage(event)
{
  var message = event.data;
  console.log(message);  //CrossDomainと表示
}

iframe外で所定のHTMLの内容を取得後、iframe内にpostMessageで送信しました。
今度はiframe内でもmessageイベントを受け取ると、event.dataに無事CrossDomainという文字が入っているかと思います。

最後に

本稿では、クロスドメイン環境下にあるiframeにおいて、postMessageを用いてiframe内外で情報の通信を行う方法や具体例を解説しました。
情報はテキストしか送れないため、テキストのパターンをiframe内外で決めておき、それに応じて処理を行うことをおすすめします。(上記の例では、「実行命令名:対象div名」というテキストパターンで通信を行いました。)

クロスドメイン制約は複数ドメインを使わないと生じない問題ですので、あまり馴染みは無いかもしれませんが、広告では最重要な技術の一つなので是非覚えてみてはいかがでしょうか。