Docker的网络模式和如何跨主机通信

简介: Docker有四种网络模式:Bridge、Host、Container、None,一般常用的是前面两种,默认的是第一种,不安全的是第二种,以下介绍一下四种网络模式,并重点介绍一下如何配置自己的跨主机通信网络。
Docker有四种网络模式:Bridge、Host、Container、None,一般常用的是前面两种,默认的是第一种,不安全的是第二种,以下介绍一下四种网络模式,并重点介绍一下如何配置自己的跨主机通信网络。

一、网络模式介绍

1、Bridge模式:

        默认是这种模式(使用docker run -p时,docker实际是在iptables做了DNAT规则,实现端口转发功能。可以使用iptables -t nat -vnL查看),用Rancher工具创建Docker对应的托管模式也属于这种。当Docker进程启动时,会在主机上创建一个名为docker0的虚拟网桥,此主机上启动的Docker容器会连接到这个虚拟网桥上。虚拟网桥的工作方式和物理交换机类似,这样主机上的所有容器就通过交换机连在了一个二层网络中。

        从docker0子网中分配一个IP给容器使用,并设置docker0的IP地址为容器的默认网关。在主机上创建一对虚拟网卡veth pair设备,Docker将veth pair设备的一端放在新创建的容器中,并命名为eth0(容器的网卡),另一端放在主机中,以vethxxx这样类似的名字命名,并将这个网络设备加入到docker0网桥中。可以通过brctl show命令查看(该命令可以通过yum install -y bridge-utils安装)。具体网络架构如下图所示:

2、Host模式:

        如果启动容器的时候使用host模式,那么这个容器将不会获得一个独立的Network Namespace,而是和宿主机共用一个Network Namespace。容器将不会虚拟出自己的网卡,配置自己的IP等,而是使用宿主机的IP和端口。但是,容器的其他方面,如文件系统、进程列表等还是和宿主机隔离的。具体网络架构如下所示:

3、Container模式

        这个模式指定新创建的容器和已经存在的一个容器共享一个 Network Namespace,而不是和宿主机共享。新创建的容器不会创建自己的网卡,配置自己的 IP,而是和一个指定的容器共享 IP、端口范围等。同样,两个容器除了网络方面,其他的如文件系统、进程列表等还是隔离的。两个容器的进程可以通过 lo 网卡设备通信。具体网络架构如下所示:

4、None模式

        使用none模式,Docker容器拥有自己的Network Namespace,但是,并不为Docker容器进行任何网络配置。也就是说,这个Docker容器没有网卡、IP、路由等信息。需要我们自己为Docker容器添加网卡、配置IP等。Node模式示意图如下:

5、其他模式

以上4种模板是基本模式,如果使用Rancher(容器编排和管理系统),还能看到托管模式(managed),这种模式是一种复杂网络模式,是通过Rancher在各个主机上部署的network-services/network-manager容器服务进行管理,IP的分配策略完全不同于Bridge。具体的管理机制目前还不清楚,但是这种模式的网络性能是比较差的(我做过一次网络吞吐压力测试),甚至有时候导致以docker attach或exec命令连接进入容器都很困难。所以从性能角度来考虑,还是推荐使用默认的Bridge模式。

二、跨主机通信

        Docker默认的网络环境下,单台主机上的Docker容器可以通过docker0网桥直接通信,而不同主机上的Docker容器之间只能通过在主机上做端口映射进行通信。这种端口映射方式对很多集群应用来说可能不方便。如果能让Docker容器之间直接使用自己的IP地址进行通信,会解决很多问题。按实现原理可分别直接路由方式、Overlay隧道方式(如flannel、ovs+gre)、桥接方式(如pipework)。

1、直接路由

        通过在Docker主机上添加静态路由实现跨宿主机通信:

2、隧道方式:Flannel(Flannel + UDP 或者 Flannel + VxLAN)

Flannel实现的容器的跨主机通信通过如下过程实现:

  • 每个主机上安装并运行etcd和flannel;
  • 在etcd中规划配置所有主机的docker0子网范围;
  • 每个主机上的flanneld根据etcd中的配置,为本主机的docker0分配子网,保证所有主机上的docker0网段不重复,并将结果(即本主机上的docker0子网信息和本主机IP的对应关系)存入etcd库中,这样etcd库中就保存了所有主机上的docker子网信息和本主机IP的对应关系;
  • 当需要与其他主机上的容器进行通信时,查找etcd数据库,找到目的容器的子网所对应的outip(目的宿主机的IP);
  • 将原始数据包封装在VXLAN或UDP数据包中,IP层以outip为目的IP进行封装;
  • 由于目的IP是宿主机IP,因此路由是可达的;
  • VXLAN或UDP数据包到达目的宿主机解封装,解出原始数据包,最终到达目的容器。

        Flannel模式如下图所示: 

3、桥接方式(Pipework)

        最重要的留在最后说,这种方式是我最喜欢的,因为Pipework是一个简单易用的Docker容器网络配置工具。由200多行shell脚本实现。通过使用ip、brctl、ovs-vsctl等命令来为Docker容器配置自定义的网桥、网卡、路由等。

  • 使用新建的bri0网桥代替缺省的docker0网桥(docker0也可以继续保留,常规容器还是用docker0,而需要互通的容器可以借助于pipework这个工具给docker容器新建虚拟网卡并绑定IP桥接到br0)
  • bri0网桥与缺省的docker0网桥的区别:bri0和主机eth0之间是veth pair

        Pipework桥接方式的示意图:

以下是用Pipework为docker容器配置独立IP的方法:

1)安装pipework
# wget https://github.com/jpetazzo/pipework/archive/master.zip
# unzip master.zip 
# cp pipework-master/pipework  /usr/local/bin/

