K8S HPA 弹性水平扩缩容 Pod 详解

文章目录

  • 1、前置准备
  • 2、需求场景
  • [3、Scale 静态扩缩容](#3、Scale 静态扩缩容)
    • [3.1、创建 Deployment 脚本](#3.1、创建 Deployment 脚本)
    • [3.2、Scale 扩缩容](#3.2、Scale 扩缩容)
  • [3、HPA 自动扩缩容](#3、HPA 自动扩缩容)
    • [3.1、安装 Metrics](#3.1、安装 Metrics)
    • [3.2、创建 Deployment 演示案例](#3.2、创建 Deployment 演示案例)
    • [3.3、创建 HPA](#3.3、创建 HPA)
    • [3.4、触发 HPA 自动扩缩容](#3.4、触发 HPA 自动扩缩容)

1、前置准备

本次案例演示,我选择了阿里云ECS(抢占式)搭建了 K8S 1主2从集群,资源配置规格如下:

  • 主节点 k8s-master:4核8G、40GB硬盘、CentOS7.9(内网IP:172.16.0.172)
  • 从节点 k8s-node1: 4核8G、40GB硬盘、CentOS7.9(内网IP:172.16.0.173)
  • 从节点 k8s-node2: 4核8G、40GB硬盘、CentOS7.9(内网IP:172.16.0.174)

K8S集群构建参考:https://blog.csdn.net/weixin_46594796/article/details/139649056

2、需求场景

在企业级生产环境中,经常会遇到某个服务容器性能不足的情况,例如:CPU、内存飚高,这种情况一般会想到对该服务进行横向扩容,创建更多的服务容器来分摊工作量。或者说容器资源过剩,想要把资源节省出来,通常这种情况需要我们去手动的进行扩缩容。动态调整应用实例数量以满足业务需求,同时优化资源利用率。

  • 突发流量:当应用访问量突然激增(如促销活动、热点事件),增加Pod副本数,避免服务过载或崩溃。
  • 低峰时段:在流量低谷时减少Pod数量,节省资源成本。

3、Scale 静态扩缩容

3.1、创建 Deployment 脚本

在K8S环境中,我们一般使用 scale 命令来对 Pod 资源进行手动扩缩容,首先先通过 Deployment 创建3个 Niginx Pod,deploy-nginx.yaml内容如下:

shell 复制代码
mkdir /etc/k8s
cat > /etc/k8s/deploy-nginx.yaml <<-'EOF'
apiVersion: apps/v1
kind: Deployment
metadata:
  name: deploy-nginx
spec:
  selector:
    matchLabels:
      app: nginx
  replicas: 3
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: container-nginx
        image: nginx:1.20.2-alpine
        ports:
        - containerPort: 80
EOF

执行 delopment 文件:

shell 复制代码
kubectl apply -f /etc/k8s/deploy-nginx.yaml

此时可以看到,3个Pod容器已经成功部署完成了:

3.2、Scale 扩缩容

上面脚本执行完毕后,已经自动创建3个Pod了,想要把3个Pod扩容为5个,就需要使用 scale 命令手动执行:

shell 复制代码
kubectl scale deploy deploy-nginx --replicas=5

就可以看到,直接将容器数量扩容为5个了:

缩容只需要把数字调小即可,这里就不演示了。

但是这样终归是需要运维人员手动的进行调整,有些特殊场景流量高峰期可能很随机,这样在通过人工进行处理就不太合适了,有没有可以根据资源使用情况自动扩缩容Pod的方案,官方提供了就是 HPA

3、HPA 自动扩缩容

3.1、安装 Metrics

首先,通过命令查看哪些 Pod 占用资源比较高:kubectl top pods,执行完毕后可以发现,错误日志:error: Metrics API not available,说明没有安装Metrics

首先在主节点上下载配置文件:

shell 复制代码
wget https://xuzhibin-bucket.oss-cn-beijing.aliyuncs.com/k8s/metric-server.yaml

这个配置文件中已经被修改过,相比于官方的配置文件有两处修改:

  1. 处理加密证书不匹配问题(生产环境需要配置好证书的)
  2. Metrics镜像改成了使用阿里云,否则无法下载

这个时候,就可以直接部署 Metrics:

shell 复制代码
kubectl apply -f metric-server.yaml

最后通过该命令查看,部署是否完毕:

shell 复制代码
kubectl get po -n kube-system | grep metrics-server

3.2、创建 Deployment 演示案例

演示案例 deployment 脚本(svc-hpa.yaml),这是由Apache提供的,配置如下:

shell 复制代码
mkdir -p /etc/sca/hpa
cd /etc/sca/hpa
cat > svc-hpa.yaml <<-'EOF'
apiVersion: apps/v1
kind: Deployment
metadata:
  name: php-apache
spec:
  selector:
    matchLabels:
      run: php-apache
  template:
    metadata:
      labels:
        run: php-apache
    spec:
      containers:
      - name: php-apache
        image: deis/hpa-example
        ports:
        - containerPort: 80
        resources:
          limits:
            cpu: 500m
          requests:
            cpu: 200m
---
apiVersion: v1
kind: Service
metadata:
  name: php-apache
  labels:
    run: php-apache
spec:
  ports:
  - port: 80
  selector:
    run: php-apache
EOF

启动演示案例容器,就会创建一个Pod:

shell 复制代码
kubectl apply -f svc-hpa.yaml

这里面主要注意的是,有个资源限定的配置:表示对pod容器资源的限定,启动最少占用0.2核CPU,最大占用0.5核CPU:

3.3、创建 HPA

创建HPA需要使用 autoscale 命令,这里--cpu-percent=50说明是50%,结合上面最大占用500m(0.5核)CPU,所以如果当前Pod占用了0.25核CPU,就会对Pod容器进行扩容,最多可以达到10个,但不会少于1个。

shell 复制代码
kubectl autoscale deployment php-apache --cpu-percent=50 --min=1 --max=10

⚠️ 如果不再使用HPA,可以用下述命令进行删除:

shell 复制代码
kubectl delete hpa php-apache

3.4、触发 HPA 自动扩缩容

先新开一个窗口,通过下述命令监听一下HPA状态:

shell 复制代码
kubectl get hpa php-apache --watch

此时没有请求量,还是比较平静的:

在新开一个窗口,通过 Linux 系统提供的工具BusyBox,每过0.1s发送请求,模拟大流量场景让HPA触发扩容,通过下述命令:

shell 复制代码
kubectl run -i --tty load-generator --rm --image=busybox:1.28 --restart=Never -- /bin/sh -c "while sleep 0.01; do wget -q -O- http://php-apache; done"

过了一段时间,可以看到窗口展示大量接口调用:

这个时候再去看监控窗口,发现确实开始自动扩容了:只要过了50%,Pod副本数量就开始不断新增,随着Pod增多,CPU占用也逐渐下降了,发现8个Pod就能控制在50%以下,就不会继续扩容了。

此时已经扩容到8个容器了:

这个时候把调用脚本停掉,再看监控日志会发现,Pod自动被逐渐销毁,但是并不是马上进行缩容,CPU使用率降下来后,他会先等待一会儿,然后才开始销毁Pod容器,原因是担心只是短暂流量跌下来,会给一点缓冲时间,重复创建销毁容器的代价太高了!