一,簡介
我們知道默認情況下容器的數(shù)據(jù)都是非持久化的瓦堵,在容器消亡以后數(shù)據(jù)也跟著丟失借帘,所以 Docker 提供了 Volume 機制以便將數(shù)據(jù)持久化存儲。類似的济蝉,Kubernetes 提供了更強大的 Volume 機制和豐富的插件杰刽,解決了容器數(shù)據(jù)持久化和容器間共享數(shù)據(jù)的問題菠发。
與 Docker 不同,Kubernetes Volume 的生命周期與 Pod 綁定容器掛掉后 Kubelet 再次重啟容器時贺嫂,Volume 的數(shù)據(jù)依然還在而 Pod 刪除時滓鸠,Volume 才會清理。數(shù)據(jù)是否丟失取決于具體的 Volume 類型第喳,比如 emptyDir 的數(shù)據(jù)會丟失糜俗,而 PV 的數(shù)據(jù)則不會丟
1,volume類型
目前kubernetes支持一下volume類型:
注意曲饱,這些 volume 并非全部都是持久化的悠抹,比如 emptyDir、secret渔工、gitRepo 等锌钮,這些 volume 會隨著 Pod 的消亡而消失桥温。
二引矩,示例
1,emptyDir
概念:
emptyDir是最基礎(chǔ)的Volume類型侵浸,用于存儲臨時數(shù)據(jù)的簡單空目錄旺韭。如果Pod設(shè)置了emptyDir類型Volume,Pod被分配到Node上時候掏觉,會創(chuàng)建emptyDir区端,只要Pod運行在Node上,emptyDir都會存在(容器掛掉不會導致emptyDir丟失數(shù)據(jù))澳腹,但是如果Pod從Node上被刪除(Pod被刪除织盼,或者Pod發(fā)生遷移),emptyDir也會被刪除酱塔,并且永久丟失沥邻。
面將用emptyDir卷實現(xiàn)在同一pod中兩個容器之間的文件共享
[root@k8s-master volumes]# cat pod-volume.yaml
apiVersion: v1
kind: Pod
metadata:
name: pod-volume
namespace: default
labels:
app: myapp
spec:
containers:
- name: myapp
image: ikubernetes/myapp:v1
imagePullPolicy: IfNotPresent
ports:
- name: http
containerPort: 80
volumeMounts:
- name: html
mountPath: /usr/share/nginx/html/
- name: busybox
image: busybox:latest
imagePullPolicy: IfNotPresent
volumeMounts:
- name: html
mountPath: /data/
command:
- "/bin/sh"
- "-c"
- "while true; do echo $(date) >>/data/index.html; sleep 2; done"
volumes:
- name: html
emptyDir: {}
查看pod
[root@k8s-master volumes]# kubectl get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
pod-volume 2/2 Running 0 2m13s 10.244.1.74 k8s-node1 <none> <none>
#使用curl 命令查看我們重定向到網(wǎng)頁文件的內(nèi)容
[root@k8s-master volumes]# curl 10.244.1.74
Thu Mar 18 08:26:58 UTC 2021
Thu Mar 18 08:27:00 UTC 2021
Thu Mar 18 08:27:02 UTC 2021
Thu Mar 18 08:27:04 UTC 2021
2,hostPath
概念:
hostPath允許掛載Node上的文件系統(tǒng)到Pod里面去羊娃。如果Pod需要使用Node上的文件唐全,可以使用hostPath。在同一個節(jié)點上運行并在其hostPath卷中使用相同路徑的pod可以看到相同的文件蕊玷。
hostPath指定的type:
#在node 上創(chuàng)建存儲目錄
mkdir -p /data/volume
echo "hello" >/data/volume/index.html
[root@k8s-master volumes]# cat pod-volume-hostpath.yaml
apiVersion: v1
kind: Pod
metadata:
name: pod-volume-hostpath
namespace: default
spec:
containers:
- name: myapp
image: ikubernetes/myapp:v1
imagePullPolicy: IfNotPresent
ports:
- name: http
containerPort: 80
volumeMounts:
- name: html
mountPath: /usr/share/nginx/html
volumes:
- name: html
hostPath:
path: /data/volume
type: DirectoryOrCreate
#創(chuàng)建pod
kubectl apply -f pod-volume-hostpath.yaml
[root@k8s-master volumes]# kubectl get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
pod-volume-hostpath 1/1 Running 0 10s 10.244.1.75 k8s-node1 <none> <none>
#訪問網(wǎng)頁文件
[root@k8s-master volumes]# curl 10.244.1.75
hello
#hostpath類型刪除pod后重新創(chuàng)建pod被調(diào)度到該node節(jié)點上數(shù)據(jù)依然不會變邮利,如果node節(jié)點宕了則存儲卷也會刪除,數(shù)據(jù)會消失垃帅,
3延届,NFS
概念:
NFS是Network File System的縮寫,即網(wǎng)絡(luò)文件系統(tǒng)贸诚。Kubernetes中通過簡單地配置就可以掛載NFS到Pod中祷愉,而NFS中的數(shù)據(jù)是可以永久保存的窗宦,同時NFS支持同時寫操作。
?emptyDir可以提供不同容器間的文件共享二鳄,但不能存儲赴涵;hostPath可以為不同容器提供文件的共享并可以存儲,但受制于節(jié)點限制订讼,不能跨節(jié)點共享髓窜;這時需要網(wǎng)絡(luò)存儲 (NAS),即既可以方便存儲容器又可以從任何集群節(jié)點訪問欺殿,本文以NFS為例做測試
首先準備一臺機器同一局域網(wǎng)的機器做為nfs-server(關(guān)閉firewalld.service和selinux)
安裝nfs軟件
[root@docker-ce ~]# yum install -y nfs-utils
創(chuàng)建共享目錄:
mkdir -p /data/volumes
[root@docker-ce ~]# cat /etc/exports
/data/volumes 10.0.0.0/24(rw,no_root_squash)
在node節(jié)點上安裝nfs-utils
[root@k8s-node2 ~]# yum install -y nfs-utils
創(chuàng)建NFS的pods
[root@k8s-master volumes]# cat volume-nfs.yaml
apiVersion: v1
kind: Pod
metadata:
name: pod-nfs
namespace: default
spec:
containers:
- name: myapp
image: ikubernetes/myapp:v1
imagePullPolicy: IfNotPresent
ports:
- name: http
containerPort: 80
volumeMounts:
- name: html
mountPath: /usr/share/nginx/html/
volumes:
- name: html
nfs:
path: /data/volumes
server: 10.0.0.100
創(chuàng)建pod
[root@k8s-master volumekubectl apply -f volume-nfs.yaml
[root@k8s-master volumes]# kubectl get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
pod-nfs 1/1 Running 0 9s 10.244.1.77 k8s-node1 <none> <none>
去存儲節(jié)點創(chuàng)建文件:
[root@docker volumes]# cat /data/volumes/index.html
<h1>NFS docker</h1
#然后去訪問pod的文件
[root@k8s-master volumes]# curl 10.244.1.77
<h1>NFS docker</h1
#刪掉pod后在重建pod后數(shù)據(jù)依然在但是如果nfs宕了數(shù)據(jù)依然會丟失寄纵。
4,pv && pvc
概念:
PersistentVolume (持久卷脖苏, 簡稱 PV)和Persistent VolumeClaim(持久卷聲明程拭,簡稱 PVC)使得K8s集群具備了存儲的邏輯抽象能力,使得在配置Pod的邏輯里可以忽略對實際后臺存儲技術(shù)的配置棍潘,而把這項配置的工作交給PV的配置者恃鞋,即集群的管理者。存儲的PV和PVC的這種關(guān)系亦歉,跟計算的Node和Pod的關(guān)系是非常類似的恤浪;PV和Node是資源的提供者,根據(jù)集群的基礎(chǔ)設(shè)施變化而變化肴楷,由K8s集群管理員配置水由;而PVC和Pod是資源的使用者,根據(jù)業(yè)務(wù)服務(wù)的需求變化而變化赛蔫,由K8s集群的使用者即服務(wù)的管理員來配置砂客。
當集群用戶需要在其pod中使用持久化存儲時,他們首先創(chuàng)建PVC清單呵恢,指定所需要的最低容量要求和訪問模式鞠值,然后用戶將待久卷聲明清單提交給Kubernetes API服務(wù)器,Kubernetes將找到可匹配的PV并將其綁定到PVC瑰剃。PVC可以當作pod中的一個卷來使用齿诉,其他用戶不能使用相同的PV,除非先通過刪除PVC綁定來釋放晌姚。
1粤剧,創(chuàng)建pv
準備環(huán)境
在nfs存儲機器上創(chuàng)建目錄
[root@docker ~]# mkdir /data/volumes/v{1..5}
[root@docker ~]# cat /etc/exports
/data/volumes/v1 10.0.0.0/24(rw,no_root_squash)
/data/volumes/v2 10.0.0.0/24(rw,no_root_squash)
/data/volumes/v3 10.0.0.0/24(rw,no_root_squash)
/data/volumes/v4 10.0.0.0/24(rw,no_root_squash)
/data/volumes/v5 10.0.0.0/24(rw,no_root_squash)
顯示正常導出:
[root@docker ~]# exportfs -avr
exporting 10.0.0.0/24:/data/volumes/v5
exporting 10.0.0.0/24:/data/volumes/v4
exporting 10.0.0.0/24:/data/volumes/v3
exporting 10.0.0.0/24:/data/volumes/v2
exporting 10.0.0.0/24:/data/volumes/v1
#
[root@docker ~]# showmount -e
Export list for docker:
/data/volumes/v5 10.0.0.0/24
/data/volumes/v4 10.0.0.0/24
/data/volumes/v3 10.0.0.0/24
/data/volumes/v2 10.0.0.0/24
/data/volumes/v1 10.0.0.0/24
定義一個nfs的pv
定義pv不能定義在namespace中,應(yīng)為pv是屬于集群級別的資源挥唠,同樣創(chuàng)建namespace是也不能指定名稱空間抵恋,這兩都是屬于集群級別的資源
#創(chuàng)建了5個pv
[root@k8s-master volumes]# cat pv-deom.yaml
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv001
spec:
capacity:
storage: 5Gi
volumeMode: Filesystem
accessModes:
- ReadWriteOnce
- ReadWriteMany
nfs:
path: /data/volumes/v1
server: 10.0.0.100
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv002
spec:
capacity:
storage: 8Gi
volumeMode: Filesystem
accessModes:
- ReadWriteOnce
- ReadWriteMany
nfs:
path: /data/volumes/v2
server: 10.0.0.100
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv003
spec:
capacity:
storage: 10Gi
volumeMode: Filesystem
accessModes:
- ReadWriteOnce
- ReadWriteMany
nfs:
path: /data/volumes/v3
server: 10.0.0.100
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv004
spec:
capacity:
storage: 15Gi
volumeMode: Filesystem
accessModes:
- ReadWriteOnce
- ReadWriteMany
nfs:
path: /data/volumes/v4
server: 10.0.0.100
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv005
spec:
capacity:
storage: 20Gi
volumeMode: Filesystem
accessModes:
- ReadWriteOnce
- ReadWriteMany
nfs:
path: /data/volumes/v5
server: 10.0.0.100
查看pv
[root@k8s-master volumes]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
pv001 5Gi RWO,RWX Retain Available 89s
pv002 8Gi RWO,RWX Retain Available 89s
pv003 10Gi RWO,RWX Retain Available 89s
pv004 15Gi RWO,RWX Retain Available 89s
pv005 20Gi RWO,RWX Retain Available 89s
創(chuàng)建pvc
[root@k8s-master volumes]# cat pvc-demo.yaml
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: mypvc
namespace: default
spec:
accessModes:
- ReadWriteMany
resources:
requests:
storage: 8Gi
---
apiVersion: v1
kind: Pod
metadata:
name: pvc-pod
namespace: default
spec:
containers:
- name: myapp
image: ikubernetes/myapp:v1
imagePullPolicy: IfNotPresent
ports:
- name: http
containerPort: 80
volumeMounts:
- name: html
mountPath: /usr/share/nginx/html/
volumes:
- name: html
persistentVolumeClaim:
claimName: mypvc
#創(chuàng)建pvc
[root@k8s-master volumes]# kubectl apply -f pvc-demo.yaml
#查看pvc
[root@k8s-master volumes]# kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
mypvc Bound pv002 8Gi RWO,RWX 18s
[root@k8s-master volumes]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
pv001 5Gi RWO,RWX Retain Available 74m
pv002 8Gi RWO,RWX Retain Bound default/mypvc 74m
pv003 10Gi RWO,RWX Retain Available 74m
pv004 15Gi RWO,RWX Retain Available 74m
pv005 20Gi RWO,RWX Retain Available 74m
spec:
capacity:
storage: 5Gi
volumeMode: Filesystem
accessModes:
- ReadWriteOnce
#access modes 使用參考:
https://v1-19.docs.kubernetes.io/docs/concepts/storage/persistent-volumes/