Webサイトの「防犯カメラ」を設置しよう!CSPで守るインジェクション攻撃対策
こんにちは。日々、数多の脆弱性と向き合っているセキュリティエンジニアです。
今日は、Webアプリケーションを守るための「最強の門番」、CSP(Content-Security-Policy)についてお話しします。特に「script-src」という設定は、まるで自宅の防犯システムのようなもの。
専門用語だらけで難しそうに感じるかもしれませんが、まずは「泥棒」に例えて、この仕組みを紐解いていきましょう。
—
1. なぜ「スクリプト」が悪さをするの?(泥棒のメカニズム)
皆さんのWebサイトを「一軒の家」だと想像してください。ブラウザ(ChromeやSafariなど)は、その家の「玄関」です。
Webページを表示するということは、玄関を開けて、外からやってきた「家具(スクリプト)」をリビングに招き入れる作業です。もし、その家具に「泥棒が隠れていたら」どうなるでしょうか?
攻撃者は、入力フォームなどを通じて、本来あるはずのない「悪意ある家具(不正なJavaScript)」を紛れ込ませます。これがクロスサイトスクリプティング(XSS)という攻撃の正体です。
この攻撃が成功すると、泥棒はリビング(ブラウザ)で好き勝手に振る舞い、あなたの顧客の個人情報を盗んだり、勝手に別のサイトへ転送したりします。これを防ぐのが、今回紹介する「CSP(Content-Security-Policy)」です。
—
2. CSPは「身元確認リスト」
CSPは、Webサーバーからブラウザに向けて「この家には、あらかじめ許可した家具しか入れてはいけないよ!」と伝える命令書のようなものです。
その中でも、特に重要なのが script-src です。これは「どのスクリプトなら実行していいか」という身元確認リストになります。
設定の基本形
例えば、自社サーバー内のスクリプトだけを許可する場合は、このように書きます。
HTTPヘッダーで送信する例
Content-Security-Policy: default-src ‘self’; script-src ‘self’;
default-src 'self': 基本的に自社サーバーのもの以外は読み込まない。script-src 'self': JavaScriptに関しては、特に厳しく「自社サーバーにあるものだけ」を許可する。
こうしておけば、外部の怪しいサイトから送り込まれたスクリプトは、ブラウザが「あ、このスクリプトはリストに載っていないから、玄関で追い返そう!」とブロックしてくれるようになります。
—
3. 「インラインスクリプト」という盲点
実は、最も厄介なのはHTMLの中に直接書き込まれたスクリプトです。これを「インラインスクリプト」と呼びます。
CSPで script-src 'self' と設定していても、HTMLの中に直書きされたスクリプトは、ブラウザから見ると「どこから来たか分からないけれど、目の前にあるから実行しちゃおう」と判断されてしまうことがあります。
そこで登場するのが、nonce(ナンス) という「使い捨てパスコード」です。
nonceを使った厳格な対策
nonceは、ページを表示するたびにサーバーが発行する「魔法の合言葉」です。
1. サーバーはページを生成する際、ランダムな文字列(nonce)を発行します。
2. ヘッダーで「このnonceを持っているスクリプトだけ実行してね」と伝えます。
3. HTMLの中のスクリプトにも、同じnonceを付与します。
設定例(HTTPヘッダー):
Content-Security-Policy: script-src ‘nonce-random123’ ‘strict-dynamic’;
HTML側:
もし攻撃者が不正なスクリプトを注入しても、正しい「合言葉(nonce)」を知らないため、ブラウザは「怪しいから実行しない!」と門前払いしてくれます。
—
4. 今日からできる最初の一歩
セキュリティ対策は、一度に完璧を目指すと疲れてしまいます。まずは「Report-Only」モードから始めるのがプロの流儀です。
実際にはブロックせず、違反をレポートするだけのモード
Content-Security-Policy-Report-Only: script-src ‘self’; report-uri /csp-violation-report-endpoint;
これなら、既存のサイトを壊すことなく、「どのスクリプトが引っかかっているのか」をログで確認できます。
まとめ:セキュリティは「疑う」ことから
script-srcは、あなたの家の「入館証チェック」です。- 泥棒(XSS)は、身元を偽って侵入しようとします。
nonceを使えば、合言葉のない侵入者を確実にシャットアウトできます。
まずは、自分のサイトのHTTPヘッダーに Content-Security-Policy が設定されているか確認してみるところから始めてみてください。一歩ずつ、強固なサイトを作っていきましょう!応援しています。
コメント