在kubernetes集群中使用虚拟节点创建1万Pod-支持在线教育业务疫情高峰

本文涉及的产品
容器镜像服务 ACR,镜像仓库100个 不限时长
容器服务 Serverless 版 ACK Serverless,317元额度 多规格
容器服务 Serverless 版 ACK Serverless,952元额度 多规格
简介: 在kubernetes集群中添加虚拟节点的方式已被非常多的客户普遍使用,基于虚拟节点可以极大提升集群的Pod容量和弹性,灵活动态的按需创建ECI Pod,免去集群容量规划的麻烦。

使用虚拟节点提升k8s集群容量和弹性

image

在kubernetes集群中添加虚拟节点的方式已被非常多的客户普遍使用,基于虚拟节点可以极大提升集群的Pod容量和弹性,灵活动态的按需创建ECI Pod,免去集群容量规划的麻烦。目前虚拟节点已广泛应用在如下场景。

  • 在线业务的波峰波谷弹性需求:如在线教育、电商等行业有着明显的波峰波谷计算特征,使用虚拟节点可以显著减少固定资源池的维护,降低计算成本。
  • 提升集群Pod容量:当传统的flannel网络模式集群因vpc路由表条目或者vswitch网络规划限制导致集群无法添加更多节点时,使用虚拟节点可以规避上述问题,简单而快速的提升集群Pod容量。
  • 数据计算:使用虚拟节点承载Spark、Presto等计算场景,有效降低计算成本。
  • CI/CD和其他Job类型任务

下面我们介绍如何使用虚拟节点快速创建1万个pod,这些eci pod按需计费,不会占用固定节点资源池的容量。

相比较而言,AWS EKS在一个集群中最多只能创建1000个 Fargate Pod。基于虚拟节点的方式可以轻松创建过万个ECI Pod。

创建多个虚拟节点

请先参考ACK产品文档部署虚拟节点:https://help.aliyun.com/document_detail/118970.html

因为使用多个虚拟虚拟节点往往用于部署大量ECI Pod,我们建议谨慎确认vpc/vswitch/安全组的配置,确保有足够的vswitch ip资源(虚拟节点支持配置多个vswitch解决ip容量问题),使用企业级安全组可以突破普通安全组的2000个实例限制。

通常而言,如果单个k8s集群内eci pod数量小于3000,我们推荐部署单个虚拟节点。如果希望在虚拟节点上部署更多的pod,我们建议在k8s集群中部署多个虚拟节点来对其进行水平扩展,多个虚拟节点的部署形态可以缓解单个虚拟节点的压力,支撑更大的eci pod容量。这样3个虚拟节点可以支撑9000个eci pod,10个虚拟节点可以支撑到30000个eci pod。

image

为了更简单的进行虚拟节点水平扩展,我们使用statefulset的方式部署vk controller,每个vk controller管理一个vk节点,statefulset的默认Pod副本数量是1。当需要更多的虚拟节点时,只需要修改statefulset的replicas即可。

# kubectl -n kube-system scale statefulset virtual-node-eci --replicas=4
statefulset.apps/virtual-node-eci scaled

# kubectl get no
NAME                            STATUS     ROLES    AGE     VERSION
cn-hangzhou.192.168.1.1         Ready      <none>   63d     v1.12.6-aliyun.1
cn-hangzhou.192.168.1.2         Ready      <none>   63d     v1.12.6-aliyun.1
virtual-node-eci-0              Ready      agent     1m     v1.11.2-aliyun-1.0.207
virtual-node-eci-1              Ready      agent     1m     v1.11.2-aliyun-1.0.207
virtual-node-eci-2              Ready      agent     1m     v1.11.2-aliyun-1.0.207
virtual-node-eci-3              Ready      agent     1m     v1.11.2-aliyun-1.0.207

# kubectl -n kube-system get statefulset virtual-node-eci
NAME              READY   AGE
virtual-node-eci  4/4     1m

