使用 Systemd 自動更新 Let’s Encrypt 憑證
各位好久不見了! 最近大家有沒有發現在使用 service status 指令的時候,輸出結果變得異常精美呢? 根據小獅查到的資料顯示 Ubuntu 從 15.04 版開始,就採用 systemd 來取代自行研發的 UpStart,成為預設的 init 系統喔!
(對~ 然後我到現在才發現…)
簡介 init
根據慣例,我們在動手之前,一定要先科普一下才行(笑)
總之,init 系統是在電腦載入 Kernal 之後,第一個啟動的程式,因此 PID 通常都會是 0。它負責初始化整台電腦上的大部分設定,包含 磁碟掛載、網路設定、服務啟動 等。
而 Systemd 則是目前最熱門的 init 系統之一,因為它透過平行啟動各個服務(在 Systemd 中稱之為 單元(Unit) ),成功改善了傳統 sysvinit 系統開機較慢的問題,而且也對熱插拔裝置有著更加優秀的管理效率。
安裝 / 設定 CertBot
CertBot 是 電子前哨基金會(EFF)所開發的一個設定工具,可以方便網站管理員快速設定自己的網站,套用 Let’s Encrypt 提供的憑證。
首先是 網頁 / 網路服務 伺服器的部份,請依照自己的需求安裝完畢,以下使用 Apache 示範
- CertBot 套件的安裝(不要問我為什麼套件不叫 CertBot)
sudo apt install python-letsencrypt-apache
- 設定配合 Apache 使用
sudo letsencrypt --apache
- 如果沒有設定 ServerName 的話就會跳出這個訊息(可以忽略)
- 設定 Domain(請依照自己的環境輸入)
- 輸入自己的 E-mail(備援使用,建議填入正確資訊)
- 授權條款
- CertBot 會詢問你該如何處理 HTTP 連線,建議 Secure 選項,把所有連線重導向至 HTTPS
- 恭喜成功!同時也提供了設定檢查的頁面
自動更新憑證
在編輯 Systemd 的設定之前,請先確認自己的 CertBot 可以正常運作,官方文件建議使用 dry-run(執行但不套用) 的方式,測試先前步驟生的設定檔的內容正確
sudo letsencrypt renew --dry-run --agree-tos
如果成功的話,畫面就會出現 Congratulations 字樣
終於要來進行期待已久的 Systemd Unit 檔案設定了,首先要決定一下設定檔要放在哪裡?
路徑 | 說明 | 優先權 |
---|---|---|
/lib/systemd/system | 系統服務預設、大部分的應用程式 | 低 |
/run/systemd/system | 較少使用(使用者而言) | 中 |
/etc/systemd/system | 使用者自訂,用來覆蓋系統設定 | 高 |
我個人偏好放置在 /lib/systemd/system
因為要是跟系統衝突的話,比較容易發現!
第一個檔案是 /lib/systemd/system/renew-letsencrypt.service
[Unit] Description=Renew Let's Encrypt certificates [Service] Type=oneshot ExecStart=/usr/bin/letsencrypt renew
接下來,我們需要幫它設定一個計時器 /lib/systemd/system/renew-letsencrypt.timer
[Unit] Description=Daily renewal of Let's Encrypt's certificates [Timer] # once a month, at 2AM OnCalendar=*-*-1 02:00:00 # Be kind to the Let's Encrypt servers: add a random delay of 0–3600 seconds RandomizedDelaySec=3600 Persistent=true [Install] WantedBy=timers.target
編輯完設定檔之後按下儲存,然後讓 Systemd 重新讀取它們!
sudo systemctl daemon-reload
測試一下 Timer 有沒有錯誤
sudo systemctl start renew-letsencrypt.timer
沒有錯誤的話就啟用它!
sudo systemctl enable renew-letsencrypt.timer
大功告成!
如果是自己的服務不在官方支援怎麼辦
根據官方文件的敘述,你可以在更新指令裡指定可更新時間,在更新前、更新後 要做什麼,通常是先關閉伺服器,更新完憑證之後再啟動
Let’s Encrypt 的政策是在授權有效期(90 天)的最後幾天開放 renewal,在之前執行 CertBot 的話,什麼事情都不會發生,當然服務也不會被重啟
ExecStart=/usr/bin/letsencrypt renew
換成
ExecStart=/usr/bin/letsencrypt renew --pre-hook "service nginx stop" --post-hook "service nginx start"