ルーティング: CSP(Content-Security-Policy)¶
このページでは、ルート単位で Content-Security-Policy (CSP) レスポンスヘッダを設定する方法と、現時点でできないこと(制限)を整理します。
このページは ルート設定 の続きです。
CSP とは¶
CSP(Content-Security-Policy)は、ブラウザに「このページではどこから読み込まれた script / style / image / その他リソースを許可するか」を伝える HTTP レスポンスヘッダです。XSS(クロスサイトスクリプティング)対策の中核となる仕組みで、適切に設定すれば、攻撃者が注入したインライン script や外部オリジンからの読み込みをブラウザ側でブロックできます。
CMSoD ではルート設定の CSP セクションで、ルート単位に Content-Security-Policy ヘッダの内容を指定できます。
設定画面¶
ルート編集画面の右側パネルに CSP セクションが追加されています。
| 項目 | 内容 |
|---|---|
| 有効 | このルートで CSP ヘッダを送出するか(チェックを外すと無効) |
| ディレクティブ一覧 | 追加したディレクティブごとに許可ソースを設定する。各行に 'self' / 'none' / https: 等のクイック追加ボタンと、任意の値を入れる入力欄がある |
| upgrade-insecure-requests | HTTP の混在リソースを HTTPS に自動アップグレードする |
| block-all-mixed-content | HTTPS ページ内の HTTP リソース読み込みをすべてブロックする(古いブラウザ向けの保険的な指定) |
| プレビュー | 設定内容から生成される Content-Security-Policy ヘッダの文字列をリアルタイムに表示する |

上の例では、object-src 'none' / base-uri 'self' / form-action 'self' / frame-ancestors 'self' と upgrade-insecure-requests を設定した状態を示しています。プレビュー欄に、実際に送出される Content-Security-Policy ヘッダの内容がリアルタイムで表示されます。
追加できるディレクティブ¶
現行バージョンで「-- directive を追加 --」セレクトボックスから追加できるディレクティブは次の通りです。
| ディレクティブ | 用途 |
|---|---|
object-src |
<object> / <embed> 等のプラグイン読み込み元 |
base-uri |
<base> タグで指定できる URL の制限 |
form-action |
フォーム送信先の制限 |
frame-ancestors |
このページを <iframe> に埋め込めるオリジンの制限(クリックジャッキング対策) |
report-uri |
CSP 違反レポートの送信先 URL |
ディレクティブの追加¶
「-- directive を追加 --」セレクトボックスからディレクティブ名を選択し、追加 ボタンを押すと、そのディレクティブの行が追加されます。値は、クイック追加ボタン('self' / 'none' / https: など)を押すか、入力欄(プレースホルダ「値を入力」。report-uri のみ「URI を入力」)に直接書いて +追加 を押すと、タグとして登録されます。不要なタグは ×、ディレクティブ行ごと消すには 削除 を押します。
upgrade-insecure-requests¶
HTTPS で配信されているページ内の HTTP リクエスト(画像 / script / iframe など)を、ブラウザが自動で HTTPS に書き換えるようになります。古いコンテンツに http:// リンクが残っている移行期に有用です。
設定例¶
ハードニング例¶
現行バージョンで追加できるディレクティブだけで構成した、堅めの設定例です。
| ディレクティブ | 値 |
|---|---|
object-src |
'none' |
base-uri |
'self' |
form-action |
'self' |
frame-ancestors |
'self' |
| upgrade-insecure-requests | ON |
「プラグインを一切許可せず、<base> タグ・フォーム送信先・<iframe> への埋め込みを自サイトに限定し、HTTP リソースを HTTPS に格上げする」設定です。プレビュー欄には次のように 1 行で表示され、これがそのまま Content-Security-Policy ヘッダの値として送出されます。
object-src 'none'; base-uri 'self'; form-action 'self'; frame-ancestors 'self'; upgrade-insecure-requests
現在の制限・できないこと¶
スコープ的な制限¶
- 設定はルート単位 — サイト全体に一括でかける機能は提供されません。サイトの主要ルート(トップ・カテゴリトップ等)ごとに個別設定する必要があります
- 追加できるディレクティブが限定的 — 現行バージョンで設定できるのは
object-src/base-uri/form-action/frame-ancestors/report-uriの 5 種類のみです。default-src/script-src/style-src/img-srcなどの fetch 系ディレクティブは今後のバージョンで対応予定です - HTML レスポンスのみ — CSP ヘッダが付与されるのは HTML を返すルート処理のみです。JSON / RSS / Atom / 静的アセット配信には付与されません
- nonce による CSP Level 3 方式は未対応 — リクエストごとに暗号論的乱数を発行し
'nonce-XXXXX'をヘッダに埋め込む方式は未サポートです。インライン<script>/<style>を許可したい場合は'unsafe-inline'をディレクティブに追加する必要があり、その場合 XSS 対策レベルは低下します - report-to は未対応 —
report-uriは設定でき、指定するとContent-Security-Policyヘッダに出力されます(レポートを受け取る集約サーバは別途用意が必要)。一方、後継のreport-toディレクティブは設定できません Content-Security-Policy-Report-Onlyモード未対応 — 「ブロックせずレポートだけ」の段階的導入モードは未サポートです。現状は実適用モード(ヘッダ名Content-Security-Policy)のみ- ディレクティブ値のシンタックスチェックは限定的 — 入力欄に書かれた URI / キーワードの厳格な妥当性検証はせず、CR / LF / セミコロンなど CSP ヘッダを壊しうる特殊文字を保存時に除去するのみです(拒否ではなく除去のため、入力エラーは出ません)。
'self'のシングルクォート抜けやhttps//のスキームのタイポは、保存後にブラウザの開発者ツールで気づくことになります
運用上の注意¶
- 複数ルートで同一画面を扱う場合 — リダイレクト経由などで複数ルートが関わる場合、最終的にレスポンスを返したルートの CSP 設定が適用されます
関連¶
- ルート設定 — ルート設定の基本
- 出力形式とキャッシュ — Cache-Control の設定
- URL リライトと SSI — リダイレクト等の関連設定