5.4. CSI 卷快照

本文档论述了如何通过支持的 Container Storage Interface (CSI) 驱动程序使用进行卷快照,以帮助防止 OpenShift Container Platform 中的数据丢失。建议先熟悉持久性卷的概念。

5.4.1. CSI 卷快照概述

快照(snapshot)代表了集群中特定时间点的存储卷的状态 。卷快照可以用来置备新卷。

OpenShift Container Platform 默认支持 Container Storage Interface(CSI)卷快照。但是,需要一个特定的 CSI 驱动程序。

通过 CSI 卷快照,集群管理员能够:

  • 部署支持快照功能的第三方 CSI 驱动。
  • 从一个现有的卷快照创建一个新的 PVC。
  • 对现有的 PVC 进行快照。
  • 将快照恢复为一个不同的 PVC。
  • 删除现有的卷快照。

通过 CSI 卷快照,应用程序开发人员可以:

  • 使用卷快照作为构建块来开发应用程序或集群级别的存储备份解决方案。
  • 快速回滚到以前的开发版本。
  • 不需要每次都进行完全备份,从而可以更有效地使用存储。

在使用卷快照时请注意以下几点:

  • 仅支持 CSI 驱动程序。不支持 in-tree 和 FlexVolumes。
  • OpenShift Container Platform 仅附带所选 CSI 驱动程序。对于不是由 OpenShift Container Platform Driver Operator 提供的 CSI 驱动程序,建议使用由社区或存储供应商提供的 CSI 驱动程序。按照 CSI 驱动程序供应商的安装说明进行操作。
  • CSI 驱动程序可能会也可能不会带有卷快照功能。提供卷快照支持的 CSI 驱动程序可能会使用 csi-external-snapshotter sidecar。详情请查看 CSI 驱动程序提供的文档。

5.4.2. CSI 快照控制器和 sidecar

OpenShift Container Platform 提供了一个部署到 control plane 中的快照控制器。另外,您的 CSI 驱动程序厂商会提供 CSI 快照 sidecar,它会在安装 CSI 驱动程序的过程中做为一个辅助(helper)容器。

CSI 快照控制器和 sidecar 通过 OpenShift Container Platform API 提供卷快照。这些外部组件在集群中运行。

外部控制器由 CSI Snapshot Controller Operator 部署。

5.4.2.1. 外部控制器

CSI 快照控制器绑定 VolumeSnapshotVolumeSnapshotContent 对象。控制器通过创建和删除 VolumeSnapshotContent 对象来管理动态置备。

5.4.2.2. 外部 sidecar

您的 CSI 驱动程序厂商提供 csi-external-snapshotter sidecar。这是和 CSI 驱动程序一起部署的单独的 helper 容器。sidecar 通过触发 CreateSnapshotDeleteSnapshot 操作来管理快照。请根据驱动程序厂商提供的说明进行操作。

5.4.3. 关于 CSI Snapshot Controller Operator

CSI Snapshot Controller Operator 在 openshift-cluster-storage-operator 命名空间中运行。默认情况下,它由 Cluster Version Operator (CVO) 在所有集群中安装。

CSI Snapshot Controller Operator 安装 CSI 快照控制器,该控制器在 openshift-cluster-storage-operator 命名空间中运行。

5.4.3.1. 卷快照 CRD

在 OpenShift Container Platform 安装过程中,CSI Snapshot Controller Operator 在 snapshot.storage.k8s.io/v1 API 组中创建以下快照自定义资源定义 (CRD) :

VolumeSnapshotContent

一个快照记录了由集群管理员在集群中置备的卷的状态。

PersistentVolume 对象类似,VolumeSnapshotContent CRD 是一个集群资源,指向存储后端的实际快照。

对于手动预置备的快照,集群管理员会创建大量 VolumeSnapshotContent CRD。它们在存储系统中记录了实际卷快照的详情。

VolumeSnapshotContent CRD 没有命名空间,供集群管理员使用。

VolumeSnapshot

PersistentVolumeClaim 对象类似, VolumeSnapshot CRD 定义了开发人员对快照的请求。CSI Snapshot Controller Operator 运行 CSI 快照控制器,该控制器使用适当的 VolumeSnapshotContent CRD 处理 VolumeSnapshot CRD 的绑定。绑定是一个一对一的映射。

VolumeSnapshot CRD 有命名空间限制。开发人员使用 CRD 作为快照的唯一请求。

VolumeSnapshotClass

