Windows環境でLet's Encrypt証明書の自動更新を実現した話

Windows環境でLet's Encrypt証明書の自動更新を実現した話

はじめに

自宅サーバーでHTTPSサイトを複数運営していると、Let's Encryptの証明書管理が意外と面倒になってきます。私の環境では25個以上のドメインの証明書を管理しており、手動での更新作業から解放されたいと思っていました。

この記事では、Windows 11 + nginx + Docker環境で、既存のシステムを大きく変更することなく証明書の自動更新を実現した過程を紹介します。

環境概要

  • OS: Windows 11
  • Webサーバー: nginx(Windows版)
  • アプリケーション: Dockerコンテナで稼働
  • 証明書管理: Certbot
  • ドメイン数: 25個以上(DuckDNS、ddnsfree.comなど)

現在の証明書取得方法

これまでは以下の手順で手動取得していました:

# nginx停止
nginx -s quit

# standalone モードで証明書取得
certbot.exe certonly --standalone -d example.com

# nginx再起動
nginx

目標:メンテナンスフリーな自動更新

既存のDocker環境は触りたくない、かつ完全に自動化したいという要件で検討しました。

検討した方法

  1. webroot認証への移行 - nginx設定変更とDocker再構築が必要
  2. acme.sh導入 - 新しいツールの学習コストあり
  3. 現在のstandaloneモードを自動化 - 既存環境をそのまま活用

結果として、3番目の現在の方法をそのまま自動化する方向で進めることにしました。

実装過程

Step 1: 現状調査

まず、現在の証明書状況を確認しました:

"C:\Program Files\Certbot\bin\certbot.exe" certificates

結果、以下の問題を発見:
- 期限切れ証明書:1個
- 期限間近証明書:数個
- 無効な設定ファイル:3個(symlinkエラー)

Step 2: 問題の解決

無効な設定ファイルを削除:

del "C:\Certbot\renewal\heath-navi.feelingsmart.ddnsfree.com.conf"
del "C:\Certbot\renewal\yousyslab.duckdns.org-0001.conf"
del "C:\Certbot\renewal\yousyslab.duckdns.org.conf"

Step 3: 自動更新バッチファイル作成

最初のバージョン:

@echo off
REM auto-renew-standalone.bat

echo %date% %time% - Starting certificate renewal >> C:\Certbot\renewal.log

nginx -s quit
timeout /t 10
certbot renew --quiet --standalone
nginx

echo %date% %time% - Renewal completed >> C:\Certbot\renewal.log

遭遇した問題と解決

問題1: nginxのパスが通っていない

エラー: nginx: command not found

原因調査:

where nginx
# → 情報: 与えられたパターンのファイルが見つかりませんでした。

cd C:\nginx
where nginx
# → C:\nginx\nginx.exe

解決方法: バッチファイルでフルパスを指定

C:\nginx\nginx.exe -s quit
start "" "C:\nginx\nginx.exe"

問題2: 設定ファイル読み込みエラー

エラー:

nginx: [alert] could not open error log file
[emerg] CreateFile() "c:\Program Files\Certbot\bin/conf/nginx.conf" failed

原因: 別のディレクトリからnginx.exeを実行すると、相対パスで設定ファイルを探してしまう

解決方法: 作業ディレクトリを変更

cd /d C:\nginx
nginx.exe -s quit

問題3: バッチファイルが終了しない

現象: start nginx.exe 後にカーソルが戻ってこない

原因: nginxがフォアグラウンドで実行される

解決方法:

start "" nginx.exe  # バックグラウンド実行

最終版バッチファイル

全ての問題を解決した最終版:

@echo off
REM C:\Program Files\Certbot\bin\auto-renew-standalone.bat

echo %date% %time% - Starting certificate renewal >> "C:\Certbot\renewal.log"

echo Stopping nginx...
cd /d C:\nginx
nginx.exe -s quit
timeout /t 10

echo Running certbot...
"C:\Program Files\Certbot\bin\certbot.exe" renew --quiet --standalone
set CERTBOT_RESULT=%errorlevel%

echo Starting nginx...
cd /d C:\nginx
start "" nginx.exe

if %CERTBOT_RESULT% equ 0 (
    echo %date% %time% - Renewal completed successfully >> "C:\Certbot\renewal.log"
) else (
    echo %date% %time% - Renewal failed with error %CERTBOT_RESULT% >> "C:\Certbot\renewal.log"
)

タスクスケジューラでの自動実行設定

設定手順

  1. タスクスケジューラを開く (taskschd.msc)
  2. 基本タスクの作成
  3. 名前: Certbot Certificate Renewal
  4. トリガー: 月単位(毎月1日 午前3時)
  5. 操作: C:\Program Files\Certbot\bin\auto-renew-standalone.bat

  6. 追加設定 (作成後にプロパティで設定)

  7. 全般タブ: 「最上位の特権で実行する」✅
  8. 条件タブ: 「AC電源接続時のみ」❌

実行結果

最初の手動テスト実行で、以下の証明書が正常に更新されました:

  • aibeauty-yuna.duckdns.org: 8日 → 89日
  • happy-life-forever.duckdns.org: 期限切れ → 89日
  • y-scrapper.duckdns.org: 25日 → 89日
  • yousystem-lab.duckdns.org: 6日 → 89日

まとめ

得られた成果

  • 完全自動化: 月1回の自動更新で手動作業が不要に
  • 既存環境維持: Docker構成や個別の設定変更なし
  • 安定運用: 25個以上の証明書を一括管理

学んだポイント

  1. 環境調査の重要性: パスの確認、設定ファイルの場所など
  2. 段階的なデバッグ: 問題を一つずつ特定・解決
  3. 実用性重視: 理想的でなくても現実的な解決策を選択

今後の展望

  • ログ監視の自動化
  • 更新失敗時の通知機能
  • より効率的な証明書管理手法の検討

自宅サーバー運営者にとって証明書管理は避けて通れない課題ですが、少しの工夫で大幅に作業負荷を軽減できます。特にWindows環境での情報が少ない中、この記録が同じような環境で悩んでいる方の参考になれば幸いです。