InfoQ Geekathon 大模型技术应用创新大赛 了解详情
写点什么

深入浅出 Kubernetes 理论篇 (三):伸缩原理

  • 2020-03-30
  • 本文字数:2983 字

    阅读完需:约 10 分钟

深入浅出Kubernetes 理论篇 (三):伸缩原理

简介:阿里云 Kubernetes 集群的一个重要特性,是集群的节点可以动态的增加或减少。有了这个特性,集群才能在计算资源不足的情况下扩容新的节点,同时也可以在资源利用率降低的时候,释放节点以节省费用。


这篇文章,我们讨论阿里云 Kubernetes 集群扩容与缩容的实现原理。


阿里云 Kubernetes 集群的一个重要特性,是集群的节点可以动态的增加或减少。有了这个特性,集群才能在计算资源不足的情况下扩容新的节点,同时也可以在资源利用率降低的时候,释放节点以节省费用。


这篇文章,我们讨论阿里云 Kubernetes 集群扩容与缩容的实现原理。理解实现原理,在遇到问题的时候,我们就可以高效地排查并定位原因。我们的讨论基于当前的 1.12.6 版本。

节点增加原理

阿里云 Kubernetes 集群可以给集群增加节点的方式有,添加已有节点,集群扩容,和自动伸缩。其中,添加已有节点又可分为手动添加已有节点和自动添加已有节点。节点的增加涉及到的组件有,节点准备,弹性伸缩(ESS),管控,Cluster Autoscaler 以及调度器。


手动添加已有节点

节点准备,其实就是把一个普通的 ECS 实例,安装配置成为一个 Kubernetes 集群节点的过程。这个过程仅靠一条命令就可以完成。这条命令使用 curl 下载 attach_node.sh 脚本,然后以 openapi token 为参数,在 ECS 上运行。


curl http:///public/pkg/run/attach//attach_node.sh | bash -s -- --openapi-token
复制代码


这里 token 是一个对的 key,而 value 是当前集群的基本信息。阿里云 Kubernetes 集群的管控,在接到手动添加已有节点请求的时候,会生成这个对,并把 key 作为 token 返回给用户。


这个 token(key)存在的价值,是其可以让 attach_node.sh 脚本,以匿名身份在 ECS 上索引到集群的基本信息(value),而这些基本信息,对节点准备至关重要。


总体上来说,节点准备就做两件事情,读和写。读即数据收集,写即节点配置。



这里的读写过程,绝大部分都很基础,大家可以通过阅读脚本来了解细节。唯一需要特别说明的是,kubeadm join 把节点注册到 Master 的过程。此过程需要新加节点和集群 Master 之间建立互信。


一边,新加节点从管控处获取的 bootstrap token(与 openapi token 不同,此 token 是 value 的一部分内容),实际上是管控通过可信的途径从集群 Master 上获取的。新加节点使用这个 bootstrap token 连接 Master,Master 则可通过验证这个 bootstrap token 来建立对新加节点的信任。


另一边,新加节点以匿名身份从 Master kube-public 命名空间中获取集群 cluster-info,cluster-info 包括集群 CA 证书,和使用集群 bootstrap token 对这个 CA 做的签名。新加节点使用从管控处获取的 bootstrap token,对 CA 生成 b 新的签名,然后将此签名与 cluster-info 内签名做对比,如果两个签名一致,则说明 cluster-info 和 bootstrap token 来自同一集群。新加节点因为信任管控,所以建立对 Master 的信任。


自动添加已有节点

自动添加已有节点,不需要人为拷贝黏贴脚本到 ECS 命令行来完成节点准备的过程。管控使用了 ECS userdata 的特性,把类似以上节点准备的脚本,写入 ECS userdata,然后重启 ECS 并更换系统盘。当 ECS 重启之后,会自动执行 Userdata 里边的脚本,来完成节点添加的过程。这部分内容,大家其实可以通过查看节点 userdata 来确认。

!/bin/bash

mkdir -p /var/log/acs
curl http:///public/pkg/run/attach/1.12.6-aliyun.1/attach_node.sh | bash -s -- --docker-version --token --endpoint --cluster-dns > /var/log/acs/init.log
复制代码


