Docker Bridge 网络原理
2021-10-10 16:31
393 查看
Docker 的网络子系统是可插拔驱动式的,默认情况下存在或支持多种网络接口,如 bridge、host、overlay、macvlan 以及 none 类型的网络接口。
bridge 是 docker 默认的网络模式,如果在创建容器时不指定网络类型,则默认时 bridge 模式,会为每个容器分配一个 Network Namespace、IP 等,并将容器的网络连接到一个网桥(docker0)上。 这种模式的特点是:同一个网桥下的容器间可以相互通信,不同网桥间的容器网络会被隔离。
Linux 网桥
bridge 模式是基于 Linux 的
网桥(一同通过软件实现的虚拟设备)实现的,
网桥可以将 Linux 内部多个网络接口连接在一起,如下图:
通过网桥将网络接口连接起来可以实现:一个网络接口接收到网络数据包后,会复制到其他网络接口中,如下图所示: 如上图所示,当网络接口A收到数据包后,
网桥会将数据包复制发送给连接到网桥的其他接口(如上图中的网卡B和网卡C)。
docker0
Docker 通过 Linux 的
网桥实现了 bridge模式,原理如下图: Docker 在启动时,会创建一个名为
docker0的
网桥,并把其IP地址设为
172.17.0.1/16(私有IP地址)。
$ brctl show bridge name bridge id STP enabled interfaces docker0 8000.0242526953be no
注:brclt 一个用来管理网桥的命令行工具。详见
$ ip addr 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000 link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 inet 127.0.0.1/8 scope host lo valid_lft forever preferred_lft forever inet6 ::1/128 scope host valid_lft forever preferred_lft forever 2: ens33: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000 link/ether 00:0c:29:9c:30:76 brd ff:ff:ff:ff:ff:ff inet 192.168.59.128/24 brd 192.168.59.255 scope global noprefixroute dynamic ens33 valid_lft 1512sec preferred_lft 1512sec inet6 fe80::b356:f4d:f6ea:25aa/64 scope link noprefixroute valid_lft forever preferred_lft forever 3: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default link/ether 02:42:52:69:53:be brd ff:ff:ff:ff:ff:ff inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0 valid_lft forever preferred_lft forever inet6 fe80::42:52ff:fe69:53be/64 scope link valid_lft forever preferred_lft forever
然后 Docker 在创建容器时,会通过虚拟设备对
veth-pair来将容器与
docker0连接起来。对于
172.17.0.0/16网段的数据包, Docker 会定义一条
iptables NAT的规则来讲这些数据包的 IP 地址转换成公网 IP 地址,然后通过真实的网络接口(如上图 ens160 接口)发送出去。 启动一个容器,默认使用 bridge 模式
$ docker run -d --name redis -p6379:6379 redis:4 5bd019a047ce
查看网桥状态,已有 veth 连接
$ brctl show bridge name bridge id STP enabled interfaces docker0 8000.0242526953be no vethed2a70d
查看容器的netns
当容器启动时,Docker 内部会自动为这个容器创建一个
netns用于网络隔离,但当我们使用
ip netns list查看时却看不到数据,是因为 Docker 把
netns创建到了其他地方,而
ip netns list命令只能读目录
/var/run/netns下面的数据。
我们可以通过以下命令来解决这个问题,方便我们学习docker网络。
# 得到容器对应的进程 pid=`docker inspect -f '{{.State.Pid}}' $container_id` # 手动创建防止文件夹不存在 mkdir -p /var/run/netns/ # 建立软连接 ln -s /proc/$pid/ns/net /var/run/netns/$container_id
将上面的命令修改为和当前环境一致并验证netns中的网卡。
$ pid=`docker inspect -f '{{.State.Pid}}' 5bd019a047ce` $ mkdir -p /var/run/netns/ $ ln -s /proc/$pid/ns/net /var/run/netns/5bd019a047ce $ ip netns list 5bd019a047ce (id: 0) $ ip netns exec 5bd019a047ce ip a 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000 link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 inet 127.0.0.1/8 scope host lo valid_lft forever preferred_lft forever 6: eth0@if7: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default link/ether 02:42:ac:11:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0 inet 172.17.0.2/16 brd 172.17.255.255 scope global eth0 valid_lft forever preferred_lft forever
可以看到我们成功输出了netns中的网卡信息,并且此信息和从docker容器中看到的一致。
相关文章推荐
- docker的网络-单主机(三种原生网络)none、host、bridge
- docker学习-bridge网络
- docker的host、bridge网络类型
- docker网络介绍之bridge网络详解
- docker容器网络通信原理分析
- docker网络之bridge
- Docker网络的原理和验证
- docker学习-bridge网络
- docker容器网络通信原理分析
- Docker网络模式与配置Docker自定义网络(bridge模式)
- docker容器网络通信原理分析
- Docker 配置网络使用bridge网络的方法
- 透过现象看本质——docker的网络模式、一边排障一边配置docker自定义网络(bridge模式)
- “深入浅出”来解读Docker网络核心原理 推荐
- Docker网络模式bridge
- Docker系列教程17-默认bridge网络中配置DNS
- Docker Libnetwork Bridge插件实现代码分析----创建网络部分
- Docker四种网络模式的原理
- docker容器网络通信原理分析
- docker bridge 网络