k8s存储之Volumes卷类型

一.Volumes配置管理

(一)容器中的文件在磁盘上是临时存放的,这给容器中运行的特殊应用程序带来一些问题。首先,当容器崩溃时,kubelet 将重新启动容器,容器中的文件将会丢失,因为容器会以干净的状态重建。其次,当在一个 Pod 中同时运行多个容器时,常常需要在这些容器之间共享文件。 Kubernetes 抽象出 Volume 对象来解决这两个问题。
(二)Kubernetes 卷具有明确的生命周期,与包裹它的 Pod 相同。 因此,卷比 Pod 中运行的任何容器的存活期都长,在容器重新启动时数据也会得到保留。 当然,当一个 Pod 不再存在时,卷也将不再存在。也许更重要的是,Kubernetes 可以支持许多类型的卷,Pod 也能同时使用任意数量的卷。
(三)卷不能挂载到其他卷,也不能与其他卷有硬链接。 Pod 中的每个容器必须独立地指定每个卷的挂载位置
(四)Kubernetes 支持类型的卷
1.emptyDir卷
(1)当 Pod 指定到某个节点上时,首先创建的是一个 emptyDir 卷,并且只要 Pod 在该节点上运行,卷就一直存在。 就像它的名称表示的那样,卷最初是空的。 尽管 Pod 中的容器挂载 emptyDir 卷的路径可能相同也可能不同,但是这些容器都可以读写 emptyDir 卷中相同的文件。 当 Pod 因为某些原因被从节点上删除时,emptyDir 卷中的数据也会永久删除
(2)emptyDir 的使用场景:
缓存空间,例如基于磁盘的归并排序。
为耗时较长的计算任务提供检查点,以便任务能方便地从崩溃前状态恢复执行。
在 Web 服务器容器服务数据时,保存内容管理器容器获取的文件
(3)创建与使用

cat emptydir.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: vol1
spec:
  containers:
  - image: busyboxplus
    name: vm1
    stdin: true
    tty: true
    volumeMounts:
    - mountPath: /cache
      name: cache-volume
  - name: vm2
    image: myapp:v1
    volumeMounts:
    - mountPath: /usr/share/nginx/html
      name: cache-volume
  volumes:
  - name: cache-volume
    emptyDir:
      medium: Memory
      sizeLimit: 100Mi

kubectl apply -f emptydir.yaml

在这里插入图片描述
k8s存储之Volumes卷类型_第1张图片
在这里插入图片描述
k8s存储之Volumes卷类型_第2张图片
k8s存储之Volumes卷类型_第3张图片
可以看到文件超过sizeLimit,则一段时间后(1-2分钟)会被kubelet evict掉。之所以不是“立即”被evict,是因为kubelet是定期进行检查的,这里会有一个时间差
(4)emptydir缺点:
不能及时禁止用户使用内存。虽然过1-2分钟kubelet会将Pod挤出,但是这个时间内,其实对node还是有风险的;
影响kubernetes调度,因为empty dir并不涉及node的resources,这样会造成Pod“偷偷”使用了node的内存,但是调度器并不知晓;
用户不能及时感知到内存不可用
2.hostPath 卷
(1)hostPath 卷能将主机节点文件系统上的文件或目录挂载到您的 Pod 中。 虽然这不是大多数 Pod 需要的,但是它为一些应用程序提供了强大的逃生舱。
(2)hostPath 的一些用法有:
运行一个需要访问 Docker 引擎内部机制的容器,挂载 /var/lib/docker 路径。
在容器中运行 cAdvisor 时,以 hostPath 方式挂载 /sys。
允许 Pod 指定给定的 hostPath 在运行 Pod 之前是否应该存在,是否应该创建以及应该以什么方式存在。
除了必需的 path 属性之外,用户可以选择性地为 hostPath 卷指定 typek8s存储之Volumes卷类型_第4张图片
(3)注意当使用这种类型的卷时要小心,因为:
具有相同配置(例如从 podTemplate 创建)的多个 Pod 会由于节点上文件的不同而在不同节点上有不同的行为。
当 Kubernetes 按照计划添加资源感知的调度时,这类调度机制将无法考虑由 hostPath 使用的资源。
基础主机上创建的文件或目录只能由 root 用户写入。您需要在 特权容器 中以 root 身份运行进程,或者修改主机上的文件权限以便容器能够写入 hostPath 卷

apiVersion: v1
kind: Pod
metadata:
  name: test-pd
