イントロダクション
JavaScript にて、「DOM Based XSS」の脆弱性を埋め込むのを防ぐためには、document.write や element.innerHTML などを使うのではなく、以下のように DOM 操作用メソッドを使用すると良いとされています。入力されたテキストをブラウザのドキュメントに表示:
element.appendChild(document.createTextNode(input_text));
input_text : 入力されたテキスト
element : テキストを追加する親要素(element オブジェクト)
このとき、テキストを追加した親要素の HTML が、入力されたテキストによってどうなるのか気になりませんか?
そこで、実際に JavaScript でコードを作成して試してみました。
element.appendChild(document.createTextNode(input_text))のHTMLはどうなるか?
element.appendChild(document.createTextNode(input_text)) の HTML がどうなるのかを確かめるため、次の検証用 JavaScript コードを作成しました。
実験用コード:
<form onsubmit="return false;">
<b>input_text:</b><br />
<textarea id="input-text" rows="4" cols="80">
<script type="text/javascript">alert("a");</script>
</textarea><br />
例)<script type="text/javascript">alert("a");</script><br />
<input type="button" value="実行" onclick="runTest_createTextNode_appendChild_innerHTML();" /><br />
</form>
<br />
<b>element.appendChild(document.createTextNode(input_text))のinnerHTML:</b><br />
<textarea id="output-html" rows="4" cols="80">
ここにデータ出力
</textarea><br />
<b>input_text(確認用):</b><br />
<textarea id="input-text-viewer" rows="4" cols="80">
ここにデータ出力
</textarea><br />
<script type="text/javascript">
<!--
function runTest_createTextNode_appendChild_innerHTML() {
var input_text = document.getElementById("input-text").value;
var parentElement = document.createElement("div");
parentElement.appendChild(document.createTextNode(input_text));
document.getElementById("output-html").value = parentElement.innerHTML;
document.getElementById("input-text-viewer").value = input_text;
}
//-->
</script>
textarea に入力されたテキストデータ(input-text)に対して、element.appendChild(document.createTextNode(input_text)) を実行し、その innerHTML を textarea (output-html)に出力しています。
また、入力されたテキストデータ(input-text)が何らかの要因によって、勝手に変換されていないことを確認するために、最後に 入力されたテキストデータ(input-text) を textarea (input-text-viewer)に出力しています。
実験結果:
次のテキストデータを入力した時の、element.appendChild(document.createTextNode(input_text)) の innerHTML を見てみます。入力テキストデータ(input-text):
<script type="text/javascript">alert("a");</script>
element.appendChild(document.createTextNode(input_text))のinnerHTML:
<script type="text/javascript">alert("a");</script>
input_text(確認用):
<script type="text/javascript">alert("a");</script>
このように、入力されたテキストデータに HTML のタグが入っていたとしても、HTML のタグとはみなされずエスケープ処理されていることが分かります。
従って、HTML 文書内に表示しようとしたテキストに、意図しない HTML タグを混入し、HTML タグとして解釈させて任意の動作を行わせるような DOM Based XSS を防止することができます。
JavaScript にて、「DOM Based XSS」の脆弱性を埋め込むのを防ぐためには、このような DOM 操作用メソッドを使用すると、確かに安全に入力データを扱うことができることが分かりました。
なお、実際に動作する上記のプログラムを、以下に設置しておきましたので、試したいデータがあれば、試してみてください。
実験用プログラム:
element.appendChild(document.createTextNode(input_text))のinnerHTML:
input_text(確認用):
関連記事
セキュリティ対策:JavaScriptでHTML操作をする人は必読!IPAテクニカルウォッチ 『DOM Based XSS』に関するレポートhttp://upa-pc.blogspot.com/2015/02/javascript-dom-based-xss-ipa.html
http://upa-pc.blogspot.com/2015/02/javascript-dom-based-xss-protect-setAttribute.html
コメントを投稿
コメント投稿機能について