创建有状态工作负载StatefulSet

更新时间:2025-03-19 01:53

StatefulSet,又称“有状态工作负载”。与Deployment不同,它会为Pod保存状态,因此适用于数据库、消息队列、分布式存储系统等场景。通过本文,您可了解StatefulSet的特点、通过控制台及kubectl创建StatefulSet的方法以及验证保持Pod状态的示例。

StatefulSet介绍

与Deployment相似,StatefulSet也会保证有既定数量的Pod在正常运行。但不同的是,StatefulSet会通过以下措施保留Pod的身份:

  • 有序、固定的名称:StatefulSet的每个Pod会按顺序命名为<StatefulSet名称>-<序号>。例如,StatefulSet的名称为db-app,则Pod名称为db-app-0、db-app-1。删除并重建Pod时,新建Pod会继承原有的名称。

  • 稳定的网络标识:StatefulSet通常需要关联一个Headless Service(通过spec.serviceName指定)。这个Headless Service并不像ClusterIP提供Pod的负载均衡,而仅用于为Pod提供固定的域名(对Headless Service进行DNS查询时,DNS会返回所有匹配的Pod的IP地址)。指定Headless Service后,Pod的域名格式为<Pod名称>.<Headless Service名称>.<namespace>.svc.<ClusterDomain>,例如db-app-01.db-app.default.svc.cluster.local。Pod重建后,域名会自动被解析到新Pod。

  • 稳定的持久化存储:在StatefulSet中,可以指定PVC模板(通过spec.volumeClaimTemplates指定)。StatefulSet会根据此模板为每个Pod生成独立的PersistentVolumeClaim(PVC),PVC名称为<PVC模板名称>-<Pod名称>。当Pod被删除时,PVC会被保留并自动关联到使用相同序号的新Pod。

以上的这些措施保证了StatefulSet的Pod在重建后能继承原有的网络和存储状态,使应用从持久化数据中恢复运行。关于StatefulSet的更多信息,请参见官方文档

创建StatefulSet

通过控制台创建
通过kubectl创建
  1. 登录容器服务管理控制台,在左侧导航栏选择集群列表

  2. 集群列表页面,单击目标集群名称,然后在左侧导航栏,选择工作负载 > 有状态

  3. 有状态页面,单击使用镜像创建

  4. 应用基本信息配置向导页面,设置应用的基本信息。然后单击下一步,进入容器配置向导页面。

  5. 容器配置区域,完成容器的镜像名称端口基本配置。其余设置均为可选设置,保持默认即可。然后单击下一步,进入高级配置向导页面。镜像地址如下所示。

    重要

    拉取此镜像前,您需要为集群开启公网访问能力。如果您在创建集群时,为专有网络配置SNAT选择保持默认勾选,则集群已拥有公网访问能力。如果未选择,请参见为集群开启访问公网的能力

    registry.cn-hangzhou.aliyuncs.com/acs-sample/nginx:latest

    image

  6. 高级配置向导页面中设置访问、伸缩、调度和标签注解。在访问设置区域,创建一个ClusterIP类型的Service,并勾选实例间服务发现(Headless Service),单击确定。然后,单击最下方的创建

    image

  7. 创建StatefulSet时,控制台上的配置项(应用基本信息容器配置高级配置)与Deployment完全相同。其余配置项的说明,请参见配置项说明

重要
  1. 复制下方的YAML文件,并保存到statefulset.yaml中。下方的YAML中定义了:

    • 用于提供稳定域名的Headless Service nginx

    • 为Pod关联了hostPath存储的StatefulSet。

    • 用于对外暴露StatefulSet的LoadBalancer类型Service,在本示例中仅作为验证Nginx页面的一种方式。

    apiVersion: v1
    kind: Service
    metadata:
      name: nginx
      labels:
        app: nginx
    spec:
      clusterIP: None  # Headless Service
      selector:
        app: nginx
      ports:
      - port: 80
        name: http
    ---
    apiVersion: apps/v1
    kind: StatefulSet   # 工作负载类型
    metadata:
      name: nginx-test
      namespace: default  # 根据需要更改命名空间
      labels:
        app: nginx
    spec:
      serviceName: "nginx" # 选择前面创建的Headless Service
      replicas: 2  # 指定-Pod数量
      selector:
        matchLabels:
          app: nginx
      template: # Pod配置
        metadata:
          labels: # Pod标签
            app: nginx 
        spec:
          containers:
          - name: nginx  # 容器名称
            image: anolis-registry.cn-zhangjiakou.cr.aliyuncs.com/openanolis/nginx:1.14.1-8.6  # 使用特定版本的 Nginx 镜像
            ports:
            - containerPort: 80  # 容器暴露的端口
              protocol: TCP  # 指定协议为 TCP/UDP
            volumeMounts:
            - name: node-dir-volume  # 卷名称,需与下方volumes名称相同
              mountPath: /tmp  # 容器内的挂载路径
          volumes:
          - name: node-dir-volume
            hostPath:
              path: /local_storage  # 节点本地的目录路径
              type: DirectoryOrCreate     # 如果目录不存在则自动创建
    ---
    apiVersion: v1
    kind: Service
    metadata:
      name: nginx-test-svc
      namespace: default  # 根据需要更改命名空间
      labels:
        app: nginx
    spec:
      selector:
        app: nginx  # 匹配标签,确保服务指向正确的 Pods
      ports:
        - port: 80           # Service 在集群内提供的端口
          targetPort: 80     # 指向容器内部应用程序监听的端口 (containerPort)
          protocol: TCP      # 协议,默认是 TCP
      type: LoadBalancer      # 服务类型,默认是 ClusterIP,内部访问
  2. 执行以下命令,创建StatefulSet及Service。

    kubectl apply -f statefulset.yaml

    预期输出:

    service/nginx created
    statefulset.apps/nginx-test created
    service/nginx-test-svc created
  3. 执行以下命令,查看Service的公网IP地址。

    kubectl get svc

    预期输出:

    NAME            TYPE           CLUSTER-IP       EXTERNAL-IP     PORT(S)        AGE
    kubernetes      ClusterIP      172.16.**.***    <none>          443/TCP        4h47m
    nginx           ClusterIP      None             <none>          80/TCP         1h10m
    nginx-test-svc  LoadBalancer   172.16.**.***    106.14.**.***   80:31130/TCP   1h10m
  4. 在浏览器中输入nginx的公网IP(106.14.**.***),即可访问工作负载所属的Nginx容器。image

验证StatefulSet特性

  1. 执行以下命令,查看Pod状态。

    kubectl get pod nginx-test-0

    预期输出如下。

    NAME           READY   STATUS    RESTARTS   AGE
    nginx-test-0   1/1     Running   0          7m41s
  2. 执行以下命令删除Pod。

    kubectl delete pod nginx-test-0

    预期输出:

    pod "nginx-test-0" deleted
  3. 执行以下命令,查看Pod状态。

    kubectl get pod nginx-test-0

    预期输出如下,STATUSRunning时,表示新Pod已正常运行,继承了原有名称。

    NAME           READY   STATUS    RESTARTS   AGE
    nginx-test-0   1/1     Running   0          20s

相关文档

  • 本页导读 (1)
  • StatefulSet介绍
  • 创建StatefulSet
  • 验证StatefulSet特性
  • 相关文档
文档反馈
phone 联系我们

立即和Alibaba Cloud在线服务人员进行交谈,获取您想了解的产品信息以及最新折扣。

alicare alicarealicarealicare