前置き
こんにちは!
この記事では、サーバー証明書という複雑そうなものについて、初心者の方でもわかりやすく解説します。
証明書って何だろう?
ウェブサイトやオンラインショッピングのセキュリティに関係しているんでしょうか?
一緒に楽しく学んでいきましょう!
インターネットのセキュリティ
インターネットでウェブサイトを見るとき、その裏では何が起きているかというと、クライアントとウェブサーバーの間でデータ通信が行われています。
クライアントというのはウェブサイトにアクセスするユーザー側のことで、
ウェブサーバーというのはウェブサイトを提供する側のことを指します。
これらがお互いにデータをやり取りするこで、クライアントはウェブサイトを閲覧することができます。
コンピューター機器が通信するときは、プロトコルと呼ばれるルールに従って行われます。
これは「私はこの形でデータを要求するから、あなたはこの形でデータを返信してね」というような取り決めのことです。
プロトコルの種類はたくさんありますが、インターネットの通信ではHTTP(HyperText Transfer Protocol)というプロトコルが使われることがかつては一般的でした。
しかし、HTTPはデータを平文で送受信するため、もし第三者が通信を盗聴したらその内容を簡単に理解できてしまうというセキュリティの問題があります。
インターネットは情報が行き交う場所であり、個人情報やお金のやり取りなどさまざまな大切なデータが送受信されます。
これらのデータのやり取りを安全に行わないと、悪意のある人たちにデータを盗聴され悪用されてしまう恐れがあります。
ここで登場するのがSSL(Secure Sockets Layer)です。
SSLは通信データを暗号化し、安全な通信を実現するための技術です。
これをHTTPに組み込んだものが、HTTPSというプロトコルです。SはSecure(安全)を表します。
HTTPSでは通信データを暗号化して送受信するので、第三者が通信を盗聴しても内容が読み取られることはありません。
現在ではインターネット通信はこのHTTPSを使うことが推奨されています。
ウェブサイトのURLが「https:// 」で始まる場合、そのサイトはHTTPSで通信しているという意味になります。

