「你的網頁為什麼慢?CDN 能解決什麼問題?HTTPS 是怎麼加密的? 這些問題的答案,都藏在瀏覽器的第一個請求裡。」
HTTP 是 Web 開發的底層基礎,但很多工程師對它的理解停在「request/response 模型」。 這篇帶你走過一次完整的瀏覽器請求旅程,從 DNS 解析到頁面渲染,每一步都拆解清楚。
完整旅程:輸入網址到畫面出現
DNS 解析
~50ms(無快取)把 chullin.tw 翻譯成 IP 位址(如 76.76.21.21)
TCP 三向握手
1× RTT與伺服器建立可靠的連線(SYN → SYN-ACK → ACK)
TLS 握手(HTTPS)
1–2× RTT協商加密方式、驗證憑證、交換金鑰
HTTP 請求
1× RTT發送 GET / POST 請求,帶上 Headers(Cookie、Accept-Language 等)
伺服器處理
視業務邏輯而定路由匹配、DB 查詢、業務邏輯、回傳 Response
瀏覽器渲染
視資源大小而定解析 HTML → 建構 DOM → 載入 CSS/JS → 渲染畫面
DNS:網路的電話簿
DNS(Domain Name System)把人類可讀的域名翻譯成機器可用的 IP 位址。 DNS 查詢有層層快取——瀏覽器快取 → OS 快取 → 路由器快取 → ISP DNS → 權威 DNS。
DNS 查詢流程(無快取情況)
💡 DNS TTL 與快取
TTL(Time To Live)決定 DNS 記錄快取多久。設太長(例如 86400s = 1 天):換 IP 時更新慢。設太短(例如 60s):查詢次數增加,有延遲。 部署新服務前,建議先把 TTL 降低,確認沒問題再恢復。
TCP 三向握手:建立可靠連線
HTTP 跑在 TCP 之上。TCP 的「可靠性」來自於連線建立時的三向握手,以及傳輸過程中的確認(ACK)和重傳機制。
客戶端 → 伺服器
「我想連線,我的序號是 X」
伺服器 → 客戶端
「好的,我收到了 X,我的序號是 Y」
客戶端 → 伺服器
「收到 Y,連線建立!」
三向握手需要 1.5× RTT(Round Trip Time)——這是 HTTP/1.1 的固定延遲成本。
TLS:HTTPS 的加密原理
HTTPS = HTTP + TLS(Transport Layer Security)。TLS 在 TCP 連線建立後, 透過握手過程協商加密方式,保證通訊內容無法被中間人竊聽或篡改。
TLS 握手做了什麼?
- Client 發送支援的加密套件清單
- Server 選擇加密套件,回傳數位憑證(含公鑰)
- Client 驗證憑證是否由可信的 CA 簽發
- 雙方用非對稱加密(RSA / ECDH)交換「預主密鑰」
- 雙方各自計算出相同的「對話金鑰(Session Key)」
- 後續所有資料用對話金鑰做對稱加密(AES)傳輸
為什麼非對稱 + 對稱混用?
非對稱加密(RSA/ECDH):安全但慢,只用於握手階段交換金鑰。
對稱加密(AES):快但需要雙方都有同一把金鑰,透過非對稱加密安全交換。
結果:安全性 + 效能兼顧。
TCP + TLS 的累積 RTT 成本
結論:使用 TLS 1.2 時,第一個請求需要 4.5× RTT 才能收到資料(TCP 1 + TLS 1.2 2 + HTTP 1 + 0.5 ACK)。 TLS 1.3 降至 3.5× RTT,HTTP/2 + TLS 1.3 + 連線復用可降至 2.5× RTT(後續請求 1× RTT)。 這就是為什麼 keep-alive、HTTP/2、以及 TLS 1.3 對頁面速度影響巨大。
HTTP/1.1 → HTTP/2 → HTTP/3
❌ 問題:Head-of-Line Blocking:同一個 TCP 連線一次只能處理一個請求。瀏覽器用「開多條連線」(6個)繞過,但有 TCP 握手 overhead。
✅ 持久連線(Connection: keep-alive)、分塊傳輸
✅ 多路復用(Multiplexing):同一個 TCP 連線可以並行傳多個請求/回應,解決 HOL Blocking。Header 壓縮(HPACK)。Server Push(伺服器主動推送資源)已於 2022 年被 Chrome 移除,實際採用率極低,可忽略。
✅ 改用 QUIC(UDP-based)取代 TCP,解決 TCP 層的 HOL Blocking。0-RTT 重連(快取的連線資訊可以重用)。網路切換(WiFi↔4G)不中斷連線。
實務:Vercel 已全面支援 HTTP/2 和 HTTP/3
部署到 Vercel 後,你的站點自動支援 HTTP/2(甚至 HTTP/3)。 在 Chrome DevTools → Network → Protocol 欄位可以看到 h2(HTTP/2)或 h3(HTTP/3)。
HTTP 訊息結構:Request & Response
Cache-Control 與 ETag:瀏覽器快取的兩層機制
Cache-Control: max-age=3600
「這份資源在 3600 秒(1 小時)內直接用快取,不需要再問伺服器。」 瀏覽器在 TTL 內連請求都不發出,速度最快。
ETag: "33a64df..."
快取過期後,瀏覽器帶著 ETag 問伺服器:「這個版本還有效嗎?」 若資源未更動,伺服器回 304 Not Modified(不傳 body),省頻寬。
兩者常搭配使用:max-age 控制「多久不用問」,ETag 控制「問了之後要不要重傳」。
| 狀態碼 | 含義 | 常見情境 |
|---|---|---|
| 200 OK | 請求成功 | GET 成功回傳資料 |
| 201 Created | 建立成功 | POST 新增資源 |
| 204 No Content | 成功但無回傳內容 | DELETE 成功 |
| 301 Moved Permanently | 永久重定向 | HTTP → HTTPS、舊網址換新網址 |
| 304 Not Modified | 快取有效,不需回傳內容 | ETag / Last-Modified 快取命中 |
| 400 Bad Request | 請求格式錯誤 | 缺少必填欄位、格式錯誤 |
| 401 Unauthorized | 未認證 | 沒帶 Token 或 Token 過期 |
| 403 Forbidden | 已認證但無權限 | 一般使用者存取管理員頁面 |
| 404 Not Found | 資源不存在 | 找不到 /users/999 |
| 409 Conflict | 狀態衝突 | 重複建立、並發修改衝突 |
| 429 Too Many Requests | 超過速率限制 | API Rate Limiting |
| 500 Internal Server Error | 伺服器內部錯誤 | 程式碼例外、DB 連線失敗 |
| 503 Service Unavailable | 服務暫時不可用 | 部署中、過載 |