MicroK8s : Dynamic Volume Provisioning (NFS)2023/06/22 |
To use Dynamic Volume Provisioning feature when using Persistent Storage,
it's possible to create PV (Persistent Volume) dynamically without creating PV manually by Cluster Administrator
when created PVC (Persistent Volume Claim) by users.
|
[1] |
Configure NFS Server on any node, refer to here.
On ths example, it uses [/home/nfsshare] directory on NFS Server that is running on [nfs.srv.world (10.0.0.35)]. |
[2] | Install NFS Client Provisioner with Helm. |
root@dlp:~#
microk8s helm3 repo add nfs-subdir-external-provisioner https://kubernetes-sigs.github.io/nfs-subdir-external-provisioner/
# nfs.server = (NFS server's hostname or IP address) # nfs.path = (NFS share Path) root@dlp:~# microk8s helm3 install nfs-client -n kube-system --set nfs.server=10.0.0.35 --set nfs.path=/home/nfsshare nfs-subdir-external-provisioner/nfs-subdir-external-provisioner
NAME: nfs-client LAST DEPLOYED: Thu Jun 22 00:57:10 2023 NAMESPACE: kube-system STATUS: deployed REVISION: 1 TEST SUITE: Noneroot@dlp:~# microk8s kubectl get pods -n kube-system NAME READY STATUS RESTARTS AGE ..... ..... nfs-client-nfs-subdir-external-provisioner-5447b54dbb-nwgf9 1/1 Running 0 38s |
[3] | This is an example to use dynamic volume provisioning by a Pod. |
root@dlp:~# microk8s kubectl get storageclass NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE nfs-client cluster.local/nfs-client-nfs-subdir-external-provisioner Delete Immediate true 35m apiVersion: v1 kind: PersistentVolumeClaim metadata: name: my-provisioner annotations: # specify StorageClass name volume.beta.kubernetes.io/storage-class: nfs-client spec: accessModes: - ReadWriteOnce resources: requests: # volume size storage: 5Gi
root@dlp:~#
root@dlp:~# microk8s kubectl apply -f my-pvc.yml persistentvolumeclaim/my-provisioner created microk8s kubectl get pvc NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE my-provisioner Bound pvc-e296db93-8814-47e2-b49d-1fb33f897068 5Gi RWO nfs-client 5s # PV is generated dynamically root@dlp:~# microk8s kubectl get pv NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE pvc-e296db93-8814-47e2-b49d-1fb33f897068 5Gi RWO Delete Bound default/my-provisioner nfs-client 35s
root@dlp:~#
vi my-pod.yml
apiVersion: v1
kind: Pod
metadata:
name: my-mginx
spec:
containers:
- name: my-mginx
image: nginx
ports:
- containerPort: 80
name: web
volumeMounts:
- mountPath: /usr/share/nginx/html
name: nginx-pvc
volumes:
- name: nginx-pvc
persistentVolumeClaim:
# PVC name you created
claimName: my-provisioner
microk8s kubectl apply -f my-pod.yml pod/my-mginx created root@dlp:~# microk8s kubectl get pod my-mginx -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES my-mginx 1/1 Running 0 18s 10.1.40.214 node01.srv.world <none> <none>root@dlp:~# microk8s kubectl exec my-mginx -- df /usr/share/nginx/html Filesystem 1K-blocks Used Available Use% Mounted on 10.0.0.35:/home/nfsshare/default-my-provisioner-pvc-e296db93-8814-47e2-b49d-1fb33f897068 29303808 1290752 26499072 5% /usr/share/nginx/html # verify accessing to create test index file root@dlp:~# echo "Nginx Index" > index.html root@dlp:~# microk8s kubectl cp index.html my-mginx:/usr/share/nginx/html/index.html root@dlp:~# curl 10.1.40.214 Nginx Index # when removing, to remove PVC, then PV is also removed dynamically root@dlp:~# microk8s kubectl delete pod my-mginx pod "my-mginx" deleted root@dlp:~# microk8s kubectl delete pvc my-provisioner persistentvolumeclaim "my-provisioner" deleted root@dlp:~# microk8s kubectl get pv No resources found in default namespace. |
[4] | To use StatefulSet, it's possible to specify [volumeClaimTemplates]. |
root@dlp:~# microk8s kubectl get storageclass NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE nfs-client cluster.local/nfs-client-nfs-subdir-external-provisioner Delete Immediate true 22m
root@dlp:~#
vi statefulset.yml
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: my-mginx
spec:
serviceName: my-mginx
replicas: 1
selector:
matchLabels:
app: my-mginx
template:
metadata:
labels:
app: my-mginx
spec:
containers:
- name: my-mginx
image: nginx
volumeMounts:
- name: data
mountPath: /usr/share/nginx/html
volumeClaimTemplates:
- metadata:
name: data
spec:
# specify StorageClass name
storageClassName: nfs-client
accessModes: [ "ReadWriteOnce" ]
resources:
requests:
storage: 5Gi
microk8s kubectl apply -f statefulset.yml statefulset.apps/my-mginx created root@dlp:~# microk8s kubectl get statefulset NAME READY AGE my-mginx 1/1 10sroot@dlp:~# microk8s kubectl get pods -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES my-mginx-0 1/1 Running 0 14s 10.1.40.215 node01.srv.world <none> <none>root@dlp:~# microk8s kubectl get pvc NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE data-my-mginx-0 Bound pvc-02a2e4cf-dafa-4295-b003-fa13f3e09568 5Gi RWO nfs-client 63sroot@dlp:~# microk8s kubectl get pv NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE pvc-02a2e4cf-dafa-4295-b003-fa13f3e09568 5Gi RWO Delete Bound default/data-my-mginx-0 nfs-client 96s |
Sponsored Link |