使用 OpenSSL 為 Nginx 創建自簽名證書 並開啟客戶端身份驗證


本文章默認讀者了解Openssl,CA,網站證書相關知識,直接實戰!配置完成后,瀏覽器會顯示“安全的HTTPS”連接。不會像其他文章那樣,是紅色警告的證書提示。

准備環境

筆者使用的是Ubuntu16 ,其實什么系統都無所謂,請不要使用舊版Openssl就好,因為里面的漏洞實在太致命。

#先創建一個文件夾
mkdir openssl.Test
cd openssl.Test
mkdir -p ./demoCA/{private,newcerts} 
touch demoCA/index.txt 
touch demoCA/serial
echo 01 > demoCA/serial
#復制一份配置文件,可能會因系統不一致
cp /etc/ssl/openssl.cnf .

自建CA

1 設置私鑰

openssl genrsa -des3 -out ./demoCA/private/cakey.pem 2048

2 申請自簽名證書
根據提示一步步填寫就好,但要記清楚填了什么,后面會用到

openssl req -new -x509 -days 365 -key ./demoCA/private/cakey.pem -out ./demoCA/cacert.pem

調整openssl.cnf

調整openssl.cnf 用來支持v3擴展,以實現多域名及擴展用途(EKU)

調整原因有二,一是讓服務端證書支持多個二級域名,二是符合Chrome的證書檢查,否則使用Chrome瀏覽時會提示不信任此證書

用自己喜歡的編輯器打開openssl.cnf
確保req下存在以下2行(默認第一行是有的,第2行被注釋了)

[ req ]
distinguished_name = req_distinguished_name
req_extensions = v3_req

新增最后一行內容 subjectAltName = @alt_names(前2行默認存在)

[ v3_req ]
# Extensions to add to a certificate request
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
#設置擴展用途 (EKU) 可選
#extendedKeyUsage = serverAuth,clientAuth
subjectAltName = @alt_names

新增 alt_names,注意括號前后的空格,DNS.x 的數量可以自己加,別忘了把申請證書時填寫的域名(Common Name)加上

[ alt_names ]
DNS.1 = abc.example.com
DNS.2 = dfe.example.org
DNS.3 = ex.abcexpale.net

創建服務端證書

1 設置私鑰

openssl genrsa -out userkey.pem 2048

2 創建證書申請
提示 Common Name 時 請填寫域名,不要設置密碼,否則Nginx部分會有麻煩,國家,省份,城市,公司,部門要和創建CA填寫的資料一致,當然在配置文件里調整策略能繞過此檢查。本文盡量使用默認的配置來完成~~~,所以請保持一致。

openssl req -new -days 365 -key userkey.pem -out userreq.pem

3 簽發

openssl ca -in userreq.pem -out usercert.pem -extensions v3_req -config openssl.cnf

4 查看證書

openssl x509 -in usercert.pem -text -noout

創建客戶端證書

與服務端類似

openssl genrsa -out clientkey.pem 2048
# Common name 隨意寫,設不設置密碼隨意
openssl req -new -days 365 -key clientkey.pem -out clientreq.pem
openssl ca -in clientreq.pem -out clientcert.pem -extensions v3_req -config openssl.cnf

轉換下格式,方便windows下導入

openssl pkcs12 -export -inkey clientkey.pem -in clientcert.pem -out client.pfx

瀏覽器端導入證書即可,忽略這句話的朋友,通常會遇到400的問題,無法自拔!

Nginx

Nginx 需要使用usercert.pem、userkey.pem、demoCA/cacert.pem,請讀者自行拷貝出來。
以下配置文件只是參考,實際情況請讀者自行配置。
PS:把證書和配置文件放在一個文件夾是不規范的行為,筆者圖方便,僅做測試用

配置文件

server {
    listen       443 ssl;
    server_name  test.com;

    #charset koi8-r;
    #access_log  /var/log/nginx/host.access.log  main;
    
    ssl_certificate /etc/nginx/conf.d/usercert.pem;
    ssl_certificate_key /etc/nginx/conf.d/userkey.pem;
    ssl_client_certificate /etc/nginx/conf.d/cacert.pem;
    ssl_verify_client on;
    ssl_session_timeout 5m;
    ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
    ssl_ciphers ALL:!ADH:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP;

    ......

}

Docker 啟動

docker run --rm --name nginx01 -p 443:443 -v /home/xxx/www/conf:/etc/nginx/conf.d nginx

Windows打開證書配置管理器

1 當前用戶

certmgr.msc

2 本地計算機(win7及以下沒有)

certlm.msc

CA證書導入到"本地計算機"->"受信任的根證書頒發機構"中
客戶端證書要從瀏覽器中導入哦!!!

常見問題

1 火狐瀏覽器 顯示 不安全連接

考慮是系統根證書被導入了一個劫持證書,Firefox 49 版本開始添加了一個參數,如果遇到未知的 CA 證書,瀏覽器可以直接對正在使用的 Windows 系統證書存儲機制進行檢查對比。
在地址欄鍵入"about:config" 點擊“我了解此風險”
在下方任意位置右鍵,選擇新建布爾值
輸入首選項名稱為“security.enterprise_roots.enabled”並把值設置為 true
重啟瀏覽器,HTTPS 網站即可正常訪問
來源:百度貼吧

2 Chrome 顯示 400 狀態碼

Ctrl + Shift + Del 清除緩存即可

3 IE8.0 如果要求使用 客戶端證書 好像會一直出現 400 狀態碼 ~~~
4 IE11、Edge、Firefox、Chrome 測試通過
5 window導入時可以把*.pem結尾的證書改為*.crt方便識別
6 如果不想使用雙向認證,請忽略【創建客戶端證書】部分,並調整Nginx配置文件ssl_verify_client off;即可

參考

OpenSSL CA keyUsage extension
openSSL命令、PKI、CA、SSL證書原理
那些證書相關的玩意兒(SSL,X.509,PEM,DER,CRT,CER,KEY,CSR,P12等)
openssl用法詳解
openssl自簽名證書生成與單雙向驗證
還有一些地址想不起來了,如果引用了您的文章筆者卻未聲明,請聯系筆者。

聲明

本文采用知識共享署名-非商業性使用-相同方式共享 2.5 中國大陸許可協議進行許可,歡迎轉載,但未經作者同意必須保留此段聲明,且在文章頁面明顯位置給出原文連接。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM