暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

用更云原生的方式做诊断 |大规模kubernetes集群诊断利器深度解析

OSC开源社区 2021-11-01
1402
alk is cheap, show me the demo
背景
我们基于Erda(现已开源)管理了有相当规模数量的Kubernetes集群,集群的稳定性决定了的服务质量以及对外口碑,很长一段时间我们在这件事情上都显得很被动,经常会出现 Erda 支持同学或者客户将问题反馈到说有业务出现了问题,需要我们协助查询一下是不是平台导致的,然后我们上去一顿操作最后解决问题,答复客户,看似专业且厉害,急用户之所急,实则无章无法,一地鸡毛。
通常我们依赖监控系统来提前发现问题,但是监控数据作为一个正向链路,很难覆盖到所有场景,经常会有因为集群配置的不一致性或者一些更底层资源的异常,即使监控数据完全正常,但是整个系统依然会有一些功能不可用,对此我们做了一套巡检系统,针对系统中一些薄弱点以及一致性做诊断,但是这套系统的扩展性不是很好,对集群跟巡检项的管理也相对粗暴了一点。
最后我们决定做一个更加云原生的诊断工具,使用operator来实现集群跟诊断项的管理,抽象出集群跟诊断项的资源概念,来解决大规模kubernetes集群的诊断问题,通过在中心来下发诊断项到其他集群,并统一收集其他集群的诊断结果来实现任何时刻都可以从中心获取到其他所有集群的运行状态,做到对大规模kubernetes集群的有效管理以及诊断。
Kubeprober
项目介绍
项目地址:https://github.com/erda-project/kubeprober
官网地址:https://k.erda.cloud
KubeProber 是一个针对大规模 Kubernetes 集群设计的诊断工具,用于在 kubernetes 集群中执行诊断项以证明集群的各项功能是否正常,KubeProber 有如下特点:
  • 支持大规模集群 支持多集群管理,支持在管理端配置集群跟诊断项的关系以及统一查看所有集群的诊断结果;

  • 云原生 核心逻辑采用 operator 来实现,提供完整的Kubernetes API兼容性;

  • 可扩展 支持用户自定义巡检项。

其核心架构如下:
区别于监控系统,kubeProber 从巡检的角度来证明集群的各项功能是否正常,监控作为正向链路,无法覆盖系统的中的所有场景,系统中各个环境的监控数据都正常,也不能保证系统是 100% 可以用的,因此需要一个工具从反向来证明系统的可用性,根本上做到先于用户发现集群中不可用的点,比如:
  • 集中的所有节点是否均可以被调度,有没有特殊的污点存在等;

  • pod是否可以正常的创建,销毁,验证从 kubernetes,kubelet 到 docker 的整条链路;

  • 创建一个service,并测试连通性,验证 kube-proxy 的链路是否正常;

  • 解析一个内部或者外部的域名,验证 CoreDNS 是否正常工作;

  • 访问一个 ingress 域名,验证集群中的 ingress 组件是否正常工作;

  • 创建并删除一个namespace,验证相关的 webhook 是否正常工作;

  • 对Etcd执行      put/get/delete 等操作,用于验证 Etcd 是否正常运行;

  • 通过 mysql-client 的操作来验证 MySQL 是否正常运行;

  • 模拟用户对业务系统进行登录,操作,验证业务的主流程是否常常;

  • 检查各个环境的证书是否过期;

  • 云资源的到期检查;

  • ... 更多