集群管理员可以指定属于 VolumeSnapshot 对象的不同属性。这些属性可能会在存储系统中使用相同卷的快照之间有所不同,在这种情况下,使用持久性卷声明的相同存储类来表示它们。

VolumeSnapshotClass CRD 定义了在创建快照时要使用的 csi-external-snapshotter sidecar 的参数。这可让存储后端知道在支持多个选项时动态创建哪些快照。

动态置备的快照使用 VolumeSnapshotClass CRD 指定在创建快照时要使用的 storage-provider 特定参数。

VolumeSnapshotContentClass CRD 没有命名空间,集群管理员使用它为存储后端启用全局配置选项。

5.4.4. 置备卷快照

置备快照的方法有两种:动态和手动。

5.4.4.1. 动态置备

您可以请求从持久性卷声明中动态获取快照,而不使用已存在的快照。参数可以通过 VolumeSnapshotClass CRD 指定。

5.4.4.2. 手动调配

作为集群管理员,您可以手动置备大量 VolumeSnapshotContent 对象。它们包括了集群用户可以获得的实际卷的快照详情。

5.4.5. 创建卷快照

当您创建 VolumeSnapshot 对象时,OpenShift Container Platform 会创建一个卷快照。

先决条件

  • 登陆到一个正在运行的 OpenShift Container Platform 集群。
  • 使用支持 VolumeSnapshot 对象的 CSI 驱动程序创建的 PVC。
  • 用于置备存储后端的存储类。
  • 您要对其进行快照的 PVC 没有被任何 pod 使用。

    注意

    如果 pod 正在使用,则不要为 PVC 创建卷快照。这样做可能会导致数据崩溃,因为 PVC 没有被静默(暂停)。确保首先停止正在运行的 pod,以确保快照的一致性。

流程

动态创建卷快照:

  1. 使用以下 YAML 描述的 VolumeSnapshotClass 对象创建一个文件:

    volumesnapshotclass.yaml

    apiVersion: snapshot.storage.k8s.io/v1
    kind: VolumeSnapshotClass
    metadata:
      name: csi-hostpath-snap
    driver: hostpath.csi.k8s.io 1
    deletionPolicy: Delete

    1
    用于创建此 VolumeSnapshotClass 对象快照的 CSI 驱动程序名称。该名称必须与存储类的 Provisioner 字段相同,它负责正在进行快照的 PVC。
  2. 运行以下命令,创建上一步中保存的对象:

    $ oc create -f volumesnapshotclass.yaml
  3. 创建 VolumeSnapshot 对象:

    volumesnapshot-dynamic.yaml

    apiVersion: snapshot.storage.k8s.io/v1
    kind: VolumeSnapshot
    metadata:
      name: mysnap
    spec:
      volumeSnapshotClassName: csi-hostpath-snap 1
      source:
        persistentVolumeClaimName: myclaim 2

    1
    卷快照对特定类的请求。如果 volumeSnapshotClassName 设置不存在,且有默认的卷快照类,则会创建一个带有默认卷快照类名称的快照。但如果该字段不存在且不存在默认卷快照类,则不会创建快照。
    2
    绑定到持久性卷的 PersistentVolumeClaim 对象的名称。这指定了您要对什么创建快照。动态置备快照需要这个信息。
  4. 运行以下命令,创建上一步中保存的对象:

    $ oc create -f volumesnapshot-dynamic.yaml

手动置备快照:

  1. 除了以上定义卷快照类外,还需要提供 volumeSnapshotContentName 参数的值作为快照的源。

    volumesnapshot-manual.yaml

    apiVersion: snapshot.storage.k8s.io/v1
    kind: VolumeSnapshot
    metadata:
      name: snapshot-demo
    spec:
      source:
        volumeSnapshotContentName: mycontent 1

    1
    预置备快照需要 volumeSnapshotContentName 参数。
  2. 运行以下命令,创建上一步中保存的对象:

    $ oc create -f volumesnapshot-manual.yaml

验证

