【问题标题】:How to mount a persistent volume on a Deployment/Pod using PersistentVolumeClaim?如何使用 PersistentVolumeClaim 在 Deployment/Pod 上挂载持久卷?
【发布时间】:2020-03-04 19:26:39
【问题描述】:

我正在尝试在 pod 上挂载一个持久卷(通过部署)。

apiVersion: apps/v1
kind: Deployment
spec:
  template:
    spec:
      containers:
      - image: ...
        volumeMounts:
        - mountPath: /app/folder
          name: volume
      volumes:
      - name: volume
        persistentVolumeClaim:
          claimName: volume-claim
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: volume-claim
spec:
  accessModes:
  - ReadWriteOnce
  resources:
    requests:
      storage: 2Gi

但是,pod 保持在“ContainerCreating”状态,并且事件显示以下错误消息。

Unable to mount volumes for pod "podname": timeout expired waiting for volumes to attach or mount for pod "namespace"/"podname". list of unmounted volumes=[volume]. list of unattached volumes=[volume]

我验证了持久卷声明没有问题并绑定到持久卷。

我在这里错过了什么?

【问题讨论】:

  • 您是在本地执行此操作还是通过任何云提供商执行此操作?
  • @paltaa 集群在 GKE 上
  • 你的Deployment中有多少个副本?
  • @znat 你似乎对 GKE storageClass 有问题,做一个 kubectl describe sc,同时检查持久卷是否用 kubectl get pv 配置,然后用 kubectl describe pv 描述它 并发布任何活动

标签: kubernetes google-kubernetes-engine persistent-volume-claims


【解决方案1】:

当您在 GKE 集群中创建 PVC 而不指定 PVStorageClass 类型时,它将回退到默认选项:

  • StorageClass: standard
  • Provisioner: kubernetes.io/gce-pd
  • Type: pd-standard

请看官方文档:Cloud.google.com: Kubernetes engine persistent volumes

可能有很多情况会产生遇到的错误消息。

由于不知道您的部署中有多少副本以及节点数量以及如何在这些节点上安排 pod,因此我尝试重现您的问题,但在执行以下步骤时遇到了相同的错误(GKE 集群是全新的创建以防止任何其他可能影响行为的依赖项)。

步骤

  • 创建 PVC
  • 使用replicas > 1 创建部署
  • 检查 pod 的状态
  • 其他链接

创建 PVC

下面是 YAML 的示例 PVC 的定义与您的相同:

apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: volume-claim
spec:
  accessModes:
  - ReadWriteOnce
  resources:
    requests:
      storage: 2Gi

应用上述定义后,请检查它是否创建成功。您可以使用以下命令来完成:

  • $ kubectl get pvc volume-claim
  • $ kubectl get pv
  • $ kubectl describe pvc volume-claim
  • $ kubectl get pvc volume-claim -o yaml

使用replicas > 1 创建部署

下面是YAML 部署定义示例,volumeMountsreplicas > 1:

apiVersion: apps/v1 
kind: Deployment
metadata:
  name: ubuntu-deployment
spec:
  selector:
    matchLabels:
      app: ubuntu
  replicas: 10 # amount of pods must be > 1
  template:
    metadata:
      labels:
        app: ubuntu
    spec:
      containers:
      - name: ubuntu
        image: ubuntu
        command:
        - sleep
        - "infinity"
        volumeMounts:
        - mountPath: /app/folder
          name: volume
      volumes:
      - name: volume
        persistentVolumeClaim:
          claimName: volume-claim

应用它并等待一段时间。

检查 pod 的状态

您可以使用以下命令检查 pod 的状态:

$ kubectl get pods -o wide

上述命令的输出:

NAME                      READY   STATUS              RESTARTS   AGE     IP            NODE                              
ubuntu-deployment-2q64z   0/1     ContainerCreating   0          4m27s   <none>        gke-node-1  
ubuntu-deployment-4tjp2   1/1     Running             0          4m27s   10.56.1.14    gke-node-2   
ubuntu-deployment-5tn8x   0/1     ContainerCreating   0          4m27s   <none>        gke-node-1   
ubuntu-deployment-5tn9m   0/1     ContainerCreating   0          4m27s   <none>        gke-node-3  
ubuntu-deployment-6vkwf   0/1     ContainerCreating   0          4m27s   <none>        gke-node-1  
ubuntu-deployment-9p45q   1/1     Running             0          4m27s   10.56.1.12    gke-node-2  
ubuntu-deployment-lfh7g   0/1     ContainerCreating   0          4m27s   <none>        gke-node-3  
ubuntu-deployment-qxwmq   1/1     Running             0          4m27s   10.56.1.13    gke-node-2 
ubuntu-deployment-r7k2k   0/1     ContainerCreating   0          4m27s   <none>        gke-node-3   
ubuntu-deployment-rnr72   0/1     ContainerCreating   0          4m27s   <none>        gke-node-3

看看上面的输出:

  • 3 个 pod 处于 Running 状态
  • 7 个 pod 处于ContainerCreating 状态

所有Running pod 都位于同一个gke-node-2

您可以通过以下方式获取更多详细信息,了解 pod 为何处于 ContainerCreating 状态:

$ kubectl describe pod NAME_OF_POD_WITH_CC_STATE

上面命令中的Events部分显示:

Events:
  Type     Reason              Age                From                                             Message
  ----     ------              ----               ----                                             -------
  Normal   Scheduled           14m                default-scheduler                                Successfully assigned default/ubuntu-deployment-2q64z to gke-node-1
  Warning  FailedAttachVolume  14m                attachdetach-controller                          Multi-Attach error for volume "pvc-7d756147-6434-11ea-a666-42010a9c0058" Volume is already used by pod(s) ubuntu-deployment-qxwmq, ubuntu-deployment-9p45q, ubuntu-deployment-4tjp2
  Warning  FailedMount         92s (x6 over 12m)  kubelet, gke-node-1  Unable to mount volumes for pod "ubuntu-deployment-2q64z_default(9dc28e95-6434-11ea-a666-42010a9c0058)": timeout expired waiting for volumes to attach or mount for pod "default"/"ubuntu-deployment-2q64z". list of unmounted volumes=[volume]. list of unattached volumes=[volume default-token-dnvnj]

Pod 无法通过 ContainerCreating 状态,因为 volume 挂载失败。提到的 volume 已被不同节点上的其他 pod 使用。

ReadWriteOnce: Volume 可以被单个节点以读写方式挂载。

其他链接

请看:Cloud.google.com: Access modes of persistent volumes

关于访问模式的话题有详细解答:Stackoverflow.com: Why can you set multiple accessmodes on a persistent volume

由于您不知道您想要实现什么,请查看 Deployment 和 Statefulsets 之间的比较:Cloud.google.com: Persistent Volume: Deployments vs statefulsets

【讨论】:

    【解决方案2】:

    如果在云提供商中执行此操作,storageClass 对象将为您的持久卷声明创建相应的卷。

    如果您尝试在 minikube 本地或自我管理的 kubernetes 集群中执行此操作,则需要手动创建将为您提供卷的 storageClass,或者像以下示例一样手动创建它:

    apiVersion: v1
    kind: PersistentVolume
    metadata:
      name: task-pv-volume
      labels:
        type: local
    spec:
      storageClassName: manual
      capacity:
        storage: 2Gi
      accessModes:
        - ReadWriteOnce
      hostPath:
        path: "/mnt/data"
    

    hostPath 变量会将这些数据挂载到当前的 pod 节点中。

    【讨论】:

    • 谢谢,集群在 GKE 中
    猜你喜欢
    • 2020-09-30
    • 1970-01-01
    • 2018-06-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-08-23
    • 2022-01-24
    • 2021-06-02
    相关资源
    最近更新 更多