本文发表于一年多前。旧文章可能包含过时内容。请检查页面中的信息自发布以来是否已变得不正确。

Kubernetes 1.23:防止在乱序删除时出现 PersistentVolume 泄漏

PersistentVolume(简称 PV)与回收策略相关联。回收策略用于确定存储后端在删除 PV 时需要采取的操作。当回收策略为 Delete 时,预期存储后端会释放为 PV 分配的存储资源。实质上,回收策略需要在 PV 删除时得到遵守。

通过最近发布的 Kubernetes v1.23,一个 Alpha 功能允许您配置集群以这种方式运行并遵守配置的回收策略。

在以前的 Kubernetes 版本中,回收是如何工作的?

PersistentVolumeClaim(简称 PVC)是用户对存储的请求。如果创建了新的 PV 或找到了匹配的 PV,则 PV 和 PVC 被视为绑定。PV 本身由存储后端分配的卷支持。

通常,如果要删除卷,则预期是删除绑定 PV-PVC 对的 PVC。但是,在删除 PVC 之前删除 PV 没有限制。

首先,我将演示运行旧版本 Kubernetes 的集群的行为。

检索绑定到 PV 的 PVC

检索现有的 PVC example-vanilla-block-pvc

kubectl get pvc example-vanilla-block-pvc

以下输出显示了 PVC 及其“已绑定”PV,PV 显示在“VOLUME”列下

NAME                        STATUS   VOLUME                                     CAPACITY   ACCESS MODES   STORAGECLASS               AGE
example-vanilla-block-pvc   Bound    pvc-6791fdd4-5fad-438e-a7fb-16410363e3da   5Gi        RWO            example-vanilla-block-sc   19s

删除 PV

当我尝试删除绑定的 PV 时,集群会阻塞,并且 kubectl 工具不会将控制权返回给 Shell;例如

kubectl delete pv pvc-6791fdd4-5fad-438e-a7fb-16410363e3da
persistentvolume "pvc-6791fdd4-5fad-438e-a7fb-16410363e3da" deleted
^C

检索 PV

kubectl get pv pvc-6791fdd4-5fad-438e-a7fb-16410363e3da

可以观察到 PV 处于 Terminating 状态

NAME                                       CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS        CLAIM                               STORAGECLASS               REASON   AGE
pvc-6791fdd4-5fad-438e-a7fb-16410363e3da   5Gi        RWO            Delete           Terminating   default/example-vanilla-block-pvc   example-vanilla-block-sc            2m23s

删除 PVC

kubectl delete pvc example-vanilla-block-pvc

如果 PVC 成功删除,则会看到以下输出

persistentvolumeclaim "example-vanilla-block-pvc" deleted

集群中的 PV 对象也被删除。尝试检索 PV 时,会发现 PV 不再存在

kubectl get pv pvc-6791fdd4-5fad-438e-a7fb-16410363e3da
Error from server (NotFound): persistentvolumes "pvc-6791fdd4-5fad-438e-a7fb-16410363e3da" not found

尽管 PV 已删除,但底层存储资源未删除,需要手动移除。

总而言之,与 Persistent Volume 关联的回收策略在某些情况下会被忽略。对于 Bound PV-PVC 对,PV-PVC 删除的顺序决定了是否遵守 PV 回收策略。如果 PVC 首先删除,则回收策略会得到遵守;但是,如果在删除 PVC 之前删除 PV,则不执行回收策略。由于这种行为,外部基础设施中关联的存储资产不会被移除。

Kubernetes v1.23 中的 PV 回收策略

新行为确保当用户手动删除 PV 时,底层存储对象会从后端删除。

如何启用新行为?

要使用新行为,您必须已将集群升级到 Kubernetes 的 v1.23 版本。您需要确保正在运行 CSI external-provisioner 版本 4.0.0 或更高版本。您还必须为 external-provisionerkube-controller-manager 启用 HonorPVReclaimPolicy 功能门控

如果您不使用 CSI 驱动程序与存储后端集成,则此修复不可用。Kubernetes 项目目前没有计划修复树内存储驱动程序的错误:这些树内驱动程序的未来是弃用并迁移到 CSI。

它是如何工作的?

新行为是通过在新的和现有 PV 上添加终结器 external-provisioner.volume.kubernetes.io/finalizer 来实现的,该终结器仅在后端存储被删除后才移除。

一个带有终结器的 PV 示例,注意终结器列表中的新终结器

kubectl get pv pvc-a7b7e3ba-f837-45ba-b243-dec7d8aaed53 -o yaml
apiVersion: v1
kind: PersistentVolume
metadata:
  annotations:
    pv.kubernetes.io/provisioned-by: csi.vsphere.vmware.com
  creationTimestamp: "2021-11-17T19:28:56Z"
  finalizers:
  - kubernetes.io/pv-protection
  - external-provisioner.volume.kubernetes.io/finalizer
  name: pvc-a7b7e3ba-f837-45ba-b243-dec7d8aaed53
  resourceVersion: "194711"
  uid: 087f14f2-4157-4e95-8a70-8294b039d30e
spec:
  accessModes:
  - ReadWriteOnce
  capacity:
    storage: 1Gi
  claimRef:
    apiVersion: v1
    kind: PersistentVolumeClaim
    name: example-vanilla-block-pvc
    namespace: default
    resourceVersion: "194677"
    uid: a7b7e3ba-f837-45ba-b243-dec7d8aaed53
  csi:
    driver: csi.vsphere.vmware.com
    fsType: ext4
    volumeAttributes:
      storage.kubernetes.io/csiProvisionerIdentity: 1637110610497-8081-csi.vsphere.vmware.com
      type: vSphere CNS Block Volume
    volumeHandle: 2dacf297-803f-4ccc-afc7-3d3c3f02051e
  persistentVolumeReclaimPolicy: Delete
  storageClassName: example-vanilla-block-sc
  volumeMode: Filesystem
status:
  phase: Bound

终结器的存在会阻止 PV 对象从集群中移除。如前所述,终结器仅在 PV 对象成功从存储后端删除后才从 PV 对象中移除。要了解有关终结器的更多信息,请参阅使用终结器控制删除

CSI 迁移的卷呢?

此修复也适用于 CSI 迁移的卷。但是,当在 1.23 上启用 HonorPVReclaimPolicy 功能且禁用 CSI 迁移时,如果 PV 对象存在终结器,则会将其移除。

一些注意事项

  1. 此修复仅适用于 CSI 卷和已迁移的卷。树内卷将表现出旧行为。
  2. 此修复作为 Alpha 功能引入到 external-provisioner 中,位于功能门控 HonorPVReclaimPolicy 下。此功能默认禁用,需要显式启用。

参考资料

我如何参与?

Kubernetes Slack 频道 SIG Storage 通信渠道是联系 SIG Storage 和迁移工作组团队的绝佳媒介。

特别感谢以下人员的深刻见解、周详考虑和宝贵贡献

  • Jan Šafránek (jsafrane)
  • Xing Yang (xing-yang)
  • Matthew Wong (wongma7)

有兴趣参与 CSI 或 Kubernetes 存储系统任何部分设计和开发的人士,请加入 Kubernetes 存储特别兴趣小组 (SIG)。我们正在快速成长,并始终欢迎新的贡献者。