数据共享是volume的关键特性,今天我们来看一下通过volume实现容器与host、容器与容器之间共享数据。

一、容器与host共享数据

在上一篇中介绍到的bind mount和docker manage volume,它们都可以实现容器与host之间共享数据,只是方式有所区别,bind mount在容器启动前便指定了volume所在host数据目录,并挂载到容器中了,容器启动后,我们向此目录写入数据,容器也能使用这些数据,而对于docker manage volume,有所不同,它在容器启动时才能确定volume所在host的目录,所以这里就需要用到docker cp 命令,它可以在容器和host之间复制数据。

  1. $ sudo docker run -d -p 80:80 -v /usr/local/apache2/htdocs httpd
  2. 0320b31996408b61a1bc363f999509f3bfdc17ca292dd08bd5f7496edb7c8947
  3. $ sudo docker cp ~/htdocs/index.html 0320b31996:/usr/local/apache2/htdocs
  4. $ curl http://127.0.0.1:80
  5. <h1>update page</h1>

二、容器之间共享数据

1、bind mount

第一种方式还是bind mount,将要共享的数据通过bind mount挂载到多个容器上,例如,我们启动三个httpd容器,并让它们挂载相同的htdocs。

  1. $ sudo docker run --name web1 -d -p 80 -v ~/htdocs:/usr/local/apache2/htdocs httpd
  2. f5a911434445f431d511b5292112fe0f9b9b44b868f98561feba895107e0cb40
  3. $ sudo docker run --name web2 -d -p 80 -v ~/htdocs:/usr/local/apache2/htdocs httpd
  4. 61e43e584c33efdab7ef5c1a72a5a4e9a0d40731d860e5fd9fb23de0a7c767df
  5. $ sudo docker run --name web3 -d -p 80 -v ~/htdocs:/usr/local/apache2/htdocs httpd
  6. 6494f68481a0f1971fdc33c13b969706c69b8ecaedc39aa707b6d35d32b6fba0
  7. $ sudo docker ps
  8. CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
  9. 6494f68481a0 httpd "httpd-foreground" 11 seconds ago Up 9 seconds 0.0.0.0:49155->80/tcp, :::49155->80/tcp web3
  10. 61e43e584c33 httpd "httpd-foreground" 19 seconds ago Up 17 seconds 0.0.0.0:49154->80/tcp, :::49154->80/tcp web2
  11. f5a911434445 httpd "httpd-foreground" 28 seconds ago Up 27 seconds 0.0.0.0:49153->80/tcp, :::49153->80/tcp web1
  12. $ curl http://127.0.0.1:49155
  13. <h1>hello docker</h1>
  14. $ curl http://127.0.0.1:49154
  15. <h1>hello docker</h1>
  16. $ curl http://127.0.0.1:49153
  17. <h1>hello docker</h1>

2、volume container

volume container是专门为其他容器提供volume的容器,它提供的volume可以是bind mount也可以是docker manage volume,我们首先创建一个volume container:

  1. $ sudo docker create --name vc_data -v ~/htdocs:/usr/local/apache2/htdocs -v /other/useful/tools busybox
  2. 178dd66f492dbe0485816a9f6f9ecde97c03e322841e6b38f4a2c7c439c6f020

我们挂载了两个volume,一个是使用bind mount挂载web静态页面,另一个使用docker manage volume挂载常用工具。注意我们使用docker create命令,这是因为volume container的作用只是提供数据,它本身不需要处于运行状态。

