排查存储问题

本文档介绍存储问题排查指南。

如果您需要其他帮助,请与 Cloud Customer Care 联系。

无法挂接卷

如果虚拟磁盘挂接到错误的虚拟机,就会出现此问题,这可能是由于 Kubernetes 1.12 中的问题 #32727 造成的。

gkectl diagnose cluster 的输出类似于以下示例:

Checking cluster object...PASS
Checking machine objects...PASS
Checking control plane pods...PASS
Checking gke-connect pods...PASS
Checking kube-system pods...PASS
Checking gke-system pods...PASS
Checking storage...FAIL
    PersistentVolume pvc-776459c3-d350-11e9-9db8-e297f465bc84: virtual disk "[datastore_nfs] kubevols/kubernetes-dynamic-pvc-776459c3-d350-11e9-9db8-e297f465bc84.vmdk" IS attached to machine "gsl-test-user-9b46dbf9b-9wdj7" but IS NOT listed in the Node.Status
1 storage errors

在此示例中,一个或多个 Pod 卡在 ContainerCreating 状态,并显示类似于以下示例输出的警告:

Events:
  Type     Reason              Age               From                     Message
  ----     ------              ----              ----                     -------
  Warning  FailedAttachVolume  6s (x6 over 31s)  attachdetach-controller  AttachVolume.Attach failed for volume "pvc-776459c3-d350-11e9-9db8-e297f465bc84" : Failed to add disk 'scsi0:6'.

如果虚拟磁盘挂接到错误的虚拟机,您可以按照以下步骤手动分离该磁盘:

  1. 排空节点。 您可以视需要在 kubectlde 命令中包含 --ignore-daemonsets--delete-local-data 标志。

  2. 关闭虚拟机电源

  3. 在 vCenter 中修改虚拟机的硬件配置以移除卷。

  4. 开启虚拟机

  5. 取消封锁节点

卷丢失

如果虚拟磁盘已被永久删除,则可能会出现此问题。如果操作员手动删除虚拟磁盘或删除挂接该磁盘的虚拟机,则可能会发生这种情况。

如果您看到与 VMDK 文件相关的“未找到”错误,则虚拟磁盘可能已被永久删除。

gkectl diagnose cluster 的输出类似于以下输出:

Checking cluster object...PASS
Checking machine objects...PASS
Checking control plane pods...PASS
Checking gke-connect pods...PASS
Checking kube-system pods...PASS
Checking gke-system pods...PASS
Checking storage...FAIL
    PersistentVolume pvc-52161704-d350-11e9-9db8-e297f465bc84: virtual disk "[datastore_nfs] kubevols/kubernetes-dynamic-pvc-52161704-d350-11e9-9db8-e297f465bc84.vmdk" IS NOT found
1 storage errors

一个或多个 Pod 卡在 ContainerCreating 状态,如以下示例所示:

Events:
  Type     Reason              Age                   From                                    Message
  ----     ------              ----                  ----                                    -------
  Warning  FailedAttachVolume  71s (x28 over 42m)    attachdetach-controller                 AttachVolume.Attach failed for volume "pvc-52161704-d350-11e9-9db8-e297f465bc84" : File []/vmfs/volumes/43416d29-03095e58/kubevols/
  kubernetes-dynamic-pvc-52161704-d350-11e9-9db8-e297f465bc84.vmdk was not found

为了防止出现此问题,请按照调整用户集群大小升级集群中所述管理虚拟机。

如需解决此问题,您可以手动清理相关的 Kubernetes 资源:

  1. 通过运行 kubectl delete pvc [PVC_NAME] 删除引用了 PV 的 PVC。

  2. 通过运行 kubectl delete pod [POD_NAME] 删除引用了 PVC 的 Pod。

  3. 针对 Kubernetes 问题 #74374,重复第 2 步。

vSphere CSI 卷分离失败

如果没有向 vSphere 用户授予 CNS > Searchable 权限,则会出现此问题。

如果您发现 pod 卡在 ContainerCreating 阶段并显示 FailedAttachVolume 警告,这可能是由于其他节点上的分离失败造成的。

如需检查 CSI 分离错误,请运行以下命令:

kubectl get volumeattachments -o=custom-columns=NAME:metadata.name,DETACH_ERROR:status.detachError.message

输出类似于以下示例:

NAME                                                                   DETACH_ERROR
csi-0e80d9be14dc09a49e1997cc17fc69dd8ce58254bd48d0d8e26a554d930a91e5   rpc error: code = Internal desc = QueryVolume failed for volumeID: "57549b5d-0ad3-48a9-aeca-42e64a773469". ServerFaultCode: NoPermission
csi-164d56e3286e954befdf0f5a82d59031dbfd50709c927a0e6ccf21d1fa60192d   <none>
csi-8d9c3d0439f413fa9e176c63f5cc92bd67a33a1b76919d42c20347d52c57435c   <none>
csi-e40d65005bc64c45735e91d7f7e54b2481a2bd41f5df7cc219a2c03608e8e7a8   <none>

如需解决此问题,请向您的 vCenter 用户帐号添加 CNS > Searchable 权限。分离操作会自动重试,直到执行成功。

ESXi 主机不支持 vSphere CSI 驱动程序

当 vSphere 集群中的 ESXi 主机运行低于 ESXi 6.7U3 的版本时,会出现此问题。

gkectl check-config 的输出包含以下警告:

The vSphere CSI driver is not supported on current ESXi host versions.
CSI requires ESXi 6.7U3 or above. See logs for ESXi version details.

要解决此问题,请将 ESXi 主机升级到 6.7U3 或更高版本。

