Basic - Creating a StatefulSet
什麼是 StatefulSet
StatefulSet 是 Kubernetes 中的一種工作負載資源,用於管理具有穩定標識(Stable Identity)和持久化存儲的應用程式。 它主要適用於需要有序部署和縮放的應用,例如資料庫或分散式系統。
StatefulSet 的應用價值
StatefulSet 對於需要滿足以下一個或多個需求的應用程序非常有價值:
- 穩定的、唯一的網路識別子
- 每個 Pod 都有穩定的網路名稱(例如
my-app-0
、my-app-1
),允許應用程序在 Pod 重啟或遷移後仍能透過固定的網路標識進行通信。這對需要點對點通信的分散式系統特別重要。
- 每個 Pod 都有穩定的網路名稱(例如
- 穩定的、持久的儲存
- 每個 Pod 都關聯到特定的 PersistentVolume(PV),即使 Pod 被刪除或重新部署,數據依然保持穩定和持久性。這對需要數據一致性的應用(如資料庫)非常有幫助。
- 有序的、優雅的部屬和縮放
- StatefulSet 確保 Pod 的部署和縮放按照固定的順序進行,例如先啟動
my-app-0
,然後依次啟動其他 Pod。縮放時,Pod 也會依照順序進行刪除或啟動。
- StatefulSet 確保 Pod 的部署和縮放按照固定的順序進行,例如先啟動
- 有序的、自動滾動更新
- 當 StatefulSet 的配置更新時,會按照 Pod 的序列進行滾動更新,確保 在更新過程中系統穩定性不受影響。
與 Deployment 的差異
StatefulSet 與 Deployment 類似,都可以用來管理 Pod,但有以下重要差異:
- 穩定的網路標識
- 每個 Pod 都有固定的名稱,格式為
pod-name-index
,如my-app-0
、my-app-1
。
- 每個 Pod 都有固定的名稱,格式為
- 穩定的存儲
- 每個 Pod 都會綁定到特定的 PersistentVolume(PV),即使 Pod 被刪除或重新調度,數據仍然保持一致。
- 有序部署和刪除
- Pod 的部署、更新和刪除按照固定順序進行。例如,只有在
my-app-0
準備好後,my-app-1
才會開始部署。
- Pod 的部署、更新和刪除按照固定順序進行。例如,只有在
StatefulSet 中的有序命名及網路 ID
有序命名(Ordinal Index)
StatefulSet 的每個 Pod 都具有穩定且有序的名稱,這些名稱由以下組成:
- StatefulSet 名稱
- 有序索引(Ordinal Index)
Pod 的命名規則為:
<StatefulSet 名稱>-<Ordinal Index>
網路 ID(Stable Network Identity)
每個 Pod 都會分配一個穩定的網路標識,確保其在集群中的網路名稱不會因重啟或重新調度而改變。網路標識由以下幾部分組成:
- Pod 名稱
- 每個 Pod 的網路名稱與其有序命名一致,例如
my-app-0
。
- 每個 Pod 的網路名稱與其有序命名一致,例如
- Headless Service
- StatefulSet 通常與一個無頭服務(Headless Service)結合使用。Headless Service 不會提供負載均衡功能,而是直接將流量引導到特定的 Pod。
DNS 的命名規則:
<Pod 名稱>.<Headless Service 名稱>.<Namespace>.svc.cluster.local
StatefulSet 中的穩定儲存
在 Kubernetes 中,StatefulSet 通過 PersistentVolume(PV)和 PersistentVolumeClaim(PVC)為每個 Pod 提供穩定的儲存資源。 這意味著即使 Pod 被刪除或重新調度,其對應的儲存數據仍然保持不變,並且在重新創建 Pod 時可以重新掛載原有的數據。
StatefulSet 中的 Headless Services
什麼是 Headless Service?
Headless Service 是 Kubernetes 中的一種特殊服務類型,用於直接將流量引導到特定的 Pod,而不進行負載均衡。 當與 StatefulSet 搭配使用時,Headless Service 為 StatefulSet 的每個 Pod 提供穩定的 DNS 條目,允許應用程序通過固定的網路標識與 Pod 通信。
Headless Service 的特點是:
- 沒有 Cluster IP(
spec.clusterIP
設置為None
)。 - 不進行流量分配,只創建 Pod 的 DNS 條目。
為什麼 StatefulSet 需要 Headless Service?
StatefulSet 使用 Headless Service 提供穩定的網路標識,解決以下問題:
- 穩定的 DNS 條目
- 每個 Pod 都有一個固定的 DNS 名稱,讓應用程序可以輕鬆地與特定 Pod 進行通信。
- 去中心化的流量管理
- Headless Service 允許流量直接路由到指定的 Pod,特別適合需要點對點通信的分散式系統。
- 有序初始化支持
- StatefulSet 配合 Headless Service 的穩定 DNS 條目,支持分散式應用在初始化時的節點自我發現和註冊。
StatefulSet 的部署與擴縮保證
部署保障
- 有序部署:Pod 按索引順序創建(如
Pod-0
→Pod-1
),每個 Pod 初始化完成後才會創建下一個。 - 穩定性:適用於需要有序啟動的應用(如分散式數據庫)。
擴縮保障
- 有序擴展:新增 Pod 時,分配唯一名稱和網路標識(如
Pod-2
→Pod-3
)。 - 有序縮減:刪除 Pod 時按索引倒序進行(如
Pod-3
→Pod-2
)。 - 數據完整性:縮減時保留對應的存儲卷,確保數據不丟失。
StatefulSet 的更新策略
StatefulSet 提供兩種更新策略,用於控制 Pod 的滾動更新方式。
- RollingUpdate(預設)
- 按照 Pod 的索引從高到低逐一更新。
- 每次僅更新一個 Pod,並在確保其穩定後更新下一個。
- 適用於需要最小化服務中斷的場景。
- OnDelete
- 不自動更新 Pod,需手動刪除舊 Pod 才會按新配置創建新 Pod。
- 適用於需要手動控制更新時機的場景 。
舉一個例子
使用 StatefulSet 部署 SQL Server(3 個 Pod:1 個主節點,2 個副本節點)
- 穩定的網路標識:StatefulSet 確保每個 Pod 擁有固定的網路標識,便於節點之間的通訊。
- 有序部署與更新:Pod 的啟動、更新、與終止按照順序進行,確保系統穩定性。
- 持久性存儲:每個 Pod 配備專屬的持久化存儲,保障數據安全。
節點角色與功能
- 主節點 (Master):負責處理讀寫操作。
- 副本節點 (Replicas):提升系統的可擴展性,並提供數據冗餘以增強可靠性。