certbotによるSSLキーの自動更新

Let’s Encryptから開発用ドメインのSSL証明書を取得、更新管理を行うためにcertbotを利用している。Let’s Encryptを使用するとSSL証明書を無料で取得することができるが、有効期限が発行から3ヶ月なので、定期的な更新管理が必要になる。

certbotのインストール

以下のコマンドを投入する

$ sudo apt install -y certbot

SSL証明書の新規取得

dev.ipadtaxi.jpのSSL証明書を取得するには以下のコマンドを投入する

証明書は様々な形で認証を受けることができるが、DNSを介して認証を受ける手順を利用する。この手順は自前のドメインを管理するDNSを自身で操作できる場合にのみ使うことができる。

  1. 次のコマンドを投入する
    $ sudo certbot certonly --manual -d dev.ipadtaxi.jp --preferred-challenges dns-01
    
  2. 起動すると以下の画面が表示されるので 自身の連絡先(メールアドレス) を入力する
    Saving debug log to /var/log/letsencrypt/letsencrypt.log
    Enter email address (used for urgent renewal and security notices)
    (Enter 'c' to cancel): 
    
  3. DNSの ACME Server エントリを登録できるかを聞かれるので Y(Yes) を押す
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    Please read the Terms of Service at
    https://letsencrypt.org/documents/LE-SA-v1.3-September-21-2022.pdf. You must
    agree in order to register with the ACME server. Do you agree?
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    (Y)es/(N)o:
    
  4. 先に登録したメールアドレスにお知らせを送ってよいかを聞かれる。
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    Would you be willing, once your first certificate is successfully issued, to
    share your email address with the Electronic Frontier Foundation, a founding
    partner of the Let's Encrypt project and the non-profit organization that
    develops Certbot? We'd like to send you email about our work encrypting the web,
    EFF news, campaigns, and ways to support digital freedom.
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    (Y)es/(N)o:
    
  5. DNSにエントリするハッシュ値が表示される。これを自身が管理しているDNSに登録することで認証を受ける仕組みである。
    with the following value:
    
    O2ZFSA-cqMtLsn44l_dl7GNE-atR7LQYixUfuO8wVIk
    
    Before continuing, verify the TXT record has been deployed. Depending on the DNS
    provider, this may take some time, from a few seconds to multiple minutes. You can
    check if it has finished deploying with aid of online tools, such as the Google
    Admin Toolbox: https://toolbox.googleapps.com/apps/dig/#TXT/_acme-challenge.dev.ipadtaxi.jp.
    Look for one or more bolded line(s) below the line ';ANSWER'. It should show the
    value(s) you've just added.
    
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    Press Enter to Continue
    

    ここでは直ぐには[ENTER]を押さずに放置しつつ、上記で指定されたハッシュ値を別途DNSに登録する手順が必要です。

    ここで直ぐに [ENTER] を押してしまうと、DNSでハッシュ値が検索できないので認証が失敗する
  6. 別画面でDNSに指示されたハッシュ値を設定する。例えばzenlogicのドメイン管理画面から以下のようにハッシュ値を登録する。
  7. 別のプロセスで登録したハッシュ値が参照可能かどうかを確認する。ここでは GoogleのDNSサーバー(8.8.8.8)に問い合わせを行い、登録値が伝搬されているかを確認する
    $ nslookup -type=txt _acme-challenge.dev.ipadtaxi.jp 8.8.8.8
    
    Server: 8.8.8.8
    Address: 8.8.8.8#53
    
    Non-authoritative answer:
    _acme-challenge.dev.ipadtaxi.jp text = "O2ZFSA-cqMtLsn44l_dl7GNE-atR7LQYixUfuO8wVIk"
    
    Authoritative answers can be found from:
    
  8. 上記のようにハッシュ値の設定内容が確認できたら、先のcertbotの待機画面で [ENTER] を押して処理を続ける。成功した場合には以下のように指定されたフォルダーに SSL証明書ファイルがダウンロードされる。
    Successfully received certificate.
    Certificate is saved at: /etc/letsencrypt/live/dev.ipadtaxi.jp/fullchain.pem
    Key is saved at: /etc/letsencrypt/live/dev.ipadtaxi.jp/privkey.pem
    This certificate expires on 2023-10-24.
    These files will be updated when the certificate renews.
    
    NEXT STEPS:
    - This certificate will not be renewed automatically. Autorenewal of --manual certificates requires the use of an authentication hook script (--manual-auth-hook) but one was not provided. To renew this certificate, repeat this same certbot command before the certificate's expiry date.
    
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    If you like Certbot, please consider supporting our work by:
    * Donating to ISRG / Let's Encrypt: https://letsencrypt.org/donate
    * Donating to EFF: https://eff.org/donate-le
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    
  9. 作成された証明書を確認する
    $ su
    パスワード: xxxxxxx[enter]
    # cd /etc/letsencrypt/live
    # cd dev.ipadtaxi.jp
    # ls -l
    合計 4
    -rw-r--r-- 1 root root 692  7月 28 09:34 README
    lrwxrwxrwx 1 root root  39  7月 28 09:34 cert.pem -> ../../archive/dev.ipadtaxi.jp/cert1.pem
    lrwxrwxrwx 1 root root  40  7月 28 09:34 chain.pem -> ../../archive/dev.ipadtaxi.jp/chain1.pem
    lrwxrwxrwx 1 root root  44  7月 28 09:34 fullchain.pem -> ../../archive/dev.ipadtaxi.jp/fullchain1.pem
    lrwxrwxrwx 1 root root  42  7月 28 09:34 privkey.pem -> ../../archive/dev.ipadtaxi.jp/privkey1.pem
    
    SSL証明書がダウンロードされる領域(/etc/letsencrypt/live)を参照するにはroot権限が必要となります。

