理解k8s控制器DaemonSet创建及使用场景

2023-12-01 0 439
目录
  • DaemonSet 简介
  • DaemonSet 使用场景
  • DaemonSet 创建
  • 查看 DaemonSet
  • 更新 DaemonSet
  • 删除 DaemonSet
  • 其它使用场景
    • 容忍性 Toleration 使用
    • 节点亲和性 nodeAffinity 使用
  • 总结

    DaemonSet 简介

    DaemonSet 的主要作用,是在 Kubernetes 集群里,运行一个 Daemon Pod。 DaemonSet 只管理 Pod 对象,然后通过 nodeAffinity 和 Toleration 这两个调度器参数的功能,保证了每个节点上有且只有一个 Pod。

    DaemonSet 是一种面向特定应用场景的 Pod 控制器,尽管它也可以管理 Pod 的多个副本,但它主要用于保证一个 Node 上只运行一个 Pod 的场景:

    DaemonSet 使用场景

    每个节点上只有一个这样的 Daemon Pod 实例,然后当有新的节点加入 Kubernetes 集群后,该 Pod 会自动地在新节点上被创建出来。当旧节点被删除后,它上面的 Pod 也会相应地被回收掉。

    Daemon Pod 的意义确实是非常重要的。比如的作用:

    • 网络插件的 Agent 组件,都必须运行在每一个节点上,用来处理这个节点上的容器网络。
    • 存储插件的 Agent 组件,也必须运行在每一个节点上,用来在这个节点上挂载远程存储目录,操作容器的 Volume 目录,比如:glusterd、ceph。
    • 监控组件和日志组件,也必须运行在每一个节点上,负责这个节点上的监控信息和日志搜集,比如:fluentd、logstash、Prometheus 等。

    DaemonSet 创建

    k8s 环境搭建参考网上教程,这里就不再赘述了。

    先来个简单的例子快速体验 DaemonSet 控制器是如何应用的。

    一个简单的 DaemonSet 配置如下:

    apiVersion: apps/v1
    kind: DaemonSet
    metadata:
    name: nginx-daemonset
    labels:
    app: nginx
    spec:
    selector:
    matchLabels:
    app: nginx
    template:
    metadata:
    labels:
    app: nginx
    spec:
    containers:
    – name: nginx
    image: nginx:1.17.0

    初步看,这份配置跟 Deployment 基本类似,唯一一个显著的差异是 DaemonSet 不需要指定副本数,因为它的副本数取决于工作节点数。

    DaemonSet 配置中 spec.selector 和 spec.template 作用我们已在介绍 Deployment 时介绍过,在此不再赘述。

    该份配置将创建一个 DaemonSet 对象,然后 DaemonSet 控制器会根据该对象信息分别在每个节点上创建一个 Pod 副本。

    接下来使用kubectl create命令将该配置提次给 kube-apiserver,如下所示:

    [root@k8s-master]# kubectl create -f daemonset.yaml
    daemonset.apps/nginx-daemonset created

    查看 DaemonSet

    首先查看刚刚创建的 DaemonSet 对象:

    [root@k8s-master]# kubectl get daemonset
    NAME DESIRED CURRENT READY UP-TO-DATE AVAILABLE NODE SELECTOR AGE
    nginx-daemonset 3 3 3 3 3 <none> 1m3s

    命令行输出中各字段含义如下:

    • NAME: DaemonSet 对象名称,同配置中的 metadata.name;
    • DESIRED:需求副本个数,由于没有刻意筛选节点,所以副本个数等同于节点个数(默认);
    • CURRENT:当前已创建的副本个数;
    • READY:处于 Ready 状态的副本个数;
    • UP-TO-DATE:已按最新 Pod 模版创建的 Pod 个数;
    • AVAILABLE:可用的副本个数;
    • NODE SELECTOR:节点选择器,本例中我们没有选择,值为空;
    • AGE:创建至今经历的时间。

    上面的字段中,除了 NODE SELECTOR 以外,我们已在前面的章节中介绍过。其实 Node Selector 并不是 DaemonSet 对象特有的配置,它是 Pod 模版中用于为 Pod 匹配节点的配置,DaemonSet 控制器使用该 Node Selector 来筛选需要创建副本的节点,如果没有指定,则默认选择全部节点。

    接着,查看 DaemonSet 控制器所创建的 Pod 副本信息:

    [root@k8s-master]# kubectl get pods -o wide
    NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
    nginx-daemonset-66dbc 1/1 Running 0 5m13s 10.135.3.2 k8s-master <none> <none>
    nginx-daemonset-akpdg 1/1 Running 0 5m13s 10.135.1.2 k8s-node1 <none> <none>
    nginx-daemonset-l3wnd 1/1 Running 0 5m13s 10.135.2.2 k8s-node2 <none> <none>

    可以看到,在每个节点上均创建了一个副本,是符合预期的。

    更新 DaemonSet

    下面我们适当的调整下 Pod 部署策略,只希望 Pod 运行在名为 k8s-node 的节点上,这样我们只需要配置 DaemonSet 对象的 spec.template.spec.nodeSelector 来选择节点即可。

    在 k8s-node 的节点中存在一个标识节点的 label:

    kubernetes.io/hostname: k8s-node1

    使用 kubectl edit 命令修改配置的 spec.template.spec.nodeSelector 参数如下:

    apiVersion: apps/v1
    kind: DaemonSet
    metadata:

    spec:

    template:

    spec:

    nodeSelector:
    kubernetes.io/hostname: k8s-node1

    然后再次观察 DaemonSet 对象和 Pod 副本:

    [root@k8s-master]# kubectl get daemonsets
    NAME DESIRED CURRENT READY UP-TO-DATE AVAILABLE NODE SELECTOR AGE
    nginx-daemonset 1 1 1 1 1 kubernetes.io/hostname=k8s-node1 37m
    [root@k8s-master]# kubectl get pods -o wide
    NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
    nginx-daemonset-66gk2 1/1 Running 0 10s 10.135.2.3 k8s-node1 <none> <none>

    可以发现 DaemonSet 状态中,NODE SELECTOR 正确地展示了上面的修改,而且需求的 Pod 副本数也变成了 1 个,符合预期。

    原来运行的 3 个 Pod 副本减少到 1 个,而且只在我们配置选定的节点(k8s-node1)上运行。

    删除 DaemonSet

    像其他 Pod 控制器一样,当删除 DaemonSet 对象时,其所管理的 Pod 默认也会被删除,操作如下所示:

    [root@k8s-master ~]# kubectl delete daemonsets nginx-daemonset
    daemonset.apps \”nginx-daemonset\” deleted
    [root@k8s-master ~]# kubectl get pods
    No resources found in default namespace.

    其它使用场景

    容忍性 Toleration 使用

    DaemonSet 还会给这个 Pod 自动加上另外一个与调度相关的字段,叫作 tolerations。这个字段意味着这个 Pod,会“容忍”(Toleration)某些 Node 的“污点”(Taint)。

    Toleration 使用 yaml 配置如下:

    apiVersion: v1
    kind: Pod
    metadata:
    name: with-toleration
    spec:
    tolerations:
    – key: node.kubernetes.io/unschedulable
    operator: Exists
    effect: NoSchedule

    在正常情况下,被标记了 unschedulable“污点”的 Node,是不会有任何 Pod 被调度上去的(effect: NoSchedule)。

    可是,DaemonSet 自动地给被管理的 Pod 加上了这个特殊的 Toleration,就使得这些 Pod 可以忽略这个限制,继而保证每个节点上都会被调度一个 Pod。

    当然,如果这个节点有故障的话,这个 Pod 可能会启动失败,而 DaemonSet 则会始终尝试下去,直到 Pod 启动成功。

    主要作用:

    通过这样一个 Toleration,调度器在调度这个 Pod 的时候,就会忽略当前节点上的“污点”,从而成功地将一些组件调度到这台机器上启动起来。

    这种机制,正是我们在部署 Kubernetes 集群的时候,能够先部署 Kubernetes 本身、再部署网络插件的根本原因:因为当时我们所创建的 Weave 的 YAML,实际上就是一个 DaemonSet。

    节点亲和性 nodeAffinity 使用

    正常情况下 DaemonSet Controller 会在创建 Pod 的时候,自动在这个 Pod 的 API 对象里,加上这样一个 nodeAffinity 定义。

    在这个 Pod 里,声明了一个 spec.affinity 字段,然后定义了一个 nodeAffinity。其中,spec.affinity 字段,是 Pod 里跟调度相关的一个字段。

    nodeAffinity 使用 yaml 配置如下:

    apiVersion: v1
    kind: Pod
    metadata:
    name: demo-node-affinity
    spec:
    affinity:
    nodeAffinity:
    requiredDuringSchedulingIgnoredDuringExecution:
    nodeSelectorTerms:
    – matchExpressions:
    – key: metadata.name
    operator: In
    values:
    – demo-node

    以上关键参数含义:

    • requiredDuringSchedulingIgnoredDuringExecution 这个代表 nodeAffinity 必须在每次调度的时候予以考虑,同时,这也意味着可以设置在某些情况下不考虑这个 nodeAffinity;
    • 这个 Pod,将来只允许运行在“metadata.name”是“demo-node”的节点上。

    总结

    DaemonSet 其实就是依靠 nodeAffinity 和 Toleration 实现的。这是一种不需要增加设计结构,而直接使用标签等方式完成的 Daemon 进程。这样的结构非常符合 Kubernetes 的控制器模式,正所谓一切皆对象。

    以上就是k8s控制器DaemonSet理解的详细内容,更多关于k8s控制器DaemonSet的资料请关注悠久资源网其它相关文章!

    收藏 (0) 打赏

    感谢您的支持,我会继续努力的!

    打开微信/支付宝扫一扫,即可进行扫码打赏哦,分享从这里开始,精彩与您同在
    点赞 (0)

    悠久资源 Linux服务器 理解k8s控制器DaemonSet创建及使用场景 https://www.u-9.cn/server/linux/2019.html

    常见问题

    相关文章

    发表评论
    暂无评论
    官方客服团队

    为您解决烦忧 - 24小时在线 专业服务