通过docker inspect可以看到这两个volume:

  1. $ sudo docker inspect vc_data
  2. [
  3. ...
  4. "Mounts": [
  5. {
  6. "Type": "bind",
  7. "Source": "/home/yangye/htdocs",
  8. "Destination": "/usr/local/apache2/htdocs",
  9. "Mode": "",
  10. "RW": true,
  11. "Propagation": "rprivate"
  12. },
  13. {
  14. "Type": "volume",
  15. "Name": "e3ba7240ef18694660ed3da4e6976fa35bb5c2d3c26f91593ea30d26289e0fd6",
  16. "Source": "/var/lib/docker/volumes/e3ba7240ef18694660ed3da4e6976fa35bb5c2d3c26f91593ea30d26289e0fd6/_data",
  17. "Destination": "/other/useful/tools",
  18. "Driver": "local",
  19. "Mode": "",
  20. "RW": true,
  21. "Propagation": ""
  22. }
  23. ...
  24. ]

接着我们在启动容器时通过--volumes_from使用刚创建的vc_data:

  1. $ sudo docker run --name web1 -d -p 80 --volumes-from vc_data httpd
  2. 14131cc7057528ac892b2661ed46e543bb30b65af789d83f0770dab4ebb06a33
  3. $ sudo docker run --name web2 -d -p 80 --volumes-from vc_data httpd
  4. 320a11bcb64ee032c65b65ee744a7afd6ebc7a24330e68c688a4b9c4b5e5eb22
  5. $ sudo docker run --name web3 -d -p 80 --volumes-from vc_data httpd
  6. f4c4bed873f3ad76b37136fc93dd915c6e4915897e7628f3b1ca1d5fc30e920a

我们以web1为例看看它的volume是否正确:

  1. $ sudo docker inspect web1
  2. [
  3. ...
  4. "Mounts": [
  5. {
  6. "Type": "bind",
  7. "Source": "/home/yangye/htdocs",
  8. "Destination": "/usr/local/apache2/htdocs",
  9. "Mode": "",
  10. "RW": true,
  11. "Propagation": "rprivate"
  12. },
  13. {
  14. "Type": "volume",
  15. "Name": "e3ba7240ef18694660ed3da4e6976fa35bb5c2d3c26f91593ea30d26289e0fd6",
  16. "Source": "/var/lib/docker/volumes/e3ba7240ef18694660ed3da4e6976fa35bb5c2d3c26f91593ea30d26289e0fd6/_data",
  17. "Destination": "/other/useful/tools",
  18. "Driver": "local",
  19. "Mode": "",
  20. "RW": true,
  21. "Propagation": ""
  22. }
  23. ...

可见,web1使用的就是vc_data的volume,我再来验证下数据共享的效果:

  1. $ sudo docker ps
  2. CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
  3. f4c4bed873f3 httpd "httpd-foreground" 10 minutes ago Up 10 minutes 0.0.0.0:49158->80/tcp, :::49158->80/tcp web3
  4. 320a11bcb64e httpd "httpd-foreground" 10 minutes ago Up 10 minutes 0.0.0.0:49157->80/tcp, :::49157->80/tcp web2
  5. 14131cc70575 httpd "httpd-foreground" 10 minutes ago Up 10 minutes 0.0.0.0:49156->80/tcp, :::49156->80/tcp web1
  6. $ curl http://127.0.0.1:49158
  7. <h1>hello docker</h1>
  8. $ curl http://127.0.0.1:49157
  9. <h1>hello docker</h1>
  10. $ curl http://127.0.0.1:49156
  11. <h1>hello docker</h1>

三个容器都共享了volume_container中的volume,相比于bind mount,我们发现volume container具备以下特点:

1)不必为每一个容器指定host path,所有path都在volume container中定义好了,容器只需和volume container关联,实现了容器与host的解耦;

2)使用volume container的容器,其mount point都是一致的,有利于配置的规范和标准化,当然这样也存在一定的局限使用时需要综合考虑。

Docker 与 K8S学习笔记(十 二)容器间数据共享的更多相关文章

  1. Docker 与 K8S学习笔记(二十)—— 使用Downward API向容器注入Pod信息

    Kubernetes在创建Pod时,会为Pod和容器设置一些额外的信息,比如Pod名称.Pod IP.Node IP.Label.Annotation.资源限制等,我们经常会在应用程序中使用到这些数据 ...

  2. Docker 与 K8S学习笔记(二)—— 容器核心知识梳理

    本篇主要对容器相关核心知识进行梳理,通过本篇的学习,我们可以对容器相关的概念有一个全面的了解,这样有利于后面的学习. 一.什么是容器? 容器是一种轻量级.可移植.自包含的软件打包技术,使应用程序可以在 ...

  3. Docker 与 K8S学习笔记(二十二)—— 高效使用kubectl的小技巧

    kubectl作为我们主要的操作K8S的工具,其具备非常丰富的功能,但是如果不经过打磨,使用起来还是存在诸多不便,今天我们来看看如何将我们的kubectl打磨的更加易用. 一.命令自动补全 kubec ...

  4. Docker 与 K8S学习笔记(二十五)—— Pod的各种调度策略(上)

    上一篇,我们学习了各种工作负载的使用,工作负载它会自动帮我们完成Pod的调度和部署,但有时我们需要自己定义Pod的调度策略,这个时候该怎么办呢?今天我们就来看一下如何定义Pod调度策略. 一.Node ...

  5. Docker 与 K8S学习笔记(二十四)—— 工作负载的使用

    我们前面讲了很多关于Pod的使用,但是在实际应用中,我们不会去直接创建Pod,我们一般通过Kubernetes提供的工作负载(Deployment.DeamonSet.StatefulSet.Job等 ...

  6. Docker 与 K8S学习笔记(二十三)—— Kubernetes集群搭建

    小伙伴们,好久不见,这几个月实在太忙,所以一直没有更新,今天刚好有空,咱们继续k8s的学习,由于我们后面需要深入学习Pod的调度,所以我们原先使用MiniKube搭建的实验环境就不能满足我们的需求了, ...

  7. python3.4学习笔记(十二) python正则表达式的使用,使用pyspider匹配输出带.html结尾的URL

    python3.4学习笔记(十二) python正则表达式的使用,使用pyspider匹配输出带.html结尾的URL实战例子:使用pyspider匹配输出带.html结尾的URL:@config(a ...

  8. Go语言学习笔记十二: 范围(Range)

    Go语言学习笔记十二: 范围(Range) rang这个关键字主要用来遍历数组,切片,通道或Map.在数组和切片中返回索引值,在Map中返回key. 这个特别像python的方式.不过写法上比较怪异使 ...

  9. Docker 与 K8S学习笔记(九)—— 容器间通信

    容器之间可通过IP.Docker DNS Server或joined三种方式进行通信,今天我们来详细学习一下. 一.IP通信 IP通信很简单,前一篇中已经有所涉及了,只要容器使用相同网络,那么就可以使 ...

随机推荐

  1. 记一次AWD

    有幸bjx师傅又让我参加了一次awd,算是第二次体验awd,又感觉学习到了很多东西. 第一次打这种模式的时候,我几乎什么都没有做,就给师傅们下载文件,上传文件了.(太菜了) 昨晚分的组,发现没有人是p ...

  2. Lookup函数(Excel函数集团)

    此处文章均为本妖原创,供下载.学习.探讨! 文章下载源是Office365国内版1Driver,如有链接问题请联系我. 请勿用于商业!谢谢 下载地址:https://officecommunity-m ...

  3. Java网络多线程开发:java.io.EOFException

    Java网络多线程开发:java.io.EOFException 在实现韩顺平Java的多用户即使通信系统实战项目中: 对于客户端线程的停止,老韩是向服务器端发送一个消息对象,提示服务器端进行资源释放 ...

  4. java 图形化小工具Abstract Window Toolit 菜单项

    AWT 中的菜单由如下几个类组合而成 MenuBar: 菜单条,菜单的容器. Menu: 菜单组件,菜单项的容器,它也是Menultem的子类,所以可作为菜单项使用. PopupMenu: 上下文菜单 ...

  5. Dockerfile使用OracleJDK创建自定义tomcat8镜像

    我们默认下载的tomcat镜像是用的openjdk ,但是我们有些项目必须使用oraclejdk 那就不能使用官方的tomcat镜像,只能重新自定义一个镜像 Dockerfile文件 FROM cen ...

  6. JAVA调用WebService接口(以调用第三方天气接口为例)

    天气接口地址:http://www.webxml.com.cn/WebServices/WeatherWebService.asmx?wsdl 1.打开项目文件目录路径文件夹,在当前文件夹打开cmd, ...

  7. Android NDK开发篇:Java与原生代码通信(数据操作)

    虽然说使用NDK可以提高Android程序的执行效率,但是调用起来还是稍微有点麻烦.NDK可以直接使用Java的原生数据类型,而引用类型,因为Java的引用类型的实现在NDK被屏蔽了,所以在NDK使用 ...

  8. 【LeetCode】118. Pascal's Triangle 解题报告(Python)

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 目录 题目描述 题目大意 解题方法 Java解法 Python解法 日期 [LeetCo ...

  9. 【LeetCode】231. Power of Two 解题报告(Java & Python)

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 目录 题目描述 题目大意 解题方法 二进制 位运算 判断是不是最大2的幂的因数 判断因子 ...

  10. 【LeetCode】1041. Robot Bounded In Circle 解题报告(Python)

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 目录 题目描述 题目大意 解题方法 找规律 日期 题目地址:https://leetco ...