Docker默认的网络环境下,单台主机上的Docker容器可以通过docker0网桥直接通信,而不同主机上的Docker容器之间只能通过在主机上做端口映射进行通信。这种端口映射方式对很多集群应用来说极不方便。如果能让Docker容器之间直接使用自己的IP地址进行通信,会解决很多问题。按实现原理可分别直接路由方式、桥接方式(如pipework)、Overlay隧道方式(如flannel、ovs+gre)等。
 
docker0网关修改:
首先删除旧的网络
  1. $ sudo ip link set dev docker0 down
  2. $ sudo brctl delbr docker0
修改 /etc/docker/daemon.json,改变默认docker0网关
  1. {
  2. "bip": "192.188.0.1/16”,
  3. }
查看
  1. $ ifconfig docker0
  2. docker0 Link encap:Ethernet HWaddr 02:42:38:60:08:25
  3. inet addr:192.188.0.1 Bcast:0.0.0.0 Mask:255.255.0.0
  4. UP BROADCAST MULTICAST MTU:1500 Metric:1
  5. RX packets:0 errors:0 dropped:0 overruns:0 frame:0
  6. TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
  7. collisions:0 txqueuelen:0
  8. RX bytes:0 (0.0 B) TX bytes:0 (0.0 B)
或者手动创建一个新的网桥bridge0
  1. $ sudo brctl addbr bridge0
  2. $ sudo ip addr add 192.188.0.1/16 dev bridge0
  3. $ sudo ip link set dev bridge0 up
  4. $ ip addr show bridge0
  5. 4: bridge0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state UP group default
  6. link/ether 66:38:d0:0d:76:18 brd ff:ff:ff:ff:ff:ff
  7. inet 192.188.0.1/16 scope global bridge0
  8. valid_lft forever preferred_lft forever
在 Docker 配置文件/etc/docker/daemon.json 中添加如下内容,即可将Docker默认桥接到 创建的网桥上。
  1. {
  2. "bridge": "bridge0",
  3. }
 
直接路由
通过在Docker主机上添加静态路由实现跨宿主机通信:
Pipework
Pipework是一个简单易用的Docker容器网络配置工具。由200多行shell脚本实现。通过使用ip、brctl、ovs-vsctl等命令来为Docker容器配置自定义的网桥、网卡、路由等。
  • 使用新建的br0网桥代替缺省的docker0网桥
  • br0网桥与缺省的docker0网桥的区别:br0和主机eth0之间是veth pair
如图,不同容器之间的通信可以借助pipework这个工具给docker容器新建虚拟网卡并绑定IP桥接到br0
 
Flannel(Flannel + UDP 或者 Flannel + VxLAN)
Flannel实现的容器的跨主机通信通过如下过程实现:
  • 每个主机上安装并运行etcd(或其它分布式健值存储数据库)和flannel;
  • 在etcd中规划配置所有主机的docker0子网范围;Flannel为每个主机自动分配独立的subnet,用户只需要指定一个大的IP池。不同subnet之间的路由信息也由Flannel自动生成和配置。
  • 每个主机上的flanneld根据etcd中的配置,为本主机的docker0分配子网,保证所有主机上的docker0网段不重复,并将结果(即本主机上的docker0子网信息和本主机IP的对应关系)存入etcd库中,这样etcd库中就保存了所有主机上的docker子网信息和本主机IP的对应关系(相当于通过etcd服务维护了一张节点间的路由表);
  • 当需要与其他主机上的容器进行通信时,查找etcd数据库,找到目的容器的子网所对应的outip(目的宿主机的IP);
  • 将原始数据包封装在VXLAN或UDP数据包中,IP层以outip为目的IP进行封装;
  • 由于目的IP是宿主机IP,因此路由是可达的:数据从源容器发出后,经由所在主机的docker0虚拟网卡转发到flannel0虚拟网卡(P2P虚拟网卡),flanneld服务监听在flannel0网卡的另一端,它将原本是数据内容封装后根据自己的路由表投递给目的节点的flanneld服务。
  • VXLAN或UDP数据包到达目的宿主机解封装,解出原始数据包,最终到达目的容器。
