Docker数据卷

容器数据卷

什么是容器数据卷

docker 的理念回顾

将应用和环境打包成一个镜像。但是我们不希望数据也保存在容器之内,因为我们容器删除的时候,数据就会丢失。要做数据持久化,就需要数据存储在容器之外。需要容器之间可以有一个数据共享的技术
Docker容器中产生的数据,同步到本地,这就卷技术。其实就是目录的挂载,将我们容器内的目录,挂载到Linux上面

文件挂载示意图

总结一句话:容器的持久化和同步操作,同时容器间也是可以数据共享的

使用数据卷

方式一:直接使用命令来挂载 -v

docker run -it -v 主机目录:容器内目录

实战

# 启动centos容器,并使用-v,挂载文件
ubuntu@VM-0-13-ubuntu:/home$ sudo docker run -it -v /home/test:/home centos /bin/bash   

# 查看容器信息
ubuntu@VM-0-13-ubuntu:~$ sudo docker inspect 079c6895af13
 "Mounts": [
            {
                "Type": "bind",
                "Source": "/home/test",
                "Destination": "/home",
                "Mode": "",
                "RW": true,
                "Propagation": "rprivate"
            }
        ],

文件挂载解释
同步示意图

停止容器以后,宿主机上修改文件,启动容器后,容器内的数据依旧是同步的。好处,我们以后修改文件只需要在本地修改即可,容器内会自动同步

实战:安装MySQL

思考:MySQL的数据持久化的问题

# 获取镜像
sudo docker pull mysql:5.7

# 运行容器,需要做数据挂载! 安装启动mysql, 需要配置密码,官方测试 docker run --name some-mysql -e MYSQL_ROOT_PASSWORD=my-secret-pw -d mysql:tag
# -e 环境变量配置
sudo docker run -d -p 3344:3306 -v /home/mysql/conf:/etc/mysql/conf.g -v /home/mysql/data:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 --name mysql01 mysql:5.7

# 通过Navicat测试连接成功,并且创建数据库,可以映射到宿主机内存

容器删除后,挂载到本地的数据卷依旧没有丢失

匿名和具名挂载

-v 容器内路径
# 不绑定主机目录
docker run -d -P --name nginx01 -v /etc/nginx nginx

# 查看所有的 volume 的情况 docker volume ls
ubuntu@VM-0-13-ubuntu:/$ docker volume --help

Usage:  docker volume COMMAND

Manage volumes

Commands:
  create      Create a volume
  inspect     Display detailed information on one or more volumes
  ls          List volumes
  prune       Remove all unused local volumes
  rm          Remove one or more volumes

ubuntu@VM-0-13-ubuntu:/$ sudo docker volume ls
DRIVER    VOLUME NAME
local     0400d5e715aabed384a7c159ef0bb7acaa6fdbb5c47de58241e796106d5f2ee2
local     df79a235014f23e9ccef8d585f81aa2c1e9da2d302ee1a47ecdc7e482a962b5b

# 具名挂载 通过 -v 卷名:容器内路径
ubuntu@VM-0-13-ubuntu:/$ sudo docker run -d -P --name nginx02 -v juming-nginx:/etc/nginx nginx
26101bcd430983f5fc7c8fe0f440f5069ee5813cfd36ddb8d18db286a7941d74
ubuntu@VM-0-13-ubuntu:/$ sudo docker volume ls
DRIVER    VOLUME NAME
local     0400d5e715aabed384a7c159ef0bb7acaa6fdbb5c47de58241e796106d5f2ee2
local     df79a235014f23e9ccef8d585f81aa2c1e9da2d302ee1a47ecdc7e482a962b5b
local     juming-nginx

# 查看一下这个卷
docker volume inspect juming-nginx

ubuntu@VM-0-13-ubuntu:/$ sudo docker volume inspect juming-nginx
[
    {
        "CreatedAt": "2021-01-08T16:22:46+08:00",
        "Driver": "local",
        "Labels": null,
        "Mountpoint": "/var/lib/docker/volumes/juming-nginx/_data",
        "Name": "juming-nginx",
        "Options": null,
        "Scope": "local"
    }
]

# 所有的docker容器内的卷,没有指定母的情况下都是在 /var/lib/docker/volumes/XXX/_data 下
# 我们通过具名挂载可以方便的找到我们的一个卷,大多数情况在使用的具名,不建议使用匿名

# 如何确定是具名挂载还是匿名挂载。还是指定路径挂载
-v 容器内路径               # 匿名挂载
-v 卷名:容器内路径         # 具名挂载
-v 宿主机路径:容器内路径   # 指定路径挂载


# 拓展
# 通过 -v 容器内路径:ro rw 改变读写权限
ro readonly # 只读
rw readwrite # 可读可写

# 一旦这个设置了容器权限,容器对我们挂载出来的内容就限定了
docker run -d -P --name ngnix02 -v juming-nginx:/etc/nginx:ro nginx
docker run -d -P --name ngnix02 -v juming-nginx:/etc/nginx:rw nginx

# ro 说明这个路径只能通过宿主机来操作,容器内部是无法操作的

初始DockerFile

DockerFile就是用来构建docker镜像的构建文件!其实就是一个命令脚本,通过这个脚本可以生成镜像,镜像是一层一层的,脚本一个个的命令

# 写一个简单DockerFile
# 文件中的内容 指令(大写) 参数
# z这里每个命令就相当于镜像的一层
FROM centos

VOLUME ["volume01", "volume02"]

CMD echo "------end------"
CMD /bin/bash


ubuntu@VM-0-13-ubuntu:/home/docker-test-volume$ sudo docker build -f dockerfile1 -t lxl/centos:1.0 .
Sending build context to Docker daemon  2.048kB
Step 1/4 : FROM centos
 ---> 300e315adb2f
Step 2/4 : VOLUME ["volume01", "volume02"]
 ---> Running in ed4ecfa1f018
Removing intermediate container ed4ecfa1f018
 ---> 2767692d8462
Step 3/4 : CMD echo "------end------"
 ---> Running in f4dc8c7e6596
Removing intermediate container f4dc8c7e6596
 ---> 344e86965ce6
Step 4/4 : CMD /bin/bash
 ---> Running in 21665510e46c
Removing intermediate container 21665510e46c
 ---> 4d31ff865eed
Successfully built 4d31ff865eed
Successfully tagged lxl/centos:1.0

启动我们自己创建的镜像
![数据卷]

这个卷和外部一定有一个同步的目录,VOLUME ["volume01", "volume02"]使用的是匿名挂载,这个方式使用的十分多,因为我们通常会构建自己的镜像,假设构建镜像时候没有挂载卷,要手动镜像挂载 -V 卷名:容器内路径

数据卷容器

容器数据同步

实现三个容器之间的数据同步

容器一
容器二
容器三

三个容器删除其中一个,另外两个容器的数据依然存在。这是一种备份的机制

多个mysql同步数据

docker run -d -p 3310:3306 -v /etc/mysql/conf.d -v /var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 --name mysql01 mysql:5.7
docker run -d -p 3310:3306  -e MYSQL_ROOT_PASSWORD=123456 --name mysql02 --volumes-from mysql02 mysql:5.7

# 这个时候,可以实现两个容器数据同步

结论

容器之间配置信息的传递,数据卷容器的声明周期一直持续到没有容器使用为止。
但是一旦你持久化到了本地,这个时候,本地的数据是不会删除的!

原文地址:https://www.cnblogs.com/lxlhelloworld/p/14286485.html