前文我们介绍了通过 Longhorn UI 可以对卷进行快照、备份恢复等功能,此外我们还可以通过 Kubernetes 来实现对卷的管理,比如可以在集群上通过 CSI 来实现快照、备份恢复、克隆、扩容等功能支持。
但是在使用该功能时,需要注意以下几点:
VolumeSnapshot、VolumeSnapshotContent 和 VolumeSnapshotClass 资源对象是 CRDs, 不属于核心 API。
VolumeSnapshot 支持仅可用于 CSI 驱动。
作为 VolumeSnapshot 部署过程的一部分,Kubernetes 团队提供了一个部署于控制平面的快照控制器,并且提供了一个叫做 csi-snapshotter 的 Sidecar 容器,和 CSI 驱动程序一起部署,快照控制器会去监听 VolumeSnapshot 和 VolumeSnapshotContent 对象,并且负责创建和删除 VolumeSnapshotContent 对象。csi-snapshotter 监听 VolumeSnapshotContent 对象,并且触发针对 CSI 端点的 CreateSnapshot 和 DeleteSnapshot 的操作,完成快照的创建或删除。
CSI 驱动可能实现,也可能没有实现卷快照功能,CSI 驱动可能会使用 csi-snapshotter 来提供对卷快照的支持,详见 CSI 驱动程序文档(https://kubernetes-csi.github.io/docs/external-snapshotter.html)。
VolumeSnapshotContents 和 VolumeSnapshots 的生命周期包括资源供应、资源绑定、对使用 PVC 的保护机制和资源删除等各个阶段,这两个对象会遵循这些生命周期。
资源供应:与 PV 的资源供应类似,VolumeSnapshotContent 也可以以静态或动态两种方式供应资源。
静态供应:集群管理员会预先创建好一组 VolumeSnapshotContent 资源,类似于手动创建 PV
动态供应:基于 VolumeSnapshotClass 资源,当用户创建 VolumeSnapshot 申请时自动创建 VolumeSnapshotContent,类似于 StorageClass 动态创建 PV
资源绑定:快照控制器负责将 VolumeSnapshot 与一个合适的 VolumeSnapshotContent 进行绑定,包括静态和动态供应两种情况,VolumeSnapshot 和 VolumeSnapshotContent 之间也是一对一进行绑定的,不会存在一对多的情况。
对使用中的PVC的保护机制:当存储快照 VolumeSnapshot 正在被创建且还未完成时,相关的 PVC 将会被标记为正被使用中,如果用户对 PVC 进行删除操作,系统不会立即删除 PVC,以避免快照还未做完造成数据丢失,删除操作会延迟到 VolumeSnapshot 创建完成(readyToUse 状态)或被终止(aborted 状态)的情况下完成。
资源删除:对 VolumeSnapshot 发起删除操作时,对与其绑定的后端 VolumeSnapshotContent 的删除操作将基于删除策略 DeletionPolicy 的设置来决定,可以配置的删除策略有:
Delete:自动删除 VolumeSnapshotContent 资源对象和快照的内容。
Retain:VolumeSnapshotContent 资源对象和快照的内容都将保留,需要手动清理。
我们这里的 Longhorn 系统在部署完成后创建了3个 csi-snapshotter 的 Pod:
复制
➜ kubectl get pods -n longhorn-system
NAME READY STATUS RESTARTS AGE
csi-snapshotter-86f65d8bc-9t7dd 1/1 Running 5 (126m ago) 2d17h
csi-snapshotter-86f65d8bc-d6xbj 1/1 Running 5 (126m ago) 2d17h
csi-snapshotter-86f65d8bc-dncwv 1/1 Running 5 (126m ago) 2d17h
这其实是启动的3个副本,同一时间只有一个 Pod 提供服务,通过 leader-election 来实现的选主高可用,比如当前这里提供服务的是 csi-snapshotter-86f65d8bc-dncwv,我们可以查看对应的日志信息:
复制
➜ kubectl logs -f csi-snapshotter-86f65d8bc-dncwv -n longhorn-system
......
E0223 04:36:33.570567 1 reflector.go:127] github.com/kubernetes-csi/external-snapshotter/client/v3/informers/externalversions/factory.go:117: Failed to watch *v1beta1.VolumeSnapshotClass: failed to list *v1beta1.VolumeSnapshotClass: the server could not find the requested resource (get volumesnapshotclasses.snapshot.storage.k8s.io)
E0223 04:37:03.773447 1 reflector.go:127] github.com/kubernetes-csi/external-snapshotter/client/v3/informers/externalversions/factory.go:117: Failed to watch *v1beta1.VolumeSnapshotContent: failed to list *v1beta1.VolumeSnapshotContent: the server could not find the requested resource (get volumesnapshotcontents.snapshot.storage.k8s.io)
可以看到提示没有 VolumeSnapshotClass 和 VolumeSnapshotContent 资源,这是因为这两个资源都是 CRDs,并不是 Kubernetes 内置的资源对象,而我们在安装 Longhorn 的时候也没有安装这两个 CRDs,所以找不到,要通过 CSI 来实现卷快照功能自然就需要先安装 CRDs,我们可以从 https://github.com/kubernetes-csi/external-snapshotter 项目中来获取:
复制
➜ git clone https://github.com/kubernetes-csi/external-snapshotter
➜ cd external-snapshotter && git checkout v5.0.1
➜ kubectl kustomize client/config/crd | kubectl create -f -
上面的命令会安装上面提到的3个 Snapshot CRDs:
复制
➜ kubectl get crd |grep snapshot
volumesnapshotclasses.snapshot.storage.k8s.io 2022-02-23T05:31:34Z
volumesnapshotcontents.snapshot.storage.k8s.io 2022-02-23T05:31:34Z
volumesnapshots.snapshot.storage.k8s.io 2022-02-23T05:31:34Z
安装完成后再去查看上面的 csi-snapshotter 相关的 Pod 日志就正常了。CRDs 安装完成后还不够,我们还需要一个快照控制器来监听 VolumeSnapshot 和 VolumeSnapshotContent 对象,同样 external-snapshotter 项目中也提供了一个 Common Snapshot Controller,执行下面的命令一键安装:
复制
# 修改 deploy/kubernetes/snapshot-controller/setup-snapshot-controller.yaml 镜像地址为 cnych/csi-snapshot-controller:v5.0.0,默认为 gcr 镜像
➜ kubectl -n kube-system kustomize deploy/kubernetes/snapshot-controller | kubectl create -f -
这里我们将快照控制器安装到了 kube-system 命名空间下,启动两个副本,同样同一时间只有一个 Pod 提供服务:
复制
➜ kubectl get pods -n kube-system -l app=snapshot-controller
NAME READY STATUS RESTARTS AGE
snapshot-controller-677b65dc6c-288w9 1/1 Running 0 3m22s
snapshot-controller-677b65dc6c-zgdcm 1/1 Running 0 39s
到这里就将使用 CSI 来配置快照的环境准备好了。
测试
下面我们仍然以前面的 mysql-pvc 这个卷为例来说明下如何使用卷快照功能:
复制
➜ kubectl get pvc mysql-pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
mysql-pvc Bound pvc-ec17a7e4-7bb4-4456-9380-353db3ed4307 1Gi RWO longhorn 2d18h
要创建 mysql-pvc 的快照申请,首先需要创建一个 VolumeSnapshot 对象:
复制
# snapshot-mysql.yaml
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshot
metadata:
name: mysql-snapshot-demo
spec:
volumeSnapshotClassName: longhorn
source:
persistentVolumeClaimName: mysql-pvc
# volumeSnapshotContentName: test-content
其中就两个主要配置参数:
volumeSnapshotClassName:指定 VolumeSnapshotClass 的名称,这样就可以动态创建一个对应的 VolumeSnapshotContent 与之绑定,如果没有指定该参数,则属于静态方式,需要手动创建 VolumeSnapshotContent。
persistentVolumeClaimName:指定数据来源的 PVC 名称。
volumeSnapshotContentName:如果是申请静态存储快照,则需要通过该参数来指定一个 VolumeSnapshotContent。
上面我们指定了一个存储快照类 longhorn,当然需要创建这个对象:
复制
# snapshotclass.yaml
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshotClass
metadata:
name: longhorn
# annotations: # 如果要指定成默认的快照类
# snapshot.storage.kubernetes.io/is-default-class: "true"
driver: driver.longhorn.io
deletionPolicy: Delete
每个 VolumeSnapshotClass 都包含 driver、deletionPolicy 和 parameters 字段,在需要动态配置属于该类的 VolumeSnapshot 时使用。
driver:表示 CSI 存储插件驱动的名称,这里我们使用的是 Longhorn 插件,名为 driver.longhorn.io
deletionPolicy:删除策略,可以设置为 Delete 或 Retain,如果删除策略是 Delete,那么底层的存储快照会和 VolumeSnapshotContent 对象一起删除,如果删除策略是 Retain,那么底层快照和 VolumeSnapshotContent 对象都会被保留。
parameters:存储插件需要配置的参数,由 CSI 驱动提供具体的配置参数。
如果想将当前快照类设置成默认的则需要添加 snapshot.storage.kubernetes.io/is-default-class: "true" 这样的 annotations。
现在我们直接创建上面的两个资源对象:
复制
➜ kubectl apply -f snapshotclass.yaml
volumesnapshotclass.snapshot.storage.k8s.io/longhorn created
➜ kubectl apply -f snapshot-mysql.yaml
volumesnapshot.snapshot.storage.k8s.io/mysql-snapshot-demo created
➜ kubectl get volumesnapshotclass
NAME DRIVER DELETIONPOLICY AGE
longhorn driver.longhorn.io Delete 43s
➜ kubectl get volumesnapshot
NAME READYTOUSE SOURCEPVC SOURCESNAPSHOTCONTENT RESTORESIZE SNAPSHOTCLASS SNAPSHOTCONTENT CREATIONTIME AGE
mysql-snapshot-demo true mysql-pvc 1Gi longhorn snapcontent-1119649a-d4f2-447f-a21a-e527f202e43e 43s 43s
这个时候会动态为我们创建一个 VolumeSnapshotContent 对象:
复制
➜ kubectl get volumesnapshotcontent
NAME READYTOUSE RESTORESIZE DELETIONPOLICY DRIVER VOLUMESNAPSHOTCLASS VOLUMESNAPSHOT VOLUMESNAPSHOTNAMESPACE AGE
snapcontent-1119649a-d4f2-447f-a21a-e527f202e43e true 1073741824 Delete driver.longhorn.io longhorn mysql-snapshot-demo default 97s
自动创建的 VolumeSnapshotContent 对象内容如下所示:
复制
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshotContent
metadata:
name: snapcontent-1119649a-d4f2-447f-a21a-e527f202e43e
spec:
deletionPolicy: Delete
driver: driver.longhorn.io
source:
volumeHandle: pvc-ec17a7e4-7bb4-4456-9380-353db3ed4307
volumeSnapshotClassName: longhorn
volumeSnapshotRef:
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshot
name: mysql-snapshot-demo
namespace: default
resourceVersion: "4967456"
uid: 1119649a-d4f2-447f-a21a-e527f202e43e
status:
creationTime: 1645597546000000000
readyToUse: true
restoreSize: 1073741824
snapshotHandle: bs://pvc-ec17a7e4-7bb4-4456-9380-353db3ed4307/backup-f5f28fd624a148ed
其中的 source.volumeHandle 字段的值是在后端存储上创建并由 CSI 驱动在创建存储卷期间返回的 Volume 的唯一标识符,在动态供应模式下需要该字段,指定的是快照的来源 Volume 信息,volumeSnapshotRef 下面就是和关联的 VolumeSnapshot 对象的相关信息。
大型站长资讯类网站! https://www.0818zz.com