# kubectl -n kube-system get pod|grep virtual-node-eci
virtual-node-eci-0                                               1/1     Running   0           1m
virtual-node-eci-1                                               1/1     Running   0           1m
virtual-node-eci-2                                               1/1     Running   0           1m
virtual-node-eci-3                                               1/1     Running   0           1m

当我们在vk namespace中创建多个nginx pod时(将vk ns加上指定label,强制让ns中的pod调度到虚拟节点上),可以发现pod被调度到了多个vk节点上。

# kubectl create ns vk
# kubectl label namespace vk virtual-node-affinity-injection=enabled

# kubectl -n vk run nginx --image nginx:alpine --replicas=10
deployment.extensions/nginx scaled

# kubectl -n vk get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE   IP             NODE                NOMINATED NODE   READINESS GATES
nginx-546c47b569-blp88   1/1     Running   0          69s   192.168.1.26   virtual-node-eci-1  <none>           <none>
nginx-546c47b569-c4qbw   1/1     Running   0          69s   192.168.1.76   virtual-node-eci-0  <none>           <none>
nginx-546c47b569-dfr2v   1/1     Running   0          69s   192.168.1.27   virtual-node-eci-2  <none>           <none>
nginx-546c47b569-jfzxl   1/1     Running   0          69s   192.168.1.68   virtual-node-eci-1  <none>           <none>
nginx-546c47b569-mpmsv   1/1     Running   0          69s   192.168.1.66   virtual-node-eci-1  <none>           <none>
nginx-546c47b569-p4qlz   1/1     Running   0          69s   192.168.1.67   virtual-node-eci-3  <none>           <none>
nginx-546c47b569-x4vrn   1/1     Running   0          69s   192.168.1.65   virtual-node-eci-2  <none>           <none>
nginx-546c47b569-xmxx9   1/1     Running   0          69s   192.168.1.30   virtual-node-eci-0  <none>           <none>
nginx-546c47b569-xznd8   1/1     Running   0          69s   192.168.1.77   virtual-node-eci-3  <none>           <none>
nginx-546c47b569-zk9zc   1/1     Running   0          69s   192.168.1.75   virtual-node-eci-2  <none>           <none>

运行1万个ECI Pod

在上述步骤中我们已经创建了4个虚拟节点,能够支撑12000个ECI Pod,我们只需要将workload指定调度到虚拟节点即可。这里我们需要关注kube-proxy的可扩展性。

  1. 虚拟节点创建的ECI Pod默认支持访问集群中的ClusterIP Service,这样每个ECI Pod都需要watch apiserver保持一个连接以监听svc/endpoints变化。当大量pod同时Running时,apiserver和slb将维持Pod数量的并发连接,所以需要确保slb规格能否支撑期望的并发连接数。
  2. 如果ECI Pod无需访问ClusterIP Service,则可以将virtual-node-eci statefulset的ECI_KUBE_PROXY环境变量值设置为"false",这样就不会有大量slb并发连接的存在,也会减少apiserver的压力。
  3. 我么也可以选择将ECI Pod访问的ClusterIP Service暴露成内网slb类型,然后通过privatezone的方式让ECI Pod不必基于kube-proxy也能否访问到集群中的Service服务。

缩减vk虚拟节点数量

因为vk上的eci pod是按需创建,当没有eci pod时vk虚拟节点不会占用实际的资源,所以一般情况下我们不需要减少vk节点数。但用户如果确实希望减少vk节点数时,我们建议按照如下步骤操作。

假设当前集群中有4个虚拟节点,分别为virtual-node-eci-0/.../virtual-node-eci-3。我们希望缩减到1个虚拟节点,那么我们需要删除virtual-node-eci-1/../virtual-node-eci-3这3个节点。

  • 先优雅下线vk节点,驱逐上面的pod到其他节点上,同时也禁止更多pod调度到待删除的vk节点上。
# kubectl drain virtual-node-eci-1 virtual-node-eci-2 virtual-node-eci-3

