Let’s Encryptを使ってみた

SSL証明証明書が無料。しかも導入がスゲー簡単と言う。
だいたいLet’s Encrypt総合ポータルに書いてあるとおりで行けるが、いくつかつまずいた点や考えた点もあったので、一応備忘録的に。

管理しているサイトのひとつで試してみた。
環境はCentOS 6でウェブサーバーはApache。

導入

iptablesの設定

SSL証明書を発行する際にサーバーの80番ポートと443番ポートにアクセスできる必要がある。
ので今まで80番ポートしか開けてなかったサーバーの443番ポートをiptablesで開けておく。

Certbot クライアントのインストール

Certbot クライアントのインストール#CentOS6を参考にcertbot-autoをダウンロードして実行。
epelはすでに設定済み。

# wget https://dl.eff.org/certbot-auto
# chmod a+x certbot-auto

テスト実行・・・のつもりが証明書発行まで

# ./certbot-auto

certbot-auto実行時にもろもろ必要なパッケージがインストールされて・・・おや、出てくるプロンプトに答えていたらそのまま証明書の発行まで行ってしまった。
あっさり完了。

手順には80番ポートを使うため、一時的にhttpdを停める必要があると書いてあるのだが、特に停めないでも問題なかった。
導入手順も日々より簡単に進化していると言うことなのだろうか。暗黙のうちにWebroot プラグインが使われたのかな。

よく分からないがとりあえずうまく行っているようなので、今は深追いはしない。

httpdの再起動

秘密鍵や証明書などもろもろのファイルは/etc/letsencrypt以下に作成されている。

そして/etc/httpd/conf.d以下にwww.example.com.confという非SSLのバーチャルホストの設定をコピーしたwww.example.com-le-ssl.confというSSLのバーチャルホスト設定ができている。
至れり尽くせりですな。

確認だけして何も変更せずにApacheを再起動。

# service httpd configtest
# service httpd restart

SSLの設定ファイルは自動で作成されない場合もあると思うので、その場合は手動で作成する必要がある。

動作確認

httpsでアクセスできるかどうかを確認。

ついでにQUALYS SSL LABSのSSL Server Testでも確認しておく。

無事A判定でした。

自動更新の設定

無事SSL証明書のインストールが済んだが、Let’s EncryptのSSL証明書は有効期限が90日間となっている。
90日ごとに手動で更新作業を行うのはダルいが、しかし更新作業も簡単に自動化ができるのでこの有効期限の短さを心配する必要はない。

まず更新のコマンドをDRY RUNしてみる。更新後に新しい証明書をロードするためhttpdを再起動するように。

# /home/akahige/bin/certbot-auto renew --post-hook "service httpd restart" --dry-run

特にエラーも出ないので普通に実行してみる。

# /home/akahige/bin/certbot-auto renew --post-hook "service httpd restart"

無事動いたが、有効期限が30日未満ではないので証明書は更新されない。証明書の更新がない場合はhttpdの再起動も行われない。

本当に更新が動くのか、–force-renewalオプションをつけて実行してみる。

# /home/akahige/bin/certbot-auto renew --post-hook --force-renewal "service httpd restart"

きちんと更新されてhttpdも再起動された。

問題なさげなのでrootのcronで毎週月曜日の午前8:00更新とするようにcrontabを設定。

0 8 * * 1 /home/akahige/bin/certbot-auto renew -q --no-self-upgrade --post-hook "service httpd restart"

エラー以外の出力を抑制する-qオプション、実行の度に自身を最新版に更新しようとするのを抑制する–no-self-upgradeオプションを付加。

これで毎週月曜日の午前8時に更新を試み、有効期限の残りが30日未満の証明書があれば更新される。

crontabで動かない問題

実は試した環境だと上記のcrontabでは動かなかった。
cronのログには実行の後が見られるが、ほかのログを見ても実行の形跡がない。

ので以下のように修正。これで動作するようになった。

0 8 * * 1 /bin/bash -l -c '/home/akahige/bin/certbot-auto renew -q --no-self-upgrade --post-hook "service httpd restart"'

ターミナルで手動でコマンドを打つと動いてcrontabで動かないのは、だいたい環境変数の問題。

* * * * * env > /tmp/cronenv.txt

のようにしてターミナルとの環境変数の違いを確認してみると良い。

自動更新実行のタイミングについて

毎月1回のチェックにすると30未満という条件をすり抜けて更新されないタイミングがあるような気がするので(例えば1日にチェックした場合31日が有効期限だと更新されない)毎週で。

チェック頻度は毎日でも問題ないっぽいが、そこまで頻度を上げる必要もないように思える。

–force-renewalについて

–force-renewalという有効期限にかかわらず強制的に証明書を更新するオプションもあるが、Let’s Encryptのサーバーにかける負荷を考えるとCronでは使わない方がよさげ。緊急時用だろう。週毎に発行回数の制限もあるようだし。

certbot-autoのコマンドリファレンスも参考に。

–no-self-upgradeは付けるべきか

cronでcertbot-autoを動かしてrenewするときに–no-self-upgradeは付けている例が多いが、これは付けた方がいいのだろうか。

付けておかないとcertbot-autoにバグが入ったときにダメージを受ける可能性がある。またバージョンアップによってコマンドのオプションが変わってしまう可能性もある。

とすると付けておくべきか。現在のところ開発はかなりアクティブでもあるし。

一方で古いバージョンを長期間使い続けていることで問題が発生する可能性もないとは言えず。
定期的にアップデートの状況をチェックして、メンテするというのは必要そうだ。そのうちいい具合に枯れてくれると安心なのだが。

ログの確認

ログは以下の場所にある。不明点があれば確認。

/var/log/letsencrypt/letsencrypt.log

情報ソースについて

Let’s Encryptのクライアントはどんどん進歩していて、このページの情報も早晩古くなってしまうかもしれない。
ネット上ではすでに古くなった情報も散見される。

公式や日本語のLet’s Encrypt総合ポータルのドキュメントがかなり充実しているので、まずはこれら基本とするのがいいだろう。

参考