在集群中创建快照后,会提供有关快照的详情。

  1. 运行以下命令显示所创建的卷快照详情:

    $ oc describe volumesnapshot mysnap

    以下示例显示有关 mysnap 卷快照的详细信息:

    volumesnapshot.yaml

    apiVersion: snapshot.storage.k8s.io/v1
    kind: VolumeSnapshot
    metadata:
      name: mysnap
    spec:
      source:
        persistentVolumeClaimName: myclaim
      volumeSnapshotClassName: csi-hostpath-snap
    status:
      boundVolumeSnapshotContentName: snapcontent-1af4989e-a365-4286-96f8-d5dcd65d78d6 1
      creationTime: "2020-01-29T12:24:30Z" 2
      readyToUse: true 3
      restoreSize: 500Mi

    1
    指向控制器创建的实际存储内容的指针。
    2
    创建快照的时间。快照包含在这个指定时间点上可用的卷内容。
    3
    如果该值设为 true,则快照可用来恢复为一个新 PVC。
    如果该值设为 false,则创建快照。但是,存储后端需要执行额外的任务来使快照可用,以便将其恢复为新卷。例如: Amazon Elastic Block Store 数据可能被移到不同的、更低成本的位置,这个过程可能需要几分钟时间。
  2. 要验证卷快照是否已创建,请运行以下命令:

    $ oc get volumesnapshotcontent

    显示指向实际内容的指针。如果 boundVolumeSnapshotContentName 字段已被填充,则代表一个 VolumeSnapshotContent 对象已存在,快照被创建。

  3. 要验证快照是否已就绪,请确认 VolumeSnapshot 带有 readyToUse: true

5.4.6. 删除卷快照

您可以配置 OpenShift Container Platform 如何删除卷快照。

流程

  1. 指定 VolumeSnapshotClass 对象中所需的删除策略,如下例所示:

    volumesnapshotclass.yaml

    apiVersion: snapshot.storage.k8s.io/v1
    kind: VolumeSnapshotClass
    metadata:
      name: csi-hostpath-snap
    driver: hostpath.csi.k8s.io
    deletionPolicy: Delete 1

    1
    当删除卷快照时,如果设置了 Delete 值,则底层快照会与 VolumeSnapshotContent 对象一起删除。如果设置了 Retain 值,则基本快照和 VolumeSnapshotContent 对象仍保留。
    如果设置了 Retain 值,且在不删除对应的 VolumeSnapshotContent 对象的情况下删除了 VolumeSnapshot 对象,则内容会保留。快照本身也保留在存储后端中。
  2. 输入以下命令删除卷快照:

    $ oc delete volumesnapshot <volumesnapshot_name>

    输出示例

    volumesnapshot.snapshot.storage.k8s.io "mysnapshot" deleted

  3. 如果删除策略被设置为 Retain,请输入以下命令删除卷快照内容:

    $ oc delete volumesnapshotcontent <volumesnapshotcontent_name>
  4. 可选:如果 VolumeSnapshot 对象没有成功删除,请输入以下命令删除左侧资源的所有终结程序,以便删除操作可以继续进行:

    重要

    如果您确信不存在来自持久性卷声明或卷快照内容到 VolumeSnapshot 对象的引用时,才删除终结器。即使使用了 --force 选项,在删除所有终结器前,删除操作也不会删除快照对象。

    $ oc patch -n $PROJECT volumesnapshot/$NAME --type=merge -p '{"metadata": {"finalizers":null}}'

    输出示例

    volumesnapshotclass.snapshot.storage.k8s.io "csi-ocs-rbd-snapclass" deleted

    删除终结器并删除卷快照。

5.4.7. 恢复卷快照

VolumeSnapshot CRD 内容可用于将现有卷恢复到以前的状态。

绑定 VolumeSnapshot CRD 并将 readyToUse 值设置为 true 后,您可以使用该资源置备一个预先填充快照数据的新卷。先决条件 * 已登陆到一个正在运行的 OpenShift Container Platform 集群。* 使用支持卷快照的容器存储接口 (CSI) 驱动程序创建的持久性卷声明 (PVC) 。* 用于置备存储后端的存储类。* 已创建卷快照并可使用。

流程

  1. 在 PVC 上指定 VolumeSnapshot 数据源,如下所示:

    pvc-restore.yaml

    apiVersion: v1
    kind: PersistentVolumeClaim
    metadata:
      name: myclaim-restore
    spec:
      storageClassName: csi-hostpath-sc
      dataSource:
        name: mysnap 1
        kind: VolumeSnapshot 2
        apiGroup: snapshot.storage.k8s.io 3
      accessModes:
        - ReadWriteOnce
      resources:
        requests:
          storage: 1Gi

    1
    VolumeSnapshot 对象的名称,代表作为源的快照。
    2
    必须设置为 VolumeSnapshot 的值。
    3
    必须设置为 snapshot.storage.k8s.io 的值 。
  2. 运行以下命令来创建一个 PVC:

    $ oc create -f pvc-restore.yaml
  3. 运行以下命令验证恢复的 PVC 是否已创建:

    $ oc get pvc

    此时会显示一个新的 PVC,如 myclaim-restore