SSL証明書の更新処理

Let’s EncryptのSSL証明書は発行から3ヶ月で有効期限が来るので、それまでに定期的に更新処理を行う必要がある。

  1. 以下のコマンドを投入する
    sudo certbot renew
    
  2. 作成したばかりなので、この時点で更新されることはないが、期限が近付くとSSL証明書が更新され、新しい証明書がダウンロードされる。
    Saving debug log to /var/log/letsencrypt/letsencrypt.log
    
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    Processing /etc/letsencrypt/renewal/dev.ipadtaxi.jp.conf
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    Certificate not yet due for renewal
    
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    The following certificates are not due for renewal yet:
      /etc/letsencrypt/live/dev.ipadtaxi.jp/fullchain.pem expires on 2023-10-25 (skipped)
    No renewals were attempted.
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    

証明書を自動的に更新する(WSL上で実施)

Let’s Encryptで作成されるSSL証明書を自動更新するには前述のコマンドを定期的に実行する必要がある。ここではcronを使ってこれを自動的に更新する。

  1. crontabを起動するには以下のコマンドを投入する
    $ sudo crontab -u root -e
    
  2. 以下の内容を記述して保存する
    # 毎月初の 4:00 に certbot を更新し、Webサーバーを再起動させる
    00 04 01 * * certbot renew && systemctl restart apache2
    
    上記の内容には更新後にWebサーバーを再起動する処理を追加している
  3. 設定内容を確認するには以下のコマンドを投入する
    $ sudo crontab -u root -l
    

証明書を自動的に更新する(Win32上で実施)

Let’s Encryptで作成されるSSL証明書を自動更新するには前述のコマンドを定期的に実行する必要がある。ここではWindowsのタスクスケジューラを使ってこれを自動的に更新する。

  • 更新処理用のWindowsバッチファイルを作成WSL上のcertbotをroot権限で実行し、処理結果をログファイルに記録する例
    @echo off
    @rem ***** 文字コードをUTF-8にする *****
    
    chcp 65001
    
    @rem ***** 現在時刻文字列の生成 *****
     
    set yy=%date:~0,4%
    set mo=%date:~5,2%
    set dd=%date:~8,2%
     
    set time2=%time: =0%
     
    set hh=%time2:~0,2%
    set mm=%time2:~3,2%
    set ss=%time2:~6,2%
     
    @rem ***** 本処理を実行する *****
    
    set datestr=%yy%%mo%%dd%
    set timestr=%hh%%mm%
    
    echo SSL証明書の更新を開始しました
    wsl -u root certbot renew > c:\users\takan\log\certbot_%datestr%_%timestr%.log
    echo SSL証明書の更新を終了しました
    pause
    
  • タスクスケジューラに上記処理を登録
    処理タスクに関するインスタンスを作成する。ユーザーがログオンしていない時にも実行できるようにした。
    処理タイミング(トリガー)は毎月1日と16日の月2回程度に設定する。
    トリガーの詳細設定は以下の通りにした。

    処理対象は上記で作成したバッチファイルを実行するように指定する。

    後続の処理でサーバーを再起動させるのも良いかと思う