这里我们看到,attach_node.sh 的参数,与前一节的参数有很大的不同。其实这里的参数,都是前一节 value 的内容,即管控创建并维护的集群基本信息。自动添加已有节点省略了通过 key 获取 value 的过程。

集群扩容

集群扩容与以上添加已有节点不同,此功能针对需要新购节点的情形。集群扩容的实现,在添加已有节点的基础上,引入了弹性伸缩 ESS 组件。ESS 组件负责从无到有的过程,而剩下的过程与添加已有节点类似,即依靠 ECS userdata 脚本来完成节点准备。下图是管控通过 ESS 从无到有创建 ECS 的过程。


自动伸缩

前边三种方式是需要人为干预的伸缩方式,而自动伸缩的本质不同,是它可以在业务需求量增加的时候,自动创建 ECS 实例并加入集群。为了实现自动化,这里引入了另外一个组件 Cluster Autoscaler。集群自动伸缩包括两个独立的过程。



其中第一个过程,主要用来配置节点的规格属性,包括设置节点的用户数据。这个用户数据和手动添加已有节点的脚本类似,不同的地方在于,其针对自动伸缩这种场景,增加了一些专门的标记。attach_node.sh 脚本会根据这些标记,来设置节点的属性。

!/bin/sh

curl http:///public/pkg/run/attach/1.12.6-aliyun.1/attach_node.sh | bash -s -- --openapi-token --ess true --labels k8s.io/cluster-autoscaler=true,workload_type=cpu,k8s.aliyun.com=true
复制代码


而第二个过程,是实现自动增加节点的关键。这里引入了一个新的组件 Autoscaler,它以 Pod 的形式运行在 Kubernetes 集群中。理论上来说,我们可以把这个组件当做一个控制器。因为它的作用与控制器类似,基本上还是监听 Pod 状态,以便在 Pod 因为节点资源不足而不能被调度的时,去修改 ESS 的伸缩规则来增加新的节点。


这里有一个知识点,集群调度器衡量资源是否充足的标准,是“预订率”,而不是“使用率”。这两者的差别,类似酒店房价预订率和实际入住率:完全有可能有人预订了酒店,但是并没有实际入住。在开启自动伸缩功能的时候,我们需要设置缩容阈值,就是“预订率”的下线。之所以不需要设置扩容阈值。是因为 Autoscaler 扩容集群,依靠的是 Pod 的调度状态:当 Pod 因为节点资源“预订率”太高无法被调度的时候,Autoscaler 就会扩容集群。

节点减少原理

与增加节点不同,集群减少节点的操作只有一个移除节点的入口。但对于用不同方法加入的节点,其各自移除方式略有不同。


首先,通过添加已有节点加入的节点,需要三步去移除:管控通过 ECS API 清楚 ECS userdata;管控通过 Kubernetes API 从集群中删除节点;管控通过 ECS InvokeCommand 在 ECS 上执行 kubeadm reset 命令清理节点。


其次,通过集群扩容加入的节点,则在上边的基础上,增加了断开 ESS 和 ECS 关系的操作。此操作由管控调用 ESS API 完成。



最后,经过 Cluster Autoscaler 动态增加的节点,则在集群 CPU 资源“预订率”降低的时候,由 Cluster Autoscaler 自动移除释放。其触发点是 CPU“预订率”,即上图写 Metrics 的原因。

总结

总体上来说,Kubernetes 集群节点的增加与减少,主要涉及四个组件,分别是 Cluster Autoscaler,ESS,管控以及节点本身(准备或清理)。根据场景不同,我们需要排查不同的组件。其中 Cluster Autoscaler 是一个普通的 Pod,其日志的获取和其他 Pod 无异;ESS 弹性伸缩有其专门的控制台,我们可以在控制台排查其伸缩配置、伸缩规则等相关子实例日志和状态;而管控的日志,可以通过查看日志功能来查看;最后,对于节点的准备与清理,其实就是排查对应的脚本的执行过程。


以上讲道理居多,希望对大家排查问题有所帮助。


作者简介


罗建龙(花名声东),阿里云技术专家。多年操作系统和图形显卡驱动调试和开发经验。目前专注云原生领域,容器集群和服务网格。


相关阅读


