zoukankan      html  css  js  c++  java
  • Volume& PersistentVolume

    Volume:
    Kubernetes中的Volume提供了在容器中挂载外部存储的能力
    Pod需要设置卷来源(spec.volume)和挂载点(spec.containers.volumeMounts)两个信息后才可以使用相应的Volume

    官方参考地址:https://kubernetes.io/docs/concepts/storage/volumes/

    1、emptyDir

    创建一个空卷,挂载到Pod中的容器。Pod删除该卷也会被删除。
    应用场景:Pod中容器之间数据共享

    [root@master01 volume]# cat emptyDir.yaml 
    apiVersion: v1
    kind: Pod
    metadata:
      name: my-pod
    spec:
    #  imagePullSecrets:
    #  - name: registry-pull-secret
      containers:
      - name: write   #一个写容器
        image: 10.192.27.111/library/busybox:1.28.4
        command: ["sh","-c","for i in {1..100};do echo $i >> /data/hello;sleep 1;done"]
        volumeMounts:
          - name: data  #使用数据卷  名字与下面一致
            mountPath: /data
      - name: read  #一个读容器
        image: 10.192.27.111/library/centos:7
        command: ["bash","-c","tail -f /data/hello"]
        volumeMounts:
          - name: data   #使用数据卷 名字与下面一致
            mountPath: /data
      volumes:
      - name: data  #新建一个数据卷
        emptyDir: {}
    [root@master01 volume]# 

    2、hostPath

    挂载Node文件系统上文件或者目录到Pod中的容器。
    应用场景:Pod中容器需要访问宿主机文件

    [root@master01 volume]# cat hostpath.yaml 
    apiVersion: v1
    kind: Pod
    metadata:
      name: my-pod
    spec:
      containers:
      - name: busybox
        image: 10.192.27.111/library/busybox:1.28.4
        args:
        - /bin/sh
        - -c
        - sleep 36000
        volumeMounts:
        - name: data
          mountPath: /data
      volumes:
      - name: data
        hostPath:
          path: /tmp
          type: Directory
    [root@master01 volume]# 
    
    
    [root@master01 volume]# kubectl apply -f hostpath.yaml 
    [root@master01 volume]# kubectl get pods
    NAME                                READY   STATUS    RESTARTS   AGE
    my-pod                              1/1     Running   0          10s
    [root@master01 volume]# kubectl get pod -o wide
    NAME                                READY   STATUS    RESTARTS   AGE     IP            NODE            NOMINATED NODE   READINESS GATES
    my-pod                              1/1     Running   0          2m19s   172.17.43.2   10.192.27.115   <none>           <none>   #查看挂载在哪个节点
    [root@master01 volume]# kubectl exec -it my-pod sh  #pod里面的 
    / # ls /data/
    systemd-private-16f6a1d6621b4a6d96d2c21f44c6bff3-chronyd.service-6Evm1r
    / # 
    [root@node01 ~]# ls /tmp/  #node01 10.192.27.115上面的  两者一样
    systemd-private-16f6a1d6621b4a6d96d2c21f44c6bff3-chronyd.service-6Evm1r
    [root@node01 ~]# 
    3、nfs
    #各个node节点安装NFS
    [root@node01 cfg]# yum -y install nfs-utils
    [root@node02 cfg]# yum -y install nfs-utils
    
    
    [root@master01 volume]# cat nfs.yaml 
    apiVersion: apps/v1beta1
    kind: Deployment
    metadata:
      name: nginx-deployment
    spec:
      replicas: 3
      selector:
        matchLabels:
          app: nginx
      template:
        metadata:
          labels:
            app: nginx
        spec:
          containers:
          - name: nginx
            image: 10.192.27.111/library/nginx:latest
            volumeMounts:
            - name: wwwroot  #使用数据卷
              mountPath: /usr/share/nginx/html
            ports:
            - containerPort: 80
          volumes:
          - name: wwwroot  #数据卷
            nfs:
              server: 10.192.27.113
              path: /home/kdzd
    [root@master01 volume]# 
    [root@master01 volume]# kubectl apply -f nfs.yaml 
    deployment.apps/nginx-deployment created
    [root@master01 volume]# kubectl get pod
    NAME                                READY   STATUS    RESTARTS   AGE
    nginx-deployment-5dfc75bdc4-5wjmj   1/1     Running   0          16s
    nginx-deployment-5dfc75bdc4-q5mrz   1/1     Running   0          16s
    nginx-deployment-5dfc75bdc4-qkmxk   1/1     Running   0          16s
    [root@master01 volume]# kubectl get ep
    NAME         ENDPOINTS                               AGE
    kubernetes   10.192.27.100:6443,10.192.27.114:6443   18d
    [root@master01 volume]# kubectl get pod -o wide
    NAME                                READY   STATUS    RESTARTS   AGE     IP            NODE            NOMINATED NODE   READINESS GATES
    nginx-deployment-5dfc75bdc4-5wjmj   1/1     Running   0          2m23s   172.17.43.3   10.192.27.115   <none>           <none>
    nginx-deployment-5dfc75bdc4-q5mrz   1/1     Running   0          2m23s   172.17.43.2   10.192.27.115   <none>           <none>
    nginx-deployment-5dfc75bdc4-qkmxk   1/1     Running   0          2m23s   172.17.46.4   10.192.27.116   <none>           <none>
    
    #测试一下
    [root@nfs-server ~]# cd /home/kdzd/
    [root@nfs-server kdzd]# vim index.html
    [root@nfs-server kdzd]# cat index.html   #10.192.27.113
    <h1>hello world!</h1>
    [root@nfs-server kdzd]# 
    
    
    [root@node02 cfg]# curl 172.17.43.2
    <h1>hello world!</h1>
    
    [root@node02 cfg]# curl 172.17.43.3
    <h1>hello world!</h1>
    
    [root@node02 cfg]# curl 172.17.46.4
    <h1>hello world!</h1>

    PersistentVolume

    PersistenVolume(PV):对存储资源创建和使用的抽象,使得存储作为集群中的资源管理
    静态
    动态
    PersistentVolumeClaim(PVC):让用户不需要关心具体的Volume实现细节

    1、静态

    手动创建pv

    [root@master01 storage]# cat pv.yaml  #麻烦 手动创建pv
    apiVersion: v1
    kind: PersistentVolume
    metadata:
      name: my-pv
    spec:
      capacity:
        storage: 5Gi
      accessModes:
        - ReadWriteMany
      nfs:
        path: /home/kdzd/data     #该目录要存在
        server: 10.192.27.113
    [root@master01 storage]# 
    [root@master01 storage]# cat pod-pvc.yaml 
    apiVersion: v1
    kind: Pod
    metadata:
      name: my-pod
    spec:
      containers:
      - name: nginx
        image: 10.192.27.111/library/nginx:latest
        ports:
        - containerPort: 80
        volumeMounts:
          - name: www
            mountPath: /usr/share/nginx/html
      volumes:
        - name: www
          persistentVolumeClaim:
            claimName: my-pvc
    
    
    ---
    
    apiVersion: v1
    kind: PersistentVolumeClaim
    metadata:
      name: my-pvc
    spec:
      accessModes:
        - ReadWriteMany
      resources:
        requests:
          storage: 5Gi
    [root@master01 storage]# 
    
    [root@master01 storage]# kubectl delete -f pod-pvc.yaml 
    pod "my-pod" deleted
    persistentvolumeclaim "my-pvc" deleted
    [root@master01 storage]# kubectl delete -f pv.yaml   注意 已使用过pv要删除掉
    persistentvolume "my-pv" deleted
    [root@master01 storage]# vim pod-pvc.yaml 
    [root@master01 storage]# kubectl apply -f pv.yaml 
    persistentvolume/my-pv created
    [root@master01 storage]# kubectl get pv
    NAME    CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS      CLAIM   STORAGECLASS   REASON   AGE
    my-pv   5Gi        RWX            Retain           Available                                   10s
    [root@master01 storage]# kubectl apply -f pod-pvc.yaml 
    pod/my-pod created
    persistentvolumeclaim/my-pvc created
    [root@master01 storage]# kubectl get pv,pvc #pv 和 pvc是通过容量和访问模式匹配
    NAME                     CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS   CLAIM            STORAGECLASS   REASON   AGE
    persistentvolume/my-pv   5Gi        RWX            Retain           Bound    default/my-pvc                           58s
    
    NAME                           STATUS   VOLUME   CAPACITY   ACCESS MODES   STORAGECLASS   AGE
    persistentvolumeclaim/my-pvc   Bound    my-pv    5Gi        RWX                           6s
    [root@master01 storage]# kubectl get pods
    NAME     READY   STATUS    RESTARTS   AGE
    my-pod   1/1     Running   0          14s
    [root@master01 storage]# kubectl exec -it my-pod bash
    root@my-pod:/# ls /usr/share/nginx/html
    index.html
    root@my-pod:/# exit
    exit
    [root@master01 storage]# kubectl get pods -o wide
    NAME     READY   STATUS    RESTARTS   AGE     IP            NODE            NOMINATED NODE   READINESS GATES
    my-pod   1/1     Running   0          3m16s   172.17.43.2   10.192.27.115   <none>           <none>
    [root@master01 storage]# 
    
    
    
    node节点上操作
    [root@node01 ~]# curl 172.17.43.2
    <h1>hello world!</h1>
    [root@node01 ~]# 

    Kubernetes支持持久卷的存储插件:https://kubernetes.io/docs/concepts/storage/persistent-volumes/

     

    2、PersistentVolume 动态供给

    Dynamic Provisioning机制工作的核心在于StorageClass的API对象。
    StorageClass声明存储插件,用于自动创建PV。
    https://github.com/kubernetes-incubator/external-storage/tree/master/nfs-client/deploy 部署的yaml文件

    [root@master01 storage-class]# ls
    deployment-nfs.yaml  nginx-demo.yaml  rbac.yaml  storageclass-nfs.yaml
    [root@master01 storage-class]# kubectl apply -f storageclass-nfs.yaml 
    storageclass.storage.k8s.io/managed-nfs-storage created
    [root@master01 storage-class]# cat storageclass-nfs.yaml 
    apiVersion: storage.k8s.io/v1beta1
    kind: StorageClass
    metadata:
      name: managed-nfs-storage
    provisioner: fuseim.pri/ifs
    [root@master01 storage-class]# 
    [root@master01 storage-class]# kubectl get StorageClass
    NAME                  PROVISIONER      AGE
    managed-nfs-storage   fuseim.pri/ifs   30s
    [root@master01 storage-class]# 
    
    [root@master01 storage-class]# kubectl apply -f rbac.yaml 
    serviceaccount/nfs-client-provisioner created
    clusterrole.rbac.authorization.k8s.io/nfs-client-provisioner-runner created
    clusterrolebinding.rbac.authorization.k8s.io/run-nfs-client-provisioner created
    [root@master01 storage-class]# cat rbac.yaml 
    apiVersion: v1
    kind: ServiceAccount
    metadata:
      name: nfs-client-provisioner
    
    ---
    
    kind: ClusterRole
    apiVersion: rbac.authorization.k8s.io/v1beta1
    metadata:
      name: nfs-client-provisioner-runner
    rules:
      - apiGroups: [""]
        resources: ["persistentvolumes"]
        verbs: ["get", "list", "watch", "create", "delete"]
      - apiGroups: [""]
        resources: ["persistentvolumeclaims"]
        verbs: ["get", "list", "watch", "update"]
      - apiGroups: ["storage.k8s.io"]
        resources: ["storageclasses"]
        verbs: ["get", "list", "watch"]
      - apiGroups: [""]
        resources: ["events"]
        verbs: ["list", "watch", "create", "update", "patch"]
    
    ---
    
    kind: ClusterRoleBinding
    apiVersion: rbac.authorization.k8s.io/v1beta1
    metadata:
      name: run-nfs-client-provisioner
    subjects:
      - kind: ServiceAccount
        name: nfs-client-provisioner
        namespace: default
    roleRef:
      kind: ClusterRole
      name: nfs-client-provisioner-runner
      apiGroup: rbac.authorization.k8s.io
    [root@master01 storage-class]# 
    [root@master01 storage-class]# cat rbac.yaml
    [root@master01 storage-class]# cat deployment-nfs.yaml 
    apiVersion: apps/v1beta1 
    kind: Deployment
    metadata:
      name: nfs-client-provisioner
    spec:
      replicas: 1
      strategy:
        type: Recreate
      template:
        metadata:
          labels:
            app: nfs-client-provisioner
        spec:
    #      imagePullSecrets:
    #        - name: registry-pull-secret
          serviceAccount: nfs-client-provisioner
          containers:
            - name: nfs-client-provisioner
              image: 10.192.27.111/lizhenliang/nfs-client-provisioner:v2.0.0
              volumeMounts:
                - name: nfs-client-root
                  mountPath: /persistentvolumes
              env:
                - name: PROVISIONER_NAME
                  value: fuseim.pri/ifs
                - name: NFS_SERVER
                  value: 10.192.27.113
                - name: NFS_PATH
                  value: /home/kdzd/data
          volumes:
            - name: nfs-client-root
              nfs:
                server: 10.192.27.113 
                path: /home/kdzd/data
    [root@master01 storage-class]# cat deployment-nfs.yaml
    [root@master01 storage-class]# kubectl get sc
    NAME                  PROVISIONER      AGE
    managed-nfs-storage   fuseim.pri/ifs   2m5s
    
    [root@master01 storage-class]# kubectl apply -f deployment-nfs.yaml 
    deployment.apps/nfs-client-provisioner created
    [root@master01 storage-class]# kubectl get pods
    NAME                                      READY   STATUS    RESTARTS   AGE
    nfs-client-provisioner-86684d5b5f-8k7x6   1/1     Running   0          6s
    [root@master01 storage-class]# 

    nginx-demo例子:https://kubernetes.io/docs/tutorials/stateful-application/basic-stateful-set/  

    [root@master01 storage-class]# cat nginx-demo.yaml 
    apiVersion: v1
    kind: Service
    metadata:
      name: nginx
      labels:
        app: nginx
    spec:
      ports:
      - port: 80
        name: web
      clusterIP: None
      selector:
        app: nginx
    ---
    apiVersion: apps/v1
    kind: StatefulSet
    metadata:
      name: web
    spec:
      selector:
        matchLabels:
          app: nginx
      serviceName: "nginx"
      replicas: 3
      template:
        metadata:
          labels:
            app: nginx
        spec:
          terminationGracePeriodSeconds: 10
          containers:
          - name: nginx
            image: 10.192.27.111/library/nginx:latest 
            ports:
            - containerPort: 80
              name: web
            volumeMounts:
            - name: www
              mountPath: /usr/share/nginx/html
      volumeClaimTemplates:
      - metadata:
          name: www
        spec:
          accessModes: [ "ReadWriteOnce" ]
          storageClassName: "managed-nfs-storage"
          resources:
            requests:
              storage: 1Gi
    [root@master01 storage-class]# 
    [root@master01 storage-class]# cat nginx-demo.yaml
    [root@master01 storage-class]# kubectl apply -f nginx-demo.yaml 
    service/nginx created
    statefulset.apps/web created
    
    
    [root@master01 storage-class]# kubectl get all
    NAME                                          READY   STATUS    RESTARTS   AGE
    pod/nfs-client-provisioner-86684d5b5f-8k7x6   1/1     Running   0          7m51s
    pod/web-0                                     1/1     Running   0          71s
    pod/web-1                                     1/1     Running   0          19s
    pod/web-2                                     1/1     Running   0          17s
    
    NAME                 TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)   AGE
    service/kubernetes   ClusterIP   10.0.0.1     <none>        443/TCP   20d
    service/nginx        ClusterIP   None         <none>        80/TCP    71s
    
    NAME                                     READY   UP-TO-DATE   AVAILABLE   AGE
    deployment.apps/nfs-client-provisioner   1/1     1            1           7m51s
    
    NAME                                                DESIRED   CURRENT   READY   AGE
    replicaset.apps/nfs-client-provisioner-86684d5b5f   1         1         1       7m51s
    
    NAME                   READY   AGE
    statefulset.apps/web   3/3     71s
    [root@master01 storage-class]# kubectl get pv,pvc
    NAME                                                                          CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS   CLAIM               STORAGECLASS          REASON   AGE
    persistentvolume/default-www-web-0-pvc-91fdee77-14a9-11ea-9860-1866dafb2f54   1Gi        RWO            Delete           Bound    default/www-web-0   managed-nfs-storage            37s
    persistentvolume/default-www-web-1-pvc-5d362b59-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            Delete           Bound    default/www-web-1   managed-nfs-storage            36s
    persistentvolume/default-www-web-2-pvc-5e5e826e-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            Delete           Bound    default/www-web-2   managed-nfs-storage            34s
    
    NAME                              STATUS   VOLUME                                                       CAPACITY   ACCESS MODES   STORAGECLASS          AGE
    persistentvolumeclaim/www-web-0   Bound    default-www-web-0-pvc-91fdee77-14a9-11ea-9860-1866dafb2f54   1Gi        RWO            managed-nfs-storage   6m17s
    persistentvolumeclaim/www-web-1   Bound    default-www-web-1-pvc-5d362b59-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            managed-nfs-storage   36s
    persistentvolumeclaim/www-web-2   Bound    default-www-web-2-pvc-5e5e826e-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            managed-nfs-storage   34s
    [root@master01 storage-class]# 
    
    
    [root@master01 storage-class]# kubectl get svc
    NAME         TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)   AGE
    kubernetes   ClusterIP   10.0.0.1     <none>        443/TCP   20d
    nginx        ClusterIP   None         <none>        80/TCP    4m52s
    [root@master01 storage-class]# kubectl get pods -o wide
    NAME                                      READY   STATUS    RESTARTS   AGE    IP            NODE            NOMINATED NODE   READINESS GATES
    nfs-client-provisioner-86684d5b5f-8k7x6   1/1     Running   0          11m    172.17.43.2   10.192.27.115   <none>           <none>
    web-0                                     1/1     Running   0          5m1s   172.17.43.3   10.192.27.115   <none>           <none>
    web-1                                     1/1     Running   0          4m9s   172.17.46.4   10.192.27.116   <none>           <none>
    web-2                                     1/1     Running   0          4m7s   172.17.43.4   10.192.27.115   <none>           <none>
    [root@master01 storage-class]# 
    
    
    测试一下:
    [root@nfs-server kdzd]# ls data/
    default-www-web-0-pvc-91fdee77-14a9-11ea-9860-1866dafb2f54  default-www-web-1-pvc-5d362b59-14aa-11ea-9860-1866dafb2f54  default-www-web-2-pvc-5e5e826e-14aa-11ea-9860-1866dafb2f54
    [root@nfs-server kdzd]# ls data/default-www-web-0-pvc-91fdee77-14a9-11ea-9860-1866dafb2f54/
    [root@nfs-server kdzd]# cp index.html data/default-www-web-0-pvc-91fdee77-14a9-11ea-9860-1866dafb2f54/
    [root@nfs-server kdzd]# cp index.html data/default-www-web-1-pvc-5d362b59-14aa-11ea-9860-1866dafb2f54/
    [root@nfs-server kdzd]# cp index.html data/default-www-web-2-pvc-5e5e826e-14aa-11ea-9860-1866dafb2f54/
    [root@nfs-server kdzd]# 
    
    [root@node01 ~]# curl 172.17.43.3
    <h1>hello world!</h1>
    [root@node01 ~]# 

    Kubernetes支持动态供给的存储插件: https://kubernetes.io/docs/concepts/storage/storage-classes/

    [root@master01 storage]# cat pod-pvc.yaml 
    apiVersion: v1
    kind: Pod
    metadata:
      name: my-pod
    spec:
      containers:
      - name: nginx
        image: 10.192.27.111/library/nginx:latest
        ports:
        - containerPort: 80
        volumeMounts:
          - name: www
            mountPath: /usr/share/nginx/html
      volumes:
        - name: www
          persistentVolumeClaim:
            claimName: my-pvc
    
    
    ---
    
    apiVersion: v1
    kind: PersistentVolumeClaim
    metadata:
      name: my-pvc
    spec:
      accessModes:
        - ReadWriteMany
      storageClassName: managed-nfs-storage
      resources:
        requests:
          storage: 5Gi
    [root@master01 storage]# 
    
    [root@master01 storage]# vim pod-pvc.yaml 
    [root@master01 storage]# kubectl apply -f pod-pvc.yaml 
    pod/my-pod created
    persistentvolumeclaim/my-pvc created
    [root@master01 storage]# kubectl get pods -o wide
    NAME                                      READY   STATUS    RESTARTS   AGE     IP            NODE            NOMINATED NODE   READINESS GATES
    my-pod                                    1/1     Running   0          5s      172.17.43.5   10.192.27.115   <none>           <none>
    nfs-client-provisioner-86684d5b5f-8k7x6   1/1     Running   0          15m     172.17.43.2   10.192.27.115   <none>           <none>
    web-0                                     1/1     Running   0          9m15s   172.17.43.3   10.192.27.115   <none>           <none>
    web-1                                     1/1     Running   0          8m23s   172.17.46.4   10.192.27.116   <none>           <none>
    web-2                                     1/1     Running   0          8m21s   172.17.43.4   10.192.27.115   <none>           <none>
    [root@master01 storage]# kubectl get pv,pvc
    NAME                                                                          CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS   CLAIM               STORAGECLASS          REASON   AGE
    persistentvolume/default-my-pvc-pvc-85a2e9bf-14ab-11ea-9860-1866dafb2f54      5Gi        RWX            Delete           Bound    default/my-pvc      managed-nfs-storage            14s
    persistentvolume/default-www-web-0-pvc-91fdee77-14a9-11ea-9860-1866dafb2f54   1Gi        RWO            Delete           Bound    default/www-web-0   managed-nfs-storage            8m33s
    persistentvolume/default-www-web-1-pvc-5d362b59-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            Delete           Bound    default/www-web-1   managed-nfs-storage            8m32s
    persistentvolume/default-www-web-2-pvc-5e5e826e-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            Delete           Bound    default/www-web-2   managed-nfs-storage            8m30s
    
    NAME                              STATUS   VOLUME                                                       CAPACITY   ACCESS MODES   STORAGECLASS          AGE
    persistentvolumeclaim/my-pvc      Bound    default-my-pvc-pvc-85a2e9bf-14ab-11ea-9860-1866dafb2f54      5Gi        RWX            managed-nfs-storage   14s
    persistentvolumeclaim/www-web-0   Bound    default-www-web-0-pvc-91fdee77-14a9-11ea-9860-1866dafb2f54   1Gi        RWO            managed-nfs-storage   14m
    persistentvolumeclaim/www-web-1   Bound    default-www-web-1-pvc-5d362b59-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            managed-nfs-storage   8m32s
    persistentvolumeclaim/www-web-2   Bound    default-www-web-2-pvc-5e5e826e-14aa-11ea-9860-1866dafb2f54   1Gi        RWO            managed-nfs-storage   8m30s
    [root@master01 storage]# 
    静态的pod-pvc.yaml 改成动态的
  • 相关阅读:
    Lua脚本语法说明(修订)
    C++ 程序文档生成器介绍(doxygen)
    [转]最快速度找到内存泄漏
    MyEclipse 8.5下安装tomcat插件
    Linux解压rar文件(unrar安装和使用,分卷解压)
    禁止root用户远程登录或者禁止其他用户登录而不删除它
    linux配置IP的方法
    log4j xml配置详解
    Sqlldr使用介绍
    Linux查看CPU和内存使用情况
  • 原文地址:https://www.cnblogs.com/linux985/p/11969299.html
Copyright © 2011-2022 走看看