28-k8s集群中-StatefulSets控制器(进阶知识)

一、statefullsets控制器概述

1,举例

假如,我们有一个deployment资源,创建了3个nginx的副本,对于nginx来讲,它是不区分启动或者关闭的先后顺序的,也就是"没有特殊状态"的一个服务,也成"无状态服务",3个副本,谁先启动、谁后启动都没有关系,它只是用来web服务分发使用的一个工具而已;

那么反之,有没有需要有启动顺序、关闭顺序这样的"有状态服务"呐?答案肯定是有啊;

【访问顺序问题】,再假如,再企业当中,的MySQL主从数据库架构中,假设是2主1从数据架构,架构本身是区分master和slave角色的,在构建主从关系的时候,master必须先启动,不然slave没办法加入到主从架构中,所以需要有相同副本服务启动的先后顺序;

【副本独立的存储问题】,我们知道,MySQL是不能多服务共享数据目录的,所以在拉去多副本的"有状态服务"时,存储独立化就成了问题,也就是说,一个pod副本对应一个单独的存储目录。

【固定的访问地址问题】,还拿MySQL做举例,我们需要对有状态服务,有固定寻址的能力,我们知道,pod删除重新拉取后,ip就会发生变化,那么对于mysql服务来说,副本的每个pod都需要有精准的、不变的唯一标识,不然主从架构等问题,一旦重新新启动pod,就会彻底摧毁架构,也就是说pod副本删除重新拉取后,能够精准的找到对应原来的服务;

2,总结:

对于同一个deployment或者其他资源创建的pod副本,我们在使用"有状态服务"的副本pod时,有着三个需求:

1,副本启动、停止要求有顺序;

2,每个副本需要有独立的存储目录空间;

3,副本重新拉起,能够有方式在其改变ip的情况下还能精准的找到对应副本;

那么以上,也是statefulsets控制器能够解决的问题;

二、启停顺序与headless网络唯一标识

1,创建一个"无头"svc资源

· 编辑无头服务svc资源清单

无头svc服务,就是没有ClusterIP的svc资源;

root@k8s231 statefulsets\]# cat headless.yaml apiVersion: v1 kind: Service metadata: name: xinjizhiwa-headless spec: ports: - port: 80 name: web # 将clusterIP字段设置为None表示为一个无头服务headless,即svc将不会分配VIP。 clusterIP: None selector: k8s: xinjizhiwa

· 创建无头svc服务

root@k8s231 statefulsets\]# kubectl apply -f headless.yaml

2,创建statefullsets使用无头服务

· 编辑statefulsets资源清单

声明使用无头svc

root@k8s231 statefulsets\]# vim staefulsets.yaml apiVersion: apps/v1 kind: StatefulSet metadata: name: xinjizhiwa-web spec: selector: matchLabels: k8s: xinjizhiwa #声明无头服务的service; serviceName: xinjizhiwa-headless replicas: 3 template: metadata: labels: k8s: xinjizhiwa spec: containers: - name: c1 image: nginx:1.20.1-alpine

root@k8s231 statefulsets\]# kubectl apply -f staefulsets.yaml

3,验证无头服务机启停顺序

· 查看pod

发现破的名称,是按照statefulsets资源的名称加上数字顺序排列生成的;

root@k8s231 statefulsets\]# kubectl get pods -o wide

· 查看无头svc

root@k8s231 statefulsets\]# kubectl get svc

· 创建一个用来测试【pod网络唯一标识 】的pod容器

root@k8s231 statefulsets\]# kubectl run -it dns-test --rm --image=alpine:latest -- sh / # / # for i in \`seq 0 2\`;do ping xinjizhiwa-web-${i}.xinjizhiwa-headless.default.svc.xinjizhiwa.com -c3;done

网路唯一标识:

【pod的名称】.【无头服务的名称】.【名称空间】.【svc】.【集群DNS域名】

拓展:这个就是集群DNS域名的所在位置,可以通过这里来查看;

