HTTPS 與 TLS 實際運作原理:實用指南
你輸入一個網址,按下 Enter,頁面就載入了。掛鎖圖示告訴你連線是安全的,但你的瀏覽器與伺服器之間到底發生了什麼事?如果你是開發者,理解 HTTPS 與 TLS 不僅是學術問題——它會影響你如何設定伺服器、除錯連線錯誤,以及保護使用者資料。
本指南會用淺顯的詞語拆解 TLS 握手、加密層與憑證驗證。你將看到 HTTPS 實際如何運作,並為自己的專案獲得實用技巧。
HTTPS 與 TLS 究竟是什麼
HTTPS 是運行在 TLS 之上的 HTTP。TLS(Transport Layer Security,傳輸層安全性)是加密傳輸中資料的密碼學協定。當你造訪一個 HTTPS 網址時,你的瀏覽器與伺服器會執行 TLS 握手,在交換任何 HTTP 資料之前先議定加密金鑰。
TLS 多年前取代了 SSL(Secure Sockets Layer,安全通訊端層),但這兩個詞經常被交替使用。現代瀏覽器支援 TLS 1.2 與 TLS 1.3;較舊的版本因已知漏洞而遭到棄用。
TLS 握手:逐步解析
握手會建立一個安全通道。以下是典型 TLS 1.2 握手中發生的情況(TLS 1.3 進一步簡化了這個過程):
- Client Hello(客戶端問候): 瀏覽器發送一份支援的加密套件清單、TLS 版本,以及一個隨機值(client random)。
- Server Hello(伺服器問候): 伺服器挑選一個加密套件,發送自己的隨機值(server random),並出示其 SSL/TLS 憑證。
- 憑證驗證: 瀏覽器會對照受信任的根 CA 來檢查憑證、驗證網域名稱,並檢查有效期限。
- 金鑰交換: 客戶端使用憑證的公鑰加密一個 pre-master secret 並傳送給伺服器。雙方推導出相同的會話金鑰。
- Finished(完成): 雙方各發送一則以新會話金鑰加密的 Finished 訊息,確認握手成功。
在 TLS 1.3 中,握手減少為一個往返(1-RTT),並支援重複連線的 0-RTT 恢復,改善延遲。
加密:對稱與非對稱
TLS 同時使用兩種加密類型:
- 非對稱加密(例如 RSA、ECDHE)用於握手期間安全地交換金鑰。它很慢,但解決了金鑰分發的問題。
- 對稱加密(例如 AES-GCM、ChaCha20-Poly1305)用於握手後的大量資料傳輸。它快速且有效率。
握手期間推導出的會話金鑰是對稱金鑰。它們確保即使有人擷取了加密流量,沒有金鑰也無法解密。
憑證驗證:信任但驗證
憑證由憑證授權單位(CA)簽發。瀏覽器與作業系統隨附一份受信任根 CA 的清單。當伺服器出示憑證時,瀏覽器會驗證:
- 憑證是由受信任的 CA 簽署(直接或透過中繼 CA)。
- 憑證的網域名稱與要求的主機相符。
- 憑證在其有效期限內。
- 憑證尚未被撤銷(透過 CRL 或 OCSP)。
如果任何檢查失敗,瀏覽器會顯示警告。作為開發者,你可以使用 openssl s_client 等工具來檢查憑證並除錯鏈結問題。
常見的 TLS 錯誤設定及修正方法
| 問題 | 症狀 | 修正 |
|---|---|---|
| 憑證過期 | 瀏覽器警告:「憑證已過期」 | 更新憑證,並使用 Let's Encrypt 自動續約 |
| 鏈結不完整 | 部分客戶端失敗,其他正常 | 在伺服器設定中包含中繼憑證 |
| 弱加密套件 | 安全掃描器標記漏洞 | 停用過時的加密演算法(例如 RC4、3DES)並啟用 TLS 1.3 |
| 混合內容 | 掛鎖顯示警告或混合內容錯誤 | 透過 HTTPS 提供所有資源(圖片、指令碼) |
定期使用線上 SSL 檢查器或命令列工具來稽核你的設定。
給開發者的實用技巧
- 啟用 HSTS: 加入
Strict-Transport-Security標頭,強制瀏覽器在未來造訪時使用 HTTPS。 - 使用 TLS 1.3: 它更快且更安全。大多數現代伺服器都支援;設定你的伺服器優先使用它。
- 自動化管理憑證: Certbot 等工具可以自動取得並續約憑證。
- 使用
openssl測試: 執行openssl s_client -connect example.com:443 -servername example.com來檢查握手與憑證鏈。
以下是啟用現代 TLS 設定的快速 Nginx 設定片段:
server {
listen 443 ssl http2;
server_name example.com;
ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256';
ssl_prefer_server_ciphers off;
add_header Strict-Transport-Security "max-age=63072000" always;
}此設定啟用 TLS 1.2 與 1.3、使用強加密演算法,並設定 HSTS。
常見問題
HTTPS 與 TLS 有什麼不同?
HTTPS 是層疊在 TLS 之上的 HTTP。TLS 是提供加密與驗證的協定。因此,HTTPS 是 HTTP 的安全版本,由 TLS 提供支援。
TLS 握手如何建立共享金鑰?
客戶端與伺服器使用非對稱密碼學(如 ECDHE)來議定一個共享秘密,而不直接傳輸它。然後他們從該秘密推導出對稱會話金鑰來加密資料。
為什麼憑證會過期?
過期限制了私鑰遭洩露時的損害,並鼓勵自動化續約。短效期憑證是一種安全最佳實務。
準備好檢查你自己的 TLS 設定了嗎?使用 TryQuickToolBox 的 Nginx 日誌分析器 來找出伺服器日誌中的 TLS 錯誤與握手失敗。