無料・アカウント不要

セキュリティヘッダーチェッカー

公開WebサイトのHTTPセキュリティヘッダーをオンラインで確認します。ドメインを入力すると、主要な8つのセキュリティヘッダーが最終レスポンスでどう判定されたかと、表示できる場合は観測された値がわかります。

ウェブサイトの公開設定を無料でチェックします。サイトに変更は加えません。

登録不要 破壊的通信なし 公開ウェブサイトのチェック
ヘッダー参照

各ヘッダーの役割と判定方法

チェッカーはこれらのヘッダーを1つのレスポンスで読みます。ほとんどの行は有無の確認です。送信されているヘッダーが評価され、値は取得できる場合に表示されるので、サイトに合っているかはご自身で判断できます。

ヘッダー役割望ましい設定このチェッカーの判定
Strict-Transport-Security再訪したブラウザが、平文のHTTPでリクエストを送る前に自動でHTTPSへ切り替えるようにします。段階的な導入が終わったら長いmax-age(180日以上)。段階はガイドで説明しています。HTTPSの対象で未設定:中。http://のアドレスを入力した場合は判定しません。
Content-Security-Policyページのコードとコンテンツに使ってよい読み込み元の許可リストをブラウザに渡します。ページが実際に使うリソースから作成し、スクリプトの広い例外を含まないポリシー。未設定:中。値は表示しますが、内容は評価しません。
X-Frame-Options · frame-ancestorsほかのサイトがあなたのページを自分のフレーム内に表示するのを防ぎます。CSPのframe-ancestorsを使い、古いブラウザ向けの予備としてX-Frame-Optionsも送る設定。どちらもない場合:中。
X-Content-Type-Options各レスポンスで宣言されたコンテンツタイプをブラウザがそのまま扱うようにします。値はnosniffのみ。未設定またはほかの値:低。
Referrer-Policy訪問者がリンクをたどったとき、ほかのサイトに伝わるページアドレスの範囲を制限します。現在のブラウザの既定値と同じか、それより厳しいポリシー。未設定:低。
Access-Control-Allow-Originどのほかのサイトのスクリプトがレスポンスを読めるかを決めます。通常のページでは送らないか、信頼できる1つのオリジンだけを指定。ワイルドカード(*):中。
Server · X-Powered-Byレスポンスの背後にあるソフトウェアを知らせます。削除するか、汎用的な値にする。ServerまたはX-Powered-Byヘッダーがあれば、バージョン番号がなくても低。表示するのは識別できた技術名だけです。
Set-CookieCookieを設定します。属性によって、どのスクリプトが読めるか、いつ送信されるかが決まります。セッションCookieはスクリプトから隠し、HTTPSでのみ送信。このレスポンスのCookieにHttpOnlyがない、またはHTTPSでSecureがない場合:中。SameSiteは確認せず、Cookieの値は表示しません。

Permissions-PolicyとCross-Origin-Opener-Policyはこのページでは判定しません。公開準備スナップショットでは、別の堅牢化の評価でのみ数えます。

修正方法

これらのヘッダーをサーバーに追加する方法

各ヘッダーは、すべてのリクエストに応答する1つの層、つまりWebサーバー、CDN、ホスティング基盤のいずれかで設定してください。下の値から始め、主要なページをテストしながら段階的に厳しくしていきます。

安全な初期値

  1. 01Strict-Transport-Security: max-age=300HTTPSのレスポンスでのみ送信します。暗号化されていないHTTPで届いたものはブラウザが無視します。max-ageは、たとえば1週間、1か月、1年(31536000)と段階的に引き上げ、各段階でサイトを確認してください。includeSubDomainsはすべてのサブドメインがHTTPSを提供している場合にのみ追加し、preloadはhstspreload.orgの要件を読んでから追加してください。プリロードリストからの削除には数か月かかります。
  2. 02Content-Security-Policy-Report-Only: default-src 'self'; object-src 'none'; base-uri 'self'; frame-ancestors 'self'Report-Onlyは何もブロックしません。ブラウザは、ポリシーがブロックする対象をコンソールに、またはレポートの送信先を追加した場合はそこに報告するだけです。主要なページを開き、実際に使っているソースを追加してから、同じポリシーをContent-Security-Policyとして送信します。スクリプトには'unsafe-inline'を避け、より厳格なnonceかハッシュを使ってください。
  3. 03frame-ancestors 'self' · X-Frame-Options: SAMEORIGIN適用中のContent-Security-Policyのframe-ancestorsが、どのサイトがページをフレームに表示できるかを決めます。X-Frame-Optionsは古いブラウザを対象とし、CSPがまだReport-Onlyの間はこちらがブロックを担います。ページを一切フレームに埋め込ませないなら'none'とDENYを使い、両方の値をそろえてください。frame-ancestorsはmetaタグでは無視されるため、ヘッダーとして送信します。
  4. 04X-Content-Type-Options: nosniffすべてのレスポンスで単一の値nosniffを送信します。ブラウザは誤ったContent-Typeで配信されたスクリプトとスタイルシートを拒否するため、先にサーバーがJavaScriptとCSSのファイルを正しい形式で返しているか確認してください。
  5. 05Referrer-Policy: strict-origin-when-cross-origin他のサイトにはページの完全なアドレスではなくオリジンだけが送られ、HTTPSからHTTPへのリンクでは何も送られません。現在のブラウザはすでにこれを既定値としていますが、送信するとどこでも同じ動作になります。URLに個人的なデータが含まれる場合はsame-originかno-referrerを選んでください。
  6. 06Permissions-Policy: camera=(), microphone=(), geolocation=()空のリスト()は、ページと、ページが埋め込むすべてのフレームでその機能を無効にします。サイトで一切使わない機能だけを列挙し、その後、地図、ビデオ通話、決済ウィジェットのあるページをテストしてください。

