Docker容器数据卷

什么是容器数据卷

当我们使用docker容器的时候,会产生一些数据,这些数据会随着docker容器的关闭而消失,但是有些时候产生的数据我们是希望他能够保存下来的。Docker将应用于运行观景大包成容器发布,我们希望在运行的时候产生的部分数据是可以持久化的,而且容器之间我们希望能够实现数据共享。

容器数据卷的特点

1、数据卷可以在入容器之间共享或重用

2、数据卷中的更改可以直接生效

3、数据卷中的更改不会包含在镜像的更新中

4、数据卷的生命周期一直持续到没有容器使用它未知

添加数据卷的方式

1、通过命令行挂载

docker run -it -v 宿主机绝对路径:容器内绝对路径 镜像名
[root@localhost ~]# docker run -itd -v /opt/test:/home centos
cc1255b353d62d0761bedbc29897705985b5811d903c426ee89e79bb6a129640
[root@localhost ~]# docker ps
CONTAINER ID   IMAGE                 COMMAND        CREATED         STATUS         PORTS                                       NAMES
cc1255b353d6   centos                "/bin/bash"    3 seconds ago   Up 2 seconds                                               inspiring_leakey
8c9eb507a4b4   portainer/portainer   "/portainer"   2 days ago      Up 9 hours     0.0.0.0:9000->9000/tcp, :::9000->9000/tcp   focused_ishizaka
[root@localhost ~]# ls /opt/
containerd  test

2、检查挂载

docker inspect 容器id
"Mounts": [
            {
                "Type": "bind",
                "Source": "/opt/test", # 宿主机路径
                "Destination": "/home", # 容器内路径
                "Mode": "",
                "RW": true,
                "Propagation": "rprivate"
            }

实战:MySQL数据持久化

1、拉取MySQL镜像

[root@localhost ~]# docker pull mysql
Using default tag: latest
latest: Pulling from library/mysql
b380bbd43752: Pull complete 
f23cbf2ecc5d: Pull complete 
30cfc6c29c0a: Pull complete 
b38609286cbe: Pull complete 
8211d9e66cd6: Pull complete 
2313f9eeca4a: Pull complete 
7eb487d00da0: Pull complete 
4d7421c8152e: Pull complete 
77f3d8811a28: Pull complete 
cce755338cba: Pull complete 
69b753046b9f: Pull complete 
b2e64b0ab53c: Pull complete 
Digest: sha256:6d7d4524463fe6e2b893ffc2b89543c81dec7ef82fb2020a1b27606666464d87
Status: Downloaded newer image for mysql:latest
docker.io/library/mysql:latest

2、启动MySQL容器并挂载数据卷

[root@localhost ~]# docker run -itd -p 3306:3306 -v /home/mysql/conf:/etc/mysql/conf.d -v /home/mysql/data:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 --name mysql01 mysql
d53d4ae8994a5e4e0c79b46b090400d17e7c2085dcb96296a702423743b6bc68
[root@localhost ~]# docker ps
CONTAINER ID   IMAGE                 COMMAND                  CREATED         STATUS         PORTS                                                  NAMES
d53d4ae8994a   mysql                 "docker-entrypoint.s…"   4 seconds ago   Up 3 seconds   0.0.0.0:3306->3306/tcp, :::3306->3306/tcp, 33060/tcp   mysql01

3、检查数据卷挂载

"Mounts": [
            {
                "Type": "bind",
                "Source": "/home/mysql/conf",
                "Destination": "/etc/mysql/conf.d",
                "Mode": "",
                "RW": true,
                "Propagation": "rprivate"
            },
            {
                "Type": "bind",
                "Source": "/home/mysql/data",
                "Destination": "/var/lib/mysql",
                "Mode": "",
                "RW": true,
                "Propagation": "rprivate"
            }
        ],

测试连接

image-20211023225020262.png

具名挂载和匿名挂载

1、匿名挂载

匿名挂载至不指定挂载到主机上的路径,至指定容器内的路径

docker run -itd -p 80:80 -v /etc/nginx --name nginx01 nginx

匿名挂载的volume name是没有名字的,所以称为匿名挂载

[root@localhost ~]# docker volume ls
DRIVER    VOLUME NAME
local     802c798952c0d2d4cef6891c9cf7faa2a7f26db57e540696862c0933b2d5d55e

2、具名挂载

给挂载未知添加名字,具名挂载名字前不能输入/,如果有/则代表路径

docker run -itd -p 80:80 -v nginx:/etc/nginx --name nginx02 nginx

具名挂载入第四行volume name有具体的名字,所以称为具名挂载

[root@localhost ~]# docker volume ls
DRIVER    VOLUME NAME
local     802c798952c0d2d4cef6891c9cf7faa2a7f26db57e540696862c0933b2d5d55e
local     nginx

检查挂载详情

1、使用docker volume inspect [volume name] 查看docker volume挂载详情

[root@localhost ~]# docker volume  inspect nginx
[
    {
        "CreatedAt": "2021-10-23T11:09:33-04:00",
        "Driver": "local",
        "Labels": null,
        "Mountpoint": "/var/lib/docker/volumes/nginx/_data",
        "Name": "nginx",
        "Options": null,
        "Scope": "local"
    }
]

如何确定是匿名挂载、具名挂载还是指定路径挂载

-v 容器内路径 # 匿名挂载
-v 挂载名:容器内路径 # 具名挂载
-v /宿主机路径:容器内路径 # 指定路径挂载

扩展

# 通过-v 宿主机路径:容器内路径:ro(rw) 来执行挂载目录的权限
# ro read only 只读,这个挂载目录只能通过宿主机来改变
# rw read write 读写
docker run -itd -p 80:80 -v /opt/nginx:/etc/nginx:ro --name nginx01 nginx
docker run -itd -p 80:80 -v /opt/nginx:/etc/nginx:rw --name nginx01 nginx