spec:
  containers:
  - image: myapp:v1
    name: vm1
    volumeMounts:
    - mountPath: /usr/share/nginx/html
      name: test-volume
  volumes:
  - name: test-volume
    hostPath:
      path: /webdata
      type: DirectoryOrCreate

# pod调度节点自动创建相关目录

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
3.nfs卷
nfs 卷能将 NFS (网络文件系统) 挂载到你的 Pod 中。 不像 emptyDir 那样会在删除 Pod 的同时也会被删除,nfs 卷的内容在删除 Pod 时会被保存,卷只是被卸载。 这意味着 nfs 卷可以被预先填充数据,并且这些数据可以在 Pod 之间共享

server1作为nfs共享主机
yum install nfs-utils -y
vim /etc/exports
/nfsdata        *(rw,no_root_squash)
systemctl enable --now rpcbind
systemctl enable --now nfs
[root@server1 harbor]# showmount -e
Export list for server1:
/nfsdata *
vim nfs.yaml
apiVersion: v1
kind: Pod
metadata:
  name: nfs-pd
spec:
  containers:
  - image: myapp:v1
    name: vm1
    volumeMounts:
    - mountPath: /usr/share/nginx/html
      name: test-volume
  volumes:
  - name: test-volume
    nfs:
      server: 172.25.2.1
      path: /nfsdata
kubectl apply -f nfs.yaml
yum install nfs-utils -y  #在节点处server3也要安装nfs管理工具

在这里插入图片描述
k8s存储之Volumes卷类型_第5张图片
4.持久卷

(1)静态供应

# 创建NFS PV卷,持久卷(PersistentVolume,PV)是集群中的一块存储,做了三个持久卷,有不同的访问模式
apiVersion: v1
kind: PersistentVolume
metadata:
  name: pv1
spec:
  capacity:
    storage: 5Gi
  volumeMode: Filesystem
  accessModes:
    - ReadWriteOnce  #单点只读,该volume只能被单个节点以读写的方式映射
  persistentVolumeReclaimPolicy: Recycle  #回收策略,
当前,只有NFS和HostPath支持回收利用,AWS EBS,GCE PD,Azure Disk,or OpenStack Cinder卷支持删除操作
  storageClassName: nfs
  nfs:
    path: /nfsdata/pv1
    server: 172.25.2.1
---
apiVersion: v1
kind: PersistentVolume
metadata:
  name: pv2
spec:
  capacity:
    storage: 10Gi
  volumeMode: Filesystem
  accessModes:
    - ReadWriteMany  #多点读写
  persistentVolumeReclaimPolicy: Recycle
  storageClassName: nfs
  nfs:
    path: /nfsdata/pv2
    server: 172.25.2.1
---
apiVersion: v1
kind: PersistentVolume
metadata:
  name: pv3
spec:
  capacity:
    storage: 20Gi
  volumeMode: Filesystem
  accessModes:
    - ReadOnlyMany  #多点只读
  persistentVolumeReclaimPolicy: Recycle
  storageClassName: nfs
  nfs:
    path: /nfsdata/pv3
    server: 172.25.2.1

kubectl apply -f pv.yml

状态:
Available:空闲的资源,未绑定给PVC
Bound:绑定给了某个PVC
Released:PVC已经删除了,但是PV还没有被集群回收
Failed:PV在自动回收中失败了
命令行可以显示PV绑定的PVC名称
在这里插入图片描述

# pvc 和pod,持久卷申领(PersistentVolumeClaim,PVC)表达的是用户对存储的请求,让pod挂载pv
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: pvc1
spec:
  storageClassName: nfs
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 5Gi
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: pvc2
spec:
  storageClassName: nfs
  accessModes:
    - ReadWriteMany
  resources:
    requests:
      storage: 10Gi

---
apiVersion: v1
kind: Pod
metadata:
  name: test-pd
spec:
  containers:
  - image: myapp:v1
    name: nginx
    volumeMounts:
    - mountPath: /usr/share/nginx/html
      name: nfs-pv
  volumes:
  - name: nfs-pv
    persistentVolumeClaim:
      claimName: pvc1

---
apiVersion: v1
kind: Pod
metadata:
  name: test-pd-2
spec:
  containers:
  - image: myapp:v1
    name: nginx
    volumeMounts:
    - mountPath: /usr/share/nginx/html
      name: nfs-pv-2
  volumes:
  - name: nfs-pv-2
    persistentVolumeClaim:
      claimName: pvc2

