在k8s中,我们使用pod对外提供服务,这个时候,需要以下两种情形需要关注:

  • pod因为不明原因挂掉,导致服务不可用
  • pod在高负载的情况下,不能支持我们的服务

如果人工监控pods,人工调整副本,那么这个工作量无疑是巨大的,但是k8s已经有了相应的机制来对应了。

HPA 弹性伸缩 (Horizontal Pod Autoscaler)

PHA

  • HPA全称是Horizontal Pod Autoscaler,中文意思是POD水平自动伸缩.

  • 可以基于 CPU 利用率自动扩缩 ReplicationController、Deployment、ReplicaSet 和 StatefulSet 中的 Pod 数量
  • 除了 CPU 利用率,内存占用外,也可以基于其他应程序提供的自定义度量指标来执行自动扩缩。

  • Pod 自动扩缩不适用于无法扩缩的对象,比如 DaemonSet。

  • Pod 水平自动扩缩特性由 Kubernetes API 资源和控制器实现。资源决定了控制器的行为。

  • 控制器会周期性的调整副本控制器或 Deployment 中的副本数量,以使得 Pod 的平均 CPU 利用率与用户所设定的目标值匹配。

PHA工作机制

HorizontalPodAutoscaler 控制 Deployment 及其 ReplicaSet 的规模

Kubernetes 将水平 Pod 自动扩缩实现为一个间歇运行的控制回路(它不是一个连续的过程)。间隔由 kube-controller-manager 的 --horizontal-pod-autoscaler-sync-period 参数设置(默认间隔为 15 秒)。

在每个时间段内,控制器管理器都会根据每个 HorizontalPodAutoscaler 定义中指定的指标查询资源利用率。 控制器管理器找到由 scaleTargetRef 定义的目标资源,然后根据目标资源的 .spec.selector 标签选择 Pod, 并从资源指标 API(针对每个 Pod 的资源指标)或自定义指标获取指标 API(适用于所有其他指标)。

  • 对于按 Pod 统计的资源指标(如 CPU),控制器从资源指标 API 中获取每一个 HorizontalPodAutoscaler 指定的 Pod 的度量值,如果设置了目标使用率,控制器获取每个 Pod 中的容器资源使用情况, 并计算资源使用率。如果设置了 target 值,将直接使用原始数据(不再计算百分比)。 接下来,控制器根据平均的资源使用率或原始值计算出扩缩的比例,进而计算出目标副本数。
  • 如果 Pod 使用自定义指示,控制器机制与资源指标类似,区别在于自定义指标只使用原始值,而不是使用率。
  • 如果 Pod 使用对象指标和外部指标(每个指标描述一个对象信息)。 这个指标将直接根据目标设定值相比较,并生成一个上面提到的扩缩比例。 在 autoscaling/v2 版本 API 中,这个指标也可以根据 Pod 数量平分后再计算。

PHA的常见用途是将其配置为从聚合API(metrics.k8s.iocustom.metrics.k8s.io 或 external.metrics.k8s.io)获取指标。 metrics.k8s.io API 通常由名为 Metrics Server 的插件提供,需要单独启动。

PHA控制器访问支持扩缩容的相应工作负载资源,如:Deployment和StatefulSet。 这些资源每一个都有一个scale的子资源,该接口允许你动态设置副本的数量并检查他们的每个当前状态。

算法:

期望副本数 = ceil[当前副本数 * (当前指标 / 期望指标)]

HPA API对象

HPA的API有三个版本

APA版本 描述
autoscaling/v1 只支持基于CPU指标的缩放
autoscaling/v2beta1 支持Resource Metrics(资源指标,如pod的CPU)和Custom Metrics(自定义指标)的缩放;
autoscaling/v2beta2 支持Resource Metrics(资源指标,如pod的CPU)和Custom Metrics(自定义指标)和ExternalMetrics(额外指标)的缩放。

kubectl对HPA的支持

