k8s中卷 vloume的使用

这是我参与更文挑战的第8天,活动详情查看: 更文挑战

Docker中的数据

保存docker启动容器,只要容器不被删除,其内部的文件不会消失

[root@k8s-node1 ~]# docker run -it -d victor2019/test:v1
e64c2bc31ac04174c1c78f9223e01a2cdec371104c58b74bdfc0a439913bf2d3
复制代码

之后往容器内写点东西,因为我这个测试镜像是nginx,所以写到主页面便于测试

[root@k8s-node1 ~]# docker exec e64c bash -c “echo hello > /usr/share/nginx/html/index.html”

查看一下容器的docker0网段的ip

[root@k8s-node1 ~]# docker inspect e64c | grep 172
            "Gateway": "172.17.0.1",
            "IPAddress": "172.17.0.2",
                    "Gateway": "172.17.0.1",
                    "IPAddress": "172.17.0.2",
复制代码

验证下写进去的内容

[root@k8s-node1 ~]# curl 172.17.0.2
hello
复制代码

然后停掉容器再启动

[root@k8s-node1 ~]# docker kill e64c
e64c
[root@k8s-node1 ~]# docker start e64c
e64c
[root@k8s-node1 ~]# curl 172.17.0.2
hello
复制代码

容器内的文件一直都还在。

所以,直接用docker起容器的话,指定–restart=always,就可以保证容器提供持续服务了。

K8s中的数据保存

但是k8s的机制不一样,每个pod都有自己完整的生命周期,即使没有被人为删除,如果pod因为其中某个容器崩溃重启,不仅pod的ip会变,里面所有容器保存的内容也会全部消失

那么有没有一种办法,可以让k8s的pod可以和docker里面的容器一样,除非是被人为删除,不然即使重启里面保存的东西一直都在。我们这一节要学习的volume就是为了解决这个问题而引入的。

需要注意,docker中也有volume的概念,不过docker中的volume是容器的内容在宿主机磁盘的持久化,即使容器删除也会一直在,和我们下一节要学习的PVC有点像,但是和这里k8s的volume是两个东西,要注意区分

k8s中的volume
volume就是一个可以被pod中所有容器使用的公共文件夹,每个容器可以将这个公共文件夹挂载到本容器内的一个目录(不同容器的目录可以不同),这样pod内容器就可以互相交换数据。volume的生命周期和pod一致,所以不管pod重启多少次volume内的内容和挂载目录都不会改变,但是如果pod被终止volume就会跟着消失。

注意这里的重启是指因为容器崩溃导致的重启,而不是手动删除pod然后因为重启策略而进行的重启

k8s支持很多种volume的类型,官方在官网中给出几十种媒介可供使用。其中的configMap和secret上一节我们已经接触过,这一节我们选其最常用的emptyDir和hostPath再来学习下。

实际操作

以下所有yaml文件托管在我的Github仓库

emptyDir操作
当一个pod被分配到node时,一个emptyDir volume首先被创建,并且其生命周期和pod一样长。正如其名字表示的那样,emptyDir一开始是空的,pod中的所有容器都可以在里面进行读写。如果pod在node上被删除,emptyDir中的数据也会被永久删除。

容器崩溃不会将pod从node上删除,而只是重启,所以emptyDir对容器崩溃来说是安全的

emptyDir通常用于声明一些临时空间,存放一些临时文件,尤其是多容器配合操作的时候。或者是容器从崩溃恢复时候的一些checkpoint。

两个配置字段在pod.spec.volumes.emptyDir中声明

字段 类型 说明
medium string 默认是空字符串表示硬盘,还可以是Memory表示内存
sizeLimit string 默认是nil表示不指定大小
通过下面这个yaml文件test-volume-emptydir.yaml来创建一个Deployment

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: test-volume-emptydir
spec:
  replicas: 1
  template:
    metadata:
      labels:
        app: test-volume-emptydir
    spec:
      containers:
        - name: mynginx
          image: mynginx:v2
          ports:
            - containerPort: 80
          volumeMounts:
            - mountPath: /usr/share/nginx/html
              name: test-emptydir
        - name: myalpine
          image: alpine
          command: ["ping","8.8.8.8"]
          volumeMounts:
            - mountPath: /emptydir
              name: test-emptydir
      volumes:
        - name: test-emptydir
          emptyDir: {}
复制代码

其中emptyDir: {}表示用默认配置,也就是不声明大小的硬盘空间。

创建成功以后进入myalpine容器,往emptyDir绑定的目录写入文件,之后再访问另一个mynginx容器时被显示

[root@k8s-master volume]# kubectl apply -f test-volume-emptydir.yaml
deployment.extensions/test-volume-emptydir created
[root@k8s-master volume]# kubectl get pod -o wide
NAME                                    READY   STATUS      RESTARTS   AGE   IP             NODE        NOMINATED NODE   READINESS GATES
test-volume-emptydir-6bf8d675fc-ds2jx   2/2     Running     0          15m   10.244.1.117   k8s-node1   <none>           <none>
[root@k8s-master volume]# kubectl exec test-volume-emptydir-6bf8d675fc-ds2jx -c myalpine -it -- /bin/sh -c "echo hello emptydir > /emptydir/index.html"
[root@k8s-master volume]# curl 10.244.1.117
hello emptydir
复制代码

说明因为emptyDir的引入一个pod内的容器可以共享同一个存储卷。

© 版权声明
THE END
喜欢就支持一下吧
点赞0 分享