# chmod +x /usr/local/bin/pipework

2)run一个容器(一般是网络模式为None,如果不为None也行,经过以下操作后形成双网卡或多网卡)

通过docker ps查看这个容器的Name,我测试用的是:r-myTest-myImage2-1-54991b1a

3)给宿主机创建网桥

[root@localhost ~]# vi /etc/sysconfig/network-scripts/ifcfg-br0 
TYPE="Bridge"
BOOTPROTO=static
IPADDR=172.17.2.131
NETMASK=255.255.255.0
GATEWAY=172.17.2.1
PREFIX=24
DNS1=8.8.8.8
DNS2=114.114.114.114
NAME=br0
ONBOOT=yes
DEVICE=br0

4)设置物理网卡桥接到网桥(标红的内容加注释或添加)

[root@localhost ~]# vi /etc/sysconfig/network-scripts/ifcfg-eno16777736 
TYPE=Ethernet
#BOOTPROTO=static
#IPADDR=172.17.2.131
#NETMASK=255.255.255.0
#GATEWAY=172.17.2.1
DEFROUTE=yes
IPV4_FAILURE_FATAL=no
IPV6INIT=yes
IPV6_AUTOCONF=yes
IPV6_DEFROUTE=yes
IPV6_FAILURE_FATAL=no
NAME=eno16777736
DEVICE=eno16777736
ONBOOT=yes
#DNS1=8.8.8.8
PEERDNS=yes
PEERROUTES=yes
IPV6_PEERDNS=yes
IPV6_PEERROUTES=yes
IPV6_PRIVACY=no
BRIDGE="br0"

以上设置完毕可以通过命令service network restart重启网络,使之生效

5)通过brctl show,查看新建的网桥(标红的)

[root@localhost ~]# brctl show
bridge name     bridge id               STP enabled     interfaces
br0             8000.005056842f3f       no              eno16777736
                                                                           veth1pl87980
docker0         8000.024202f83b04       no          veth7ef0d8f
                                                                           vethb559941
                                                                           vethr1c49ea0c4f
                                                                           vethr89fb5f9e4b

6)pipework容器的IP(直接创建个与宿主机同网段未被使用的IP)

pipework br0 r-myTest-myImage2-1-54991b1a 172.17.2.134/24@172.17.2.1

再到该容器下ifconfig一下,就能看到新创建的网卡了:

通过宿主机也能直接ping通

目录
相关文章
|
8天前
|
安全 Docker 容器
docker的默认网络模式有哪些
Docker 默认网络模式包括:1) bridge:默认模式,各容器分配独立IP,可通过名称或IP通信;2) host:容器与宿主机共享网络命名空间,性能最优但有安全风险;3) none:容器隔离无网络配置,适用于仅需本地通信的场景。
20 6
|
12天前
|
存储 缓存 监控
Docker容器性能调优的关键技巧,涵盖CPU、内存、网络及磁盘I/O的优化策略,结合实战案例,旨在帮助读者有效提升Docker容器的性能与稳定性。
本文介绍了Docker容器性能调优的关键技巧,涵盖CPU、内存、网络及磁盘I/O的优化策略,结合实战案例,旨在帮助读者有效提升Docker容器的性能与稳定性。
41 7
|
16天前
|
安全 搜索推荐 网络安全
HTTPS协议是**一种通过计算机网络进行安全通信的传输协议
HTTPS协议是**一种通过计算机网络进行安全通信的传输协议
43 11
|
13天前
|
网络协议
计算机网络与通信
计算机网络基本概念:了解计算机网络的定义、功能、分类和拓扑结构(如总线型、星型、环型、树形、网状等)。 网络通信原理:了解网络通信的基本原理、协议和技术,如TCP/IP协议、网络通信设备等。
20 3
|
18天前
|
安全 网络安全 数据安全/隐私保护
利用Docker的网络安全功能来保护容器化应用
通过综合运用这些 Docker 网络安全功能和策略,可以有效地保护容器化应用,降低安全风险,确保应用在安全的环境中运行。同时,随着安全威胁的不断变化,还需要持续关注和研究新的网络安全技术和方法,不断完善和强化网络安全保护措施,以适应日益复杂的安全挑战。
38 5
|
21天前
|
算法
数据结构之卫星通信网络(BFS)
本文介绍了卫星通信网络及其重要性,并探讨了广度优先搜索(BFS)算法在其中的应用。卫星通信网络通过在轨卫星提供全球覆盖的通信服务,尤其在偏远地区和紧急救援中发挥关键作用。BFS算法用于网络拓扑分析、路径规划和故障排除,确保通信网络的高效运行。文章还包括BFS算法的工作原理、特点、优缺点及其实现代码示例。
33 1
|
21天前
|
网络协议 算法 数据库
OSPF 与 BGP 的互操作性:构建复杂网络的通信桥梁
OSPF 与 BGP 的互操作性:构建复杂网络的通信桥梁
37 0
|
28天前
|
Docker 容器
【赵渝强老师】Docker的None网络模式
Docker容器在网络方面实现了逻辑隔离,提供了四种网络模式:bridge、container、host和none。其中,none模式下容器具有独立的网络命名空间,但不包含任何网络配置,仅能通过Local Loopback网卡(localhost或127.0.0.1)进行通信。适用于不希望容器接收任何网络流量或运行无需网络连接的特殊服务。
|
28天前
|
Docker 容器
【赵渝强老师】Docker的Host网络模式
Docker容器在网络环境中是隔离的,可通过配置不同网络模式(如bridge、container、host和none)实现容器间或与宿主机的网络通信。其中,host模式使容器与宿主机共享同一网络命名空间,提高性能但牺牲了网络隔离性。