通过 kubectl create 命令创建一个 HPA 对象
通过 kubectl get hpa 命令来获取所有 HPA 对象
通过 kubectl describe hpa 命令来查看 HPA 对象的详细信息
通过 kubectl delete hpa 命令删除对象。
#将会为名 为 foo 的 ReplicationSet 创建一个 HPA 对象, 目标 CPU 使用率为 80%,副本数量配置为 2 到 5 之间
kubectl autoscale rs foo --min=2 --max=5 --cpu-percent=80

PHA演示:

apiVersion: apps/v1
kind: Deployment
metadata:
name: php
spec:
selector:
matchLabels:
run: php-apache
replicas: 1
template:
metadata:
labels:
run: php-apache
spec:
containers:
- name: php-apache
image: nginx
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

查看命令:

[root@k8s-master01 ns-slx-study]# kubectl get hpa
NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE
php Deployment/php 0%/50% 1 10 3

找到pod对应的ip:

[root@k8s-master01 ns-slx-study]# kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
busybox 1/1 Running 0 21m 172.25.3.208 k8-node1 <none> <none>
php-5b6df965db-7rx5j 1/1 Running 0 9m20s 172.25.244.225 k8s-master01 <none> <none>
php-5b6df965db-vvjd6 1/1 Running 0 9m15s 172.29.131.33 k8s-node2 <none> <none>

增加负载:

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://172.29.131.33; done

然后观察hpa的状态:

kubectl get hpa php --watch

就会看到自动水平扩容,然后停掉压测,之后就会慢慢的回到初始状态

还有其他事情,详细可以参考: HorizontalPodAutoscaler 演练 | Kubernetes

HPA 弹性伸缩的更多相关文章

  1. Kubernetes使用metric-server让HPA弹性伸缩运行

    监控架构概述 kubernetes监控指标大体可以分为两类:核心监控指标和自定义指标,核心监控指标是kubernetes内置稳定可靠监控指标,早期由heapster完成,现由metric-server ...

  2. Kubernetes 弹性伸缩全场景解析(三) - HPA 实践手册

    在上一篇文章中,给大家介绍和剖析了 HPA 的实现原理以及演进的思路与历程.本文我们将会为大家讲解如何使用 HPA 以及一些需要注意的细节. autoscaling/v1 实践 v1 的模板可能是大家 ...

  3. Kubernetes 弹性伸缩全场景解读(二)- HPA 的原理与演进

    前言 在上一篇文章 Kubernetes 弹性伸缩全场景解析 (一):概念延伸与组件布局中,我们介绍了在 Kubernetes 在处理弹性伸缩时的设计理念以及相关组件的布局,在今天这篇文章中,会为大家 ...

  4. Kubernetes 弹性伸缩HPA功能增强Advanced Horizontal Pod Autoscaler -介绍部署篇

    背景 WHAT(做什么) Advanced Horizontal Pod Autoscaler(简称:AHPA)是kubernetes中HPA的功能增强. 在兼容原生HPA功能基础上,增加预测.执行模 ...

  5. 在腾讯云容器服务 TKE 中利用 HPA 实现业务的弹性伸缩

    在 TKE 上利用 HPA 实现业务的弹性伸缩 概述 Kubernetes Pod 水平自动扩缩(Horizontal Pod Autoscaler,以下简称 HPA)可以基于 CPU 利用率.内存利 ...

  6. Effective HPA:预测未来的弹性伸缩产品

    作者 胡启明,腾讯云专家工程师,专注 Kubernetes.降本增效等云原生领域,Crane 核心开发工程师,现负责成本优化开源项目 Crane 开源治理和弹性能力落地工作. 余宇飞,腾讯云专家工程师 ...

  7. Kubernetes 弹性伸缩全场景解析 (四)- 让核心组件充满弹性

    前言 在本系列的前三篇中,我们介绍了弹性伸缩的整体布局以及HPA的一些原理,HPA的部分还遗留了一些内容需要进行详细解析.在准备这部分内容的期间,会穿插几篇弹性伸缩组件的最佳实践.今天我们要讲解的是 ...

  8. Kubernetes 弹性伸缩全场景解析 (一)- 概念延伸与组件布局

    传统弹性伸缩的困境 弹性伸缩是Kubernetes中被大家关注的一大亮点,在讨论相关的组件和实现方案之前.首先想先给大家扩充下弹性伸缩的边界与定义,传统意义上来讲,弹性伸缩主要解决的问题是容量规划与实 ...

  9. Kubernetes 弹性伸缩全场景解读(五) - 定时伸缩组件发布与开源

    作者| 阿里云容器技术专家刘中巍(莫源) 导读:Kubernetes弹性伸缩系列文章为读者一一解析了各个弹性伸缩组件的相关原理和用法.本篇文章中,阿里云容器技术专家莫源将为你带来定时伸缩组件  kub ...

  10. Kubernetes 弹性伸缩全场景解析 (一):概念延伸与组件布局

    传统弹性伸缩的困境 弹性伸缩是 Kubernetes 中被大家关注的一大亮点,在讨论相关的组件和实现方案之前.首先想先给大家扩充下弹性伸缩的边界与定义,传统意义上来讲,弹性伸缩主要解决的问题是容量规划 ...

