一、数据卷
众所周知,Docker Image可以理解成多个只读文件叠加而成,因此Docker Image是只读的。
当我们将其运行起来,就相当于在只读的Image外包裹了一层读写层变成了容器。
当你删除容器之后,使用这个镜像重新创建一个容器,此时的镜像的只读层还和原来的一样,但是你在读写层的修改全部都会丢失。
那么问题就来了,如果想要持久化在读写层的数据,该怎么利用docker做到呢?
docker使用volume实现数据的持久化,不仅如此volume还能帮助容器和容器之间,容器和host之间共享数据。
二、数据卷特点
- 数据卷可以在容器之间共事和重用,容器间传递数据将变得高效与方便;
- 对数据卷内数据的修改会立马生效,无论是容器内操作还是本地操作;
- 对数据卷的更新不会影响镜像,解摘开应用和数据 ;
- 卷会一直存在,直到没有容器使用,可以安全地卸载它。
三、数据卷操作
(一)创建数据卷
命令:docker volume create [OPTIONS] [VOLUME] 选项:
-
-d, --driver string:指定所在位置,默认是local
存放位置
创建完的数据卷,实际上会对应存放在某个位置,根据mac安装的机器在Linux和mac略有不同。
- Linux上
会存放在/var/lib/docker/volumes路径。 - Mac上
由于mac上运行docker,实际上是启动类一个虚拟机,所以,这个目录实际上是在虚拟机里面,我们执行下面的命令进入找一个虚拟机:screen ~/Library/Containers/com.docker.docker/Data/vms/0/tty.注意:当你的docker version是18.06.0-ce-mac70 (26399)采用上面的指令,如果不是这个version请使用screen ~/Library/Containers/com.docker.docker/Data/com.docker.driver.amd64-linux/tty。
然后你会看到一个新的命令行,请按下enter,此时你就在docker虚拟机中了此时cd /var/lib/docker/volumes/test/_data就是test这个volume的。
(二)查看数据卷详情
命令:docker volume inspect [OPTIONS] VOLUME [VOLUME...] 选项:
-
-f, --format string:通过go模板进行格式化
(三)显示所有数据卷
命令:docker volume ls [OPTIONS] 选项:
-
-q, --quiet:只显示数据卷名
(四)删除数据卷
命令:docker volume rm [OPTIONS] VOLUME [VOLUME...]
(五)清理数据卷
命令:docker volume prune [OPTIONS]
删除命令会同时删除掉数据卷中的数据。
(六)绑定数据卷
除了使用 volume 子命令来管理数据卷外,还可以在创建容器时将主机本地的任意路径 挂载到容器内作为数据卷,这种形式创建的数据卷称为绑定数据卷 。
绑定数据卷的命令,之前的版本和现在的本本有所变化。
旧版本
命令:docker run -v hostdir:containerDir ... 默认的权限是读写,我们可以设置成只读rw,这样容器就不能进行更改了,方式:docker run -v hostdir:containerDir:ro ...
例如:docker run -it -v /Users/syswin/Documents/dockersoft/ubuntuvo:/opt ubuntu
新版本
命令格式:docke run --mount ....--mount支持三种类型的数据卷,通过type指定,默认是volume:
- volume : 普通数据卷,映射到主机/ var/lib/docker/volumes 路径下;
- bind:绑定数据卷,映射到主机指定路径下;
- tmpfs :临时数据卷,只存在于内存中 ;
在–mout的后面,还可以跟上一些选项:
- source(src):主机目录或者是已经创建了的数据卷的名字
- destination(dst或者target):容器内目录
- readonly(ro):只读
如:docker run -it --mount type=bind,src=/Users/syswin/Documents/dockersoft/ubuntuvo,dst=/opt,ro ubuntu
不管哪种方式绑定的数据卷,都会有下面的结论:
- 如果主机目录不存在,会自动的创建;
- 如果没有指定容器内的目录,会和主机目录一样,如果容器内没有存在,就会自动创建;
三、数据卷容器
如果用户需要在多个容器之间共享一些持续更新的数据,最简单的方式是使用数据卷容器,数据卷容器也是一个容器,但是它的目的是专门提供数据卷给其他容器挂载 。
- 创建一个数据卷,并且把它绑定到一个容器上
方法一:先创建、再绑定docker volume create mydbdocker run -v mydb:/db3 --name tb ubuntu方法二:启动容器的时候直接绑定数据卷docker run -d --name dbdata -v /Users/syswin/Documents/dockersoft/db:/db ubuntu只要有了数据卷,不管这个容器是否运行着都无所谓,甚至,可以删掉 - 启动别的容器的时候通过
- volumes-from来挂载dbdata容器中的数据卷docker run -it --volumes-from dbdata --name db1 ubuntudocker run -it --volumes-from dbdata --name db2 ubuntu这样,多个容器对db目录的操作,都会进行同步
四、利用数据卷容器迁移数据
- 备份
这里备份dbdata容器数据docker run --volumes-from dbdata -v /Users/syswin/Documents/dockersoft/back:/backup --name backup ubuntu tar -cvf /backup/backup.tar db这样的话,在本机的/Users/syswin/Documents/dockersoft/back就备份好了dbdata这个容器的数据为backup.tar
这个命令有点复杂,解释如下:
- 启动一个容器,名字是backup,
--name指定的 - 通过
--volumes-from来挂载dbdata的数据卷; - 通过-v来把本机的/Users/syswin/Documents/dockersoft/back目录和backup容器的/backup目录进行绑定;
- backup容器启动后,通过
tar -cvf /backup/backup.tar db命令来把db目录(dbdata容器的数据目录)的数据打包到/backup目录,生成backup.tar。 - 由于主机有目录和/backup对应,所以就能在主机对应目录拿到这个tar文件
- 恢复
这里把数据恢复到dbdata2容器
①. 先启动dbdata2容器docker run -it --name dbdata2 -v /Users/syswin/Documents/dockersoft/dbdata2:/dbdata2 ubuntu指定了dbdata2的/dbdata2目录和本机的 /Users/syswin/Documents/dockersoft/dbdata2进行了绑定;
②. 通过别的容器恢复数据docker run --name recovery --volumes-from dbdata2 -v /Users/syswin/Documents/dockersoft/back:/recover ubuntu tar -xvf /recover/backup.tar -C /dbdata2
- 启动一个容器recovery,同时挂载了dbdata2的数据卷;
- 把本机存放有备份数据的 /Users/syswin/Documents/dockersoft/back目录和recovery容器的/recover目录绑定
- 在容器启动后,把/recover/backup.tar解压到/dbda2目录
这样的话,数据就恢复到了dbdata2容器。
其实吧,我觉得意义不大,直接把数据存放到要恢复的容器对应的目录即可,也就是说,提前把数据存放到dbdata2目录就可以了,就不用这么麻烦了。
