# kubectl get no
NAME                      STATUS                     ROLES    AGE    VERSION
cn-hangzhou.192.168.1.1   Ready                      <none>   66d    v1.12.6-aliyun.1
cn-hangzhou.192.168.1.2   Ready                      <none>   66d    v1.12.6-aliyun.1
virtual-node-eci-0        Ready                      agent    3d6h   v1.11.2-aliyun-1.0.207
virtual-node-eci-1        Ready,SchedulingDisabled   agent    3d6h   v1.11.2-aliyun-1.0.207
virtual-node-eci-2        Ready,SchedulingDisabled   agent    3d6h   v1.11.2-aliyun-1.0.207
virtual-node-eci-3        Ready,SchedulingDisabled   agent    66m    v1.11.2-aliyun-1.0.207

之所以需要先优雅下线vk节点的原因是vk节点上的eci pod是被vk controller管理,如果vk节点上还存在eci pod时删除vk controller,那样将导致eci pod被残留,vk controller也无法继续管理那些pod。

  • 待vk节点下线后,修改virtual-node-eci statefulset的副本数量,使其缩减到我们期望的vk节点数量。
# kubectl -n kube-system scale statefulset virtual-node-eci --replicas=1
statefulset.apps/virtual-node-eci scaled

# kubectl -n kube-system get pod|grep virtual-node-eci
virtual-node-eci-0                                                1/1     Running   0          3d6h

等待一段时间,我们会发现那些vk节点变成NotReady状态。

# kubectl get no
NAME                      STATUS                        ROLES    AGE    VERSION
cn-hangzhou.192.168.1.1   Ready                         <none>   66d    v1.12.6-aliyun.1
cn-hangzhou.192.168.1.2   Ready                         <none>   66d    v1.12.6-aliyun.1
virtual-node-eci-0        Ready                         agent    3d6h   v1.11.2-aliyun-1.0.207
virtual-node-eci-1        NotReady,SchedulingDisabled   agent    3d6h   v1.11.2-aliyun-1.0.207
virtual-node-eci-2        NotReady,SchedulingDisabled   agent    3d6h   v1.11.2-aliyun-1.0.207
virtual-node-eci-3        NotReady,SchedulingDisabled   agent    70m    v1.11.2-aliyun-1.0.207
  • 手动删除NotReady状态的虚拟节点