组件介绍
Kubeprober整体采用Operator来实现核心逻辑,集群之间的管理使用 remotedialer 来维持被纳管集群跟管理集群之间的心跳链接,被纳管集群通过RBAC赋予probe-agent最小所需权限并且通过心跳链接实时上报被纳管集群元信息以及访问apiserver的token,实现在管理集群可以对被管理集群的相关资源进行操作的功能。
probe-master
运行在管理集群上的 operator,这个 operator 维护两个 CRD,一个是 Cluster,用于管理被纳管的集群,另一个是 Probe,用于管理内置的以及用户自己便编写的诊断项,probe-master 通过 watch 这两个 CRD,将最新的诊断配置推送到被纳管的集群,同时 probe-master 提供接口用于查看被纳管集群的诊断结果。
probe-agent
运行在被纳管集群上的 operator,这个 operator 维护两个 CRD,一个是跟 probe-master 完全一致的 Probe,probe-agent 按照 probe 的定义去执行该集群的诊断项,另一个是 ProbeStatus,用于记录每个 Probe 的诊断结果,用户可以在被纳管的集群中通过kubectl get probestatus 来查看本集群的诊断结果。
什么是Probe
kubeprobe中运行的诊断计划我们称之为Probe,一个Probe为一个诊断项的集合,我们建议将统一场景下的诊断项作为一个Probe来运行,probe-agent组件会watch probe资源,执行Probe中定义的诊断项,并且将结果写在 ProbeStatus的资源中。
我们期望有一个输出可以清晰的看到当前集群的运行状态,因此我们建议所有的Probe都尽可能数属于应用,中间件,Kubernets,基础设置这四大场景,这样我们可以再展示状态的时候清楚的自上而下的查看究竟是系统中的哪个层面引起的问题。
目前的Probe还比较少,我们还在继续完善,也希望跟大家一起共建。自定义Probe
对比其他诊断工具
目前社区已经有kuberhealthy以及kubeeye来做kubernetes集群诊断这件事情。
kuberheathy提供一套比较清晰的框架可以让你轻松编写自己的诊断项,将诊断项CRD化,可以轻松的使用kubernetes的方式来对单个kubernetes进行体检。
kubeeye同样是针对单个集群,主要通过调用kubernetes 的 event api 以及 Node-Problem-Detector 来检测集群控制平面以及各种节点问题,同时也支持自定义诊断项。
kubeprober 做的也是诊断 kubernetes 集群这件事情,提供框架来编写自己的诊断项,除此之外,kubeprober 主要解决了大规模kubernetes 集群的诊断问题,通过中心化的思路,将集群跟诊断项抽象成CRD,可以实现在中心 kubernetes 集群管理其他kubernetes 诊断项配置,诊断结果收集,未来也会解决大规模 kubernetes 集群的运维问题。

