美文网首页
k8s nodeAffinity

k8s nodeAffinity

作者: john瀚 | 来源:发表于2019-10-16 14:10 被阅读0次

    简介

    Node Affinity
    Affinity 翻译成中文是“亲和性”,它对应的是 Anti-Affinity,我们翻译成“互斥”。这两个词比较形象,可以把 pod 选择 node 的过程类比成磁铁的吸引和互斥,不同的是除了简单的正负极之外,pod 和 node 的吸引和互斥是可以灵活配置的。

    Affinity的优点:

    匹配有更多的逻辑组合,不只是字符串的完全相等
    调度分成软策略(soft)和硬策略(hard),在软策略下,如果没有满足调度条件的节点,pod会忽略这条规则,继续完成调度。
    目前主要的node affinity:

    requiredDuringSchedulingIgnoredDuringExecution
    表示pod必须部署到满足条件的节点上,如果没有满足条件的节点,就不停重试。其中IgnoreDuringExecution表示pod部署之后运行的时候,如果节点标签发生了变化,不再满足pod指定的条件,pod也会继续运行。

    requiredDuringSchedulingRequiredDuringExecution
    表示pod必须部署到满足条件的节点上,如果没有满足条件的节点,就不停重试。其中RequiredDuringExecution表示pod部署之后运行的时候,如果节点标签发生了变化,不再满足pod指定的条件,则重新选择符合要求的节点。

    preferredDuringSchedulingIgnoredDuringExecution
    表示优先部署到满足条件的节点上,如果没有满足条件的节点,就忽略这些条件,按照正常逻辑部署。

    preferredDuringSchedulingRequiredDuringExecution
    表示优先部署到满足条件的节点上,如果没有满足条件的节点,就忽略这些条件,按照正常逻辑部署。其中RequiredDuringExecution表示如果后面节点标签发生了变化,满足了条件,则重新调度到满足条件的节点。

    缘由

    pod绑定节点最简单的方法是使用 nodeSelector,但它比较简单粗暴,使用起来不能灵活调度,这个在后续版本中也会慢慢过实,所以我们一般用 nodeAffinity来实现这些需求。
    如果我不希望pod调度到打了 tester=chenqiang 这个标签的 node,那么需要使用 NotIn 这个介词,否则使用 In 。
    假设不希望调度,则添加如下的 nodeAffinity:

        spec:
          affinity:
            nodeAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
                nodeSelectorTerms:
                - matchExpressions:
                  - key: tester
                    operator: NotIn
                    values:
                    - chenqiang
    

    完整实例

    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: nginx-hello-deployment
      namespace: chenqiang-ns1
      labels:
        app: nginx-hello
    spec:
      replicas: 2
      selector:
        matchLabels:
          app: nginx-hello
      template:
        metadata:
          labels:
            app: nginx-hello
        spec:
          affinity:
            nodeAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
                nodeSelectorTerms:
                - matchExpressions:
                  - key: tester
                    operator: NotIn
                    values:
                    - chenqiang
          containers:
          - name: nginx-hello
            image: docker-registry.saicstack.com/chenqiang/nginx-hello:v2.0
            ports:
            - containerPort: 80
          imagePullSecrets:
          - name: regcred
    
    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: gcr.io/google_containers/pause:2.0
    

    这条规则表示,pod可以被调度到标签key为“kubernetes.io/e2e-az-name”,值为“e2e-az1”或“e2e-az2”的节点。另外,在满足该条件的节点中,优先使用具有“another-node-label-key”标签,且至为“another-node-label-value”的节点。
    这个 pod 同时定义了 requiredDuringSchedulingIgnoredDuringExecution 和 preferredDuringSchedulingIgnoredDuringExecution 两种 nodeAffinity。第一个要求 pod 运行在特定 AZ 的节点上,第二个希望节点最好有对应的 another-node-label-key:another-node-label-value 标签。

    这里的匹配逻辑是label在某个列表中,可选的操作符有:

    In: label的值在某个列表中
    NotIn:label的值不在某个列表中
    Exists:某个label存在
    DoesNotExist:某个label不存在
    Gt:label的值大于某个值(字符串比较)
    Lt:label的值小于某个值(字符串比较)
    如果nodeAffinity中nodeSelector有多个选项,节点满足任何一个条件即可;如果matchExpressions有多个选项,则节点必须同时满足这些选项才能运行pod 。

    需要说明的是,node并没有anti-affinity这种东西,因为NotIn和DoesNotExist能提供类似的功能。

    相关文章

      网友评论

          本文标题:k8s nodeAffinity

          本文链接:https://www.haomeiwen.com/subject/iptumctx.html