第18关 K8s数据安全无忧——持久化存储详解

这篇具有很好参考价值的文章主要介绍了第18关 K8s数据安全无忧——持久化存储详解。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

------> 课程视频同步分享在今日头条和B站

大家好,我是博哥爱运维,本期课程将深入解析Kubernetes的持久化存储机制,包括PV、PVC、StorageClass等的工作原理、使用场景、最佳实践等,帮您构建稳定可靠的状态存储,确保应用和数据 100% 安全。

Volume

我们这里先来聊聊K8s的存储模型Volume,来实践下如何将各种持久化的存储映射到Pod中的容器。

在我们上面的实战中,大家如果细心的话,会发现把nginx服务pod内的默认页面改了,但当重启pod后,这个页面又恢复成nginx容器初始的状态了,所以这里要和大家说的是,在没有配置持久化存储前,任何新增的数据在pod发生重启时都是无法保留的,而在K8s上,Pod的生命周期可能是很短,它们会被频繁地销毁和创建,自然在容器销毁时,里面运行时新增的数据,如修改的配置及日志文件等也会被清除。

那么怎么解决这一现象呢,我们可以用K8s volume来持久化保存容器的数据,Volume的生命周期独立于容器,Pod中的容器可能被销毁重建,但Volume会被保留。

本质上,K8s volume是一个目录,这点和Docker volume差不多,当Volume被mount到Pod上,这个Pod中的所有容器都可以访问这个volume,在生产场景中,我们常用的类型有这几种:

  • emptyDir
  • hostPath
  • PersistentVolume(PV) & PersistentVolumeClaim(PVC)
  • StorageClass
emptyDir

我们先开始讲讲emptyDir,它是最基础的Volume类型,pod内的容器发生重启不会造成emptyDir里面数据的丢失,但是当pod被重启后,emptyDir数据会丢失,也就是说emptyDir与pod的生命周期是一致的,那么大家可能有个疑问,这个之前讲的没有配置它也没什么区别呀,实际上在某些时候,它的作用还是挺大的,在生产中它的最实际实用是提供Pod内多容器的volume数据共享,下面我会用一个实际的生产者,消费者的例子来演示下emptyDir的作用,相信大家动动手就会理解得更快了

# cat web.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: web
  name: web
  namespace: default
spec:
  replicas: 1
  selector:
    matchLabels:
      app: web
  template:
    metadata:
      labels:
        app: web
    spec:
      containers:
      - image: nginx:1.21.6
        name: nginx
        resources:
          limits:
            cpu: "50m"
            memory: 20Mi
          requests:
            cpu: "50m"
            memory: 20Mi
        volumeMounts:         # 准备将pod的目录进行卷挂载
          - name: html-files  # 自定个名称,容器内可以类似这样挂载多个卷
            mountPath: "/usr/share/nginx/html"

      - name: busybox       # 在pod内再跑一个容器,每秒把当时时间写到nginx默认页面上
        image: registry.cn-shanghai.aliyuncs.com/acs/busybox:v1.29.2
        args:
        - /bin/sh
        - -c
        - >
           while :; do
             if [ -f /html/index.html ];then
               echo "[$(date +%F\ %T)] hello" > /html/index.html
               sleep 1
             else
               touch /html/index.html
             fi
           done
        volumeMounts:
          - name: html-files  # 注意这里的名称和上面nginx容器保持一样,这样才能相互进行访问
            mountPath: "/html"  # 将数据挂载到当前这个容器的这个目录下
      volumes:
        - name: html-files   # 最后定义这个卷的名称也保持和上面一样
          emptyDir:          # 这就是使用emptyDir卷类型了
            medium: Memory   # 这里将文件写入内存中保存,这样速度会很快,配置为medium: "" 就是代表默认的使用本地磁盘空间来进行存储
            sizeLimit: 10Mi  # 因为内存比较珍贵,注意限制使用大小

更新这个web的配置

# kubectl apply -f web.yaml 
deployment.apps/web configured

# 可以看到READY下面容器数量变为2了
# kubectl get pod
NAME                    READY   STATUS    RESTARTS   AGE
......
web-5bf769fdfc-44p7h    2/2     Running   0          2m4s

