【入門編】CSRF対策のテスト自動化と脆弱性スキャン手法 – アプリケーションセキュリティ & 安全な開発防御ガイド

こんにちは。セキュリティの世界へようこそ。

「CSRF(クロスサイト・リクエスト・フォージェリ)」という言葉、セキュリティの勉強を始めると必ず耳にしますよね。でも、教科書を開くと「クロスサイトでリクエストをフォージェリして…」なんて難解なカタカナが並んでいて、頭が痛くなってしまう気持ち、痛いほどよくわかります。

今日は、この「CSRF」を、もっと身近な「家の鍵」の話に置き換えて、なぜこれが必要で、どうやってテストすればいいのかを一緒に紐解いていきましょう。

—

そもそもCSRFって何?「勝手に合鍵を作られる」恐怖

想像してみてください。あなたは今、信頼している銀行のWebサイトにログインしています。その状態で、たまたま開いた別の怪しいサイトから、あなたのブラウザ経由で「この銀行サイトの送金ボタンをこっそり押してくれ」と命令が飛んできたらどうでしょう?

これがCSRFの正体です。

  • 家の鍵に例えると: あなたが玄関の鍵を閉めずに家の中にいるとき、泥棒が「外からノックして、あなたがうっかり開けてしまった隙に勝手に部屋の中の荷物を動かす」ようなものです。
  • Webの世界では: ユーザーがログインしている状態を悪用して、知らないうちに「パスワード変更」や「商品購入」を勝手に実行させられてしまうのです。

—

防御の要「CSRFトークン」という「使い捨ての合鍵」

この攻撃を防ぐために、現代のWebアプリケーションでは「CSRFトークン」という仕組みを使います。

これは、「その操作が、本当に本人から正当な手順で送られたものか?」を確認するための「使い捨ての魔法のチケット」です。サーバーは、画面を表示するたびに「この画面で何かするなら、このチケット(トークン)を必ず持ってくること!」と、隠しポケットの中にチケットを忍ばせます。

もし泥棒(攻撃者)が外から勝手に操作しようとしても、その「魔法のチケット」の番号を知らないため、サーバーは「おっと、君はチケットを持っていないね。怪しいから拒否するよ!」とシャットアウトできるのです。

—

どうやってテストすればいいの?(DASTツールと手動確認)

さて、ここからが本題です。開発したWebアプリにこの「チケットのチェック」がちゃんと入っているか、どうやって確認すればいいのでしょうか。

1. DASTツール(自動スキャン)で探る

DAST(動的アプリケーションセキュリティテスト)ツール、例えば「OWASP ZAP」などを使うと、ツールが勝手にあなたの代わりに攻撃を試みてくれます。

  • ツールの動き: ツールは、リクエストの中から「CSRFトークンっぽいパラメータ」を見つけ出し、わざとそれを「空っぽ」にしたり「偽物」に書き換えたりして送信します。
  • チェックポイント: その時、サーバーが「403 Forbidden(アクセス拒否)」を返せば合格です! 逆に、トークンがなくても処理が通ってしまうなら、そこが脆弱性です。

2. 手動で確認する「泥臭い」確認手順

ツールに頼り切るのもいいですが、自分の手で確認する癖をつけると「何が起きているか」が深く理解できます。

1. ブラウザの開発者ツール(F12)を開く

  • 「ネットワーク」タブを開いて、何かボタン(例:プロフィールの更新ボタン)を押してみましょう。

2. 送信されたデータを見る

  • 送信データ(Payload)の中に authenticity_token や csrf_token という名前の長い文字列が含まれているか確認してください。

3. リクエストを書き換えてみる

  • 「Burp Suite」などのプロキシツールを使うか、ブラウザの「コピーとして編集」機能を使って、トークンの値をわざと消して送信してみます。
  • ここで「処理が失敗する」ことが確認できれば安心です。

—

実務で役立つ!コードでの対策サンプル

多くのフレームワーク(Rails, Django, Spring, Laravelなど)では、標準でこの機能が備わっています。例えば、HTMLフォームに一行追加するだけで、裏側でトークンが生成されます。

【HTMLの例】




【サーバー側(擬似コード)】

def update_profile(request):
# 送られてきたトークンと、サーバーが発行したトークンを照合
if request.params[‘csrf_token’] != session[‘csrf_token’]:
# 一致しなければ、泥棒とみなして拒否!
return “403 Forbidden: 不正なリクエストです”, 403

# 処理の続行
save_to_db(request.params[‘username’])

—

最後に:セキュリティは「疑う」ことから始まる

「自動スキャンツールがOKと言ったから大丈夫」……そう思いたいですよね。でも、プロの現場では「ツールがチケットの存在を見つけられなかっただけかもしれない」と疑うことも大切です。

  • 自動化はあくまで補助輪。
  • 「本当にトークンが変更されたら弾かれるか?」を自分の手で壊してみる。

この泥臭い検証の積み重ねこそが、あなたの作るアプリケーションを「鉄壁」にする唯一の近道です。最初は難しく感じるかもしれませんが、一歩ずつやっていけば必ず身につきます。一緒に頑張っていきましょう!

何か分からないことがあれば、またいつでも聞きに来てくださいね。あなたのコードが、世界で一番安全な場所になりますように。

コメント

タイトルとURLをコピーしました