全部產品
Search
文件中心

Container Service for Kubernetes:使用雲端硬碟儲存快照

更新時間:Oct 30, 2024

Container ServiceKubernetes版ACK(Container Service for Kubernetes)的雲端硬碟儲存快照特性可以協助您實現應用資料的備份和恢複。本文介紹ACK的儲存快照的基本概念、使用流程,並說明如何動態、靜態建立快照。

前提條件

背景資訊

在阿里雲ACK叢集中部署具狀態服務通常使用雲端硬碟資料卷儲存資料,雖然雲端硬碟本身提供了資料的備份(快照)恢複機制,但是如何將這種機制和Kubernetes服務整合並靈活地提供給應用使用?為瞭解決這個問題,Kubernetes使用以下兩個特性來實現備份恢複能力:

  • 通過VolumeSnapshot資源實現雲端硬碟的備份(快照功能)。

  • 通過PVC的DataSource功能實現資料的恢複。

計費說明

雲端硬碟快照基於阿里雲ECS快照實現,關於ECS雲端硬碟快照的計費資訊,請參見快照計費

自2023年10月12日11:00起,阿里雲ECS快照升級新版不再收取快照極速可用儲存費和快照極速可用次數費,更多資訊,請參見快照極速可用能力

使用說明

為了實現快照相關功能,ACK通過CRD定義了以下3個相關的資源類型。

資源類型名稱

描述

VolumeSnapshotContent

儲存後端的快照執行個體,由系統管理員建立維護,無NameSpace。類似PV概念。

VolumeSnapshot

聲明一個快照執行個體,由使用者建立維護,屬於特定Namespace。類似PVC概念。

VolumeSnapshotClass

定義一個快照類,描述建立快照使用的參數、Controller。類似StorageClass概念。

儲存快照資源的綁定規則如下:

  • 在使用Snapshot資源類型時,和PV、PVC一樣,首先您需綁定VolumeSnapshot與VolumeSnapshotContent。

  • 叢集會自動為正確配置了VolumeSnapshotClassName欄位的VolumeSnapshot資源,建立VolumeSnapshotContent資源。 如果您沒有配置或者配置錯誤,則無法自動建立VolumeSnapshotContent,您需要手動建立VolumeSnapshotContent,並綁定VolumeSnapshot。

  • VolumeSnapshotContent與VolumeSnapshot綁定是一對一的關係。

重要

刪除VolumeSnapshotContent時,後端的快照也會被刪除。

動態建立快照

ACK使用雲端硬碟動態建立快照使用流程如下圖所示。snapshot

使用PL0、PL1、PL2、PL3層級的ESSD雲端硬碟或ESSD AutoPL雲端硬碟時,動態建立的快照預設開啟快照極速可用功能。

使用流程說明如下。

流程步驟

描述

建立原始應用,建立雲端硬碟卷儲存資料。

建立VolumeSnapshot,此時叢集會自動建立VolumeSnapshotContent和儲存端的快照執行個體。

建立新的應用,並配置PVC引用步驟②中建立的快照對象。

上述的三個步驟實現:

  • 備份:圖中的Volume1的資料被備份到Snapshot1

  • 恢複:Snapshot1的資料(也就是Volume1的資料)被恢複成Volume2

