【結論】
・SQLインジェクションとは、
フォームに直接SQLを入力する事で、
意図しないSQL文を実行させる攻撃手法
・XSSとは、入力フォームなどを用いて
WebページにJavaScriptなどのスクリプトを仕込み、
意図しない動作を実行させる攻撃手法
・CSRFとは、対象のWebサービスへのログイン状態が
維持されたユーザーに、悪意あるスクリプトが組み込まれた
URLをクリックさせる事で、ユーザーが意図していない操作を
強制的に実行させる攻撃手法
【目次】
【本題】
脆弱性攻撃とは
ソフトウェアに、開発者が意図しない操作を実行させて、
本来出来ない様な情報の取得/改竄などを行う事を指します。
脆弱性は、セキュリティホールとも呼ばれています。
今回は、代表的な脆弱性攻撃と対策についてまとめます。
※参考URL
railsguides.jp
SQLインジェクション
アプリケーションが意図していないSQL文を実行させる事で、
本来アクセス出来ない情報の取得や改竄などを行う手法です。
実行されると、下記の様な問題が起こる可能性があります。
・データベース内の個人情報を取得する
・アカウント認証を回避してサービスを利用する
・別ユーザーになりすまして、サービスを利用する
・データベースの情報を削除して、サービスを機能しなくする
具体的な実行方法としては、
ログイン画面のユーザー名・パスワードといった
入力フォームに直接SQLを入力する方法です。
脆弱性があると、そのSQLをアプリケーションが実行してしまい、
その命令文に応じた処理を行ってしまいます。
対策
Railsの場合、findやwhereなどのメソッドが 指定した条件に基づいて、SQL文を生成します。
モデルクラスのインスタンスメソッドである 「find」「find_by」に関しては、「'」「"」「NULL」「改行」といった 特殊なSQL文字をエスケープする仕様が元々実装されています。
しかし、「where」「execute」「find_by_sql」に関しては、 その仕様が実装されていない為、手動でエスケープする必要があります。
なお、条件オプションで文字列を直接渡さず、 ハッシュか配列を渡すことで、汚染された文字列をサニタイズすることもできます。 サニタイズとは、特殊文字を一般的な文字列に変換する処理の事です。
↓例
○ハッシュ
User.where(name: params[:name], password: params[:password])
○配列
User.where(["name = ? and password = ?", params[:name], params[:password]])
×文字列
User.where("name = '#{params[:name]}', password = '#{params[:password]}'")
XXS
入力フォームなどを用いて
WebページにJavaScriptなどのスクリプトを仕込み、
意図しない動作を実行させる攻撃手法です。
クロスサイトスクリプティング と呼ばれる下記の様な攻撃を行います。
・クッキーの盗難による不正アクセス
・偽サイトに誘導してフィッシングでアカウント情報を不正取得
・不正なスクリプトを含むリクエストを送信し権限を変更
これを防ぐには、フォームで「<」「>」「?」などHTMLタグとして
認識される文字が入力された際に、エスケープさせる必要があります。
Railsでは、<%= %>というタグを用いれば、
文字列の変換が自動的に行われるような仕組みになっています。
CSRF
あるWebサービスへのログインが維持された状態で 悪意あるスクリプトが組み込まれたURLをクリックする事で、 ユーザーが意図していない操作を実行させる攻撃手法です。
ユーザーがURLをクリックすると、
ブラウザのCookieに保持されているログイン情報を用いて
WEBサービスに強制的にアクセスさせ、
ユーザーの権限で実行できる様々な操作を行わせます。
Railsの場合、ApplicationControllerに
下記の記述を施す事で対策しています。
protect_from_forgery with: :exception
これはアプリのフォームに対してトークンを発行するコードで、 フォーム送信時にこのトークンも合わせて送信する事で、 正しいフォームからの通信なのかを判別することができます。
これにより、Cookieに保持されたセッション情報だけで
WEBサービスにアクセス出来ない様になっています。
《今日の学習進捗(3年以内に10000時間に向けて)》
学習開始からの期間 :101日
今日までの合計時間:962h
一日あたりの平均学習時間:9.6h
今日までに到達すべき目標時間:922h
目標との解離:40h
「10,000時間」まで、
残り・・・「9038時間!」