k8s集群中金丝雀发布 + 声明式资源管理yaml

news/2024/12/5 5:08:34/

一、K8S常见的发布方式

旨在降低发布风险并提高发布速度

1、蓝绿发布

两套环境(设备)交替升级,旧版本保留一定时间便于回滚

优点:对用户无感,是最安全的发布方式,业务稳定

缺点:需要两套系统,对资源要求比较高,成本特别高
根据比例将老版本升级,例如80%用户访问是老版本,20%用户访问是新版本

2、灰度发布(金丝雀发布) 

特点:对自动要求比较高,对比起来系统更加稳定发布,如果遇到问题可以减少影响范围

先更新一部分pod,然后再暂停更新

安排一小部分的用户流量去访问更新的pod来进行测试,高比例的流量(如95%)继续走旧版本,而低比例的流量(如5%)被切换到新版本。当测试没问题后再扩大比例,直到全部更新完成为止(测试服,体验服

类似于“金丝雀”在煤矿中用来检测有害气体的角色

3、滚动发布 

按批次停止老版本实例,启动新版本实例。

特点:节约资源,用户无感,但是部署和回滚的速度慢

按照他的比例,一部分一部分滚动更新,是k8s默认的更新机制

不用创建一定比例的pod;先创建,确定没问题后,删除旧日版本的pod

滚动发布涉及整个服务器集群的逐步升级,而金丝雀发布则更侧重于一小部分用户进行初步测试和验证。

简单的说

滚动发布是一个持续的过程,涉及分批升级服务器或实例,直到所有实例都升级到新版本。

而金丝雀发布则是一个分阶段的过程,首先进行小范围的测试,然后逐渐扩大发布范围。

二、金丝雀发布详细+部署

Deployment控制器支持自定义控制更新过程中的滚动节奏,如“暂停(pause)”或“继续(resume)”更新操作。比如等待第一批新的Pod资源创建完成后立即暂停更新过程,此时,仅存在一部分新版本的应用,主体部分还是旧的版本

然后,再筛选一小部分的用户请求路由到新版本的Pod应用,继续观察能否稳定地按期望的方式运行。确定没问题之后再继续完成余下的Pod资源滚动更新,否则立即回滚更新操作。这就是所谓的金丝雀发布

金丝雀发布的思想则是将少量的请求引流到新版本上,因此部署新版本服务只需极小数的机器。验证新版本符合预期后,逐步调整流量权重比例,使得流量慢慢从老版本迁移至新版本,期间可以根据设置的流量比例,对新版本服务进行扩容,同时对老版本服务进行缩容,使得底层资源得到最大化利用

创建一个命名空间隔离

kubectl create namespace test

创建deployment

因为我们刚刚删除了,所有我们重新创建一个

kubectl create deployment nginx-yc --image=nginx:1.14 --port=80 --replicas=3 -n test

暴露服务 (创建svc)

kubectl expose deployment nginx-yc --port=80 --target-port=80 --name=nginx-service -n test --type=NodePort

更新deployment的版本,并配置暂停deployment(多一个新版本)

  1. 更新名为"nginx-yc"的部署(Deployment)中的 "nginx" 容器的镜像版本为"nginx:1.22

  2. 暂停名为"nginx-yc"的部署的滚动更新,这意味着在执行这个命令后,将不会继续推进新的副本集,并且当前的副本集将保持不变

  3.  查看在 test 命名空间下名为 nginx-yc 的部署的更新(rollout)状态

kubectl set image deployment/nginx-yc nginx=nginx:1.22 -n test && kubectl rollout pause deployment nginx-yc -n test
 
kubectl rollout status deployment nginx-yc -n test

观察更新状态

开启另一个窗口查看 pod 信息

监控更新的过程,可以看到已经新增了一个资源,但是并未按照预期的状态去删除一个旧的资源,就是因为使用了 pause 暂停命令

-w 选项,它会使命令进入监视模式,实时显示资源的变化情况

kubectl get pod -w -n test

查看信息 

kubectl get pod -owide -n test

查看新版本

curl -I

其他的

如何做新旧版本分离呢

分阶段访问

在金丝雀发布中,将流量分流到新旧版本的这个过程被称为分阶段访问(Staged Access),也可以称为阶段性流量调度(Staged Traffic Shifting)。即将流量逐步引导到新版本的过程,以确保新版本的稳定性和可靠性。

默认情况下,访问 server 流量将会负载均衡至4个实例上,新增 server 实现新的实例与旧实例访问分流:

在开始的时候我们创了一个svc

查看kubectl get endpoints -n tesst

发现在这个service有四个地址,我们再创一个svc,并且把新版本放到新svc,老svc存老svc就可以了

创建新svc

kubectl expose deployment nginx-yc --port=80 --target-port=80 --name=new-nginx-service -n test --type=NodePort

现在要把svc对应放入

kubectl get svc -n test new-nginx-service -oyaml

或者

kubectl edit svc new-nginx-service -n test

复制内容

复制内容,替换标签

kubectl get pod --show-labels  -n test

对应

vim new-nginx.yaml

删除new-nginx-sevice 并且用申明式写

kubectl delete svc  new-nginx-service -n tes

kubectl apply -f new-nginx.yaml  

老版本同样过程

kubectl edit svc nginx-service -n test

#vim old-nginx.yaml

kubectl delete svc  nginx-service -n test

kubectl apply -f old-nginx.yaml -n test

测试

总结: 简单的来说就把看kubectl edit svc内容找新老两个svc(当一个模版),对应不同名称在kubectl get pod --show-lables的LABELS中查看不同的名称放到spec.selector下的标签名称用键值对去写,本质是用svc访问新旧的pod

当业务没有问题

确保更新的pod没问题了,继续更新

kubectl rollout resume deployment/nginx-yc -n test
 
kubectl rollout status deployment nginx-yc -n test

测试下新旧版本访问

旧service无法访问,由于更新了新版本,现在由新的版本提供服务

kubectl get pods,svc -n test -o wide

三、声明式管理方法

适合于对资源的修改操作
声明式资源管理方法依赖于资源配置清单文件对资源进行管理
资源配置清单文件有两种格式:yaml(人性化,易读),json(易于api接口解析)
对资源的管理,是通过事先定义在统一资源配置清单内,再通过陈述式命令应用到k8s集群里

语法格式:kubectl create/apply/delete -f xxxx.yaml


3.1、解释资源配置清单

kubectl explain deployment.metadata
 
kubectl explain service.metadata
 
修改资源配置清单并应用
离线修改:
修改yaml文件,并用 kubectl apply -f xxxx.yaml 文件使之生效
注意:当apply不生效时,先使用delete清除资源,再apply创建资源
 
kubectl get service -n test new-nginx-service  -o yaml > nginx-svc.yaml
vim nginx-svc.yaml                #修改port: 8080
kubectl delete -f nginx-svc.yaml
kubectl apply -f nginx-svc.yaml
kubectl get svc
 
在线修改:
直接使用 kubectl edit service nginx 在线编辑资源配置清单并保存退出即时生效(如port: 888)
PS:此修改方式不会对yaml文件内容修改
 
 
删除资源配置清单


陈述式删除:
kubectl delete service nginx
 
声明式删除:
kubectl delete -f nginx-svc.yaml

3.2、常用字段含义


每一个控制器通常对应一种资源类型,如Deployment、Service等等,在YAML中,我们可以指定这些资源的状态以及如何管理它们

Deployment控制器在YAML文件中的定义可能包括:

Metadata:例如控制器的名称和命名空间
Spec:例如应用的副本数量,以及图像的URL

spec 是 "specification"(规范)的缩写,它用于定义资源的期望状态或配置
Selector:例如确定哪些Pods应由该控制器管理的标签
Template:例如Pod的基本设计

3.3、快速编写YAML文件

--dry-run——读取而不创建
kubectl run nginx-cs --image=soscscs/myapp:v1 --port=80 --dry-run=clientkubectl create deployment nginx-dpm --image=soscscs/myapp:v1 --port=80 --replicas=3 --dry-run=client
-o yaml——查看生成yaml格式
kubectl run nginx-cs --image=soscscs/myapp:v1 --port=80 --dry-run=client -o yaml

查看字段帮助信息,可一层层的查看相关资源对象的帮助信息

kubectl explain pods.spec.containers

3.4、示例

需求

资源名称:my-nginx-yc

命名空间:my-yc

容器镜像:nginx:1.21

容器端口:80

标签:yc-: my-bq

创建 server去关联上面的pod

nodePort: 32037

结果:首先修改页面:welcome to china 对外访问, 输入地址就能访问

 vim my-nginx-yc-deployment.yaml

apiVersion: apps/v1
kind: Deployment
metadata:name: my-nginx-ycnamespace: my-yclabels:yc-: my-bq
spec:replicas: 1selector:matchLabels:app: my-nginx-yctemplate:metadata:labels:app: my-nginx-ycyc-: my-bqspec:containers:- name: nginximage: nginx:1.21ports:- containerPort: 80# Add an init container to modify the default Nginx pageinitContainers:- name: modify-nginx-pageimage: busybox:1.32command: ["sh", "-c", "echo 'welcome to china' > /tmp/index.html && cp /tmp/index.html /usr/share/nginx/html/index.html"]volumeMounts:- name: nginx-htmlmountPath: /usr/share/nginx/htmlvolumes:- name: nginx-htmlemptyDir: {}

创建 Service

 vim my-nginx-yc-deployment.yaml

# my-nginx-yc-service.yaml
apiVersion: v1
kind: Service
metadata:name: my-nginx-ycnamespace: my-yc
spec:selector:app: my-nginx-ycports:- protocol: TCPport: 80targetPort: 80nodePort: 32037type: NodePort

kubectl apply -f my-nginx-yc-deployment.yaml
kubectl apply -f my-nginx-yc-service.yaml 

四、yaml介绍语法格式

  • 通过缩进表示层级关系
  • 不能使用Tab进行缩进,只能使用空格缩进(一般缩进两个空格)
  • 字符后缩进一个空格,比如" : "、" , "等
  • 使用" --- "表示新的yaml文件的开头
  • 使用" # "表示注释

此章内容有点赶,后期会修改


http://www.ppmy.cn/news/1552474.html

相关文章

蓝桥杯准备训练(lesson1,c++方向)

前言 报名参加了蓝桥杯(c)方向的宝子们,今天我将与大家一起努力参赛,后序会与大家分享我的学习情况,我将从最基础的内容开始学习,带大家打好基础,在每节课后都会有练习题,刚开始的练…

【微服务】http客户端Feign

一、Fegin替代RestTemplate RestTemplate:代码可读性差,编程体验不统一,参数复杂URL难以维护。 Feign:是一个声明式的http客户端,官方地址: https://github.com/OpenFeign/feign,其作用就是帮助我们优雅的…

mysql--二进制安装编译安装yum安装

二进制安装 创建用户和组 [rootlocalhost ~]# groupadd -r -g 306 mysql [rootlocalhost ~]# useradd -r -g 306 -u 306 -d /data/mysql mysql 创建文件夹并添加所属文件用户和组 [rootlocalhost ~]# mkdir -p /data/mysql [rootlocalhost ~]# chown mysql:mysql /data/mysql …

【NLP高频面题 - LLM架构篇】旋转位置编码RoPE相对正弦位置编码有哪些优势?

【NLP高频面题 - LLM架构篇】旋转位置编码RoPE相对正弦位置编码有哪些优势? 重要性:⭐⭐⭐ 💯 NLP Github 项目: NLP 项目实践:fasterai/nlp-project-practice 介绍:该仓库围绕着 NLP 任务模型的设计、训练…

Java 中的 remove 方法深度解析

在 Java 编程中,remove方法是一个经常被使用的操作。它可以用于从各种数据结构中移除特定的元素,帮助我们有效地管理和操作数据。本文将深入探讨 Java 中的remove方法,包括在不同数据结构中的应用、使用场景、注意事项以及性能考虑等方面。 …

RouterOS ROSV7 基于域名的分流实现

使用RouterOS进行分流,网上早已有大神进行了实现,比较普通的是基于IP的分流,基于域名的分流也要,不过是V6的,这里总结了V7基于域名的分流方式,要比V6方便许多 本人也是看了多篇文章有所启发,比较…

elasticsearch修改Ik分词器源码实现基于MySQL更新分词

本文主要记录如何修改Ik分词器源码来实现基于MySQL数据库更新分词,所有步骤均为本人实际操作验证。如果你也刚好刷到这篇文章,希望对你有所帮助。 使用过Ik分词器的应该都知道,它提供了三种配置热词词库的方式: Ik内置词库Ik外置…

mysql 更新字段

更新字段 UPDATE familydb.familyinfo SET familyName cuicuis home WHERE familyName homenew; 同时更新相同字段不同值 UPDATE familydb.familyinfo SET familyName CASE WHEN familyName homenew THEN cuicuis home WHEN familyName lala THEN 17611111118s home ELSE…