PS:Flannel网络有两种模式:上述是一种overlay覆盖网络,而host-gw模式将主机作为网关,依赖于纯三层的ip转发;
缺点:不同Flannel网络中的容器可以直接通信,Flannel没有提供网络隔离。与外网通信需要通过bridge网络。
 
Weave
Weave网络也是一种overlay覆盖网络;
Weave自己负责在主机间交换网络配置信息,不需要etcd或consul这些数据库;
Weave默认配置下所有容器使用10.32.0.0/12的subnet,如果此地址空间与现有IP冲突,则可以通过--ipalloc-range分配特定的subnet。
Weave网络默认配置下所有容器在一个大的subnet中,可以自由通信。如果要实现网络隔离,需要为容器指定不同的subnet或IP;若要与外网通信,则需要将主机加入到weave网络,并把主机当作网关。
 
Calico
Calico是一个纯三层的方案,为虚机及容器提供多主机间通信,没有使用重叠网络(如flannel)驱动,采用虚拟路由代替虚拟交换,每一台虚拟路由器通过BGP协议传播可达信息(路由)到其他虚拟或物理路由器。
Calico通过IP Pool可以为每个主机定制自己的subnet。
Calico默认配置下只允许同一网络中的容器之间通信,但通过其强大的Policy能够实现几乎任意场景的访问控制。
calico包括如下重要组件:
  • Felix:Calico agent,运行在每台workload节点。主要负责路由配置以及ACLS规则的配置以及下发,确保endpoint的连通状态。
  • etcd:分布式键值存储,主要负责网络元数据一致性,确保Calico网络状态的准确性,可以与kubernetes共用;
  • BGP Client:主要负责把Felix写入kernel的路由信息分发到当前Calico网络,确保workload间的通信的有效性;
  • BGP Route Reflector:大规模部署时使用,摒弃所有节点互联的mesh模式,通过一个或者多个BGPRoute Reflector来完成集中式的路由分发。
如下图所示,描述了从源容器经过源宿主机,经过数据中心的路由,然后到达目的宿主机最后分配到目的容器的过程。
整个过程中始终都是根据iptables规则进行路由转发,并没有进行封包、解包的过程。而flannel在进行路由转发的基础上进行了封包解包的操作,浪费了CPU的计算资源。
下图是从网上找到的各个开源网络组件的性能对比。可以看出无论是带宽还是网络延迟,calico和主机的性能是差不多的。

Docker-Docker容器跨主机通信的更多相关文章

  1. Docker 网络管理及容器跨主机通信

    1.网络模式 docker支持四种网络模式,使用--net选项指定: host,--net=host,如果指定此模式,容器将不会获得一个独立的network namespace,而是和宿主机共用一个. ...

  2. overlay实现容器跨主机通信

    本节内容: Docker容器跨主机通信方案 环境信息 升级内核 安装docker 防火墙设置和开启内核转发 安装启动consul 启动Docker 创建overlay network 创建容器 测试容 ...

  3. Docker容器跨主机通信

    默认情况下Docker容器需要跨主机通信两个主机节点都需要在同一个网段下,这时只要两个Docker容器的宿主机能相互通信并且该容器使用net网络模式,改实现方式为网桥模式通信: 除此之外我们还可以通过 ...

  4. Docker:macvlan实现容器跨主机通信 [十四]

    一.什么是macvlan 1.macvlan 本身是 linux kernel 模块,其功能是允许在同一个物理网卡上配置多个 MAC 地址, 2.即多个 interface,每个 interface ...

  5. Docker容器跨主机通信之:直接路由方式

    一.Docker网络基本原理 直观上看,要实现网络通信,机器需要至少一个网络接口(物理接口或虚拟接口)与外界相通,并可以收发数据包:此外,如果不同子网之间要进行通信,需要额外的路由机制. Docker ...

  6. Docker容器跨主机通信--overlay网络

    一.Docker主机间容器通信的解决方案 Docker网络驱动 Overlay: 基于VXLAN封装实现Docker原生Overlay网络 Macvlan: Docker主机网卡接口逻辑上分为多个子接 ...

  7. Docker容器跨主机通信之:OVS+GRE

    一.概述 由于docker自身还未支持跨主机容器通信,需要借助docker网络开源解决方案 OVS OpenVSwich即开放式虚拟交换机实现,简称OVS,OVS在云计算领域应用广泛,值得我们去学习使 ...

  8. centos7下安装docker(15.5容器跨主机网络--flanneld)

    flannel是由CoreOS研究的一种覆盖网络(overlay network)网络工具,目的是帮助每一个host主机有一个完整的子网: 功能是:让集群中不同节点的主机创建的容器都有一个唯一的虚拟I ...

  9. 【06】循序渐进学 docker:跨主机通信

    写在前面的话 目前解决容器跨主机通信的方案有很多种,这里给出的只是其中的一种,而且还不是最好的方案,不过归根结底,大同小异.在学习 docker swarm 之前,大家可以先看看这种. 啥是 over ...

