持久化存储和卷间状态共享
- 存储卷的简介
- 存储卷的两种类型
- 宿主机和容器之间如何共享数据
- 容器之间如何共享数据
- 存储卷的生命周期
- 存储卷之间的数据管理和控制模式
- 归纳
- 环境
- 笔记
- 存储卷的介绍
- union文件系统仅提供镜像挂载
- 存储卷时一个数据分割和共享的工具,有一个与容器无关的范围和生命周期
- 存储卷是docker中union文件系统的补充,镜像适合打包和分发相对静态的文件;存储卷则持有动态或专门数据。这种区别使得镜像可重用,数据可以简单共享。而这种相对静态和动态文件空间的分离,允许应用程序或镜像作者实现高级模式,如多态和可组合工具
- 存储卷可以隔离应用程序和主机的关系。镜像被装载到主机,创建出容器。Docker不知道主机在哪里运行,只能判断哪些文件在容器中可用;但有主机知识的用户可以使用存储卷,在容器中将这些目录映射到主机的存储上
- 例子(单节点Cassandra集群):
- 存储卷容器()
dcoker inspect -f {{.Mounts}} <容器id>
查看存储在主机的位置docker run -d -v /var/lib/cassandra/data --name cass-shared alpine echo Data Container
(创建存储卷容器,为将来的容器提供操作句柄)docker run -d --volumes-from cass-shared --name cass1 registry.docker-cn.com/library/cassandra:2.1
(继承存储卷的定义,书中使用了cassandra:2.2镜像,但是本人使用时候没法下载其中的某一层,修改为2.1)docker run -it --link cass1:cass --rm cassandra:2.1 cqlsh cass
(运行cassandra客户端,进行测试)select * from system.schema_keyspaces where keyspace_name='docker_hello_world';
(在客户端输入查询语句)create keyspace docker_hello_world with replication={'class':'SimpleStrategy','replication_factor':1};
(插入数据)select * from system.schema_keyspaces where keyspace_name='docker_hello_world';
(查看新插入的数据)quit
(退出客户端)docker stop cass1
docker rm -vf cass1
(删除容器)docker run -d --volumes-from cass-shared --name cass2 registry.docker-cn.com/library/cassandra:2.1
docker run -it --link cass2:cass --rm cassandra:2.1 cqlsh cass
select * from system.schema_keyspaces where keyspace_name='docker_hello_world';
quit
docker rm -vf cass2 cass-shared
- 该例子演示了存储卷的而一种使用方式
- 存储卷的类型
- 存储卷就是容器目录树的挂载点在主机目录树中的位置
- 绑定挂载卷
- 主机目录树的所有位置
- 使用:
-v 主机目录树路径:容器目录树路径
(冒号前后都是用绝对路径) docker run -d --name bmweb -v ~/example-docs:/usr/local/apache2/htdocs -p 80:80 docker.io/centos/httpd
- 绑定挂载卷容器路径中的内容将被主机上的内容覆盖,这种行为是多态容器模式的基础。
- 给挂载卷和存储卷设置只读权限,
docker run -d --name bmweb -v ~/example-docs:/usr/local/apache2/htdocs:ro -p 80:80 docker.io/centos/httpd
- 测试只读权限:
docker run --rm -v ~/example-docs:/testspace:ro alpine /bin/sh -c 'echo test>/testspace/test'
- 绑定挂载卷可以挂载目录或文件,根据需求而定。挂载文件时,文件必须在创建容器之前存在与主机上,否则docker认为你想挂载目录。
- 绑定挂载卷的缺点
- 容器绑定了特定的主机文件系统,降低了可移植性。
- 创造了与其他容器发生冲突的机会,如多个容器挂载同一个主机目录,在竞争相同的文件时如果没有其他工具,将可能导致数据库损坏。
- 管理存储卷
- 挂载于docker守护进程控制的位置,这是一种在文件系统特定位置解耦卷的方法。
- 使用
-v 容器目录树路径
docker run -d -v /var/lib/cassandra/data --name cass-shared alpine echo Data Container
- 查看主机目录树中的位置
docker inspect -f {{.Mounts}} cass-shared
/var/lib/docker/volumes/<容器id>/_data
- 优点:
- 有效组织数据,清理工作有docker完成,有利于管理混乱
- 可移植性强
- 共享存储卷
- volumes-from标志
- 该标志可以复制任何本卷所引用的源容器到新的容器
- 可以直接或间接复制
- 复制卷始终具有相同的挂载点。
- 不能使用–volumes-from的三种情况
- 构建的新容器需要共享卷挂载到不同的位置
- 源容器的挂载目录:
/var/log/nginx
- 新容器想要的挂载目录:
/var/log/apache
- 源容器的挂载目录:
- 源卷冲突,或者有新的卷规则。
docker run --name test1 -v /library/ss alpine echo "test1 created"
docker run --name test2 -v /library/ss alpine echo "test2 created"
docker run --name test --volumes-from test1 --volumes-from test2 alpine ls -l /library/
docker inspect -f {{.Mounts}} test
- 两个源卷使用同一个挂载点,docker inspect会显示只有一个存储卷挂载在/library。复制到新容器的两个卷处于竞争状态,只有一个能复制成功。在这种情况下,挂载点发生冲突,只能访问到所需数据的子集
- 构建的新容器需要共享卷挂载到不同的位置
- volumes-from标志
- 存储卷的生命周期
- 管理卷的权限
- 为每个管理卷定义一个容器(卷容器)
docker run --name test -v ~test alpine echo "test created."
- 该容器执行完echo命令后将处于exited状态。
- 提供卷句柄,给别的容器复制使用。
- 可以用来区分管理卷,便于删除容器卷
- docker跟踪管理卷的引用确保没有删除当前引用的存储卷
- 为每个管理卷定义一个容器(卷容器)
- 存储卷的清理
- 清理管理卷是手动的任务
- docker守护进程无法删除绑定挂载卷,因为源卷不在docker的管理范围内
- 删除管理卷
docker rm -v <容器id>
- docker rm命令加 -v参数,试图删除容器引用的任何管理卷。任何有其他容器引用的管理卷将被忽略,但内部引用计数器会递减。
- 清理容器时,习惯带上-v参数,避免产生孤立卷。
- 删除停止的容器:
docker rm -v $(docker ps -aq)
- 管理卷的权限
- 存储卷的高级容器模式(整个第4章最有价值的部分)
- 卷容器
- 存储卷的生命周期第一点创建的就是卷容器。
- 容器卷对数据句柄的维护非常重要,即使单个容器对数据具有一定的独占访问权限,这些句柄仍使其轻松地备份、恢复和迁移数据
- 使挂载点的命名惯例标准化,可最大化卷容器的作用。
- 数据打包的存储卷容器
- 数据打包的卷容器将镜像中的静态内容复制到其定义的存储卷。这些容器可用于分发关键架构信息,如配置、密钥材料和代码。
docker run --name dpvc -v /config dockerinaction/ch4_packed /bin/sh -c 'cp /packed/* /config/'
docker run --rm --volumes-from dpvc alpine ls /config
docker run --rm --volumes-from dpvc alpine cat /config/packedData
docker rm -vf dpvc
- 数据打包的卷容器将镜像中的静态内容复制到其定义的存储卷。这些容器可用于分发关键架构信息,如配置、密钥材料和代码。
- 多态容器模式
- 例子1:
docker run --name tools dockerinaction/ch4_tools
docker run --rm --volumes-from tools alpine ls /operations/*
docker run -d --name important_application --volumes-from tools dockerinaction/ch4_ia
docker exec important_application /operations/tools/someTool
docker rm -vf important_application
docker rm -v tools
- 例子2:
docker run --name devConfig -v /config dockerinaction/ch4_packed_config /bin/sh -c 'cp /development/* /config/'
docker run --name proConfig -v /config dockerinaction/ch4_packed_config /bin/sh -c 'cp /production/* /config/'
docker run --name devApp --volumes-from devConfig dockerinaction/ch4_polyapp
docker run --name proApp --volumes-from proConfig dockerinaction/ch4_polyapp
- 例子1:
- 卷容器
- 存储卷的介绍
- 总结
- 存储卷允许容器与主机或其他容器共享文件
- 存储卷时主机文件系统的一部分,Docker将主机文件系统挂载到容器中指定位置
- 两种类型的存储卷:Docker管理卷挂载主机文件系统的Docker目录,绑定挂载卷可挂载主机文件系统的任何位置
- 存储卷有生命周期,且独立于任何特定的容器,但是一个用户只能通过容器句柄引用docker管理卷
- 孤立卷问题会导致磁盘空间难以恢复,可用docker rm命令使用-v选项来避免此问题。
- 卷容器模式对保证卷有序组织,并避免孤立卷问题非常有用。
- 数据打包的卷容器模式对其他容器分发静态内容非常有用。
- 多态容器模式是一种组成最小功能组件并最大化重用的方法。