CSI 卷创建失败并显示 NotSupported 错误

当 vSphere 集群中的 ESXi 主机运行低于 ESXi 6.7U3 的版本时,会出现此问题。

kubectl describe pvc 的输出包含以下错误:

Failed to provision volume with StorageClass <standard-rwo>: rpc error:
code = Internal desc = Failed to create volume. Error: CnsFault error:
CNS: Failed to create disk.:Fault cause: vmodl.fault.NotSupported

要解决此问题,请将 ESXi 主机升级到 6.7U3 或更高版本。

vSphere CSI 卷挂接失败

当节点关闭、删除或故障时,开源 vSphere CSI 驱动程序中的这一 Kubernetes 已知问题会发生。

kubectl describe pod 的输出如下所示:

Events:
 Type    Reason                 From                     Message
 ----    ------             ... ----                     -------
 Warning FailedAttachVolume ... attachdetach-controller  Multi-Attach error for volume
                                                         "pvc-xxxxx"
                                                         Volume is already exclusively attached to one
                                                         node and can't be attached to another

如需解决此问题,请完成以下步骤:

  1. 请记下上述输出中 PersistentVolumeClaim (PVC) 的名称,并找到与 PVC 关联的 VolumeAttachment:

    kubectl get volumeattachments | grep pvc-xxxxx
    

    以下示例输出显示了 VolumeAttachment 的名称:

    csi-yyyyy   csi.vsphere.vmware.com   pvc-xxxxx   node-zzzzz ...
    
  2. 描述 VolumeAttachment:

    kubectl describe volumeattachments csi-yyyyy | grep "Deletion Timestamp"
    

    记下删除时间戳,如以下示例所示:

    Deletion Timestamp:   2021-03-10T22:14:58Z
    
  3. 等待删除时间戳指定的时间,然后强制删除 VolumeAttachment。为此,请修改 VolumeAttachment 对象并删除终结器。

    kubectl edit volumeattachment csi-yyyyy
    

    删除终结器:

    [...]
      Finalizers:
       external-attacher/csi-vsphere-vmware-com
    

vSphere CSI VolumeSnapshot 由于版本无法准备就绪

当 vCenter Server 或 ESXi 主机版本低于 7.0 Update 3 时,就会出现此问题。

kubectl describe volumesnapshot 的输出包含如下错误:

rpc error: code = Unimplemented desc = VC version does not support snapshot operations.

如需解决此问题,请将 vCenter Server 和 ESXi 主机升级到 7.0 Update 3 或更高版本。

vSphere CSI VolumeSnapshot 由于每个卷的快照数上限无法准备就绪

当每个卷的快照数达到 vSphere 容器存储驱动程序的最大值时,就会出现此问题。默认值为 3。

kubectl describe volumesnapshot 的输出包含如下错误:

rpc error: code = FailedPrecondition desc = the number of snapshots on the source volume 5394aac1-bc0a-44e2-a519-1a46b187af7b reaches the configured maximum (3)

如需解决此问题,请按照以下步骤更新每个卷的快照数上限:

  1. 获取向 vSphere CSI 控制器提供 vSphere 配置的 Secret 的名称:

    kubectl --kubeconfig <var class="edit">ADMIN_CLUSTER_KUBECONFIG</var> get deployment vsphere-csi-controller \
        --namespace <var class="edit">USER_CLUSTER_NAME</var> \
        --output json \
        | jq -r '.spec.template.spec.volumes[] \
        | select(.name=="vsphere-secret") .secret.secretName'
    

    请替换以下内容:

    • ADMIN_KUBECONFIG:管理员集群 kubeconfig 文件的路径
    • USER_CLUSTER_NAME:您的用户集群的名称
  2. 从 Secret 中获取 data.config 的值,对其进行 base64 解码,然后将其保存在名为 config.txt 的文件中:

    kubectl --kubeconfig <var class="edit">ADMIN_CLUSTER_KUBECONFIG</var> get secret <var class="edit">SECRET_NAME</var> \
        --namespace <var class="edit">USER_CLUSTER_NAME </var> \
        --output json | jq -r '.data["config"]' | base64 -d > config.txt
    

    SECRET_NAME 替换为上一步中 Secret 的名称。

  3. 打开 config.txt 进行修改:

    [Snapshot] 部分中修改或添加 global-max-snapshots-per-block-volume 字段,如以下示例所示:

    [Global]
    cluster-id = "my-user-cluster"
    insecure-flag = "0"
    user = "my-account.local"
    password = "fxqSD@SZTUIsG"
    [VirtualCenter "my-vCenter"]
    port = "443"
    datacenters = "my-datacenter1"
    [Snapshot]
    global-max-snapshots-per-block-volume = 4
    
  4. 删除并重新创建 Secret:

    kubectl --kubeconfig <var class="edit">ADMIN_CLUSTER_KUBECONFIG</var> delete secret <var class="edit">SECRET_NAME</var> \
        --namespace <var class="edit">USER_CLUSTER_NAME</var>
    
    kubectl --kubeconfig <var class="edit">ADMIN_CLUSTER_KUBECONFIG</var> create secret generic <var class="edit">SECRET_NAME</var> \
        --namespace <var class="edit">USER_CLUSTER_NAME</var> \
        --from-file=config
    
  5. 重启 vsphere-csi-controller Deployment:

    kubectl --kubeconfig <var class="edit">ADMIN_CLUSTER_KUBECONFIG</var> rollout restart deployment vsphere-csi-controller \
        --namespace <var class="edit">USER_CLUSTER_NAME</var>
    

后续步骤

如果您需要其他帮助,请与 Cloud Customer Care 联系。