随机推荐

  1. 统计学习导论(ISLR)(三):线性回归(超详细介绍)

    统计学习导论(ISLR) 参考资料: The Elements of Statistical Learning An Introduction to Statistical Learning 统计学习 ...

  2. vue基础 · 过滤器(3)

    过滤器:filter Vue.js 允许你自定义过滤器,可被用于一些常见的文本格式化.过滤器可以使用在2个地方:{{ }} 插值 和 v-bind 表达式(后者从 2.1.0+ 开始支持) 过滤器分为 ...

  3. JavaScript异步概念及与c#异步的区别

    JS的异步操作函数往往是通过回调函数来实现异步任务的结果处理,在ES6之前如setTimeout函数和异步AJAX编程: 在ES6规范后Promise 类对象使得书写异步任务更加容易,返回Promis ...

  4. JQuery 页面滚动至指定元素位置

    $(window).scrollTop($("#id").offset().top - 20);

  5. Python3之并发(四)---线程锁

    一.线程锁 保证多线程数据的一致性,对锁内的资源进行锁定,同一时间只能有一个线程来修改共享的数据多个线程同时加了同一个锁对象时,先获取到锁的线程会继续运行,未获取到锁的线程会处于堵塞状态,直到前面的线 ...

  6. Docker info 查看报错 WARNING: No swap limit support 解决

    docker可以通过启动命令来限制容器可以使用的最大物理内存和swap,但是通常在使用这些命令的时候经常会碰到"WARNING: No swap limit support"警告 ...

  7. Unity3D发布Android注意事项

    当你制作完一款游戏,准备发布Android平台时,需要进行一些设置.如下: 一.设置AndroidSDK路级和JDK路径 AndroidSDK目录可以通过AndroidStudio查看,如下: 这个路 ...

  8. 【电脑】电脑windows10添加开机启动项

    1.添加开机启动项,首先按组合键"win+R"唤出运行窗口,输入"shell:startup"点击确认,打开启动项文件夹. 2.将需要设置为开机启动的软件快捷方 ...

  9. Windows 10 ~ Jenkins 安装

    首先: jenkins是由java写的,所以在使用之前请安装好JDK(最好安装JDK1.8) 下载jenkins.war包并放到一个自己创建的目录D:\jenkins下:https://mirrors ...

  10. python笔记:list--pop与remove的区别

    正常情况下: # coding=utf-8 fruit = ['apple', 'pear', 'banana' ] #指定索引删除 fruit.pop(0) #符合元素删除,具体数值 fruit.r ...