深入浅出Kubernetes 理论篇 (一):理解控制器


深入浅出Kubernetes 理论篇 (二):网络详解


活动推荐:

2023年9月3-5日,「QCon全球软件开发大会·北京站」 将在北京•富力万丽酒店举办。此次大会以「启航·AIGC软件工程变革」为主题,策划了大前端融合提效、大模型应用落地、面向 AI 的存储、AIGC 浪潮下的研发效能提升、LLMOps、异构算力、微服务架构治理、业务安全技术、构建未来软件的编程语言、FinOps 等近30个精彩专题。咨询购票可联系票务经理 18514549229(微信同手机号)。

2020-03-30 17:05838

评论

发布
暂无评论
发现更多内容

不是吧,都2021年了你别说你还不会Spring MVC基本应用

热爱java的分享家

Java 架构 程序人生 编程语言 经验分享

Prometheus Exporter (十一)Kafka Exporter

耳东@Erdong

kafka Prometheus exporter 11月日更

【死磕Java并发】-----J.U.C之重入锁:ReentrantLock

chenssy

11月日更 死磕 Java 死磕 Java 并发

坐标东京,诚招IT工程师~

马农驾驾驾

软件 软件开发 日本 IT 日语

.NET6新东西--插值字符串优化

喵叔

11月日更

历史上最伟大的一次 Git 代码提交

沉默王二

git

看完了阿里大牛的Leetcode刷题笔记, 我成功拿到了字节跳动的offer

热爱java的分享家

Java 面试 算法 LeetCode 经验分享

Go语言学习查缺补漏ing Day7

Regan Yue

Go 语言 11月日更

Linux 中的 15 个强大的 firewall-cmd 命令,牛牛牛!

Ethereal

Linux 运维 防火墙 Firewalld防火墙

在线文本对比工具

入门小站

工具

Pulsar 在2.8升级过程中需要注意的TopicPolicy问题

Zike Yang

Apache Pulsar 11月日更

Flutter - TabController监听index

坚果

flutter 11月日更

Android C++系列:Linux信号(一)

轻口味

c++ android jni 11月日更

字节大牛把算法常见面试:哈希、链表、队列、递归全部总结出来了

热爱java的分享家

Java 面试 程序人生 编程语言 经验分享

终于有腾讯架构师把困扰我多年的《计算机网络原理》全部讲明白了

热爱java的分享家

Java 面试 编程语言 网络协议 经验分享

linux重要的目录之etc

入门小站

Linux

修复一个BaseRecyclerViewAdapterHelper漏洞

Changing Lin

11月日更

阿里大牛最新公开压轴的“Redis深度笔记”,GitHub已标星81.6K

热爱java的分享家

Java 架构 面试 程序人生 编程语言

听说版本会说话,你相信吗?

程序那些事

版本控制 程序那些事 版本管理 版本升级 11月日更

25 K8S之Endpoint对象

穿过生命散发芬芳

k8s 11月日更

使用MRS CDL实现实时数据同步的极致性能

华为云开发者联盟

延迟 实时数据 MRS CDL 吞吐 实时数据复制

【高并发】浅谈AQS中的ReentrantLock、ReentrantReadWriteLock、StampedLock与Condition

冰河

Java 并发编程 多线程 高并发 异步编程

对元宇宙 我们期待什么?

CECBC

大厂算法面试之leetcode精讲7.双指针

全栈潇晨

LeetCode 算法面试

数字人民币的基础:共识与信任!

CECBC

路由器或交换机配置中line vty 0 4到底是什么意思?

Ethereal

交换机 路由器 网络技术

什么是IS-IS中间系统到中间系统?网工、运维必看!

Ethereal

网络技术

人脸检测实战进阶:使用 OpenCV 进行活体检测

AI浩

面试不慌,拿这70张思维导图,怒怼面试官

奔着腾讯去

c++ golang 数据结构 思维导图 TCP/IP

简述以太坊P2P网络之UDP

devpoint

区块链 以太坊 udp 11月日更

区块链将掀开人类的伟大时代

CECBC

  • 扫码添加小助手
    领取最新资料包
深入浅出Kubernetes 理论篇 (三):伸缩原理_文化 & 方法_罗建龙(声东)_InfoQ精选文章