プラットフォーム別のコピー用サンプル

どのサンプルも同じ初期値を設定します。ホスティング基盤がすでにStrict-Transport-Securityを送っている場合があるため、Vercel、Netlify、Next.jsのサンプルには含めていません。実際のレスポンスを確認し、ない場合にのみ追加してください。

nginx

HTTPSを提供するserverブロックに行を追加します。alwaysパラメーターを付けると、エラーレスポンスにも追加されます。独自のadd_header行を持つlocationブロックでは、serverブロックから継承されるadd_headerがすべて失われるため、そこにも同じ一式を書くか、1つのincludeファイルにまとめてください。

# In the server block that serves HTTPS (listen 443 ssl)
add_header Strict-Transport-Security "max-age=300" always;
add_header Content-Security-Policy-Report-Only "default-src 'self'; object-src 'none'; base-uri 'self'; frame-ancestors 'self'" always;
add_header X-Frame-Options "SAMEORIGIN" always;
add_header X-Content-Type-Options "nosniff" always;
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
add_header Permissions-Policy "camera=(), microphone=(), geolocation=()" always;

Apache

mod_headersを有効にし、ポート443のバーチャルホスト、またはAllowOverride FileInfoが設定された場所の.htaccessに行を追加します。Header always setはエラーレスポンスとリダイレクトにも適用されます。

# <VirtualHost *:443> or .htaccess; needs mod_headers (Debian/Ubuntu: a2enmod headers)
Header always set Strict-Transport-Security "max-age=300"
Header always set Content-Security-Policy-Report-Only "default-src 'self'; object-src 'none'; base-uri 'self'; frame-ancestors 'self'"
Header always set X-Frame-Options "SAMEORIGIN"
Header always set X-Content-Type-Options "nosniff"
Header always set Referrer-Policy "strict-origin-when-cross-origin"
Header always set Permissions-Policy "camera=(), microphone=(), geolocation=()"

Cloudflare

ダッシュボードでホスト名に対するResponse Header Transform Ruleを作成し、各ヘッダーをSet static操作で追加します。この操作はオリジンから届いた同名のヘッダーを置き換えます。HSTSにはSSL/TLSのEdge Certificatesに専用の設定があるため、その設定とルールのどちらか一方だけを使ってください。メニュー名はダッシュボードのバージョンによって異なる場合があります。

Rule type   Response Header Transform Rule
When        Hostname equals example.com
Then        Set static, one row per header:
  X-Content-Type-Options               nosniff
  Referrer-Policy                      strict-origin-when-cross-origin
  X-Frame-Options                      SAMEORIGIN
  Permissions-Policy                   camera=(), microphone=(), geolocation=()
  Content-Security-Policy-Report-Only  default-src 'self'; object-src 'none'; base-uri 'self'; frame-ancestors 'self'

HSTS        SSL/TLS > Edge Certificates > HTTP Strict Transport Security (HSTS)

Vercel

プロジェクトのルートにあるvercel.jsonにheadersの項目を追加します。sourceパターン/(.*)はすべてのパスに一致します。一部のルートに別のポリシーが必要なら範囲を絞ってください。

{
  "headers": [
    {
      "source": "/(.*)",
      "headers": [
        { "key": "Content-Security-Policy-Report-Only", "value": "default-src 'self'; object-src 'none'; base-uri 'self'; frame-ancestors 'self'" },
        { "key": "X-Frame-Options", "value": "SAMEORIGIN" },
        { "key": "X-Content-Type-Options", "value": "nosniff" },
        { "key": "Referrer-Policy", "value": "strict-origin-when-cross-origin" },
        { "key": "Permissions-Policy", "value": "camera=(), microphone=(), geolocation=()" }
      ]
    }
  ]
}

Netlify