HTTPSは、HTTPにはない下記の2つの特徴があります。
- 通信するウェブサーバーが信頼できるサーバーかどうか確認する
- 通信内容を暗号化して送受信する
この2つの特徴を実現するために使われるのが「証明書」です。
証明書とはウェブサイトが信頼できるものであることを証明する情報が書かれたファイルです。
証明書はウェブサイトごとに用意します。
1の特徴について見てみましょう。
たとえ通信内容を暗号化したとしても、通信相手のウェブサーバーが悪意があったら意味がありません。
そこでまず、クライアントは通信するウェブサーバーの信頼性を確認します。
ウェブサーバーは自身が信頼できることを証明するために、あらかじめ第三者の専門機関に頼んで証明書というファイルを取得しておきます。
証明書はあるウェブサイトが安全であることの証明が書かれています。
これをクライアントに渡すことで、安全なサイトであることを伝えます。
2の特徴についても見てみましょう。
通信を暗号化するには、通信内容を何らかの暗号鍵で暗号化すればOKです。
この暗号化を実現するために使われる鍵の一つが、「公開鍵」と呼ばれる鍵です。
これはウェブサイトごとに作成します。
証明書にはこの公開鍵の情報も含まれています。
先ほど書いたように証明書はウェブサーバーからクライアントに送られます。
クライアントはサイトの証明を確認するだけでなく、証明書の中のこの公開鍵の情報も暗号化のために使用します。
このように、HTTPSを実現するために証明書が使われている事がわかりました。
とはいえまだ概要だけなのでもう少し詳しく説明したいのですが、証明書に関する用語はたくさんあり、それぞれを説明するだけでは理解が難しいと思いました。
そこで、実際に証明書を使ってウェブサイトをHTTPS化する流れを説明したいと思います。
その中で操作や用語について説明をしていきます。
まずは証明書の取得するところから見ていきましょう!
公開鍵・秘密鍵の作成
さて、ウェブサーバーをHTTPS化するにはまず証明書を手に入れる必要があります。
証明書の発行を申請するためには、あらかじめウェブサーバー側の人が公開鍵と秘密鍵と呼ばれる暗号鍵を作っておく必要があります。
暗号鍵とは、ある情報を暗号化するのに利用される数学的な情報のことです。
例えばプライベートな情報を暗号鍵を使って暗号化すれば、まったく別の情報に変換されるので、誰かに見られても中身が解読されることはありません。
暗号鍵には対になる複合鍵が存在します。複合鍵を使うと暗号化した情報を元の情報に戻すことができます。
今回の場合、公開鍵は暗号鍵で情報を暗号化するのに使われます。
一方、秘密鍵は複合鍵でその暗号を複合して元の情報を読み取るときに使います。
まずはこの公開鍵と秘密鍵を生成しましょう。
これらは証明書を発行するために必要なのに加え、通信を暗号化するときにも使われる重要な情報です。
その実体は”.pem”や”.key”などの拡張子を持つファイルです。
公開鍵/秘密鍵を生成する方法は環境によって異なります。
サーバーによく使われるLinuxの場合はOpenSSLというツールを使うことでコマンドラインから生成できます。
Windowsの場合は「証明書管理コンソール」、macの場合は「Keychain Access」という標準搭載されているソフトを使います。
OpenSSLを使った例を見ておきましょう。
まずは下記のコマンドで秘密鍵を生成します。
openssl genpkey -algorithm RSA -out private_key.pem
これを実行するとprivate_key.pemという秘密鍵が作成されます。
次に下記のコマンドで公開鍵を生成します。
先ほどの秘密鍵の情報を利用しています。
openssl rsa -pubout -in private_key.pem -out public_key.pem
これを実行するとpublic_key.pemという公開鍵が作成されます。
ファイルの中は鍵の情報がエンコードされて書かれています。
下記はファイル内のイメージです。
-----BEGIN PRIVATE KEY-----
MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQDG/yOx8Eo+yM1D
u7AxOaTH8h81DYuAI9xFlH+8TpOk9y7L1D/q7JXf4zMWiXMnO2Lc9H8NgPPLpEMD
9Qizx6d1b+lVtN8hNz0Z1Z8ASk4HGO5s1CFEYRbZDn4kkMslU7FG9bMQd8n6foVg
KuAP3vD/9DzP7JedlhrLX8zQxS9S4ceZBrj8iG3HAt
... (中略) ...
9I7wP4+2tLxXTXCcYYbT/rLjFqbygeyHzThgBymjxUJ7BszIZ9fQ
-----END PRIVATE KEY-----
なお、秘密鍵は名前の通り機密情報です。
ウェブサーバー側がこの情報はしっかりと保管しておく必要があります。
これが漏れると、安全な通信ができなくなってしまいます。
CAへ申請
生成した鍵の情報を用いて、CA(認可局)に証明書発行を申請します。
CAというのは証明書を発行する機関のことです。
証明書はウェブサイトの身元を証明するものですが、これは誰でも発行できるわけではありません。
運転免許所は運転免許センターでないと発行できないのと同じように、信頼された機関に申請して発行してもらう必要があります。
機関といっても何も公的なものではなく、いくつかの一般の民間企業がサービスとしてそのような証明書発行機能を提供しています。
CAに申請するときはCSRという形にして情報を渡します。
Linuxの場合、これも同じく下記のようにコマンドで作成できます。
openssl req -new -key private_key.pem -out certificate_request.csr
これを実行し指示に従ってウェブサイトの情報を入力すると、certificate_request.csrというCSRファイルが作成されます。
生成されたCSRには次のような情報が含まれています。
- 申請者の身元情報(名前、住所、メールアドレス、組織名など)
- ウェブサイトのURL
- 公開鍵
どのCAを使うかはセキュリティ要件や予算に合わせて行います。
代表的なものには、GlobalSign、DigiCert、Let’s Encryptなどがあります。
CRSの提出方法もCAにより異なりますが、CAのサイト上でオンラインアップロードを行う、メールで送信する、などの方法があります。
CAが申請内容を確認
CAは提出されたCSRを使って、下記の2点を確認して証明書の発行可否を判定します。
- 申請内容の信頼性
CAは申請内容が正しいことを確認します。 - ドメイン所有者の確認
申請した個人または組織が申請所に記載のドメイン(URL)を所有していることを確認します。
要は本当にそのウェブサイトの運営者が申請しているのかを確認します。
証明書の発行
審査を通過した場合、CAは証明書を発行します。
この証明書にはCAのデジタル署名が付与されています。
デジタル署名というのは文字通りデジタルなサインのことで、この署名により誰が(どのCAが)承認した証明書か分かるようになります。
証明書には以下の情報が含まれます。
- サーバーの公開鍵
証明書にはサーバーの公開鍵が含まれており、クライアントが安全な通信を確立するために使用します。 - ドメイン名
証明書は特定のドメイン(URL)に関連付けられています。 - 有効期限
証明書には有効期限が設定されており、一定の期間内に使用することができます。
有効期限切れの証明書は信頼性が低くなります。 - CAのデジタル署名
CAによって証明書に付けられたデジタル署名は、証明書の正当性を確認するのに役立ちます。
証明書のインストール
申請者はCAから証明書を取得し、これをウェブサーバーにインストールします。
インストールする方法はサーバーの種類によって異なります。
一つ例を挙げると下記のようなインストール手順になります。
- サーバーに秘密鍵を配置
証明書をサーバーにインストールする際、まずは先ほど生成した秘密鍵をサーバーの適切なディレクトリに配置します。 - 証明書ファイルをアップロード
CAから受け取った証明書ファイルをサーバーの適切なディレクトリに配置します。 - サーバーソフトウェアの設定
サーバーソフトウェア(例: Apache、Nginx)の設定ファイルを更新し、証明書と秘密鍵の場所を指定します。
また、HTTPS通信を有効にするためのポートやプロトコルの設定も行います。
これで証明書のインストールは完了です。
あとはサーバーを再起動すればHTTPSで通信できるようになっているはずです。
HTTPS通信時の流れ
HTTPSで通信したとき、どのように通信が暗号化されるのかをざっくり見てみましょう。
ここで秘密鍵や公開鍵が使われていることが分かると思います。
- ウェブサイトにアクセス
クライアントは「https:// 」から始まるURLでサイトにアクセスします。
- サーバーの証明書の検証
いくら通信を暗号化したとしても、通信先のサーバーが悪意のあるサーバーであれば意味がありません。
そのため、クライアントは初回のアクセス時にウェブサーバーが信頼できるかどうか検証します。
検証するために、ウェブサーバーはクライアントに自身の証明書を渡します。
クライアントは証明書を使って次のようなことを確認して、信頼できるサーバーかどうか確認します。
- 証明書が信頼されたCA(証明書発効機関)から発行されているか
- 信頼できるCAのリストはあらかじめブラウザに登録されています
- ウェブサイトのドメインが証明書に含まれているか
– 証明書の有効期限が切れていないか
もし証明書が有効で信頼できるものであれば、クライアントはウェブサイトへの通信を続行します。
証明書が無効であれば、クライアントは警告を表示し、通信をブロックすることがあります。
- データの暗号化
この後、HTTPS通信の核となる通信データの暗号化を行う準備をします。
証明書には公開鍵といういかにもそれっぽい鍵が含まれているので、この鍵でデータを暗号化するのかと思いきや、この方法は上手く行きません。
なぜなら、公開鍵で暗号化したデータは秘密鍵で複合できますが、逆はできないからです。
前述した通り、公開鍵は暗号化を、秘密鍵は複合化を行うための鍵です。
つまり、クライアントが公開鍵で暗号化したデータを送りサーバーが解読することは可能ですが、
サーバーが秘密鍵で暗号化したデータをクライアントが解読することはできません。
(もちろん公開鍵で暗号化したデータを同じ公開鍵で複合することもできません。
公開鍵はその名の通り誰にでも公開しているので、これができてしまうと誰でも通信を解読することができてしまいます)
ではどのように暗号化するかというと、クライアントが生成するセッション鍵という新たな鍵を使って通信データを暗号化します。
この鍵は、これ一つで暗号化も複合化もできます。
そのため、これをクライアントとサーバーが共有すればお互いの通信を暗号化して行えます。
とはいえ、この重要な鍵をどうやってサーバーに渡せばいいでしょうか?
まだ暗号化する準備が整っていないので、普通に平文で鍵を渡して万が一途中で通信を盗聴されたら大問題です。
ここで使われるのが、サーバーの証明書に含まれる公開鍵です。
公開鍵でこのセッション鍵を暗号化し、サーバーに送ります。
サーバーはこれを複合できる秘密鍵を持っているので、渡されたデータを複合してセッション鍵を取得します。
こうすることで、世界でこのクライアントとサーバーだけが知る共通の鍵を共有できました。
あとは送受信の内容をこの鍵で暗号化/複合化すれば、安全な通信を行うことができます。
つまり、公開鍵と秘密鍵は何に使われるかというと、HTTPS通信をする準備段階で通信を暗号化ためのセッション鍵を受け渡すのに使用するということです。
終わり
以上、証明書についてでした。
もし誤りは不明点があればご連絡ください!
ありがとうございました。