あたらしく構築したwebサーバーを常時SSL化したときの手順の覚書。
参考サイト:https://knowledge.sakura.ad.jp/10534/
1.ApacheのSSLモジュールmod_sslをインストールする
サイトを常時SSL化するに、ApacheのSSLモジュール(mod_ssl)がインストールされている必要がある。
mod_sslが導入済みかどうかを確認
# httpd -M | grep ssl
ssl_module があるか確認して、なければインストールする。
インストール
dnf -y install mod_ssl
インストールが終わったら apache を再起動して有効化。
apache の再起動
-------------------------
systemctl restart httpd
-------------------------
https://~ でアクセスできるようになるが、警告が出る。警告は出るが、暗号化はできているらしい。
警告を消すには、SSL証明書のインストールが必要。
2.Let’s Encrypt をインストールする
Let’s Encrypt は無料のSSL証明書。
独自ドメインのアクセスには対応しているが、IPアドレスを指定したアクセスには対応していないので注意。
2023年2月現在、Let’s EncryptのSSL証明書発行ツール「certbot」は「snap」を利用したインストールが推奨されているので、Snapdをインストールする。
すでに certbot がインストールされているかの確認
certbot --version
すでにsnapがインストールされているか
snap version
リポジトリに snap があるか確認する。
リポジトリに snap があるか
dnf list available | grep snap
↓この二行があるか
snapd.x86_64 2.58-1.el9 epel
snap-confine.x86_64 2.58-1.el9 epel
あったので snap をインストールする。
snap をインストール
sudo dnf install snapd
インストールしたら、メインのsnap通信ソケットを管理するsystemdユニットの自動起動を有効にする。
snapdデーモンを有効化と自動起動を有効。
sudo systemctl enable --now snapd.socket
--now をつけると自動起動を設定しつつ、サービスもすぐに起動する。
こんなメッセージが出た
Created symlink /etc/systemd/system/sockets.target.wants/snapd.socket → /usr/lib/systemd/system/snapd.socket.
3.certbot パッケージのインストール
3-1.certbot をインストールする
snap 経由で certbot をインストール
snap install --classic certbot
--classic
オプションにより、システム全体へのアクセスが許可された状態(Classic confinement)でCertbotをインストール
エラーが出た
error: cannot install "certbot": classic confinement requires snaps under /snap
or symlink from /snap to /var/lib/snapd/snap
Classic snap
一部の snap (例: Skype や Pycharm) は classic confinement を使用しますが、classic confinement は FHS に準拠していない /snap ディレクトリを必要とします。snapd パッケージには /snap ディレクトリは含まれていません。classic snap をインストールしたい場合、/var/lib/snapd/snap から /snap に手動でシンボリックリンクを作成してください:
classic snapをサポートするため、指示通りにシンボリックリンクを作成する。
ln -s /var/lib/snapd/snap /snap
# /snap/bin/certbotへのシンボリックリンクを作成してcertbotコマンドを実行できるようにする
$ sudo ln -s /snap/bin/certbot /usr/bin/certbot
# シンボリックリンクが作成されていることの確認
$ sudo ls -la /usr/bin/certbot
lrwxrwxrwx 1 root root 17 Jan 18 18:32 /usr/bin/certbot -> /snap/bin/certbot
$ sudo ls -la /snap/bin/certbot
lrwxrwxrwx 1 root root 13 Jan 18 18:31 /snap/bin/certbot -> /usr/bin/snap
#バージョンが出ることを確認
$ sudo certbot --version
3-2.証明書の発行
※サーバー移行途中で新サーバー用にDNSの設定がまだの場合は、旧サーバーから一時的にコピーした証明書を利用することもできる
Apache用のものを発行
sudo certbot --apache -d example.com
エラーが出た
Unable to find a virtual host listening on port 80 which is currently needed for Certbot to prove to the CA that you control your domain. Please add a virtual host for port 80.
日本語訳:現在Certbotがドメインを管理していることをCAに証明するために必要なport 80である仮想ホストが見つかりませんでした。port 80用の仮想ホストを追加してください。
指示通りにバーチャルホストを追記する。記述場所は、httpd.conf の一番下や、conf.d ディレクトリに vhost.conf という新しいファイルを作ってもいい。conf.d に作った *.conf ファイルは httpd.conf に自動で読み込まれる。
# 新しい apache では「NameVirtualHost *:80」の記述は不要。
# NameVirtualHost *:80
httpd.conf の一番下に追記
<VirtualHost *:80>
ServerAdmin root@example.com
DocumentRoot /var/www/html
ServerName example.com
</VirtualHost>
新しくファイルを作る場合
# 空のファイルを作る
sudo touch vhost.conf
有効にするために apache を再起動。
httpd を再起動
sudo systemctl restart httpd
再度実行
sudo certbot --apache -d example.com
この状態で、apachectl configtest を実行したらエラーが出た。
$ apachectl configtest
AH00526: Syntax error on line 13 of /etc/httpd/conf.d/vhost-le-ssl.conf:
SSLCertificateFile: file '/etc/letsencrypt/live/ドメイン名/fullchain.pem' does not exist or is empty
上のサイトを参考にパーミッションを変更したら、エラーが出なくなった。
$ sudo chmod 755 /etc/letsencrypt/archive/ $ sudo chmod 755 /etc/letsencrypt/live/
apachectl configtest を実行して次のメッセージが出ていたら「NameVirtualHost *:80 」を消す。
NameVirtualHost has no effect and will be removed in the next release /etc/httpd/conf.d/vhost.conf:2
# NameVirtualHost *:80
↓
NameVirtualHost *:80
自動更新の設定
certbot renew --dry-run
次のエラーが出た
The following error was encountered:
[Errno 13] Permission denied: '/var/log/letsencrypt/.certbot.lock'
Either run as root, or set --config-dir, --work-dir, and --logs-dir to writeable paths.
sudo がないだけ。
sudo certbot renew --dry-run
snap版certbotの自動更新について
snap経由でインストールしたcertbotは証明書が自動更新されるので、crontabへの記述は不要
snap.certbot.renew.timerが有効になっていることを確認
systemctl list-timers | grep certbot
更新のタイミングを確認
snap refresh --time
ちなみにsnap経由のcertbotだと、以下のコマンドではエラーになる
sudo systemctl status certbot-renew.timer