随机推荐

  1. LQB2013A01高斯日记

    诶,今天发生了点不是很开心的事.说实话挺影响心情的啊(谁遇见这种事不生气呢啊啊啊啊) 但是不能水更,还是得好好更新呀. 这个题居然直接用excel哈哈哈哈 那,,就这样吧!

  2. Fortify Audit Workbench 笔记 Race Condition: Singleton Member Field 竞争条件:单例的成员字段

    Race Condition: Singleton Member Field 竞争条件:单例的成员字段 Abstract Servlet 成员字段可能允许一个用户查看其他用户的数据. Explanat ...

  3. Ubuntu Linux markdown编辑工具 typora 安装

    Typora简介 Typora是一款轻便简洁的Markdown编辑器,支持即时渲染技术,这也是与其他Markdown编辑器最显著的区别.即时渲染使得你写Markdown就想是写Word文档一样流畅自如 ...

  4. PHP define() 函数

    实例 定义一个大小写敏感的常量: <?php define("GREETING","Hello you! How are you today?"); ec ...

  5. UOJ 422 [集训队作业2018] 小Z的礼物 min-max容斥 期望 轮廓线dp

    LINK:小Z的礼物 太精髓了 我重学了一遍min-max容斥 重写了一遍按位或才写这道题的. 还是期望多少时间可以全部集齐. 相当于求出 \(E(max(S))\)表示最后一个出现的期望时间. 根据 ...

  6. 7.9 NOI模拟赛 数列 交互 高精 字符串

    这是交互题 也是一个防Ak的题目 4个\(subtask\) 需要写3个不尽相同的算法. 题目下发了交互程序 所以调试的时候比较方便 有效防止\(CE\). 题目还有迷糊选手的点 数字位数为a 范围是 ...

  7. async和await的使用总结 ~ 竟然一直用错了c#中的async和await的使用。。

    对于c#中的async和await的使用,没想到我一直竟然都有一个错误.. ..还是总结太少,这里记录下. 这里以做早餐为例 流程如下: 倒一杯咖啡. 加热平底锅,然后煎两个鸡蛋. 煎三片培根. 烤两 ...

  8. HTML学习笔记(一)——基础标签及常用编辑器技巧

    HTML 初识html 什么是html? html是超文本标记语言(hyper text markup language) html5的基本结构 <!DOCTYPE html> <! ...

  9. AsyncTask被废弃了,换Coroutine吧

    本文主要是学习笔记,有版权问题还请告知删文 鸣谢:guolin@第一行代码(第三版) 你是否也在最近的代码中看见了 AsyncTask 被一条横杠划掉了 这表明--他要被Google放弃了 Googl ...

  10. Azure Load Balancer(二) 基于内部的负载均衡来转发为访问请求

    一,引言 上一节,我们使用 Azure Load Balancer 类型为外部的,来转发我们的 Web 服务.今天我们看看另一种类型为 “Internal” 的 Azure Load Balancer ...