# kubelet delete no virtual-node-eci-1 virtual-node-eci-2 virtual-node-eci-3
node "virtual-node-eci-1" deleted
node "virtual-node-eci-2" deleted
node "virtual-node-eci-3" deleted
# kubectl get no
NAME                      STATUS     ROLES    AGE    VERSION
cn-hangzhou.192.168.1.1   Ready      <none>   66d    v1.12.6-aliyun.1
cn-hangzhou.192.168.1.2   Ready      <none>   66d    v1.12.6-aliyun.1
virtual-node-eci-0        Ready      agent    3d6h   v1.11.2-aliyun-1.0.207
相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
目录
相关文章
|
15天前
|
存储 Kubernetes 负载均衡
CentOS 7.9二进制部署K8S 1.28.3+集群实战
本文详细介绍了在CentOS 7.9上通过二进制方式部署Kubernetes 1.28.3+集群的全过程,包括环境准备、组件安装、证书生成、高可用配置以及网络插件部署等关键步骤。
98 3
CentOS 7.9二进制部署K8S 1.28.3+集群实战
|
15天前
|
Kubernetes 负载均衡 前端开发
二进制部署Kubernetes 1.23.15版本高可用集群实战
使用二进制文件部署Kubernetes 1.23.15版本高可用集群的详细教程,涵盖了从环境准备到网络插件部署的完整流程。
31 2
二进制部署Kubernetes 1.23.15版本高可用集群实战
|
15天前
|
存储 Kubernetes 测试技术
k8s使用pvc,pv,sc关联ceph集群
文章介绍了如何在Kubernetes中使用PersistentVolumeClaim (PVC)、PersistentVolume (PV) 和StorageClass (SC) 来关联Ceph集群,包括创建Ceph镜像、配置访问密钥、删除默认存储类、编写和应用资源清单、创建资源以及进行访问测试的步骤。同时,还提供了如何使用RBD动态存储类来关联Ceph集群的指南。
31 7
|
15天前
|
存储 Kubernetes 数据安全/隐私保护
k8s对接ceph集群的分布式文件系统CephFS
文章介绍了如何在Kubernetes集群中使用CephFS作为持久化存储,包括通过secretFile和secretRef两种方式进行认证和配置。
22 5
|
15天前
|
Kubernetes 负载均衡 应用服务中间件
kubeadm快速构建K8S1.28.1高可用集群
关于如何使用kubeadm快速构建Kubernetes 1.28.1高可用集群的详细教程。
33 2
|
15天前
|
Kubernetes Linux API
CentOS 7.6使用kubeadm部署k8s 1.17.2测试集群实战篇
该博客文章详细介绍了在CentOS 7.6操作系统上使用kubeadm工具部署kubernetes 1.17.2版本的测试集群的过程,包括主机环境准备、安装Docker、配置kubelet、初始化集群、添加节点、部署网络插件以及配置k8s node节点管理api server服务器。
46 0
CentOS 7.6使用kubeadm部署k8s 1.17.2测试集群实战篇
|
18天前
|
API UED 开发者
超实用技巧大放送:彻底革新你的WinForms应用,从流畅动画到丝滑交互设计,全面解析如何在保证性能的同时大幅提升用户体验,让软件操作变得赏心悦目不再是梦!
【8月更文挑战第31天】在Windows平台上,使用WinForms框架开发应用程序时,如何在保持性能的同时提升用户界面的吸引力和响应性是一个常见挑战。本文探讨了在不牺牲性能的前提下实现流畅动画与交互设计的最佳实践,包括使用BackgroundWorker处理耗时任务、利用Timer控件创建简单动画,以及使用Graphics类绘制自定义图形。通过具体示例代码展示了这些技术的应用,帮助开发者显著改善用户体验,使应用程序更加吸引人和易于使用。
37 0
|
18天前
|
运维 Kubernetes Cloud Native
探索云原生:Kubernetes集群的部署与管理
【8月更文挑战第31天】 本文将带领读者深入了解云原生技术,特别是以Kubernetes为核心的集群部署和管理。文章不仅介绍了Kubernetes的基础概念和架构,还通过实际的代码示例展示了如何在云平台上搭建一个Kubernetes集群。我们将从基础的安装步骤到高级的服务部署,一步步揭示如何利用Kubernetes来简化容器化应用的管理与扩展。无论你是云原生新手还是希望提升现有技能的开发者,这篇文章都将成为你实践云原生技术的宝贵指南。
|
18天前
|
Kubernetes Cloud Native 应用服务中间件
云原生之旅:构建你的首个Kubernetes集群
【8月更文挑战第31天】在这个数字化迅速演进的时代,云原生技术如同星辰般璀璨。它不仅是企业数字化转型的引擎,更是开发者们探索创新的乐园。本文将带你开启一场云原生的奇妙旅程,从零开始,一步步构建属于你自己的Kubernetes集群。想象一下,当你的应用在云端自如地伸缩、滚动更新时,那份成就感和掌控感,是不是已经让你跃跃欲试了呢?那就让我们开始吧!
|
18天前
|
Kubernetes Cloud Native JavaScript
云原生之旅:Kubernetes 集群搭建与应用部署实践
【8月更文挑战第31天】云原生技术正在改变软件开发和运维的方式,而Kubernetes作为其核心组件之一,提供了一个强大的平台来编排容器化的应用。本文将引导你了解如何搭建一个基本的Kubernetes集群,并通过一个简单的Node.js应用示例,展示如何在集群中部署和管理应用。我们将从零开始,逐步构建起对Kubernetes的直观理解,并在实践中学习其核心概念。

相关产品

  • 容器服务Kubernetes版