HTTPS
TLSで暗号化されたHTTP。現代のWebでは事実上の必須要件。
概要
HTTPSは、HTTPの通信をTLSという暗号化の層で包んだものです。プロトコルとして別物が発明されたわけではなく、「HTTPをそのまま、暗号化されたトンネルの中に通す」という構成になっています。ブラウザのアドレスバーに表示される鍵マークの正体はこれで、サーバ証明書の検証によって「通信相手が本物のexample.comである」ことを暗号技術で確かめた印です。
HTTPSが守ってくれるのは3つです。通信内容を第三者に読まれない(盗聴の防止)、途中で書き換えられない(改ざんの防止)、偽サーバに接続させられない(なりすましの防止)。ログインパスワードやクレジットカード番号はもちろん、Cookieに載るセッションIDのような「盗まれたらアカウントを乗っ取られる」情報も、この層に守られています。
現在のWebではHTTPSは選択肢ではなく前提です。ブラウザは素のHTTPのサイトに「保護されていない通信」と警告を出し、位置情報やカメラなどの新しいブラウザAPIの多くはHTTPSでしか動作しません。
なぜ生まれたか
素のHTTPは平文で流れます。通信は多数のネットワーク機器を経由して届くため、経路上のどこか——たとえば同じカフェのWi-Fi——でパケットを覗けば、パスワードもCookieも丸見えでした。1990年代半ば、Webで買い物(EC)を成立させたかったNetscape社にとって、これは致命的な問題でした。カード番号が平文で流れるサイトで買い物をする人はいません。
そこでNetscapeが開発したのがSSL(後のTLS)で、これをHTTPと組み合わせたHTTPSが1995年頃に登場します。ただし長い間、証明書は有料で設定も面倒だったため、「決済ページだけHTTPS」という使い方が普通でした。転機は2010年代です。無線LANの普及で盗聴が現実的な脅威になり、Snowden事件で大規模な通信監視が明るみに出て、「全ページ常時HTTPS」への圧力が高まりました。決定打は2016年頃からのLet’s Encrypt——証明書を無料・自動で発行する認証局の登場で、コストの言い訳が消え、HTTPSはWeb全体の標準になりました。
詳細
接続が確立するまで
HTTPSの通信は「まず暗号化トンネルを作り、その中でいつものHTTPを話す」という二段構えです。TCP/IPの接続を張った後、TLSのハンドシェイクで証明書の検証と鍵の交換を行い、以降のHTTPリクエスト・レスポンスはすべて暗号化されて流れます。
ここで重要なのは、HTTPそのものは何も変わっていないことです。メソッドもステータスコードもヘッダも同じで、暗号化の仕事はすべてTLS層が引き受けます。この層の分離のおかげで、Webアプリのコードは暗号化をほぼ意識せずに済みます。なお、暗号化されるのはパスやヘッダ、ボディまでで、接続先のドメイン名やIPアドレスは経路上から見えます(「どこと通信しているか」までは隠れません)。
証明書と信頼の連鎖
なりすまし防止の要がサーバ証明書です。証明書は「この公開鍵暗号の公開鍵はexample.comのものである」ことを、認証局(CA)が署名して保証した電子文書です。ブラウザにはあらかじめ信頼できるCAの一覧が組み込まれており、受け取った証明書の署名をルートCAまで辿って検証します。この「信頼の連鎖」が成立して初めて鍵マークが表示されます。証明書には有効期限があり、期限切れは「証明書エラーでサイトが全断」という定番の障害を引き起こすため、実務ではLet’s Encryptなどによる自動更新を組むのが常識になっています。
実務での構成
自前のアプリケーションサーバでTLSを処理することは実は少なく、多くの構成では前段のリバースプロキシやロードバランサ、あるいはCDNが「TLS終端」を担います。つまりインターネット区間はHTTPSで守り、内部ネットワークでは平文HTTPで中継する構成です。このときアプリ側からは「自分はHTTPで受けている」ように見えるため、元のプロトコルを伝えるX-Forwarded-Protoヘッダの扱いを誤ると、リダイレクトループなどの典型的なハマりが発生します。
HTTPSを前提にした防御
HTTPSの効果を確実にするための仕組みも整備されています。HSTS(HTTP Strict Transport Security)は「このサイトには今後HTTPSでのみ接続せよ」をブラウザに記憶させるヘッダで、最初の1回だけ平文で接続してしまう隙(そこを突く中間者攻撃)を塞ぎます。CookieのSecure属性は「HTTPS経由でしか送信しない」指定で、セッションIDの平文漏えいを防ぎます。逆に言えば、HTTPSは万能ではありません。守るのはあくまで「通信経路」であり、XSSやSQLインジェクションのようなアプリケーション自体の脆弱性、フィッシング(本物の証明書を持つ偽サイト)には別の対策が必要です。