# 接着创建一个service来请求测试下
kubectl expose deployment web --port 80 --target-port 80

# kubectl get svc
NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
......
web          ClusterIP   10.68.229.231   <none>        80/TCP    4h36m

# 可以看到每次访问都是被写入当前最新时间的页面内容
[root@node-1 ~]# curl 10.68.229.231
[2020-11-27 07:21:34] hello
[root@node-1 ~]# curl 10.68.229.231
[2020-11-27 07:21:35] hello
[root@node-1 ~]# curl 10.68.229.231
[2020-11-27 07:21:36] hello
[root@node-1 ~]# curl 10.68.229.231
[2020-11-27 07:21:38] hello

我们来探究下原理

# 下面这个是docker容器运行时的记录
# 看下这个web的pod的描述信息
# kubectl describe pod web-5bf769fdfc-44p7h 
......
Node:         10.0.1.203/10.0.1.203     # 找到这个pod运行在哪个node上
......
Containers:
  nginx:
    Container ID:   docker://c1482a15f756ff3bc089973ec942a4e60f7ec34674ab8435a47a94d4b93411a7   # 找到pod内nginx容器的ID
......
  busybox:
    Container ID:  docker://ecedf3b0ffa6b5101e84a21f8dbf6188179875b5db61980bc93b65195f558c6f   # 找到pod内busybox容器的ID
    
    
# 我们登陆10.0.1.203 这台node,查看pod内这两个容器的volume挂载信息,我们发现两个容器都 mount 了同一个目录
[root@node-3 ~]# docker inspect c1482a15f756ff3bc089973ec942a4e60f7ec34674ab8435a47a94d4b93411a7|grep volume|grep html
                "/var/lib/container/kubelet/pods/cc4832f3-c73c-479f-9088-12b079ff4608/volumes/kubernetes.io~empty-dir/html-files:/usr/share/nginx/html",
                "Source": "/var/lib/container/kubelet/pods/cc4832f3-c73c-479f-9088-12b079ff4608/volumes/kubernetes.io~empty-dir/html-files",
                
                
[root@node-3 ~]# docker inspect ecedf3b0ffa6b5101e84a21f8dbf6188179875b5db61980bc93b65195f558c6f|grep volume|grep html
                "/var/lib/container/kubelet/pods/cc4832f3-c73c-479f-9088-12b079ff4608/volumes/kubernetes.io~empty-dir/html-files:/html",
                "Source": "/var/lib/container/kubelet/pods/cc4832f3-c73c-479f-9088-12b079ff4608/volumes/kubernetes.io~empty-dir/html-files",    
                
                
                
# Containerd运行时日志目录: 
# ll /var/log/containers/|grep web

hostPath

hostPath Volume 的作用是将容器运行的node上已经存在文件系统目录给mount到pod的容器。在生产中大部分应用是是不会直接使用hostPath的,因为我们并不关心Pod在哪台node上运行,而hostPath又恰好增加了pod与node的耦合,限制了pod的使用,这里我们只作一下了解,知道有这个东西存在即可,一般只是一些安装服务会用到,比如下面我截取了网络插件calico的部分volume配置:

    volumeMounts:
    - mountPath: /host/driver
      name: flexvol-driver-host
......
  volumes:
......
  - hostPath:
      path: /usr/libexec/kubernetes/kubelet-plugins/volume/exec/nodeagent~uds
      type: DirectoryOrCreate
    name: flexvol-driver-host

PersistentVolume(PV) & PersistentVolumeClaim(PVC)

现在讲Volume里面在生产中用的最多的PersistentVolume(持久卷,简称PV)和 PersistentVolumeClaim(持久卷消费,简称PVC),通常在企业中,Volume是由存储系统的管理员来维护,他们来提供pv,pv具有持久性,生命周期独立于Pod;Pod则是由应用的开发人员来维护,如果要进行一卷挂载,那么就写一个pvc来消费pv就可以了,K8s会查找并提供满足条件的pv。

有了pvc,我们在K8s进行卷挂载就只需要考虑要多少容量了,而不用关心真正的空间是用什么存储系统做的等一些底层细节信息,pv这些只有存储管理员才应用去关心它。

