-required-
3、创建pv
[root@k8s-master ~]# cat pv.yaml
apiVersion: v1
kind: PersistentVolume
metadata:
name: v1
spec:
capacity:
storage: 1Gi #pv的存储空间容量
accessModes: ["ReadWriteOnce"]
nfs:
path: /data/v1 #把nfs的存储空间创建成pv
server: 192.168.166.7 #nfs服务器的地址
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v2
spec:
capacity:
storage: 2Gi
accessModes: ["ReadWriteMany"]
nfs:
path: /data/v2
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v3
spec:
capacity:
storage: 3Gi
accessModes: ["ReadOnlyMany"]
nfs:
path: /data/v3
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v4
spec:
capacity:
storage: 4Gi
accessModes: ["ReadWriteOnce","ReadWriteMany"]
nfs:
path: /data/v4
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v5
spec:
capacity:
storage: 5Gi
accessModes: ["ReadWriteOnce","ReadWriteMany"]
nfs:
path: /data/v5
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v6
spec:
capacity:
storage: 6Gi
accessModes: ["ReadWriteOnce","ReadWriteMany"]
nfs:
path: /data/v6
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v7
spec:
capacity:
storage: 7Gi
accessModes: ["ReadWriteOnce","ReadWriteMany"]
nfs:
path: /data/v7
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v8
spec:
capacity:
storage: 8Gi
accessModes: ["ReadWriteOnce","ReadWriteMany"]
nfs:
path: /data/v8
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v9
spec:
capacity:
storage: 9Gi
accessModes: ["ReadWriteOnce","ReadWriteMany"]
nfs:
path: /data/v9
server: 192.168.166.7
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: v10
spec:
capacity:
storage: 10Gi
accessModes: ["ReadWriteOnce","ReadWriteMany"]
nfs:
path: /data/v10
server: 192.168.166.7
更新资源清单文件
[root@k8s-master ~]# kubectl apply -f pv.yaml
persistentvolume/v1 created
persistentvolume/v2 created
persistentvolume/v3 created
persistentvolume/v4 created
persistentvolume/v5 created
persistentvolume/v6 created
persistentvolume/v7 created
persistentvolume/v8 created
persistentvolume/v9 created
persistentvolume/v10 created
查看pv资源
[root@k8s-master ~]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
v1 1Gi RWO Retain Available 88s
v10 10Gi RWO,RWX Retain Available 88s
v2 2Gi RWX Retain Available 88s
v3 3Gi ROX Retain Available 88s
v4 4Gi RWO,RWX Retain Available 88s
v5 5Gi RWO,RWX Retain Available 88s
v6 6Gi RWO,RWX Retain Available 88s
v7 7Gi RWO,RWX Retain Available 88s
v8 8Gi RWO,RWX Retain Available 88s
v9 9Gi RWO,RWX Retain Available 88s
#STATUS是Available,表示pv是可用的
NAME(名称)
通常用于标识某个特定的对象,在这里可能是指存储相关的实体(比如存储卷等)的具体名字,方便对其进行区分和引用。
CAPACITY(容量)
代表该对象所具备的存储容量大小,一般会以特定的存储单位(如字节、KB、MB、GB、TB 等)来衡量,表示其能够容纳的数据量多少。
ACCESS MODES(访问模式)
指的是允许对相应存储资源进行访问的方式,例如可以是只读、读写、可追加等不同模式,决定了用户或系统对其存储内容操作的权限范围。
RECLAIM POLICY(回收策略)
关乎当存储资源不再被使用或者释放时,对其所占用空间等资源的处理方式,常见的策略比如立即回收、延迟回收、按特定条件回收等,确保资源能合理地被再次利用。
STATUS(状态)
描述该存储相关对象当前所处的情况,例如可能是可用、不可用、正在初始化、已损坏等不同状态,便于了解其是否能正常工作。
CLAIM(声明)
在存储语境中,往往涉及对存储资源的一种请求或者占用声明,表明某个主体对相应存储资源有着相关权益或者正在使用它等情况。
STORAGECLASS(存储类别)
用于区分不同特性的存储分类,比如可以根据存储的性能(高速、低速)、存储介质(磁盘、磁带等)、存储成本(昂贵、廉价)等因素划分出不同的存储类,以满足不同场景的需求。
VOLUMEATTRIBUTESCLASS(卷属性类别)
主要是针对存储卷这一特定存储对象而言,涵盖了该卷在诸如容量属性、性能属性、安全属性等多方面的类别划分,体现其具备的各类特性。
REASON(原因)
如果存储对象处于某种特定状态(比如异常状态等),此处用于说明造成该状态的具体缘由,方便排查问题、分析情况。
AGE(时长)
一般是指从该存储对象创建开始到当前所经历的时间长度,可用于衡量其存在的时间阶段,辅助判断其使用情况等。
4、创建pvc,和符合条件的pv绑定
[root@k8s-master ~]# cat pvc.yaml
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: my-pvc
spec:
accessModes: ["ReadWriteMany"]
resources:
requests:
storage: 2Gi
更新资源清单文件
[root@k8s-master ~]# kubectl apply -f my-pvc.yaml
persistentvolumeclaim/my-pvc created
查看pv和pvc,STATUS是Bound,表示这个pv已经被my-pvc绑定了
[root@k8s-master ~]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
v1 1Gi RWO Retain Available 17m
v10 10Gi RWO,RWX Retain Available 17m
v2 2Gi RWX Retain Bound default/my-pvc 17m
v3 3Gi ROX Retain Available 17m
v4 4Gi RWO,RWX Retain Bound default/my-pvc1 17m
v5 5Gi RWO,RWX Retain Available 17m
v6 6Gi RWO,RWX Retain Available 17m
v7 7Gi RWO,RWX Retain Available 17m
v8 8Gi RWO,RWX Retain Available 17m
v9 9Gi RWO,RWX Retain Available 17m
[root@k8s-master ~]# kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
my-pvc Bound v2 2Gi RWX 12m
my-pvc1 Bound v4 4Gi RWO,RWX 4m11s
5、创建pod,挂载pvc
[root@hd1 volume]# cat pod_pvc.yaml
apiVersion: v1
kind: Pod
metadata:
name: pod-pvc
spec:
containers:
- name: nginx
image: nginx
imagePullPolicy: IfNotPresent
volumeMounts:
- name: nginx-html
mountPath: /usr/share/nginx/html
volumes:
- name: nginx-html
persistentVolumeClaim:
claimName: my-pvc
更新资源清单文件
[root@k8s-master ~]# kubectl apply -f pod-pvc.yaml
pod/pod-pvc created
查看pod状态
[root@k8s-master ~]# kubectl get pod -o wide | grep pvc
pod-pvc 1/1 Running 0 16s 172.16.79.127 k8s-node1
403 Forbidden
403 Forbidden
nginx/1.25.3
####在nfs服务器端写入index.html
[root@k8s-master ~]# cd /data/v2
[root@k8s-master v2]# echo pvc > index.html
[root@k8s-master ~]# curl 172.16.79.127
pvc
###创建另一个pod测试
删除pod-pvc 这个pod,发现pvc还是存在的
[root@k8s-master ~]# kubectl delete pod pod-pvc
[root@k8s-master ~]# kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
my-pvc Bound v2 2Gi RWX 36s
my-pvc1 Bound v4 4Gi RWO,RWX 20m
[root@k8s-master ~]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
v1 1Gi RWO Retain Available 54s
v10 10Gi RWO,RWX Retain Available 33m
v2 2Gi RWX Retain Bound default/my-pvc 54s
v3 3Gi ROX Retain Available 33m
v4 4Gi RWO,RWX Retain Bound default/my-pvc1 33m
v5 5Gi RWO,RWX Retain Available 33m
v6 6Gi RWO,RWX Retain Available 33m
v7 7Gi RWO,RWX Retain Available 33m
v8 8Gi RWO,RWX Retain Available 33m
v9 9Gi RWO,RWX Retain Available 33m
删除pvc
[root@k8s-master ~]# kubectl delete pvc my-pvc
persistentvolumeclaim "my-pvc" deleted
[root@k8s-master ~]# kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
my-pvc1 Bound v4 4Gi RWO,RWX 20m
#发现pv的状态发生了变化
[root@k8s-master ~]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
v1 1Gi RWO Retain Available 2m9s
v10 10Gi RWO,RWX Retain Available 34m
v2 2Gi RWX Retain Released default/my-pvc 2m9s
v3 3Gi ROX Retain Available 34m
v4 4Gi RWO,RWX Retain Bound default/my-pvc1 34m
v5 5Gi RWO,RWX Retain Available 34m
v6 6Gi RWO,RWX Retain Available 34m
v7 7Gi RWO,RWX Retain Available 34m
v8 8Gi RWO,RWX Retain Available 34m
v9 9Gi RWO,RWX Retain Available 34m
此时我们进入到nfs的共享目录,发现我们建立的index.html还是存在的
[root@k8s-master v2]# ls
index.html
注:使用pvc和pv的注意事项
1、我们每次创建pvc的时候,需要事先有划分好的pv,这样可能不方便,那么可以在创建pvc的时候直接动态创建一个pv这个存储类,pv事先是不存在的
2、pvc和pv绑定,如果使用默认的回收策略retain,那么删除pvc之后,pv会处于released状态,我们想要继续使用这个pv,需要手动删除pv,kubectl delete pv pv_name,删除pv,不会删除pv里的数据,当我们重新创建pvc时还会和这个最匹配的pv绑定,数据还是原来数据,不会丢失。
5、 k8s存储类:storageclass
5.1 概述
上面介绍的PV和PVC模式都是需要先创建好PV,然后定义好PVC和pv进行一对一的Bond,但是如果PVC请求成千上万,那么就需要创建成千上万的PV,对于运维人员来说维护成本很高,Kubernetes提供一种自动创建PV的机制,叫StorageClass,它的作用就是创建PV的模板。k8s集群管理员通过创建storageclass可以动态生成一个存储卷pv供k8s pvc使用。
每个StorageClass都包含字段provisioner,parameters和reclaimPolicy。
具体来说,StorageClass会定义以下两部分:
1、PV的属性 ,比如存储的大小、类型等;
2、创建这种PV需要使用到的存储插件,比如Ceph、NFS等
有了这两部分信息,Kubernetes就能够根据用户提交的PVC,找到对应的StorageClass,然后Kubernetes就会调用 StorageClass声明的存储插件,创建出需要的PV。
StorageClass运行原理
volumeClaimTemplates实现了pvc的自动化,StorageClass实现了pv的自动化
每个 StorageClass 都包含 provisioner、parameters 和 reclaimPolicy 字段, 这些字段会在 StorageClass 需要动态分配 PersistentVolume 时会使用到。
StorageClass 对象的命名很重要,用户使用这个命名来请求生成一个特定的类。 当创建 StorageClass 对象时,管理员设置 StorageClass 对象的命名和其他参数,一旦创建了对象就不能再对其更新。
管理员可以为没有申请绑定到特定 StorageClass 的 PVC 指定一个默认的存储类
要使用 StorageClass,我们就得安装对应的自动配置程序,比如我们这里存储后端使用的是 nfs,那么我们就需要使用到一个 nfs-client 的自动配置程序,我们也叫它 Provisioner(制备器),这个程序使我们已经配置好的 nfs 服务器,来自动创建持久卷,也就是自动帮我们创建 PV。 
搭建StorageClass+NFS,大致有以下几个步骤:
1.创建一个可用的NFS Serve(实际存储文件的空间)
2.创建Service Account 这是用来管控NFS provisioner在k8s集群中运行的权限
3.创建StorageClass 负责建立PVC并调用NFS provisioner进行预定的工作,并让PV与PVC建立管理
4.创建NFS provisioner(存储制备器)
1)每个 StorageClass 都有一个制备器(Provisioner)用来决定使用哪个卷插件制备 PV。 该字段必须指定。
2)主要有两个功能
一个是在NFS共享目录下创建挂载点(volume)
另一个则是建了PV并将PV与NFS的挂载点建立关联
storageclass字段
#查看定义的storageclass需要的字段
[root@k8s-master~]# kubectl explain storageclass
KIND: StorageClass
VERSION: storage.k8s.io/v1
DESCRIPTION:
StorageClass describes the parameters for a class of storage for which
PersistentVolumes can be dynamically provisioned.
StorageClasses are non-namespaced; the name of the storage class according
to etcd is in ObjectMeta.Name.
FIELDS:
allowVolumeExpansion
allowedTopologies <[]Object>
apiVersion
kind
metadata