kuberhealthy
kubeeye
kubeprober
开发团队
kuberhealthy
kubesphere
erda
开发语言
GoLang
GoLang
GoLang
诊断范围
k8s集成测试
k8s控制面功能,节点异常检测,yaml规范
k8s核心链路,节点异常事件,中间件状态等。
自定义诊断项
支持
支持基于npd的自定义检查规则
支持
命令行工具
kubectl
ke
kubectl + plugin
多集群支持
不支持
不支持
支持
支持手动触发诊断任务
支持
不支持
支持
告警
不支持
不支持
支持
可视化
不支持
不支持
支持
如何使用
kubeprober主要解决大规模kubernetes集群的诊断问题,通常我们选择其中一个集群作为master集群,部署probe-master,其他集群作为被纳管集群,部署probe-agent。
master端的安装
master 端只有一个 probe-master 的组件,其依赖与 Kubernetes 的 Webhook做一个资源的前置校验工作,我们使用 cert-manager 服务来进行 webhook 证书的自动签发,所以需要先部署一下 cert-manager 服务,等 cert-manager 的 pod 全部启动成功后再进行后续组件的安装。
    kubectl apply -f https://github.com/jetstack/cert-manager/releases/download/v1.3.1/cert-manager.yaml
    关于Secret-key
    probe-master 跟 probe-tunnel(agent端中的一个组件)交互使用Secret-key来进行认证,用户可以在 probe-master 配置 Secret-key 来作为集群接入的统一凭证,被管理集群的 probe-tunnel 组件也配置相应的 Secret-key 来跟probe-master 交互。
    配置 probe-master 的 Secret-key
      vim deployment/probe-master.yaml
      apiVersion: apps/v1
      kind: Deployment
      metadata:
      name: probe-master
      spec:
      template:
      spec:
      containers:
      - command:
      - /probe-master
      env:
      - name: SERVER_SECRET_KEY
      value: your-token-here
      部署master组件
        APP=probe-master make deploy
        agent端的安装
        agent 端包含 probe-agent 跟 probe-tunnel 组件,probe-tunnel 使用 websocket 跟 probe-master 建立连接,提供 probe-master 到被管理集群的控制通道,probe-agent 管理诊断项的声生命周期,创建,执行,删除等。
        由于 Kubernetes 本身没有集群名的概念,因此我们在 agent 端加入了集群名的概念,结合 master 端介绍的 Secret-key,因此在 agent 端需要配置 master地址, 集群名,Secret-key这三个配置。
          vim deployment/probe-agent.yaml
          ---
          apiVersion: v1
          kind: ConfigMap
          metadata:
          name: probeagent
          namespace: system
          data:
          probe-conf.yaml: |
          probe_master_addr: http://probe-master.kubeprober.svc.cluster.local:8088
          cluster_name: erda-cloud
          secret_key: your-token-here
          部署 agent 组件
            APP=probe-agent make deploy
            检查集群信息是否上报
            probe-agent 跟 probe-tunnel 启动成功后,会将集群信息上报给 probe-master, probe-master会创建出对应的集群资源,可以用如下命令来进行查看。
              kubectl get cluster

              执行诊断
              Kubeprober 采用中心管理的方式对诊断项进行管理,使用给 cluster 打上 probe label 方式来将诊断项关联到某一个集群中。
              创建 probe
              在 probe-master 所在的集群来创建 probe 资源(在default的namespace下)。
                apiVersion: kubeprober.erda.cloud/v1
                kind: Probe
                metadata:
                name: k8s
                spec:
                policy:
                # unit: minute
                runInterval: 30
                template:
                containers:
                - env:
                - name: NODE_NAME
                valueFrom:
                fieldRef:
                fieldPath: spec.nodeName
                name: k8s
                image: kubeprober/probe-k8s:v0.1.5
                resources:
                requests:
                cpu: 10m
                memory: 50Mi
                restartPolicy: Never
                configs:
                - name: control-plane
                env:
                - name: PRIVATE_DOMAIN
                value: "kubernetes.default"
                - name: DNS_CHECK_NAMESPACE
                value: "kube-system"
                - name: DNS_NODE_SELECTOR
                value: "k8s-app=kube-dns"
                - name: PUBLIC_DOMAIN
                value: "www.baidu.com"

                上述 probe 指定了运行策略,即每隔 30 分钟运行一次 k8s 的诊断。
                  kubectl apply -f probe.yaml

                  probe 关联集群
                  通过 kuebctl label 来关联 probe 跟 cluster,比如将 k8s 的 probe 关联给了 erda-cloud 集群。
                    kubectl label cluster erda-cloud probe/k8s=true

                    查看诊断结果
                    可以使用 kubectl probe 指令来查看特定集群的诊断结果。
                    创建 kubectl probe 所需要的配置文件,没有该文件则 kubectl probe 会自动将 ws://probe-master.kubeprober.svc.cluster.local:8088/clusterdialer 作为 master 的 地址,其他情况可以自行修改该配置文件。
                      vi ~/.kubeprober/config
                      {
                      "masterAddr": "ws://probe-master.kubeprober.svc.cluster.local:8088/clusterdialer"
                      }

                      查看诊断结果
                      使用 kubectl probe status 可以查看特定集群的当前诊断结果的状态, 由于诊断项是定时在运行的,因此该命令查到的就是最新一次的诊断结果。
                        kubectl probe status -c erda-cloud

                        执行一次性诊断
                        除了定时诊断的场景, Kubeprober 也支持一次性诊断,常用来在系统做了变更之后想要查看系统各个方面是否正常使用,默认会诊断当前集群 attach 了的probe,同时也可用指定 probe 进行诊断。
                          kubectl probe once -c erda-cloud                    #诊断已经 attatch 了的 probe
                          kubectl probe once -c erda-cloud -p k8s,host #诊断特定 probe


                          一次性诊断的历史记录会被保存起来,可以使用如下命令来进行查看历史记录。
                            kubectl probe oncestatus -c erda-cloud -l

                            查看历史某一次一次性诊断的诊断结果。
                              kubectl probe oncestatus -c erda-cloud -i 1630566675
                              单集群使用kubeprober
                              同时kubeprober也可以用于单集群的诊断,适用于没有那么多kubernetes集群需要诊断的场景,具体的使用方法参考这里:https://docs.erda.cloud/1.3/manual/eco-tools/kubeprober/best-practices/standalone_kubeprober.html
                              可视化
                              kubeprober在多集群中根据probe的策略执行诊断项,会产生大量的诊断事件,那对这些诊断项进行可视化的展示就显得尤为重要,可以有一个全局的dashborad对大规模集群的海量诊断项进行统一的查看分析会更有利于我们掌握这些集群的运行状态。
                              kubeprober支持将诊断项事件写入 infuxdb,通过grafana来配置图表来统一展示诊断结果,比如我们将 ERROR 事件统一展示出来作为最高优先级进行关注。
                              同时我们也可以通过扩展probe-agent上报的集群信息来展示一张详尽的集群列表
                              欢迎参与
                              当前kubeprobe已经发布了第一个版本0.1.0,还有许多功能不太完善,probe-master的管理能力还可以进一步的被放大挖掘,probe的编写也需要更加的简单易用,我们希望跟社区一期共建,通过打造一个大规模Kubernetes集群的管理神器。
                              Contributing to KubeProber:https://github.com/erda-project/kubeprober/blob/master/CONTRIBUTING.md

                              END



                              想象中运行代码 VS 实际中运行代码
                              有点意思


                              觉得不错,请点个在看

                              文章转载自OSC开源社区,如果涉嫌侵权,请发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

                              评论