zoukankan      html  css  js  c++  java
  • 11.Docker存储管理

    Docker Data Volume

    Docker镜像由多个只读层叠加,启动容器时,Docker会加载只读镜像层并在镜像栈顶部添加一个读写层

    如果运行中的容器修改了现有一个已存在的文件,那该文件将会从读写层下面的只读层复制到读写层,该文件的只读版本仍然存在,只是已经被读写层中该文件的副本所隐藏;即“写时复制(COW)”机制

    关闭并重启容器,其数据不受影响;但删除Docker容器,则其更改将会全部丢失

    存在的问题

    • 存储于联合文件系统中,不易于宿主机访问;
    • 容器间数据不方便共享
    • 删除容器其数据会丢失

    解决方案:”volume“

    卷是容器上的一个或多个目录,此类目录可绕过联合文件系统(AUFS),与宿主机上的某目录绑定

    volume的初衷是独立于容器生命周期实现数据持久化,因此删除容器不会删除卷

    image

    Docker的数据持久化即使数据不随着container的结束而结束,数据存在于host机器上——要么存在于host的某个指定目录中(使用bind mount),要么使用docker自己管理的volume(/var/lib/docker/volumes下)。

    bind mount

    bind mount自docker早期便开始为人们使用了,用于将host机器的目录mount到container中。需明确指定宿主机路径与容器内部路径,进行绑定;具有高耦合性,强自由行;

    bind mount在不同的宿主机系统时不可移植的,比如Windows和Linux的目录结构是不一样的,bind mount所指向的host目录也不能一样。这也是为什么bind mount不能出现在Dockerfile中的原因,因为这样Dockerfile就不可移植了。

    docker run -it -v HOSTDIR:VOLUMEDIR --name bbox2 busybox
    #查看bbox2容器的卷、卷标识符及挂载的主机目录(-f 指定Go模板)
    docker inspect -f {{.mounts}} bbox2
    #绑定当前路径下host-dava到容器/container-data下
    docker run -it -v $(pwd)/host-dava:/container-data alpine sh
    

    有几点需要注意:

    • host机器的目录路径必须为全路径(准确的说需要以/~/开始的路径),不然docker会将其当做volume而不是volume处理
    • 如果host机器上的目录不存在,docker会自动创建该目录
    • 如果container中的目录不存在,docker会自动创建该目录
    • 如果container中的目录已经有内容,那么docker会使用host上的目录将其覆盖掉

    volume

    只需指定容器内需要挂载路径,由docker daemon自动创建维护特定目录下;低耦合性,但无法指定特定宿主机路径

    volume也是绕过container的文件系统,直接将数据写到host机器上,只是volume是被docker管理的,docker下所有的volume都在host机器上的指定目录下/var/lib/docker/volumes。

    docker run -it -name bbox1 -v /data busybox
    #查看bbox1容器的卷、卷标识符及挂载的主机目录
    docker inspect -f {{.mounts}} bbox1
    
    docker run -it -v my-volume:/mydata alpine sh
    

    然后可以查看到给my-volume的volume:

    docker volume inspect my-volume
    [
        {
            "CreatedAt": "2019-08-28T19:42:49Z",
            "Driver": "local",
            "Labels": null,
            "Mountpoint": "/var/lib/docker/volumes/my-volume/_data",
            "Name": "my-volume",
            "Options": {},
            "Scope": "local"
        }
    ]
    
    LowerDir: image镜像层(镜像本身,只读)
    UpperDir:容器的上层(读写)
    MergedDir:容器的文件系统,使用UnionFS(联合文件系统)将lowerdir和upperdir合并给容器使用
    WorkDir:容器在宿主机的工作目录
    

    可以看到,volume在host机器的目录为/var/lib/docker/volumes/my-volume/_data。此时,如果my-volume不存在,那么docker会自动创建my-volume,然后再挂载。

    也可以不指定host上的volume:

    docker run -it -v /mydata alpine sh
    

    此时docker将自动创建一个匿名的volume,并将其挂载到container中的/mydata目录。匿名volume在host机器上的目录路径类似于:/var/lib/docker/volumes/30b32264cd0acfe8625e07edf156eb197716c20f69e7e9a053c87c2182b2e7d8/_data

    创建volume

    除了让docker帮我们自动创建volume,我们也可以自行创建:

    docker volume create my-volume-2
    

    然后将这个已有的my-volume-2挂载到container中:

    docker run -it -v my-volume-2:/mydata alpine sh
    

    需要注意的是,与bind mount不同的是,如果volume是空的而container中的目录有内容,那么docker会将container目录中的内容拷贝到volume中,但是如果volume中已经有内容,则会将container中的目录覆盖。

    创建数据容器(一个不运行的容器)

    docker  run -it  -v /father/path:/child/path  --name data  ubuntu
    exit
    上面两步是创建号了数据container,接下来就用 --volumes--from 来挂载数据到新的容器中
    docker  run -it   --volumes--from data    ubuntu
    

    复制容器volume(共享容器存储)

    单个容器的卷使用同一个主机目录

    docker run -it --name c1 -v /docker/volume/v1:/data busybox
    docker run -it --name c2 -v /docker/volume/v1:/data busybox
    

    复制使用其它容器的卷,为docker run命令使用--volumes-from选项

    docker run -it --name bbox1 -v /docker/volumes/v1:/data busybox
    docker run -it --name bbox2 --volumes-from bbox1 busybox
    

    tmpfs

    tmpfs:挂载存储在主机系统的内存中,而不会写入主机的文件系统。如果不希望将数据持久存储在任何位置,可以使用

    tmpfs,同时避免写入容器可写层提高性能。

    # 使用--tmpfs
    docker run -dit --name tmpfs-test --tmpfs /app busybox
    
  • 相关阅读:
    Delphi代码获取网卡物理地址三种方法 本文来自Delphi之窗,原文地址:http://www.52delphi.com...
    SQL SERVER 中实现公历到农历的转换
    cxgrid相同列合并显示
    rzCheckList.ItemChecked[Index]就可以判断指定节点地状态.
    为什么PING域名得到IP与实际公网IP不符
    如何让sql server2005和sql server2000共存安装在同一机器上
    如何编译通过 Raize 5.3 中的 RzBorder.pas
    u6升级到u890的过程
    技术部门到底该如何管理才能“和谐”
    在CXGRID中如何让字段能以0.00的格式显示
  • 原文地址:https://www.cnblogs.com/Gmiaomiao/p/14289243.html
Copyright © 2011-2022 走看看