存储-docker存储(12)

storage driver 和 data volume 是容器存放数据的两种方式

storage driver方式

docker info | grep "Storage Driver"  #查看系统底成文件系统
Ubuntu 用的 AUFS,底层文件系统是 extfs,各层数据存放在 /var/lib/docker/aufs。 
Redhat/CentOS 的默认 driver 是 Device Mapper,SUSE 则是 Btrfs。

这种方式存储方式在构建镜像过程中把数据copy在镜像中

data volume 方式:

1.data volume介绍

Data Volume 本质上是 Docker Host 文件系统中的目录或文件,能够直接被 mount 到容器的文件系统中。Data Volume 有以下特点1. Data Volume 是目录或文件,而非没有格式化的磁盘(块设备)。 
    2. 容器可以读写 volume 中的数据。 
    3. volume 数据可以被永久的保存,即使使用它的容器已经销毁。 
好,现在我们有数据层(镜像层和容器层)和 volume 都可以用来存放数据,具体使用的时候要怎样选择呢?考虑下面几个场景1. Database 软件 vs Database 数据 
    2. Web 应用 vs 应用产生的日志 
    3. 数据分析软件 vs input/output 数据 
    4. Apache Server vs 静态 HTML 文件 
相信大家会做出这样的选择1. 前者放在数据层中。因为这部分内容是无状态的,应该作为镜像的一部分。 
    2. 后者放在 Data Volume 中。这是需要持久化的数据,并且应该与镜像分开存放。 
还有个大家可能会关心的问题:如何设置 voluem 的容量? 
因为 volume 实际上是 docker host 文件系统的一部分,所以 volume 的容量取决于文件系统当前未使用的空间,目前还没有方法设置 volume 的容量。 

在具体的使用上,docker 提供了两种类型的 volume:bind mount 和 docker managed volume。
  

2.data volume 的bind mount 方式

例如 docker host 上有目录 $HOME/htdocs: 
通过 -v 将其 mount 到 httpd 容器:
  docker run -tid -v $HOME/htdocs:/usr/local/nginx/html httpd
  [-v 的格式为 <host path>:<container path>。
  /usr/local/apache2/htdocs 就是 apache server 存放静态文件的地方。
  由于 /usr/local/apache2/htdocs 已经存在,原有数据会被隐藏起来,取而代之的是 host $HOME/htdocs/ 中的数据,
  这与 linux mount 命令的行为是一致的。
  bind mount 可以让 host 与容器共享数据。这在管理上是非常方便的.即使容器没有了,bind mount 也还在。
  这也合理,bind mount 是 host 文件系统中的数据,只是借给容器用用,哪能随便就删了啊]
另外,bind mount 时还可以指定数据的读写权限,默认是可读可写,可指定为只读:
  docker run -tid -v $HOME/htdocs:/usr/local/nginx/html:ro httpd ro
  设置了只读权限,在容器中是无法对 bind mount 数据进行修改的。
  只有 host 有权修改数据,提高了安全性.
另外,bind mount 可以挂载当个文件
  [docker run -tid -v /etc/passwd:/etc/passwd httpd.
  注意:使用单一文件有一点要注意:host 中的源文件必须要存在,不然会当作一个新目录 bind mount 给容器] 缺点:bind mount 的使用直观高效,易于理解,但它也有不足的地方:
  bind mount 需要指定 host 文件系统的特定路径,这就限制了容器的可移植性,
  当需要将容器迁移到其他 host,而该 host 没有要 mount 的数据或者数据不在相同的路径时,操作会失败。

2.data volume 的dockermanaged volume方式

docker managed volume 与 bind mount 在使用上的最大区别是不需要指定 mount 源,指明 mount point 就行了。还是以 httpd 容器为例:
docker run -tid -v /usr/local/nginx/html httpd
我们通过 -v 告诉 docker 需要一个 data volume,并将其 mount 到 /usr/local/apache2/htdocs。那么这个 data volume 具体在哪儿呢?
这个答案可以在容器的配置信息中找到,执行 docker inspect xxxxx(容器id)命令:
"Mounts": [ 
    { 
        "Name": "f4a0a1018968f47960efe760829e3c5738c702533d29911b01df9f18babf3340", 
        "Source": "/var/lib/docker/volumes/f4a0a1018968f47960efe760829e3c5738c702533d29911b01df9f18babf3340/_data", 
        "Destination": "/usr/local/apache2/htdocs", 
        "Driver": "local", 
        "Mode": "", 
        "RW": true, 
        "Propagation": "" 
    } 
], 
docker inspect 的输出很多,我们感兴趣的是 Mounts 这部分,这里会显示容器当前使用的所有 data volume,包括 bind mount 和 docker managed volume。
Source 就是该 volume 在 host 上的目录
原来,每当容器申请 mount docker manged volume 时,docker 都会在/var/lib/docker/volumes 下生成一个目录(例子中是 "/var/lib/docker/volumes/f4a0a1018968f47960efe760829e3c5738c702533d29911b01df9f18babf3340/_data ),这个目录就是 mount 源。
volume 的内容跟容器原有 /usr/local/apache2/htdocs 完全一样,这是怎么回事呢?
这是因为:如果 mount point 指向的是已有目录,原有数据会被复制到 volume 中。 
但要明确一点:此时的 /usr/local/apache2/htdocs 已经不再是由 storage driver 管理的层数据了,它已经是一个 data volume。
我们可以像 bind mount 一样对数据进行操作,例如更新数据 : echo
"this is test...." >> /var/lib/docker/volumes/f4a0a1018968f47960efe760829e3c5738c702533d29911b01df9f18babf3340/_data/index.html 简单回顾一下 docker managed volume 的创建过程1.容器启动时,简单的告诉 docker "我需要一个 volume 存放数据,帮我 mount 到目录 /abc"2. docker 在 /var/lib/docker/volumes 中生成一个随机目录作为 mount 源。 3. 如果 /abc 已经存在,则将数据复制到 mount 源, 4. 将 volume mount 到 /abc

3.我们已经学习了两种 data volume 的原理和基本使用方法,下面做个对比

  •   相同点:两者都是 host 文件系统中的某个路径。        
  •         不同点:        

 bind mount                            docker managed volume            
                volume 位置                             可任意指定             /var/lib/docker/volumes/...            
对已有mount point 影响                             隐藏并替换为 volume             原有数据复制到 volume            
是否支持单个文件                             支持                             不支持,只能是目录            
                权限控制                             可设置为只读,默认为读写权限                             无控制,均为读写权限            
                移植性                             移植性弱,与 host path 绑定                             移植性强,无需指定 host 目录            
posted @ 2018-03-13 16:22  xgmxm  阅读(690)  评论(1编辑  收藏  举报