Kubernetesの親和と反親和

7532 ワード

podを配備する場合、kubernetesのスケジューラはpodをクラスタ内の適切なノードにスケジューリングできます.しかし、ユーザーは、SSDストレージノードを所有し、同じサービスの複数のバックエンドを異なるラックに配置してセキュリティを向上させ、通信が頻繁なサービスを同じ利用可能なドメインに配置して通信リンクの長さを低減するなど、podをそのノードにスケジューリングするためのより多くの制御を必要とする場合がある.pod配置ノードに対するユーザーの制御は、label selectorに関連しています.
NodeSelector(ノードセレクタ)
NodeSelectorはラベルセレクタでもあり、pod配置nodeを最も簡単で直接制御する方法であり、daemonsetでnodeSelectorで配置可能なノードをフィルタします.以下は一般的な応用例です.
手順1:ノードにラベルを追加する
  • kubectl get nodesは、クラスタ内のすべてのnodeを返します.
  • kubectl node label=、nodeで選択したnodeにラベルを追加します.例えばkubectl label nodes kubernetes-foo-node-1.c.a-robinson.internal disktype=ssd
  • pod configuration追加ノードセレクタ:
    apiVersion: v1
    kind: Pod
    metadata:
      name: nginx
      labels:
        env: test
    spec:
      containers:
      - name: nginx
        image: nginx
        imagePullPolicy: IfNotPresent
      nodeSelector:
        disktype: ssd
  • kubectl create-fを実行するとhttps://k8s.io/examples/pods/pod-nginx.yamlコマンドでpodを作成すると、ノードセレクタに上記のノードが選択され、条件を満たすnodeがない場合はスケジューリングに失敗し、podにスケジューリング失敗イベントを出力し、失敗の原因を指定します.podは適切なノードが見つかるまでpending状態にある.
    kubectl get pods-o wideを実行して、podで選択されたノードを表示します.
    Interlude:built-in node labels(エピソード:内蔵ノードラベル)
    上記の例では、ユーザー定義ラベルを使用するか、システムが自動的に生成する組み込みノードラベルを使用します.異なるkubernetesバージョン、異なるインフラストラクチャベンダーでは、デフォルトで追加された内蔵ノードラベルが異なる場合があります.関連ドキュメントの確認を問い合わせる必要があります.以下はkubernetes 1です.4の内蔵ノードラベル:
  • kubernetes.io/hostname
  • failure-domain.beta.kubernetes.io/zone
  • failure-domain.beta.kubernetes.io/region
  • beta.kubernetes.io/instance-type
  • beta.kubernetes.io/os
  • beta.kubernetes.io/arch 

  • 親和性と逆親和性(Affinity and anti-affinity)
    NodeSelectorはノードラベル制御podに基づいてnodeを配置するしかなく、セレクタはAND論理操作のみをサポートします.親和性と反親和性は現在テスト段階にあり、ノードセレクタよりも柔軟で、機能がより強く、以下の3つの点に現れている.
  • は、ANDだけでなく、より多くの論理式をサポートします.
  • nodeSelectorはハード要件であり、親和性と反親和性はソフト・ハードの2つの要件をサポートする.
  • ノードラベルに加えて、親和性と反親和性は、ノードに配置されたpodに基づいてノード選択をサポートすることが重要である.たとえば、2つの計算が密集しているpodを同じノードに配置したくない場合は、podを配置してフィルタを選択します.

  • ノード親和性と内部pod親和性、逆親和性の2つのタイプのセレクタに細分化されます.ノード親和性はnodeSelectorと類似しており,上記1,2の2つの利点を備えている.内部pod親和性は,ノードラベルではなくノード上にpodのラベルがあることに依存し,上述した3つの利点を兼ね備えている.ノード親和性はnodeSelectorが動作し、追加の利点を備えているため、nodeSelectorはまだ使用できますが、メンテナンスは行われず、将来削除される可能性があります.
    ノード親和性(テスト特性)
    ノード親和性はnodeSelectorと同様に動作し、nodeラベルでノードを選択します.2つの違いがあります.1つ目は、ノード親和性がソフトとハードの2つのノードをサポートすることです.前者は硬性条件を満たさなければならないが,後者は軟性条件であり,好ましい配置に属する.2つ目は、ノードを選択するときにnodeSelectorよりもノード親和性がより柔軟な式をサポートすることです.例は次のとおりです.
    apiVersion: v1
    kind: Pod
    metadata:
      name: with-node-affinity
    spec:
      affinity:
        nodeAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
            nodeSelectorTerms:
            - matchExpressions:
              - key: kubernetes.io/e2e-az-name
                operator: In
                values:
                - e2e-az1
                - e2e-az2
          preferredDuringSchedulingIgnoredDuringExecution:
          - weight: 1
            preference:
              matchExpressions:
              - key: another-node-label-key
                operator: In
                values:
                - another-node-label-value
      containers:
      - name: with-node-affinity
        image: k8s.gcr.io/pause:2.0

    条件を満たすノードは、r e q u i r e d D u r g S h e d u l i n g I g n o r edDuringExecutionの条件を満たす必要があります.その上で、p r e f r e d D u r g S h e d u l i n g I g n o r edDuringExecutionの条件を満たすノードがあれば、後者に配置する傾向があります.クエリー式で使用できるオペレータは、In、NotIn、Exists、DoesNotExist、Gt、Ltなどです.
    r e q u i r e d D u r g S h e d u l i n g I gnoredDuringExecutionのmatchExpressionsには、複数の選択式が含まれ、互いに「論理と」の関係であり、同時に満たさなければならない.P r e f e r e d D D u r g S h e d u l i n g I gnoredDuringExecutionのmatchExpressionsは、必ずしも完全に一致するわけではないため、一致するエントリが多ければ多いほど条件に合致するため、複数あることができます.また、好みの式に異なる重みweightを付与し、0〜100の値をとり、最後に重みを計算し、そのノードがより条件に合致することを決定することもできる.
    NodeSelectorとnodeAffinityが同時に使用されている場合、ターゲットノードは両方のセレクタを同時に満たす必要があります.
    内部pod親和と反親和(試験特性)
    内部pod親和性と反親和性はkubernetes 1.4リリースでは、ノードに配置されたpodのラベルに基づいて親和性と反親和性を計算します.たとえば、2つの通信頻度podを同じノードに配置したり、2つの計算密集型podを異なるノードに配置したりします.
    ヒント:内部親和と反親和を実現するには数の大きい計算ステップが必要であり、podスケジューリングの速度を著しく低下させ、クラスタ規模が大きいほどノードが多くなるほど速度が低下し、指数級の増加を示し、この特性を使用する際にスケジューリング速度への影響を考慮する必要がある.
    ヒント:反親和と関係があり、意味が分からなかった.
    構成時、内部pod親和性はpodAffinityフィールド、内部pod反親和性はpodAntiAffinityフィールド、その他はノード親和性と同様にソフトとハードの2種類のセレクタがあり、各セレクタは複数のフィルタ条件が可能である.
    内部pod親和例:
    apiVersion: v1
    kind: Pod
    metadata:
      name: with-pod-affinity
    spec:
      affinity:
        podAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
          - labelSelector:
              matchExpressions:
              - key: security
                operator: In
                values:
                - S1
            topologyKey: failure-domain.beta.kubernetes.io/zone
        podAntiAffinity:
          preferredDuringSchedulingIgnoredDuringExecution:
          - weight: 100
            podAffinityTerm:
              labelSelector:
                matchExpressions:
                - key: security
                  operator: In
                  values:
                  - S2
              topologyKey: kubernetes.io/hostname
      containers:
      - name: with-pod-affinity
        image: k8s.gcr.io/pause:2.0

    前の例のtopologyKeyは、ノード選択範囲を縮小するために使用され、その値は任意の合法的なノードラベルであってもよく、大規模なクラスタでは、このフィールドにエラー値を指定したり指定したりしないと、大きなパフォーマンス、セキュリティの問題を引き起こす可能性があります.このため、使用には次の制限があります.
  • 親和性と硬性の逆親和性については、topologyKeyフィールド値を空にすることはできません.
  • 硬性反親和性に対してtopoloygKeyはkubernetesのみである.LimitPodHardAntiAffinityTopologyがコントローラにアクセスしたり、実装を変更したりすることを禁止しない限り、io/hostname.
  • は、ソフトウェアの非親和性に対して、topoloygKeyが空であることを許可し、ノードトポロジに制限がないことを示す.
  • 以上の場合、topologyKeyは任意の合法的なラベルであってもよい.

  • 例1:pod位置交渉を逆親和特性で実現
    クラスタに5つのワークノードがあると仮定し、1つのウェブアプリケーションを配置し、redisをメモリキャッシュとして使用すると仮定し、合計3つのコピーが必要であると仮定し、3つのredisコピーをそれぞれ3つの異なるノードに逆親和的に配置することで、可用性を向上させ、Deploymentの構成は以下の通りである.
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: redis-cache
    spec:
      selector:
        matchLabels:
          app: store
      replicas: 3
      template:
        metadata:
          labels:
            app: store
        spec:
          affinity:
            podAntiAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
              - labelSelector:
                  matchExpressions:
                  - key: app
                    operator: In
                    values:
                    - store
                topologyKey: "kubernetes.io/hostname"
          containers:
          - name: redis-server
            image: redis:3.2-alpine

    逆親和性は、同相のredisコピーが同じノードに配置されることを阻止します.
    3つのnginxウェブフロントエンドを配備し、3つのコピーが異なるノードに別々に配備されず、上の列と似た逆親和によって実現されることを要求します.同時に、redisがすでに配備されているノードに3つのwebフロントエンドを配備し、通信コストを削減する必要があります.親和的に実現することで、以下のように構成されています.
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: web-server
    spec:
      selector:
        matchLabels:
          app: web-store
      replicas: 3
      template:
        metadata:
          labels:
            app: web-store
        spec:
          affinity:
            podAntiAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
              - labelSelector:
                  matchExpressions:
                  - key: app
                    operator: In
                    values:
                    - web-store
                topologyKey: "kubernetes.io/hostname"
            podAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
              - labelSelector:
                  matchExpressions:
                  - key: app
                    operator: In
                    values:
                    - store
                topologyKey: "kubernetes.io/hostname"
          containers:
          - name: web-app
            image: nginx:1.12-alpine

    参照先:https://kubernetes.io/docs/concepts/configuration/assign-pod-node/