三年前 使用 Certbot 來為網站申請 Let’s Encrtpt 憑證 (CentOS 7),解決了網站需要加解密傳輸的問題,但憑證僅有90天的有效期,所以每隔90天便得重新申請憑證。
如果我若能(1)更新憑證(非重新申請),且(2)每90天期限一到,便能自動更新憑證,那就太好了。
(1)更新網站憑證(非手動重新申請)
依據 certbot 的功能,只要輸入 sudo certbot renew ,便可以更新憑證。
但我一開始在輸入之後,出現以下錯誤訊息:
Failed to renew certificate yowlab.idv.tw with error: The manual plugin is not working; there may be problems with your existing configuration.
The error was: PluginError(‘An authentication script must be provided with –manual-auth-hook when using the manual plugin non-interactively.’)
原來是我的網站(yowlab.idv.tw)使用了手動方式來獲取證書,而憑證更新時,Certbot 需要一個身份驗證腳本來證明我對我的網域名稱(yowlab.idv.tw)擁有控制權。
適合我的解決方法:
sudo certbot renew –manual-auth-hook /etc/letsencrypt/renewal/auth-hook.sh
但是,什麼是「auth-hook.sh」?系統裡面並沒有這個東西!
既然沒有這個檔案,我就自己來新增一個,因為我是使用「HTTP 驗證」方式來申請憑證,所以 auth-hook.sh 內容如下:
#!/bin/bash # 確保傳入了所有必要的環境變數 if [ -z "$CERTBOT_TOKEN" ] || [ -z "$CERTBOT_VALIDATION" ] || [ -z "$CERTBOT_DOMAIN" ]; then echo "缺少必要的環境變數" >&2 exit 1 fi # 設定 Web 服務器根目錄,依據自己網站目錄來做設定 WEBROOT="/var/www/html" # 創建驗證文件 mkdir -p "$WEBROOT/.well-known/acme-challenge" echo "$CERTBOT_VALIDATION" > "$WEBROOT/.well-known/acme-challenge/$CERTBOT_TOKEN" # 給予足夠的時間讓變更生效 sleep 10 echo "HTTP 驗證文件已創建"
在新增「auth-hook.sh」檔案與執行 sudo certbot renew –manual-auth-hook /etc/letsencrypt/renewal/auth-hook.sh 後,便可以達成更新憑證目的。
但若將 manual_auth_hook = /etc/letsencrypt/renewal/auth-hook.sh 這一行放入設定檔: /etc/letsencrypt/renewal/(域名).conf 裡面,便能簡化成只要輸入: sudo certbot renew ,便可以達成更新憑證目的。
(2)每90天,自動自動更新憑證
要達成每90天,自動自動更新憑證這一件事,簡單說,只要讓 cron 每 90 天執行一次 sudo certbot renew 動作就好。
問題是~ /etc/crontab 並無法做出每90天執行一次的設定。
而可以達成這個目標的方法有不少,我採用以下方法。
- 先建立一個判斷是否 90天期限已到的程式: run_every_90_days.sh
- 再到 /etc/crontab 設定每天凌晨0時定時執行
- 最後記得重新啟動 cron 服務,好讓系統能夠記得執行。
#!/usr/bin/bash LAST_RUN_FILE="/etc/letsencrypt/renewal/last_run_file" CURRENT_TIME=$(date +%s) if [ ! -f "$LAST_RUN_FILE" ]; then # 如果文件不存在,創建它並執行命令 echo $CURRENT_TIME > "$LAST_RUN_FILE" /usr/bin/certbot renew else LAST_RUN_TIME=$(cat "$LAST_RUN_FILE") DAYS_SINCE_LAST_RUN=$(( ($CURRENT_TIME - $LAST_RUN_TIME) / 86400 )) if [ $DAYS_SINCE_LAST_RUN -ge 90 ]; then # 如果距離上次執行已經過了 90 天或更長時間,執行命令 echo $CURRENT_TIME > "$LAST_RUN_FILE" /usr/bin/certbot renew fi fi
sudo service cron restart
補充事項
- 「certbot renew –dry-run」,模擬憑證更新動作
- 「certbot certificates」,可以觀看目前憑證狀況。
- 憑證更新完成後,記得要將所有與憑證有相關的服務重新啟動。
在做憑證更新時:「certbot renew」,可以先下:「certbot renew –dry-run」,模擬憑證更新是否正確,以免發生不容易挽回的錯誤。