配置和使用基本存储
文章目录
- 配置和使用基本存储
- @[toc]
- 一、什么是卷?
- 二、卷的类型
- 三、使用EmptyDir卷存储数据
- 1.了解EmptyDir卷
- 2.测试EmptyDir卷的使用
- 四、使用HostPath卷挂载宿主机文件
- 1.了解HostPath卷
- 2.测试HostPath卷的使用
- 五、使用NFS卷挂载NFS共享目录
- 1.准备NFS共享目录
- 2.测试NFS卷的使用
文章目录
- 配置和使用基本存储
- @[toc]
- 一、什么是卷?
- 二、卷的类型
- 三、使用EmptyDir卷存储数据
- 1.了解EmptyDir卷
- 2.测试EmptyDir卷的使用
- 四、使用HostPath卷挂载宿主机文件
- 1.了解HostPath卷
- 2.测试HostPath卷的使用
- 五、使用NFS卷挂载NFS共享目录
- 1.准备NFS共享目录
- 2.测试NFS卷的使用
一、什么是卷?
Pod容器中的文件在磁盘上是临时存放的,一旦容器崩溃就会造成文件丢失,容器重新启动也会丢掉运行过程中产生的数据,恢复到最初的状态。在同一个Pod中运行多个容器时,这些容器可能需要共享文件。 Kubernetes使用卷来解决这些问题。
kubernetes的卷是Pod的一部分,卷不是单独的对象,不能独立创建,只能在Pod中定义。卷关联到外部的存储设备之上的存储空间,独立于容器自身的文件系统。
卷也是Pod中所有容器挂载的共享目录,Pod中所有容器都可以访问卷,但必须要挂载,卷可以挂载到容器中的任何目录。Pod中的每个容器都必须单独指定每个卷的挂载位置,需要为Pod配置卷的相关参数。Pod本身的.spec.volumes字段用于定义卷;其容器的.spec.containers.volumeMounts字段用于指定将卷挂载到容器的路径。
卷的生命周期与挂载它的Pod相同,但是卷中的文件可能在卷消失后仍然存在,这取决于具体的卷的类型。
Docker也有卷的概念,但它对卷提供的管理功能有限。Docker的卷是磁盘上或另外一个容器内的目录,其生命周期不受管理。Docker提供卷驱动程序,但是其功能非常有限。
二、卷的类型
- EmptyDir:一种简单的空目录,主要用于临时存储
- HostPath:将主机路径(主机的某个目录)挂载到容器中
- ConfigMap:特殊类型的卷,将Kubernetes特定的配置信息挂载到Pod
- PersistentVolumeClaim:Kubernetes的持久化存储类型
- NFS:将网络文件系统挂载到Pod中
三、使用EmptyDir卷存储数据
1.了解EmptyDir卷
EmptyDir卷是Kubernetes中一种与Pod生命周期绑定的临时存储卷,当Pod被调度到节点时自动创建空目录供容器间共享数据,Pod删除时数据永久丢失,适用于缓存、临时文件共享等场景。
2.测试EmptyDir卷的使用
(1)编写配置文件
[root@master ~]# cat emptydir-pod.yaml
apiVersion: v1
kind: Pod
metadata:name: emptydir-demo
spec:containers:- name: busyboximage: busyboxvolumeMounts: # 容器挂载卷- name: pod-volume # 要挂载的卷名称mountPath: /pod-data # 挂载到容器的路径# 容器启动命令及参数command: ["/bin/sh"] args: ["-c","while true;do /bin/echo $(date +%T) '记录' >> /pod-data/test.txt;sleep 60; done;"] volumes: # 在Pod级别定义卷- name: pod-volume # 卷名称emptyDir: {} # emptyDir卷
(2)创建Pod
[root@master ~]# kubectl apply -f emptydir-pod.yaml
pod/emptydir-demo created
(3)进入该Pod容器的shell环境,列出该容器根目录下的子目录,可发现挂载卷的pod-data目录;查看该目录下由容器命令写入的test.txt文件,可发现该文件中记录的内容。
[root@master ~]# kubectl get po
NAME READY STATUS RESTARTS AGE
emptydir-demo 1/1 Running 0 117s
[root@master ~]# kubectl exec -it emptydir-demo -- /bin/sh
/ # ls
bin etc lib pod-data root tmp var
dev home lib64 proc sys usr
/ # cat /pod-data/test.txt
08:18:12 记录
08:19:12 记录
08:20:12 记录
/ # exit
[root@master ~]#
(4)查看该Pod所在的节点,本例的pod在node1上运行
[root@master ~]# kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
emptydir-demo 1/1 Running 0 3m39s 10.244.166.135 node1 <none> <none>
[root@master ~]#
(5)登录到node1节点主机上,从根目录下查找名称为EmptyDir卷名称的文件
[root@node1 ~]# find / -name pod-volume
/var/lib/kubelet/pods/4de96c82-982b-42f4-9203-19c33d0a9b32/volumes/kubernetes.io~empty-dir/pod-volume
/var/lib/kubelet/pods/4de96c82-982b-42f4-9203-19c33d0a9b32/plugins/kubernetes.io~empty-dir/pod-volume
其中第1个子目录是EmptyDir卷所在的目录,第2个子目录为EmptyDir卷的定义,目录路径中最长的字符串就是该Pod的全局唯一标识符
(6)继续查看EmptyDir卷所在目录的内容,可以发现Pod容器所使用的文件
[root@node1 ~]# ls /var/lib/kubelet/pods/4de96c82-982b-42f4-9203-19c33d0a9b32/volumes/kubernetes.io~empty-dir/pod-volume
test.txt
[root@node1 ~]#
(7)切换回控制平面节点,删除pod
[root@master ~]# kubectl delete pod emptydir-demo
pod "emptydir-demo" deleted
(8)转到node1节点上查找pod-volume文件,可以发现找不到了,表明随着pod的删除,卷也被自动删除了
[root@node1 ~]# find / -name pod-volume
[root@node1 ~]#
四、使用HostPath卷挂载宿主机文件
1.了解HostPath卷
HostPath卷是Kubernetes中一种将宿主机节点上的目录或文件挂载到Pod的持久化存储卷,数据生命周期与节点而非Pod绑定,适用于单节点场景下的日志持久化、宿主机资源访问等需求,但存在安全风险与跨节点数据不一致的限制。
2.测试HostPath卷的使用
(1)编写Pod配置文件
[root@master ~]# cat hostpath-pod.yaml
apiVersion: v1
kind: Pod
metadata:name: hostpath-demo
spec:containers:- name: busyboximage: busyboxvolumeMounts: # 容器挂载卷- name: pod-volume # 要挂载的卷名称mountPath: /pod-data # 挂载到容器的路径# 容器启动命令及参数command: ["/bin/sh"] args: ["-c","while true;do /bin/echo $(date +%T) '记录' >> /pod-data/test.txt;sleep 60; done;"] volumes: # 在Pod级别定义卷- name: pod-volume # 卷名称hostPath:path: /test-data # hostPath卷所在的路径
(2)创建Pod
[root@master ~]# kubectl apply -f hostpath-pod.yaml
pod/hostpath-demo created
(3)进入该Pod容器的Shell环境,查看由容器命令写入的test.txt文件,可发现该文件中记录的内容
[root@master ~]# kubectl exec -it hostpath-demo -- /bin/sh
/ # cat /pod-data/test.txt
15:07:17 记录
15:08:17 记录
/ # exit
(4)查看该Pod所在的节点,可发现本例Pod在node1节点上
[root@master ~]# kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
hostpath-demo 1/1 Running 0 2m21s 10.244.166.136 node1 <none> <none>
[root@master ~]#
(5)登录到node1节点上,可以发现kubernetes在该节点主机上自动创建了以HostPath卷名称命名的目录,且容器写入的文件位于该目录
[root@node1 ~]# ls /test-data/
test.txt
[root@node1 ~]#
(6)回到控制平面,执行删除Pod
[root@master ~]# kubectl delete pod hostpath-demo
pod "hostpath-demo" deleted
(7)回到node1节点上查看,可以发现用作HostPath卷的目录仍然存在,其中容器操作的文件也存在
[root@node1 ~]# cat /test-data/test.txt
15:07:17 记录
15:08:17 记录
15:09:17 记录
15:10:17 记录
15:11:17 记录
15:12:17 记录
15:13:17 记录
[root@node1 ~]#
五、使用NFS卷挂载NFS共享目录
1.准备NFS共享目录
(1)安装nfs服务器,并启动设置为开机自启
[root@master ~]# yum install -y nfs-utils rpcbind
[root@master ~]# systemctl start nfs-server && systemctl enable nfs-server
Created symlink /etc/systemd/system/multi-user.target.wants/nfs-server.service → /usr/lib/systemd/system/nfs-server.service.
(2)配置nfs共享目录
在控制平面节点上执行以下命令准备一个拟用于共享的目录
[root@master ~]# mkdir -p /test-storage/nfs
编辑/etc/exports文件,在其中添加以下内容将该目录的读写权限提供给192.168.10.0/24网段中所有主机
[root@master ~]# vim /etc/exports
[root@master ~]# cat /etc/exports
/test-storage/nfs 192.168.10.0/24(rw,sync,no_subtree_check,no_root_squash)
列出可共享的NFS共享目录,并使共享目录生效
[root@master ~]# exportfs -av
exporting 192.168.10.0/24:/test-storage/nfs
(3)在集群中其他节点上测试对NFS共享目录的访问
[root@node1 ~]# yum install -y nfs-utils rpcbind
[root@node1 ~]# showmount -e 192.168.10.30
Export list for 192.168.10.30:
/test-storage/nfs 192.168.10.0/24
2.测试NFS卷的使用
(1)编写pod文件
[root@master ~]# cat nfs-pod.yaml
apiVersion: v1
kind: Pod
metadata:name: nfs-demo
spec:containers:- name: busyboximage: busyboxvolumeMounts: # 容器挂载卷- name: pod-volume # 要挂载的卷名称mountPath: /pod-data # 挂载到容器的路径# 容器启动命令及参数command: ["/bin/sh"] args: ["-c","while true;do /bin/echo $(date +%T) '记录' >> /pod-data/test.txt;sleep 60; done;"] volumes: # 在Pod级别定义卷- name: pod-volume # 卷名称nfs:server: 192.168.10.30 # NFS服务器地址path: /test-storage/nfs # 共享文件路径
(2)创建pod
[root@master ~]# kubectl apply -f nfs-pod.yaml
pod/nfs-demo created
(3)进入该pod容器的shell环境,查看由容器命令写入的test.txt文件,可发现该文件中记录的内容
[root@master ~]# kubectl exec -it nfs-demo -- /bin/sh
/ # cat /pod-data/test.txt
15:29:16 记录
15:30:16 记录
/ # exit
(4)查看NFS共享目录中的文件内容,可以发现pod中容器写入的新数据
[root@master ~]# cat /test-storage/nfs/test.txt
15:29:16 记录
15:30:16 记录
(5)查看该pod所在的节点,发现本例的pod在节点node1上运行
[root@master ~]# kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
nfs-demo 1/1 Running 0 2m55s 10.244.166.137 node1 <none> <none>
[root@master ~]#
(6)执行删除pod
[root@master ~]# kubectl delete pod nfs-demo
pod "nfs-demo" deleted
(7)执行创建pod
[root@master ~]# kubectl apply -f nfs-pod.yaml
pod/nfs-demo created
(8)查看该pod所在的节点,发现已经被调度到node2节点上运行
[root@master ~]# kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
nfs-demo 1/1 Running 0 45s 10.244.166.140 node2 <none> <none>
如果没有在另一个节点上运行,可以在pod配置文件中指定选择器定义
nodeSelector: kubernetes.io/hostname: node2 # 调度到node2上运行
(9)进入该pod容器的shell环境,查看由容器命令写入的test.txt文件
[root@master ~]# kubectl exec -it nfs-demo -- /bin/sh
/ # cat /pod-data/test.txt
15:29:16 记录
15:30:16 记录
15:31:16 记录
15:32:16 记录
15:33:16 记录
15:34:16 记录
15:35:16 记录
15:36:22 记录
15:37:22 记录
15:51:16 记录
15:52:16 记录
/ # exit
可以发现,不同节点之间的pod依然可以共享NFS卷中的数据
(10)删除所创建的pod,清理实验环境。注意保留NFS共享目录以供后续实验使用
[root@master ~]# kubectl delete pod nfs-demo
pod "nfs-demo" deleted