本文樣本將通過建立MySQL應用並恢複應用的資料,說明如何使用儲存快照功能。操作步驟如下。

  1. 建立VolumeSnapshotClass快照類。

    1. 使用以下YAML內容建立volumesnapshotclass.yaml檔案。

      apiVersion: snapshot.storage.k8s.io/v1
      kind: VolumeSnapshotClass
      metadata:
       name: default-snapclass
      driver: diskplugin.csi.alibabacloud.com
      parameters:
        retentionDays: "5"
      deletionPolicy: Delete

      參數

      說明

      deletionPolicy

      • 當值為Delete時,說明刪除VolumeSnapshot時,VolumeSnapshotContent以及關聯的快照也會一起被刪除。

      • 當值為Retain時,說明刪除VolumeSnapshot時,VolumeSnapshotContent以及關聯的快照不會被刪除。

      parameters.retentionDays

      指定快照自動回收時間。

      parameters.forceDelete

      當指定forceDelete"true"時,表示使用強制移除快照功能。自csi-provisioner組件v1.26.5-92f859a-aliyun版本起,預設使用強制移除且不可修改,此前預設為普通刪除。

      • 強制移除:強制移除使用者建立的所有已使用和未使用的快照。

      • 普通刪除:只能刪除未使用的快照。已經使用過的快照,不能使用普通刪除。

    2. 執行以下命令建立VolumeSnapshotClass快照類。

      kubectl apply -f volumesnapshotclass.yaml
  2. 建立原始應用並寫入資料。

    1. 使用以下YAML內容建立mysql.yaml檔案。

      apiVersion: apps/v1
      kind: StatefulSet
      metadata:
        name: mysql
      spec:
        selector:
          matchLabels:
            app: mysql
        serviceName: "mysql"
        replicas: 1
        template:
          metadata:
            labels:
              app: mysql
          spec:
            containers:
            - name: mysql
              image: mysql:5.7
              env:
              - name: MYSQL_ROOT_PASSWORD
                valueFrom:
                  secretKeyRef:
                    name: mysql-pass
                    key: password
              imagePullPolicy: IfNotPresent
              volumeMounts:
              - name: disk
                mountPath: /data
        volumeClaimTemplates:
        - metadata:
            name: disk
          spec:
            accessModes: [ "ReadWriteOnce" ]
            storageClassName: "alicloud-disk-topology-alltype"
            resources:
              requests:
                storage: 20Gi
      ---
      apiVersion: v1
      kind: Secret
      metadata:
        name: mysql-pass
      type: Opaque
      data:
        username: dGVz****            
        password: dGVzdDEt****    
    2. 執行以下命令建立應用MySQL。

      kubectl apply -f mysql.yaml
    3. 執行以下命令往Pod(mysql-0)中寫入資料。

      kubectl exec -it mysql-0 -- touch /data/test
      kubectl exec -it mysql-0 -- ls /data

      輸出:

      lost+found test
  3. 建立VolumeSnapshot。

    說明
    • 若您叢集使用的CSI版本不低於v1.22.12-b797ad9-aliyun,建立快照時, 不依賴該PVC是否有Running Pod存在,可對任意掛載過的雲端硬碟建立快照。關於CSI版本更多資訊,請參見csi-provisioner

    • 若您叢集使用的CSI版本低於v1.22.12-b797ad9-aliyun,建立快照時,則需要保證有Pod正在使用當前PVC,即保證雲端硬碟處於掛載狀態。

    1. 使用以下YAML內容建立snapshot.yaml檔案。

      apiVersion: snapshot.storage.k8s.io/v1
      kind: VolumeSnapshot
      metadata:
        name: new-snapshot-demo
        namespace: default
      spec:
        volumeSnapshotClassName: default-snapclass
        source:
          persistentVolumeClaimName: disk-mysql-0
    2. 執行以下命令建立VolumeSnapshot。

      kubectl apply -f snapshot.yaml
    3. 執行以下命令查看是否建立VolumeSnapshot和VolumeSnapshotContent。您也可以登入ECS控制台查看快照執行個體。

      查看VolumeSnapshot命令:

      kubectl get volumesnapshots.snapshot.storage.k8s.io

      輸出:

      NAME                      AGE
      new-snapshot-demo                    36m

      查看VolumeSnapshotContent命令:

      kubectl get VolumeSnapshotContent

      輸出:

      NAME                      AGE
      snapshotcontent-222222                  36m
  4. 恢複資料。

    1. 使用以下YAML內容建立mysql-restore檔案。

      apiVersion: apps/v1
      kind: StatefulSet
      metadata:
        name: mysql-restore
      spec:
        selector:
          matchLabels:
            app: mysql
        serviceName: "mysql"
        replicas: 1
        template:
          metadata:
            labels:
              app: mysql
          spec:
            containers:
            - name: mysql
              image: mysql:5.7
              env:
              - name: MYSQL_ROOT_PASSWORD
                valueFrom:
                  secretKeyRef:
                    name: mysql-pass
                    key: password
              imagePullPolicy: IfNotPresent
              volumeMounts:
              - name: disk
                mountPath: /data
        volumeClaimTemplates:
        - metadata:
            name: disk
          spec:
            accessModes: [ "ReadWriteOnce" ]
            storageClassName: "alicloud-disk-topology-alltype"
            resources:
              requests:
                storage: 20Gi
            dataSource:
              name: new-snapshot-demo
              kind: VolumeSnapshot
              apiGroup: snapshot.storage.k8s.io
      說明

      volumeClaimTemplates中,需設定dataSource的類型為VolumeSnapshot,且VolumeSnapshot的名字為步驟3中建立的new-snapshot-demo。

    2. 執行以下命令恢複資料。

      kubectl apply -f mysql-restore.yaml
  5. 執行以下命令查看Pod(mysql-restore-0)資料。

    kubectl exec -it mysql-restore-0 -- ls /data

    輸出:

    lost+found test

    可見在不同的Pod中返回相同的資料,實現了資料的恢複。

