使用Let's Encrypt保護你的數據包
來自: https://www.leavesongs.com/SHARE/lets-encrypt-guide.html
【過年了,每天發一篇以前的存貨,一共七篇。】
Let's Encrypt是去年底推出的一個免費SSL證書,且申請這個證書基本沒有任何限制,只要你證明你是域名的所有者,你就可以為你的域名申請一個SSL證書。
我今天就來為我的 wiki.ioin.in 申請一個時髦的Let's Encrypt證書。
首先,我利用到的是acme-tiny,這是第三方人士開發的一個擴展。因為Let's Encrypt官方給出的方法比較麻煩,而acme-tiny這個小工具可以讓用戶敲幾條命令即可生成好我們需要的證書。
下載acme-tiny: https://github.com/diafygi/acme-tiny
首先,生成一個用戶私鑰: account.key,acme-tiny通過這個證書來登錄Let's Encrypt。再生成一個域名私鑰,domain.key
openssl genrsa 4096 > account.key openssl genrsa 4096 > domain.key
然后利用ACME協議,將domain.key生成domain.csr。如果你只有一個域名需要ssl,只需執行下面的語句:
openssl req -new -sha256 -key domain.key -subj "/CN=yoursite.com" > domain.csr
如果你有多個域名,比如www.xxx.com和xxx.com,你就執行下面的語句:
openssl req -new -sha256 -key domain.key -subj "/" -reqexts SAN -config <(cat /etc/ssl/openssl.cnf <(printf "[SAN]\nsubjectAltName=DNS:yoursite.com,DNS:www.yoursite.com")) > domain.csr
我的 wiki.ioin.in 是單域名證書,所以執行下面語句即可:
Let's Encrypt有多種方法來驗證你是否是域名的所有人,而acme-tiny這個小工具用的是最簡單的方法,也就是利用http文件驗證。
簡單來說,就是生成一個驗證文件,放在
http://xxxx.com/.well-known/acme-challenge/ 下,Let's Encrypt官方驗證這個文件是否存在、內容是否正確。如果一切正確,說明域名是你所有。所以我這里,新建了一個/home/www/challenges/目錄,將它別名指向 /.well-known/acme-challenge/ 。這樣,我在challenges目錄里寫入的文件,即可通過 http://xxxx.com/.well-known/acme-challenge/ 訪問了。nginx配置如下:
然后,運行acme_tiny.py腳本:
python acme_tiny.py --account-key /etc/ssl/letsencrypt/account.key --csr /etc/ssl/letsencrypt/domain.csr --acme-dir /home/www/challenges/ > /etc/ssl/letsencrypt/signed.crt
其中,將--account-key的值改為你生成的account.key的路徑;--csr的值改成你生成的domain.csr的路徑;--acme-dir的值改為我要寫入驗證文件的文件夾。
最后成功生成signed.crt,這就是我的域名證書:
在nginx里,還需要將Let's Encrypt的中間證書放到自己的證書后面,構成一個證書鏈chained.pem:
wget -O - https://letsencrypt.org/certs/lets-encrypt-x1-cross-signed.pem > intermediate.pem cat signed.crt intermediate.pem > chained.pem
另外,還需要生成一個較強的dh。(位數不要太多!我生成了一個4096位的dh,半個小時還沒生成好)。關于dh的安全性,可以關注這個網站: https://weakdh.org ,這篇文章: https://weakdh.org/sysadmin.html
openssl dhparam -out dhparam.pem 2048
生成好以后,將以上生成的私鑰、證書、dh等寫入nginx的配置文件:
server { listen 80; listen 443 ssl;#listen [::]:80; server_name wiki.ioin.in; index index.html index.htm; ssl on; ssl_certificate /etc/ssl/letsencrypt/chained.pem; ssl_certificate_key /etc/ssl/letsencrypt/domain.key; ssl_session_timeout 5m; ssl_protocols TLSv1 TLSv1.1 TLSv1.2; ssl_ciphers ECDHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES128-GCM-SHA256:DH$ ssl_session_cache shared:SSL:50m; ssl_dhparam /etc/ssl/letsencrypt/dhparam.pem; ssl_prefer_server_ciphers on; ...the rest of your config
}</pre>
重啟nginx,一切萬事大吉: https://wiki.ioin.in
![]()
另外,我們看證書的過期日期。算一下這個證書其實只有3個月,也就是一個季度。當證書快要過期的時候,我們還需要重新頒發一下證書。
重新頒發證書的過程就比較簡單了,只需要重新執行acme_tiny.py即可。我們可以將重新頒發的過程寫在一個腳本里:
#!/usr/bin/sh python /path/to/acme_tiny.py --account-key /path/to/account.key --csr /path/to/domain.csr --acme-dir /var/www/challenges/ > /tmp/signed.crt || exit wget -O - https://letsencrypt.org/certs/lets-encrypt-x1-cross-signed.pem > intermediate.pem cat /tmp/signed.crt intermediate.pem > /path/to/chained.pem service nginx reload然后將這個腳本加入cron,每月執行一次:
#example line in your crontab (runs once per month) 0 0 1 * * /path/to/renew_cert.sh 2>> /var/log/acme_tiny.log就不需要人工操作了~
最后,測試一下SSL質量: https://www.ssllabs.com/ssltest/
</div>
![]()