K8s支持多种类型的pv,我们这里就以生产中常用的NFS来作演示(在云上的话就用NAS),生产中如果对存储要求不是太高的话,建议就用NFS,这样出问题也比较容易解决,如果有性能需求,可以看看rook的ceph,以及Rancher的Longhorn,这些我都在生产中用过,如果有需求的同学可以在评论区留言,我会单独做课程来讲解。

开始部署NFS-SERVER

# 我们这里在10.0.1.201上安装(在生产中,大家要提供作好NFS-SERVER环境的规划)
# yum -y install nfs-utils
# ubuntu安装NFS服务端
# apt-get install nfs-kernel-server -y


# 创建NFS挂载目录
# mkdir /nfs_dir
# chown nobody.nogroup /nfs_dir

# 修改NFS-SERVER配置
# echo '/nfs_dir *(rw,sync,no_root_squash)' > /etc/exports

# 重启服务
# systemctl restart rpcbind.service
# systemctl restart nfs-kernel-server.service 
# systemctl restart nfs-utils.service 
# systemctl restart nfs-server.service 

# 增加NFS-SERVER开机自启动
# systemctl enable nfs-server.service 
Created symlink from /etc/systemd/system/multi-user.target.wants/nfs-server.service to /usr/lib/systemd/system/nfs-server.service.

# 验证NFS-SERVER是否能正常访问
## 注:如果查看不到目录,可以到另一机器上挂载试试  
## root@node-2:~# mount.nfs 10.0.1.201:/nfs_dir /mnt/
# showmount -e 10.0.1.201                 
Export list for 10.0.1.201:
/nfs_dir *

创建基于NFS的PV

首先在NFS-SERVER的挂载目录里面创建一个目录

# mkdir /nfs_dir/pv1

接着准备好pv的yaml配置,保存为pv1.yaml

# cat pv1.yaml 
apiVersion: v1
kind: PersistentVolume
metadata:
  name: pv1
  labels:
    type: test-claim    # 这里建议打上一个独有的标签,方便在多个pv的时候方便提供pvc选择挂载
