前兩篇處理了跨 VPC,以及公司網路要怎麼連到 AWS。
當網路路徑建立好之後,接下來就是另一個常見問題:
流量進入 AWS 後,要怎麼分配到後端服務?
前面的網站架構使用 ALB 接收 HTTPS 請求,再轉送到私有子網中的 EC2,AWS 也提供 NLB,同樣能分配流量,但兩者處理的層級與功能不同。
我會先確認三件事:服務使用什麼協定、是否需要依 HTTP 內容分流,以及用戶端是否要求固定 IP。
不管使用 ALB 還是 NLB,都會看到兩個很常出現的名詞:
例如:
Client
│
HTTPS 443
▼
Listener
│
▼
Target Group
│
├── EC2 A : 8080
└── EC2 B : 8080
所以用戶端連到 Load Balancer,和 Load Balancer 再連到後端,其實是兩段不同的連線,AWS 也是透過 Listener Rule 決定流量最後要送到哪個 Target Group。
另外,對外或對內使用,與選擇 ALB 或 NLB 是不同問題。
ALB 和 NLB 都可以建立成:
Internet-facing
→ 提供給 Internet Client 使用
Internal
→ 使用 Private IP,提供 VPC 內或能連進 VPC 的 Client 使用
例如上一篇公司透過 Site-to-Site VPN 連進 AWS,如果要存取的是一個內部網站,一樣可以使用 Internal ALB,不需要因為流量來自私有網路就改成 NLB。
Application Load Balancer(ALB) 工作在應用層,主要處理 HTTP、HTTPS 流量。
它最大的特色不是單純「把流量平均分給後端」,而是可以看 HTTP Request 的內容,再決定要送到哪個 Target Group。
例如一個購物網站同時有:
shop.example.com
admin.example.com
還有不同 API:
/api/orders
/api/products
就可以設計成:
| 請求 | Target Group | 用途 |
|---|---|---|
admin.example.com |
admin-tg |
管理後台 |
shop.example.com/api/* |
api-tg |
API |
shop.example.com 其他路徑 |
web-tg |
網站前端 |
概念上可以想像成下圖:
ALB
│
┌───────────┼───────────┐
│ │ │
admin.* /api/* 其他路徑
│ │ │
▼ ▼ ▼
admin-tg api-tg web-tg
ALB 的 Listener Rule 可以依 Host、Path、HTTP Header、HTTP Method、Query String 等條件進行判斷,多條規則會按照設定的 Priority 依序處理,最後才是 Default Rule。
所以像:
/api/*
這種規則如果可能和其他規則同時符合,就要安排好 Priority,讓流量進到預期的 Target Group。
對 Web Application、REST API 或 Microservices 來說,如果本身就需要依網域或 URL Path 分流,ALB 通常會比較合適。
Network Load Balancer(NLB) 主要處理傳輸層流量,適合原生 TCP、UDP 等服務。
如果服務並不需要判斷:
/orders
/products
而是單純需要把某個 TCP、UDP 或 TLS 連線送到後端,就比較接近 Network Load Balancer(NLB) 的使用情境。
例如:
Client
│
TCP 9000
▼
NLB
│
├── Server A
├── Server B
└── Server C
下面舉幾個簡單的情境例子:
| 需求 | 可優先評估 | 原因 |
|---|---|---|
| 網站依網域、URL 路徑分流 | ALB | 能判斷 HTTP 請求內容 |
| 原生 MQTT over TCP | NLB | 需要接收非 HTTP 的 TCP 連線 |
| 使用 UDP 的即時服務 | NLB | ALB 無法直接處理一般 UDP 流量 |
| 對方防火牆要求固定目的 IP | NLB | 可提供每個啟用可用區的固定 IP |
NLB 另一個很常見的選型原因,就是 固定 IP。
NLB 在每個啟用的 Availability Zone 都會建立自己的 Network Interface,Internet-facing NLB 也可以在各個 Availability Zone 指定 Elastic IP。
例如:
AZ-A
→ Elastic IP A
AZ-B
→ Elastic IP B
如果合作廠商的 Firewall 只能透過 IP Allow List 放行,NLB 就比較容易符合這類需求。
不過這裡也要注意:如果 NLB 同時使用兩個 Availability Zone,對方的 Firewall 也應該放行對應的入口 IP。
如果只放行其中一個:
AZ-A IP ✓
AZ-B IP ✕
即使 AWS 這邊已經做成 Multi-AZ,實際存取還是可能受到對方 Allow List 的限制。
另外,「長連線」本身也不能直接當成選 NLB 的理由。
例如 ALB 本身就支援 WebSocket,所以遇到 WebSocket 時,還是要回頭看是否需要 ALB 的 HTTP Routing,而不是看到長連線就直接改用 NLB。
可以先整理成:
| 比較項目 | ALB | NLB |
|---|---|---|
| 常見協定 | HTTP / HTTPS / WebSocket | TCP / TLS / UDP 等 |
| HTTP 內容路由 | 支援 | 不是主要用途 |
| Host-based Routing | 支援 | 不適合 |
| Path-based Routing | 支援 | 不適合 |
| 固定 IP | 通常透過 DNS Name 使用 | 可提供固定 IP / Elastic IP |
| 常見情境 | Website、API、Microservices | TCP / UDP Service、固定 IP 需求 |
選擇時,可以先從流量本身開始:
流量進入 AWS
│
▼
需不需要依 HTTP 內容分流?
│
├── 需要
│ ↓
│ ALB
│
└── 不需要
│
▼
是 TCP / UDP 等服務,
或需要固定 IP?
│
▼
NLB
例如今天是一個網站:
shop.example.com
shop.example.com/api/*
admin.example.com
需要根據不同 Host 與 URL Path 把 Request 分給不同後端,就比較適合 ALB。
但如果是一個 TCP 9000 的內部服務,或合作廠商明確要求提供固定 IP 加入 Firewall Allow List,就可以優先評估 NLB。
還有一點要特別注意:
有 HTTPS,不代表就一定要使用 ALB。
ALB 可以使用 HTTPS Listener;NLB 也支援 TLS Listener,甚至可以透過 TCP Listener 將加密流量直接送到後端,差別仍然在於:需不需要 Load Balancer 理解 HTTP Request,並依內容進行路由。
不需要因為所有服務都在同一套系統裡,就強迫它們使用同一種 Load Balancer。
網站和 API 可以走 ALB,另外的 TCP 或 UDP Service 仍然可以使用 NLB。
現在已經決定流量進到 AWS 後,要使用 ALB 還是 NLB。
但如果使用者分布在不同地區,問題就不只是「後端要怎麼分流」,還會開始遇到:
下一篇會繼續比較 CloudFront、Global Accelerator 與 Route 53,看看這三個服務分別處理哪一段流量,以及什麼情況會搭配使用。