在这里插入图片描述
在这里插入图片描述
k8s存储之Volumes卷类型_第6张图片
k8s存储之Volumes卷类型_第7张图片
k8s存储之Volumes卷类型_第8张图片
k8s存储之Volumes卷类型_第9张图片
(2)动态供应
NFS Client Provisioner是一个automatic provisioner,使用NFS作为存储,自动创建PV和对应的PVC,本身不提供NFS存储,需要外部先有一套NFS存储服务。

PV以 ${namespace}-${pvcName}-${pvName}的命名格式提供(在NFS服务器上)
PV回收的时候以 archieved-${namespace}-${pvcName}-${pvName} 的命名格式(在NFS服务器上)

NFS动态分配源码

docker pull heegor/nfs-subdir-external-provisioner:v4.0.0  #并上传到本地仓库

k8s存储之Volumes卷类型_第10张图片
k8s存储之Volumes卷类型_第11张图片
在参考文件上面,其中rbac.yaml配置授权,deployment.yml部署NFS Client Provisioner,class.yaml创建 NFS SotageClass,根据自己实际情况修改镜像位置,nfs服务端,和备份设置,也可以部署在其他namespace中,方便pod管理
k8s存储之Volumes卷类型_第12张图片
k8s存储之Volumes卷类型_第13张图片
a.这里我将上面的三个文件全部放在deploy.yaml,动态卷分配器的安装
kubectl apply -f deploy.yaml
k8s存储之Volumes卷类型_第14张图片
k8s存储之Volumes卷类型_第15张图片

#b pvc创建
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: test-claim
spec:
  storageClassName: managed-nfs-storage
  accessModes:
    - ReadWriteMany
  resources:
    requests:
      storage: 2Gi

在这里插入图片描述
在这里插入图片描述

#c pod使用卷
kind: Pod
apiVersion: v1
metadata:
  name: test-pod
spec:
  containers:
  - name: test-pod
    image: myapp:v1
    volumeMounts:
      - name: nfs-pvc
        mountPath: "/usr/share/nginx/html"
  volumes:
    - name: nfs-pvc
      persistentVolumeClaim:
        claimName: test-claim

NFS服务端
在这里插入图片描述
k8s存储之Volumes卷类型_第16张图片

#c 动态创建多个卷
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: test-claim-2
spec:
  storageClassName: managed-nfs-storage
  accessModes:
    - ReadOnlyMany
  resources:
    requests:
      storage: 5Gi
---
kind: Pod
apiVersion: v1
metadata:
  name: test-pod-2
spec:
  containers:
  - name: test-pod-2
    image: myapp:v1
    volumeMounts:
      - name: nfs-pvc
        mountPath: "/usr/share/nginx/html"
  volumes:
    - name: nfs-pvc
      persistentVolumeClaim:
        claimName: test-claim-2

k8s存储之Volumes卷类型_第17张图片
在这里插入图片描述
在这里插入图片描述
5.StorageClass资源
A.StorageClass提供了一种描述存储类(class)的方法,不同的class可能会映射到不同的服务质量等级和备份策略或其他策略等。
更多了解
B.每个 StorageClass 都包含 provisioner、parameters 和 reclaimPolicy 字段, 这些字段会在StorageClass需要动态分配 PersistentVolume 时会使用到。
C.StorageClass的属性
Provisioner(存储分配器):用来决定使用哪个卷插件分配 PV,该字段必须指定。可以指定内部分配器,也可以指定外部分配器。外部分配器的代码地址为: kubernetes-incubator/external-storage,其中包括NFS和Ceph等。
Reclaim Policy(回收策略):通过reclaimPolicy字段指定创建的Persistent Volume的回收策略,回收策略包括:Delete 或者 Retain,没有指定默认为Delete
在这里插入图片描述
D.默认的 StorageClass 将被用于动态的为没有特定 storage class 需求的 PersistentVolumeClaims 配置存储:(只能有一个默认StorageClass),如果没有默认StorageClass,PVC 也没有指定storageClassName 的值,那么意味着它只能够跟 storageClassName 也是“”的 PV 进行绑定
kubectl patch storageclass managed-nfs-storage -p ‘{“metadata”: {“annotations”:{“storageclass.kubernetes.io/is-default-class”:“true”}}}’
在这里插入图片描述

你可能感兴趣的:(k8s,k8s数据卷)