spec:
  capacity:
    storage: 1Gi     # <----------  1
  accessModes:
    - ReadWriteOnce     # <----------  2
  persistentVolumeReclaimPolicy: Recycle     # <----------  3
  storageClassName: nfs     # <----------  4
  nfs:
    path: /nfs_dir/pv1     # <----------  5
    server: 10.0.1.201
  1. capacity 指定 PV 的容量为 1G。

  2. accessModes 指定访问模式为 ReadWriteOnce,支持的访问模式有:
    ReadWriteOnce – PV 能以 read-write 模式 mount 到单个节点。
    ReadOnlyMany – PV 能以 read-only 模式 mount 到多个节点。
    ReadWriteMany – PV 能以 read-write 模式 mount 到多个节点。

  3. persistentVolumeReclaimPolicy 指定当 PV 的回收策略为 Recycle,支持的策略有:
    Retain – 需要管理员手工回收。
    Recycle – 清除 PV 中的数据,效果相当于执行 rm -rf /thevolume/*。
    Delete – 删除 Storage Provider 上的对应存储资源,例如 AWS EBS、GCE PD、Azure Disk、OpenStack Cinder Volume 等。

  4. storageClassName 指定 PV 的 class 为 nfs。相当于为 PV 设置了一个分类,PVC 可以指定 class 申请相应 class 的 PV。

  5. 指定 PV 在 NFS 服务器上对应的目录,这里注意,我测试的时候,需要手动先创建好这个目录并授权好,不然后面挂载会提示目录不存在 mkdir /nfsdata/pv1 && chown -R nobody.nogroup /nfsdata 。

创建这个pv

# kubectl apply -f pv1.yaml 
persistentvolume/pv1 created

# STATUS 为 Available,表示 pv1 就绪,可以被 PVC 申请
# kubectl get pv
NAME   CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS      CLAIM   STORAGECLASS   REASON   AGE
pv1    1Gi        RWO            Recycle          Available           nfs                     4m45s

接着准备PVC的yaml,保存为pvc1.yaml

# cat pvc1.yaml 
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: pvc1
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 1Gi
  storageClassName: nfs
  selector:
    matchLabels:
      type: test-claim

创建这个pvc

# kubectl apply -f pvc1.yaml          
persistentvolumeclaim/pvc1 created

# 看下pvc的STATUS为Bound代表成功挂载到pv了
# kubectl get pvc           
NAME   STATUS   VOLUME   CAPACITY   ACCESS MODES   STORAGECLASS   AGE
pvc1   Bound    pv1      1Gi        RWO            nfs            2s

# 这个时候再看下pv,STATUS也是Bound了,同时CLAIM提示被default/pvc1消费
# kubectl get pv
NAME   CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS   CLAIM          STORAGECLASS   REASON   AGE
pv1    1Gi        RWO            Recycle          Bound    default/pvc1   nfs  

下面我们准备pod服务来挂载这个pvc,这里就以上面最开始演示用的nginx的deployment的yaml配置来作修改

# cat nginx.yaml 
apiVersion: v1
kind: Service
metadata:
  labels:
    app: nginx
  name: nginx
spec:
  ports:
  - port: 80
    protocol: TCP
    targetPort: 80
  selector:
    app: nginx

---
apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: nginx
  name: nginx
spec:
  replicas: 1
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - image: nginx:1.21.6
        name: nginx
        volumeMounts:    # 我们这里将nginx容器默认的页面目录挂载
          - name: html-files
            mountPath: "/usr/share/nginx/html"
      volumes:
        - name: html-files
          persistentVolumeClaim:  # 卷类型使用pvc,同时下面名称处填先创建好的pvc1
            claimName: pvc1

更新配置

# kubectl apply -f nginx.yaml 
service/nginx unchanged
deployment.apps/nginx configured

# 我们看到新pod已经在创建了
# kubectl get pod
NAME                     READY   STATUS              RESTARTS   AGE
nginx-569546db98-4nmmg   0/1     ContainerCreating   0          5s
nginx-f89759699-6vgr8    1/1     Running             1          23h
web-5bf769fdfc-44p7h     2/2     Running             0          113m

# 我们这里直接用svc地址测试一下
# kubectl get svc
NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
kubernetes   ClusterIP   10.68.0.1       <none>        443/TCP   23h
nginx        ClusterIP   10.68.238.54    <none>        80/TCP    23h
web          ClusterIP   10.68.229.231   <none>        80/TCP    6h27m

# 咦,这里为什么是显示403了呢,注意,卷挂载后会把当前已经存在这个目录的文件给覆盖掉,这个和传统机器上的磁盘目录挂载道理是一样的
[root@node-1 ~]# curl 10.68.238.54
<html>
<head><title>403 Forbidden</title></head>
<body>
<center><h1>403 Forbidden</h1></center>
<hr><center>nginx/1.19.5</center>
</body>
</html>

# 我们来自己创建一个index.html页面
# echo 'hello, world!' > /nfs_dir/pv1/index.html

# 再请求下看看,已经正常了
# curl 10.68.238.54                             
hello, world!

# 我们来手动删除这个nginx的pod,看下容器内的修改是否是持久的呢?
# kubectl delete pod nginx-569546db98-4nmmg 
pod "nginx-569546db98-4nmmg" deleted

# 等待一会,等新的pod被创建好
# kubectl get pod
NAME                     READY   STATUS    RESTARTS   AGE
nginx-569546db98-99qpq   1/1     Running   0          45s

# 再测试一下,可以看到,容器内的修改现在已经被持久化了
# curl 10.68.238.54        
hello, world!

# 后面我们再想修改有两种方式,一个是exec进到pod内进行修改,还有一个是直接修改挂载在NFS目录下的文件
# echo 111 > /nfs_dir/pv1/index.html
# curl 10.68.238.54  
111

下面讲下如何回收PVC以及PV

# 这里删除时会一直卡着,我们按ctrl+c看看怎么回事
# kubectl delete pvc pvc1 
persistentvolumeclaim "pvc1" deleted
^C

# 看下pvc发现STATUS是Terminating删除中的状态,我分析是因为服务pod还在占用这个pvc使用中
# kubectl get pvc
NAME   STATUS        VOLUME   CAPACITY   ACCESS MODES   STORAGECLASS   AGE
pvc1   Terminating   pv1      1Gi        RWO            nfs            21m

# 先删除这个pod
# kubectl delete pod nginx-569546db98-99qpq 
pod "nginx-569546db98-99qpq" deleted

# 再看先删除的pvc已经没有了
# kubectl get pvc
No resources found in default namespace.

# 根据先前创建pv时的数据回收策略为Recycle – 清除 PV 中的数据,这时果然先创建的index.html已经被删除了,在生产中要尤其注意这里的模式,注意及时备份数据,注意及时备份数据,注意及时备份数据
# ll /nfs_dir/pv1/
total 0

# 虽然此时pv是可以再次被pvc来消费的,但根据生产的经验,建议在删除pvc时,也同时把它消费的pv一并删除,然后再重启创建都是可以的

我们先提到了K8s的设计是,pv交给存储管理员来管理,我们是管用pvc来消费就好,但这里我们实际还是得一起管理pv和pvc,在实际工作中,我们(存储管理员)可以提前配置好pv的动态供给StorageClass,来根据pvc的消费动态生成pv

StorageClass

我这是直接拿生产中用的实例来作演示,利用nfs-client-provisioner来生成一个基于nfs的StorageClass,部署配置yaml配置如下,保持为nfs-sc.yaml:

apiVersion: v1
kind: ServiceAccount
metadata:
  name: nfs-client-provisioner
  namespace: kube-system

---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
  name: nfs-client-provisioner-runner
rules:
  - apiGroups: [""]
    resources: ["persistentvolumes"]
    verbs: ["get", "list", "watch", "create", "delete"]
  - apiGroups: [""]
    resources: ["persistentvolumeclaims"]
    verbs: ["get", "list", "watch", "update"]
  - apiGroups: ["storage.k8s.io"]
    resources: ["storageclasses"]
    verbs: ["get", "list", "watch"]
  - apiGroups: [""]
    resources: ["events"]
    verbs: ["list", "watch", "create", "update", "patch"]
  - apiGroups: [""]
    resources: ["endpoints"]
    verbs: ["get", "list", "watch", "create", "update", "patch"]

---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
  name: run-nfs-client-provisioner
subjects:
  - kind: ServiceAccount
    name: nfs-client-provisioner
    namespace: kube-system 
roleRef:
  kind: ClusterRole
  name: nfs-client-provisioner-runner
  apiGroup: rbac.authorization.k8s.io

---
kind: Deployment
apiVersion: apps/v1
metadata:
  name: nfs-provisioner-01
  namespace: kube-system
spec:
  replicas: 1
  strategy:
    type: Recreate
  selector:
    matchLabels:
      app: nfs-provisioner-01
  template:
    metadata:
      labels:
        app: nfs-provisioner-01
    spec:
      serviceAccountName: nfs-client-provisioner
      containers:
        - name: nfs-client-provisioner
          image: bogeit/nfs-subdir-external-provisioner:v4.0.2
          imagePullPolicy: IfNotPresent
          volumeMounts:
            - name: nfs-client-root
              mountPath: /persistentvolumes
          env:
            - name: PROVISIONER_NAME
              value: nfs-provisioner-01  # 此处供应者名字供storageclass调用
            - name: NFS_SERVER
              value: 10.0.1.201   # 填入NFS的地址
            - name: NFS_PATH
              value: /nfs_dir   # 填入NFS挂载的目录
      volumes:
        - name: nfs-client-root
          nfs:
            server: 10.0.1.201   # 填入NFS的地址
            path: /nfs_dir   # 填入NFS挂载的目录

---
# use aliyun's nas need configure: https://help.aliyun.com/document_detail/130727.html?spm=a2c4g.11174283.6.715.1aad2ceeUrijYZ
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
  name: nfs-boge
provisioner: nfs-provisioner-01
# Supported policies: Delete、 Retain , default is Delete
reclaimPolicy: Retain

开始创建这个StorageClass:

# kubectl apply -f nfs-sc.yaml 
serviceaccount/nfs-client-provisioner created
clusterrole.rbac.authorization.k8s.io/nfs-client-provisioner-runner created
clusterrolebinding.rbac.authorization.k8s.io/run-nfs-client-provisioner created
deployment.apps/nfs-provisioner-01 created
  orageclass.storage.k8s.io/nfs-boge created

# 注意这个是在放kube-system的namespace下面,这里面放置一些偏系统类的服务
# kubectl -n kube-system get pod -w
NAME                                       READY   STATUS              RESTARTS   AGE
calico-kube-controllers-7fdc86d8ff-dpdm5   1/1     Running             1          24h
calico-node-8jcp5                          1/1     Running             1          24h
calico-node-m92rn                          1/1     Running             1          24h
calico-node-xg5n4                          1/1     Running             1          24h
calico-node-xrfqq                          1/1     Running             1          24h
coredns-d9b6857b5-5zwgf                    1/1     Running             1          24h
metrics-server-869ffc99cd-wfj44            1/1     Running             2          24h
nfs-provisioner-01-5db96d9cc9-qxlgk        0/1     ContainerCreating   0          9s
nfs-provisioner-01-5db96d9cc9-qxlgk        1/1     Running             0          21s

# StorageClass已经创建好了
# kubectl get sc
NAME       PROVISIONER          RECLAIMPOLICY   VOLUMEBINDINGMODE   ALLOWVOLUMEEXPANSION   AGE
nfs-boge   nfs-provisioner-01   Retain          Immediate           false                  37s

我们来基于StorageClass创建一个pvc,看看动态生成的pv是什么效果:

# vim pvc-sc.yaml 
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: pvc-sc
spec:
  storageClassName: nfs-boge
  accessModes:
    - ReadWriteMany
  resources:
    requests:
      storage: 1Mi
      
# kubectl  apply -f pvc-sc.yaml 
persistentvolumeclaim/pvc-sc created

# kubectl  get pvc
NAME     STATUS   VOLUME                                     CAPACITY   ACCESS MODES   STORAGECLASS   AGE
pvc-sc   Bound    pvc-63eee4c7-90fd-4c7e-abf9-d803c3204623   1Mi        RWX            nfs-boge       3s
pvc1     Bound    pv1                                        1Gi        RWO            nfs            24m

# kubectl  get pv
NAME                                       CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS   CLAIM            STORAGECLASS   REASON   AGE
pv1                                        1Gi        RWO            Recycle          Bound    default/pvc1     nfs                     49m
pvc-63eee4c7-90fd-4c7e-abf9-d803c3204623   1Mi        RWX            Retain           Bound    default/pvc-sc   nfs-boge                7s

我们修改下nginx的yaml配置,将pvc的名称换成上面的pvc-sc:文章来源地址https://www.toymoban.com/news/detail-754754.html

# vim nginx.yaml 
---
apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: nginx
  name: nginx
spec:
  replicas: 1
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - image: nginx:1.21.6
        name: nginx
        volumeMounts:    # 我们这里将nginx容器默认的页面目录挂载
          - name: html-files
            mountPath: "/usr/share/nginx/html"
      volumes:
        - name: html-files
          persistentVolumeClaim:
            claimName: pvc-sc
            
            
# kubectl apply -f nginx.yaml 
service/nginx unchanged
deployment.apps/nginx configured

# 这里注意下,因为是动态生成的pv,所以它的目录基于是一串随机字符串生成的,这时我们直接进到pod内来创建访问页面
# kubectl exec -it nginx-57cdc6d9b4-n497g -- bash
root@nginx-57cdc6d9b4-n497g:/# echo 'storageClass used' > /usr/share/nginx/html/index.html
root@nginx-57cdc6d9b4-n497g:/# exit

# curl 10.68.238.54                              
storageClass used

# 我们看下NFS挂载的目录
# ll /nfs_dir/
total 0
drwxrwxrwx 2 root root 24 Nov 27 17:52 default-pvc-sc-pvc-63eee4c7-90fd-4c7e-abf9-d803c3204623
drwxr-xr-x 2 root root  6 Nov 27 17:25 pv1


到了这里,关于第18关 K8s数据安全无忧——持久化存储详解的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • DevOps工具:k8s数据共享与持久化-nfs

    可伸缩 :可利用k8s集群的资源执行自动化任务。 可追溯 :通过将构建产物和相关数据持久化,可以确保每个构建版本的可追溯性,有利于快速排查和解决问题,同时可回滚到之前得版本。而CI、CD和测试各阶段都可能产生文件(不适合存储数据库),因此需要持久化。 数据

    2024年03月25日
    浏览(45)
  • 持续集成部署-k8s-数据持久化-NFS安装与使用

    网络文件系统(Network File System, NFS),是基于内核的文件系统,nfs主要是通过网络实现服务器和客户端之间的数据传输,采用远程过程调用RPC(Romete Procedure Call)机制,让不同的机器节点共享文件目录。只需将nfs服务器共享的文件目录挂载到nfs客户端,这样客户端就可以对远程

    2024年02月07日
    浏览(38)
  • k8s1.28.8版本安装prometheus并持久化数据

    本文参考 前置要求: 已经部署了NFS或者其他存储的K8s集群. 这里注意networkpolicies网络策略问题,可以后面删除这个策略,这里可以查看我之前的文档。 部署kube-prometheus 这里是配置好才执行这个,我们还没有配置存储什么的需要进行修改 持久化数据我这里用的是NFS创建动态的

    2024年04月15日
    浏览(32)
  • 03-k8s的pod资源01-数据持久化、env环境变量、网络暴露

    1,pod资源是k8s集群当中,最小的管理单位; 2,其他所有资源都是围绕着为pod资源提供服务的;给pod提供服务的; 3,pod就是“一组”容器,一个pod中可以有1个或者多个容器;         emptyDir存储卷,本质上是一个临时的目录,其生命周期与pod相同,pod被删除,则数据也会被

    2024年02月21日
    浏览(41)
  • k8s 持久化存储

    我们继续来查看 k8s 的卷,上一次我们分享了将磁盘挂载到容器中,empyDir 和 gitRepo 都是会随着 pod 的启动而创建,随着 pod 的删除而销毁 那么我们或许会有这样的需求,期望在 pod 上面读取节点的文件或者使用节点的文件系统来访问节点的设备 这个时候,我们就可以让 hostP

    2024年02月16日
    浏览(43)
  • K8S之持久化存储

    在K8S中部署的应用都是以pod容器的形式运行的,假如部署数据库服务 例如:MySQL、Redis等,需要对产生的数据做备份。如果pod不挂载数据卷,那pod被删除或重启后这些数据会随之消失,想要长久的保留这些数据就要用到pod数据持久化存储。 查看K8S支持哪些存储 常用的如下:

    2024年04月09日
    浏览(44)
  • [Kubernetes]5. k8s集群StatefulSet详解,以及数据持久化(SC PV PVC)

    前面通过 deployment 结合 service 来部署 无状态的应用 ,下面来讲解通过 satefulSet 结合 service 来部署 有状态的应用 无状态: 无状态 (stateless) 、牲畜 (cattle) 、无名 (nameless) 、可丢弃 (disposable) 有状态: 有状态 (stateful) 、宠物 (pet) 、具有名 (haviing name) 、不可丢弃 (non-disposable) St

    2024年02月01日
    浏览(44)
  • 飞天使-k8s基础组件分析-持久化存储

    emptyDir hostpath pv和pvc介绍 nfs作为静态pv案例 nfs作为动态pv案例 使用本地文件夹作为pv 改变默认存储类及回收策略 参考文档

    2024年02月11日
    浏览(46)
  • 【k8s存储--使用OpenEBS做持久化存储】

    使用OpenEBS,你可以将有持久化数据的容器,像对待其他普通容器一样来对待。OpenEBS本身也是通过容器来部署的,支持Kubernetes、Swarm、Mesos、Rancher编排调度,存储服务可以分派给每个pod、应用程序、集群或者容器级别,包括: 跨节点的数据持久化 跨可用区和云厂商的数据同步

    2024年04月23日
    浏览(37)
  • k8s 部署 skywalking 并持久化到es

    skywalking集群情况下需要保证用同一数据源,这里我们存储方式改为es https://skywalking.apache.org/downloads/#Agents 2.2.1 创建项目server-order 并创建web控制层 2.2.2 创建项目web-monitor 并创建feign和monitor的控制层 2.2.3 增加环境变量 2.2.3 查看skywalking-ui链路 2.3.1 构建镜像 2.3.2 创建k8s无状态服

    2024年02月02日
    浏览(41)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包