公開ディレクトリ、つまりNetlifyがデプロイするフォルダーに_headersという名前のファイルを作成します。/*のようなパスの行の後に、インデントした「名前: 値」の行を続けます。同じルールはnetlify.tomlの[[headers]]にも書けます。

/*
  Content-Security-Policy-Report-Only: default-src 'self'; object-src 'none'; base-uri 'self'; frame-ancestors 'self'
  X-Frame-Options: SAMEORIGIN
  X-Content-Type-Options: nosniff
  Referrer-Policy: strict-origin-when-cross-origin
  Permissions-Policy: camera=(), microphone=(), geolocation=()

Next.js

next.config.jsのasync headers()関数からヘッダーを返します。source '/:path*'ですべてのルートが対象になります。静的エクスポート(output: 'export')ではheaders()が実行されないため、その場合はエクスポートしたファイルを配信するホスト側でヘッダーを設定してください。

// next.config.js
const securityHeaders = [
  { key: 'Content-Security-Policy-Report-Only', value: "default-src 'self'; object-src 'none'; base-uri 'self'; frame-ancestors 'self'" },
  { key: 'X-Frame-Options', value: 'SAMEORIGIN' },
  { key: 'X-Content-Type-Options', value: 'nosniff' },
  { key: 'Referrer-Policy', value: 'strict-origin-when-cross-origin' },
  { key: 'Permissions-Policy', value: 'camera=(), microphone=(), geolocation=()' },
];

module.exports = {
  async headers() {
    return [{ source: '/:path*', headers: securityHeaders }];
  },
};

デプロイ後にチェッカーを再実行してください。最終レスポンスを読むため、CDNやプラットフォームが実際に送っている内容がわかります。続けて、ブラウザの開発者ツールでエラーページと静的ファイルを開いてください。ヘッダーが一部のレスポンスにしか設定されていないことはよくあります。

結果の読み方

各ステータスの読み方。

  1. 01合格ヘッダーが見つかり、有無の確認を満たしています。
  2. 02低 · 中 · 高何かが欠けているか、このチェックが指摘する設定になっています。レベルは完全なスナップショットと同じです。
  3. 03観測値は記録されましたが、合格にも指摘にもなりませんでした。
  4. 04観測なしチェックは実行されましたが、記録するものがありませんでした。たとえばレスポンスにCookieがない場合です。
  5. 05対象外チェックの対象外です。たとえばhttp://のアドレスを入力したときのHSTSです。
  6. 06未計測使えるレスポンスを受け取れなかったため、合格には数えません。
範囲

このチェッカーがしないこと。

  1. 01入力したオリジンのトップページだけをリクエストします。パスとクエリ文字列は破棄し、ほかのページはリクエストしません。
  2. 02主にヘッダーの有無を確認し、値がサイトに合っているかは判断しません。
  3. 03HTTPからHTTPSへのリダイレクトは、http://のアドレスを入力したときだけテストします。その実行ではTLSを省略し、HSTSの未設定も報告しません。
  4. 04脆弱性スキャンやペネトレーションテストではなく、攻撃トラフィックも送りません。
  5. 05結果は1つのレスポンスのある時点の状態です。CDNのルールや別のページでは、異なるヘッダーが送られることがあります。
よくある質問

ヘッダーチェックについての質問。

バージョンがないのに、なぜServer: nginxが指摘されるのですか?

ServerやX-Powered-Byヘッダーは、名前だけでもサイトで動くソフトウェアを訪問者に伝えるため、すべて低と判定します。プラットフォームが許すなら、ヘッダーを削除するか汎用的な値にしてください。

結果がサーバー設定と違うのはなぜですか?

チェッカーは最大5回のリダイレクト後に受け取ったレスポンスを読みます。CDN、プロキシ、ホスティング基盤が追加または削除したヘッダーが評価の対象になり、CDN、プロキシ、ボット対策のルールはブラウザとチェッカーに異なる応答を返すことがあります。

自分のものではないサイトも確認できますか?

はい。ヘッダーチェックは、サイトがすべての訪問者にすでに送っている通常のレスポンスを1つ読むだけです。実行全体では、ほかのチェックのために通常のリクエストをいくつか追加で送ります。保護モジュールと完全な監査には、検証済みの対象または明示的な承認が必要です。

これは脆弱性スキャンですか?

いいえ。レスポンスヘッダーのパッシブな確認であり、脆弱性スキャンやペネトレーションテストではありません。サイトが安全であることを証明するものでもありません。

一部のレスポンスにヘッダーがないのはなぜですか?

ヘッダーは、特定のルート、ファイル形式、ステータスコードだけに設定されていることがよくあります。nginxでは、alwaysのないadd_headerはエラーレスポンスに付かず、独自のadd_header行を持つlocationブロックではserverブロックの設定が失われます。静的ファイル、APIのルート、別のサービスが配信するページも、ヘッダーを付けるルールの対象外になることがあります。

同じヘッダーをアプリとCDNの両方で設定してもよいですか?

各ヘッダーは1つの層だけで設定してください。2つの層が追加すると、ブラウザが2つの値を受け取ることがあります。Content-Security-Policyでは送られたすべてのポリシーが適用されるため、どちらよりも厳しい結果になり、Strict-Transport-Securityでは最初のヘッダーだけが使われます。

ドメインをHSTSプリロードリストに登録すべきですか?

現在と将来のすべてのサブドメインがHTTPSを提供できる場合に限ります。リストには、includeSubDomainsとpreloadを付けた1年以上のmax-ageが必要です。登録後はブラウザが初回訪問の前からそのドメインにHTTPSを使い、リストからの削除が利用者に届くまで数か月かかることがあります。preloadなしでも、長いmax-ageで再訪問者には効果があります。