靜態建立快照(使用ECS上已有快照)

將已有ECS快照匯入至ACK叢集中的操作步驟如下。

  1. 使用以下YAML內容建立VolumeSnapshotContent。

    apiVersion: snapshot.storage.k8s.io/v1
    kind: VolumeSnapshotContent
    metadata:
      name: new-snapshot-content-test
    spec:
      deletionPolicy: Retain
      driver: diskplugin.csi.alibabacloud.com
      source:
        snapshotHandle: <your-snapshotid>
      volumeSnapshotRef:
        name: new-snapshot-demo
        namespace: default

    參數

    描述

    snapshotHandle

    填寫在ECS頁面上的已產生的快照ID。

    volumeSnapshotRef

    填寫要建立的VolumeSnapshot的資訊:

    • name:將要建立的VolumeSnapshot的名稱。

    • namespace:將要建立的VolumeSnapshot所在的命名空間。

  2. 使用以下YAML內容建立VolumeSnapshot。

    apiVersion: snapshot.storage.k8s.io/v1
    kind: VolumeSnapshot
    metadata:
      name: new-snapshot-demo
      namespace: default
    spec:
      source:
        volumeSnapshotContentName: new-snapshot-content-test

    參數

    描述

    metadata.name

    VolumeSnapshot的名稱,需要和上述VolumeSnapshotContent中指定的相同。

    spec.source.volumeSnapshotContentName

    當前VolumeSnapshot綁定的VolumeSnapshotContent的名稱,需與上述建立的VolumeSnapshotContent的名稱一致。

  3. 恢複資料。

    1. 使用以下YAML內容建立mysql-restore檔案。

      apiVersion: apps/v1
      kind: StatefulSet
      metadata:
        name: mysql-restore
      spec:
        selector:
          matchLabels:
            app: mysql
        serviceName: "mysql"
        replicas: 1
        template:
          metadata:
            labels:
              app: mysql
          spec:
            containers:
            - name: mysql
              image: mysql:5.7
              env:
              - name: MYSQL_ROOT_PASSWORD
                valueFrom:
                  secretKeyRef:
                    name: mysql-pass
                    key: password
              imagePullPolicy: IfNotPresent
              volumeMounts:
              - name: disk
                mountPath: /data
        volumeClaimTemplates:
        - metadata:
            name: disk
          spec:
            accessModes: [ "ReadWriteOnce" ]
            storageClassName: "alicloud-disk-topology-alltype"
            resources:
              requests:
                storage: 20Gi
            dataSource:
              name: new-snapshot-demo
              kind: VolumeSnapshot
              apiGroup: snapshot.storage.k8s.io
      說明

      volumeClaimTemplates中,需設定dataSource的類型為VolumeSnapshot,且VolumeSnapshot的名字為步驟2中建立的new-snapshot-demo。

    2. 執行以下命令恢複資料。

      kubectl apply -f mysql-restore.yaml
  4. 執行以下命令查看Pod(mysql-restore-0)資料。

    kubectl exec -it mysql-restore-0 -- ls /data

    輸出:

    lost+found test

    可見在不同的Pod中返回相同的資料,實現了資料的恢複。