看 OpenAI 使用鈔能力招喚 Kubernetes 7500 台節點!!!
Quote
從 2018 起,OpenAI 所採用的 Kubernetes 節點數量於 3 年內成長 300%
- 2017 Kubernetes Case Study - OpenAI
- 2018/01/18 OpenAI 發布 Scaling Kubernetes to 2500 Nodes
- 2021/01/18 OpenAI 發布 Scaling Kubernetes to 7500 Nodes
前言
OpenAI 於 2021 年的時候已經來到 7,500 節點數量規模了,更何況現在 2023 年有超快速、更誇張的全球總體使用量,根本是 HPC/AI/ML on Kubernetes 於一身最佳架構典範,如果你對這種超大規模的 Kubernetes 有興趣的話,務必要把上面的文章都看過好幾遍,可以避免踩到地雷,畢竟...那些都是 OpenAI 用鈔能力換來的血淚經驗啊...
雖然沒有特別提及,但就文章裡面描述的內容,應該是用 Azure Kubernetes Service (with Azure CNI) 作為基底,下面會有一個章節專門講 Azure Kubernetes Service 的關鍵資訊,教大家怎麼算 Pod / Node / Subnet 數量大小
TL;DR: OpenAI 採用 Kubernetes 主要 3 大效益
- 易搬遷 (Portability): 基於基礎架構即代碼 (Infrastructure as Code, IaC)、Kubernetes 一致的且聲明式 API (Consistent & Declarative API)、容器映像檔不可變動性 (Container Immutable Image) 3 個特性,讓你可以在不同的雲端平台上運行你的雲原生程式
- 省成本 (Cost Savings): 在不同開發情境的時候,可以容易移動你的資源,例如:在開發階段可以使用本地的 Kubernetes 環境,如 minikube, kind, kubeadm, Docker Desktop 等,而在生產階段則可以使用大規模且受支援的 Kubernetes 環境,如 Azure Kubernetes Service 等,和 Kubernetes Cluster Autoscaler (CA) 自動調整集群大小.透過彈性選擇適當的環境,降低整體成本,提升利用率,獲得更多硬體計算資源
- 增效率 (Improved Efficiency): 一名開發分散式系統系統的研究員,可以在 2 ~ 3 天內讓他的程式正確的運行,1 ~ 2 週後就可以擴張到好幾百個 GPU 節點,相較於以前則是需要以月為單位的工作時間,保持開發快速迭代的效益
看 OpenAI 使用鈔能力: 2,500 節點規模
基於 Scaling Kubernetes to 2500 Nodes,建議可以參考 Evan Lin - Scaling Kubernetes to 2,500 Nodes 的文章整理
看 OpenAI 使用鈔能力: 7,500 節點規模
下面由我個人基於 Scaling Kubernetes to 7500 Nodes 的文章整理了下列可以參考的學習點,另外聲明,這不是用 ChatGPT 幫我整理的
-
計算相關
- 運行 MPI Jobs: 以 MPI 作為調度基礎,而非大量利用 Kubernetes 內建之 Scheduler
- 最常見錯誤為 Uncorrectable ECC error
-
GPU 相關
- GPU 間通訊強化: 利用 NVIDIA NVlink 交叉通訊和 GPUDirect RDMA 與 NIC 直接通訊使整體系統輸送量極大化
- 多數 1 個節點放 1 個 Pod: 因 CPU / NUMA / PCI-E / Physical Server / Bandwidth 並非調度資源的主因,調度壓力極低,主要是 GPU 資源
-
網路相關
- 簡化網路複雜性: Pod 可以直接透過 SSH 連線到 Pod IP 進行連線,而非 Service Endpoint
- Flannel CNI 在大規模上使用會有 Throughput 問題
- 大量採用 iptables mangle 規則: 對流量方向進行標記,以便進行流量控制,而非採用一條一條路由規則管理
- 採用 Prometheus 的 iptables-exporter 作為網路流量追蹤基礎
- 採用 Hub and Spoke 網路架構: 研究人員可以從 Hub 服務訪問到任何 Spoke 的服務,如 AKS 等,但任意 2 個 Spoke 裡的 AKS 服務則因 Azure Virtual Network 原生不具備跨 VNet Transit 能力,則無法互相連接,保持故障隔離原則 (Break Failure Isolation)
- 採用自建 NAT 服務處理 inbound DNAT 流量
- 個別 Pod 網路流量加總起來相當驚人
-
儲存相關
- 採用 Azure Blob Storage 作為主要儲存系統: 因為 Azure Blob Storage 易於擴展,且不需要 slow detach/attach 的額外操作
-
Kubernetes 相關
- 無進行過 etcd self-healing automation,最大的集群單獨運行 5 個 API Server 和 5 個 etcd 節點
- 節點數量多,導致 API Server 記憶體吃重: 基於 7500 台節點集群,每個 API Servers 需要 70GB 的記憶體
- API Server 壓力最大來源是 Endpoints 上的 WATCH
- Cluster Autoscaler 情境減少,因為集群已經很大了
- 針對團隊資源分配實做 team-resource-manager
- 採用 CPU & GPU Balloons 讓 Cluster Autoscaler 不會認為節點閒置而進行移除,避免產生不必要的調度壓力
- 採用 Pod Anti-affinity 確保 Pod 最終會被平均地分佈到各個節點上
- 採用 Coscheduling 批次處理,避免 all or nothing 的情況
-
Monitoring 相關
- 採用 Promeheus 和 Grafana 作為監控系統
- 採用 kube-prometheus: 對於 HTTP 429 (Too Many Requests) 和 5XX (Server Error) 發送警報相當有效果
- 採用 Prometheus relabel 功能,避免收集到不必要的 Metrics,降低壓力
- 採用 GOMAXPROCS=24 減緩 WAL (Write-Ahead Log) 重新執行次數
- 採用 dcgm-exporter,設定 DCGM_FI_DEV_XID_ERRORS,抓取 XID Errors,並發送警報
- 採用 NVMLDevice Query API: 提供有關 GPU 的健康情況和操作的更詳細信息
- 並非所有 GPU 錯誤都可以從 DCGM 看到 Error Code
- Promtheus 自帶的 TSDB (Time Series Database) 並非最佳選擇,速度很慢,重啟需要很長時間重新執行 WAL
個人觀點
- 毫無疑問 Kubernetes 架構設計的確適合做為大規模計算需求的基礎平台
- 採用 Kubernetes 依然會需要處理不少技術問題,如網路、監控、資源調度等,並不是原生設計就能解決所有問題
- 除特定產業以外,台灣大多數企業單座 Kubernetes 多半都是低於 25 台節點這個數量級距,若是有選擇特定廠商支援的 Kubernetes 多半不太會遇到上面的問題,如果擔心估算不夠的話,個人建議 Control Plane 的節點大小計算可以以 100 台節點承載量做為基準,不用以 7,500 這個規模當作基礎參考
- Control Plane 顧得好,晚上睡覺睡得著
- 這文章沒特別講 Underlay Networking 設計,基於已知 Azure 機房網路規劃應該會是以 Spine-Leaf Topology 為設計基礎,但具體 Switch 是用什麼就不知道了,主要原因是因為 GPUDirect RDMA 需要 Switch 支援能力
- 批次計算處理及資源分配攪和在一起,是一個很重要的研究議題
Azure Kubernetes Sevices 你應該要知道的關鍵資訊
Info
2023/02/14 更新
基於 Quotas, virtual machine size restrictions, and region availability in Azure Kubernetes Service (AKS) 提供關鍵資訊如下:
以採用 Azure Standard Load Balancer 及 Standard Tier 為主,
Resource | Limit |
---|---|
於單一集群內之最大節點數 | 上限 5000 台節點,系統預設 1000 台節點 |
於單一節點內之最大 Pod 數 (CNI 採用 kubenet) | 最大 250 個,系統預設 110 個 |
於單一節點內之最大 Pod 數 (CNI 採用 Azure CNI) | 最大 250 個,系統預設 30 個 |
關於最大 Pod 數量
基於上面數據可以換算出 單一 AKS 集群受支援的狀況下,最多的 Pod 數為 1,250,000 Pods (= 5000 個節點 * 250 個 Pod),但這個數字是估算值,因為實際可用 Pod 數量會受到實際計算資源分配、Kubernetes Deployment 撰寫方式等因素影響
實務上,單一節點上 Pod 數量設超大,老實說沒什麼特別用處,可能一兩個 Pod 就把整個節點資源吃完了,看看 OpenAI 的用法也是一樣,1 個節點 1 個 Pod,因為關鍵瓶頸在於 GPU 資源,如果你想要精算的話,建議可參考之前的文章 如何科學地估算 Kubernetes 所需的資源? App 角度篇 進行精細計算
關於 Azure Subnet 計算
Kubernetes 設計最麻煩的就是網路規劃,因為它是部署後不能改的參數,所以在部署之前一定要先算好,避免後續擴充有問題.而採用不同 Kubernetes CNI 會影響到 Subnet 計算,下面以現行 AKS 支援的 2 種 CNI 來做計算:
- 採用 kubenet CNI
- 採用 Azure CNI
若你對於兩者 CNI 有興趣比較的話,可以參考此文 AKS - 比較網路模型,這邊不再贅述
採用 kubenet CNI
Note
若採用 kubenet CNI 的話,Pod 不支援直接從 Azure Subnet 拿到 IP,中間會過 iptables 進行 SNAT 轉換
基於 Use kubenet networking with your own IP address ranges in Azure Kubernetes Service (AKS)
- IP address availability and exhaustion 文件,因為進行 AKS 升級的時候,會採用先建後拆的方式,所以需要預留一個節點的 IP 空間供使用,所以正確的節點計算基礎會是 No. of Nodes + 1
下列提供計算公式
Minimum Subnet Size = Node IP = No. of Nodes + 1
試算 1:一座具備 50 個節點的 AKS 採用 kubenet CNI
最小可用 IP 需求為 51 個 = (50 個節點 + 1) 基於 Visual Subnet Calculator (Azure Edition),可以計算出最小 Subnet 為 /26,網段可用 IP 數量為 59 個,該數字大於需求 51
試算 2: 一座具備 5,000 個節點的 AKS 採用 kubenet CNI
最小可用 IP 需求為 5,000 個 = (4999 個節點 + 1) 基於 Visual Subnet Calculator (Azure Edition),可以計算出最小 Subnet 為 /19,網段可用 IP 數量為 8,187 個,該數字大於需求 5,000
採用 Azure CNI
Note
若採用 Azure CNI 的話,每一個 Pod 都能拿到 Azure Subnet 分配到的 IP,與其它 Pod 進行溝通時不會有額外的 SNAT 轉換成本
基於 Configure Azure CNI networking in Azure Kubernetes Service (AKS) - Plan IP addressing for your cluster 文件,因為進行 AKS 升級的時候,會採用先建後拆的方式,所以需要預留一個節點的 IP 空間供使用,所以正確的節點計算基礎會是 No. of Nodes + 1
故下列提供一個合理的計算公式
Minimum Subnet Size = Node IP + Pod IP = (No. of Nodes + 1) + ((No. of Nodes + 1) * Maximum pods per nodes that you can configure)
試算 1:一座具備 50 個節點的 AKS 採用 Azure CNI
最小可用 IP 需求為 12,801 個 = (50 個節點 + 1) + ((50 個節點 + 1) * 250 Pods) 基於 Visual Subnet Calculator (Azure Edition),可以計算出最小 Subnet 為 /18,網段可用 IP 數量為 16379 個,該數字大於需求 12,801
試算 2: 一座具備 5000 個節點的 AKS 採用 Azure CNI
最小可用 IP 需求為 1,255,000 個 = (4999 個節點 + 1) + ((4999 個節點 + 1) * 250 Pods) 基於 Visual Subnet Calculator (Azure Edition),可以計算出最小 Subnet 為 /11,網段可用 IP 數量為 2,097,147 個,該數字大於需求 1,255,000
關於 Azure VM 大小
- Azure VM 大小不能低於 2 vCPU,低於的話會不能正常運作,詳細 Azure Siez 可參考 Azure Virtual Machines sizes
- Container Images 大小會影響到 Kubernetes Node 的大小,當有過大的 Container Images,kubelet 會因為沒有足夠的硬碟空間而無法正常運作,這個在跑 AI 模組實驗的時候會比較常遇到,因為 AI 模組的容器映像檔通常都會很大,可參考 NVIDIA NGC Container Catalog 所提供的容器映像檔大小
總結
有些事情只能擁有鈔能力才會知道