StatefulSet レプリカの分散配置の確認

同じ障害領域にレプリカが集中しないよう、配置ポリシーを確認してください。

説明

StatefulSet のレプリカが同じノードに集まると、一つのノード障害で複数の Pod が影響を受けます。Pod アンチアフィニティやトポロジー分散制約で配置を制御でき、セレクターは実際の Pod ラベルに一致する必要があります。

required は配置条件を強制し、preferred は優先度として働きます。ホスト単位の分散だけで、ゾーン障害やアプリケーションの複製クォーラムまで保護されるわけではありません。

想定される影響

  • 一つのノード障害で複数のレプリカが同時に停止する場合があります。
  • 厳しい条件に合うノードが足りないと、Pod が Pending のままになる場合があります。

対処方法

  • ワークロードの障害・クォーラム要件に合わせて podAntiAffinity やトポロジー分散制約を設定してください。実際の Pod ラベルと topologyKey を確認してください。
  • 必須ルールに必要なノード数、容量、ストレージの配置条件を確認し、実際の配置を試してください。IgnoredDuringExecution は、実行中の Pod を自動移動させるものではありません。

例

既存の ZooKeeper イメージで配置ルールだけを比較します。運用にはサポートされるイメージを使い、zk-hs Headless Service を別途用意してください。変更後は、条件に合う異なるノードが最低 3 台必要です。

変更前

yaml
apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: zk
spec:
  serviceName: zk-hs
  replicas: 3
  selector:
    matchLabels:
      app: zk
  template:
    metadata:
      labels:
        app: zk
    spec:
      containers:
        - name: zookeeper
          image: k8s.gcr.io/kubernetes-zookeeper:1.0-3.4.10

3 レプリカを定義しますが、この抜粋には分散ルールがありません。実際の配置と他のポリシーを確認する必要があります。

変更後

yaml
apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: zk
spec:
  serviceName: zk-hs
  replicas: 3
  selector:
    matchLabels:
      app: zk
  template:
    metadata:
      labels:
        app: zk
    spec:
      affinity:
        podAntiAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
            - labelSelector:
                matchLabels:
                  app: zk
              topologyKey: kubernetes.io/hostname
      containers:
        - name: zookeeper
          image: k8s.gcr.io/kubernetes-zookeeper:1.0-3.4.10

app: zk の Pod が同じホストに配置されないよう強制します。適切なノードが不足すると、すべてのレプリカを実行できない場合があります。

参考資料