root@k8s231 deploy\]# vim /var/lib/kubelet/config.yaml ....... clusterDNS: - 10.200.0.10 clusterDomain: xinjizhiwa.com

root@k8s231 deploy\]# kubectl delete pods --all

删除pod,等待重新拉取

· 结论

通过ping唯一标识,ping通后,删除pod,在ping唯一标识还可以ping通,查看pod的ip已经重新拉起后改变了,可还是ping通了,就证明,唯一标识成功;

三、StatefulSets副本独立存储

1,创建一个无头服务

root@k8s231 vol\]# vim headless.yaml apiVersion: v1 kind: Service metadata: name: xjzw-headless spec: ports: - port: 80 name: web clusterIP: None selector: k8s: xjzw \[root@k8s231 vol\]# kubectl apply -f headless.yaml

查看无头svc

root@k8s231 vol\]# kubectl get svc

2,创建StatefulSets资源

声明独立存储

root@k8s231 vol\]# cat statefulset.yaml apiVersion: apps/v1 kind: StatefulSet metadata: name: xjzw-web spec: selector: matchLabels: k8s: xjzw serviceName: xjzw-headless replicas: 3 #声明创建pvc;存储卷卷申请模板,会为每个Pod去创建唯一的pvc并与之关联哟! volumeClaimTemplates: - metadata: name: data spec: accessModes: \[ "ReadWriteOnce"

声明咱们自定义的动态存储类,即storageclass动态存储资源。

storageClassName: "managed-nfs-storage"

resources:

requests:

storage: 2Gi

template:

metadata:

labels:

k8s: xjzw

spec:

containers:

  • name: nginx

image: nginx:1.20.1-alpine

volumeMounts:

  • name: data

mountPath: /usr/share/nginx/html

root@k8s231 vol\]# kubectl apply -f statefulset.yaml

查看statefulsets资源

root@k8s231 vol\]# kubectl get statefulsets NAME READY AGE xinjizhiwa-web 3/3 55m xjzw-web 3/3 17s

3,验证是否有独立存储

查看nfs挂载地址,可以看到,创建出来三个存储地址,证明3个副本都有自己的独立存储空间了;

root@k8s231 vol\]# kubectl exec -it xjzw-web-0 -- sh / # echo 111111111 \> /usr/share/nginx/html/index.html / # exit \[root@k8s231 vol\]# kubectl exec -it xjzw-web-1 -- sh / # echo 222222222 \> /usr/share/nginx/html/index.html / # exit \[root@k8s231 vol\]# kubectl exec -it xjzw-web-2 -- sh / # echo 333333333 \> /usr/share/nginx/html/index.html / # exit

证明三个pod副本的存储是相互独立的

至此,咱们的statefulset资源学习完毕;

四、总结:

1,唯一的pod副本网络标识,重启pod时ip改变也不影响访问;

2,启停顺序,安转数字排序;

3,个副本通过声明存储卷申请模板,独立存储;

相关推荐
阿里云云原生8 分钟前
移动端性能监控探索:iOS RUM SDK 技术架构与实践
云原生
阿里云云原生15 分钟前
Nacos 3.1.0 正式发布,支持 A2A 注册中心与 MCP 注册协议增强
微服务·云原生
阿里云云原生1 小时前
Qoder 上线提示词增强功能,将开发者从“提示词”的负担中解放出来
云原生
suknna1 小时前
通过命令模拟pod创建
kubernetes
维诺菌1 小时前
k8s java应用pod内存占用过高问题排查
java·jvm·云原生·容器·性能优化·kubernetes
回忆是昨天里的海2 小时前
k8s安装-kubeadm join,将工作节点加入k8s集群
java·服务器·kubernetes
浪飘2 小时前
k8s device plugin
java·docker·kubernetes
冬夜戏雪2 小时前
milvus容器restart不成功,但docker仍在running问题排查
docker·容器·milvus
m0_579146652 小时前
docker desktop的容器间通信
docker·容器·php
helloworddm2 小时前
Orleans 与 Kubernetes 结合的价值分析
云原生·容器·kubernetes