Docker-数据卷和数据容器卷

默认情况下,在容器内创建的所有文件都存储在可写容器层中。这意味着:

  • 当该容器不再存在时,数据不会持久存在,并且如果另一个进程需要,则可能很难从容器中获取数据。
  • 容器的可写层紧密耦合到运行容器的主机。您无法轻松地将数据移动到其他位置。
  • 写入容器的可写层需要 存储驱动程序来管理文件系统。存储驱动程序使用Linux内核提供联合文件系统。与使用直接写入主机文件系统的数据卷相比,这种额外的抽象降低了性能 

Docker有三种方式可以在宿主机中持久化存储文件:

  • 存储(Volume)在由Docker/var/lib/docker/volumes/在Linux上)管理的主机文件系统的一部分中非Docker进程不应修改文件系统的这一部分。卷是在Docker中保留数据的最佳方式。

  • 绑定挂载(bind mount)可以存储在主机系统的任何位置它们甚至可能是重要的系统文件或目录。Docker主机或Docker容器上的非Docker进程可以随时修改它们。

  • tmpfs mount仅存储在主机系统的内存中,永远不会写入主机系统的文件系统。

  

 使用数据卷

1. 创建卷

docker volume create my-vol

  

2. 查看卷

docker volume list

  

3. 查看卷的详细信息

docker inspect my-vol
[
    {
        "CreatedAt": "2019-03-14T17:10:04+08:00",
        "Driver": "local",
        "Labels": {},
        "Mountpoint": "/var/lib/docker/volumes/my-vol/_data",
        "Name": "my-vol",
        "Options": {},
        "Scope": "local"
    }
]

  

4. 删除卷

docker volume rm  my-vol

  

5. 启动一个含有卷的容器

如果卷myvol2不存在,则会自动创建,并且挂载在容器的/app目录下

$ docker run -d 
  --name devtest 
  --mount source=myvol2,target=/app 
  nginx:latest

  也可以简写成

$ docker run -d 
  --name devtest 
  -v myvol2:/app 
  nginx:latest

  

删除容器中含的卷

$ docker container stop devtest

$ docker container rm devtest

$ docker volume rm myvol2

  

6. 启动一个包含卷的服务

$ docker service create -d 
  --replicas=4 
  --name devtest-service 
  --mount source=myvol2,target=/app 
  nginx:latest

  

7. 创建一个只读卷

$ docker run -d 
  --name=nginxtest 
  -v nginx-vol:/usr/share/nginx/html:ro 
  nginx:latest

  

8. 在远程机器上创建卷,并挂载

在Docker主机上,安装vieux/sshfs插件:

$ docker plugin install --grant-all-permissions vieux/sshfs

 使用驱动程序创建卷

docker volume create --driver vieux/sshfs 
  -o sshcmd=root@192.168.0.10:/tmp/test 
  -o password=mypassword 
  sshvolume

  在容器中挂载卷

$ docker run -d 
  --name sshfs-container 
  --volume-driver vieux/sshfs 
  --mount src=sshvolume,target=/app,volume-opt=sshcmd=root@192.168.0.10:/tmp/test,volume-opt=password=mypassword  
nginx:latest

  

备份,迁移,恢复数据卷

备份

1. 创建一个名为dbvolume的数据卷并挂载在名为dbstore容器的/dbdate目录下。

docker run  -d --name dbstore -v dbvolume:/dbdata alpine sh

2. 在dbvolume卷中写入数据

[root@node2 ~]# docker exec  -it dbstore  sh
/ #  echo hello > /dbdata/test.txt
/ # exit  

3. 备份容器中的数据卷

[root@node2 ~]# docker run --rm --volumes-from dbstore -v $(pwd):/backup alpine tar cvf /backup/backup.tar /dbdata
tar: removing leading '/' from member names
dbdata/
dbdata/test.txt

 

  --volumes-from  挂载dbstore容器中的数据卷到新建的容器中,注意挂载的目录和容器dbstore位置相同,都为/dbdata

-v $(pwd):/backup 将宿主机的当前目录挂载到新建容器的/backup目录下

tar cvf /backup/backup.tar /dbdata 在新建的容器中将目录/dbdata打包到/backup目录下,因为backup目录映射为宿主机的当前目录,所以本地目录生成备份。


恢复


  1. 创建一个新容器dbstore2,并挂载一个名为volume_restore的卷

docker run -v volume_restore:/dbdata --name dbstore2 alpine sh

 2.从容器dbstore2中挂载卷

docker run --rm --volumes-from dbstore2 -v $(pwd):/backup alpine  sh -c "cd /dbdata && tar xvf /backup/backup.tar --strip 1"

  

数据卷容器

如果容器之间需要共享一些持续更新的数据,最简单的方式就是是用户数据卷容器,数据卷容器就是一种普通容器,专门提供数据卷供其它容器挂载使用。

创建数据卷容器dbdata

[root@wls12c /]$ docker run -it -v dbdata:/dbdata --name dbdata centos
[root@07e4ad5587e1 /]

创建db1和db2两个容器,并使用--volumes-from挂载dbdata容器中的数据卷

[root@wls12c /]$ docker run -it --volumes-from dbdata --name db1 centos
[root@wls12c /]$ docker run -it --volumes-from dbdata --name db2 centos

这样三个容器任何一个容器在该目录下写入,其它容器都能看见。

创建自动删除匿名卷的容器

挂载在/foo目录下的匿名卷将会被自动删除,awesome却不会

docker run --rm -v /foo -v awesome:/bar busybox top

  

删除所有未被使用的卷

docker volume prune

  

使用绑定数据卷(bind mount)

使用-v可以挂载一个本地的目录到容器中作为数据卷。如果将bind-mount绑定到容器上的非空目录中,则会隐藏目录的现有内容。

下面将宿主机的当前目录下的target目录挂载到容器的/app目录下

docker run -d 
  -it 
  --name devtest 
  -v "$(pwd)"/target:/app 
  nginx:latest

  

也可以使用--mount参数挂载

-v
$ docker run -d 
  -it 
  --name devtest 
  --mount type=bind,source="$(pwd)"/target,target=/app 
  nginx:latest

  

原文地址:https://www.cnblogs.com/zydev/p/5809616.html