docker 网络实现原理及网络模式
docker的网络隔离底层技术为linux提供的网络命名空间。
基本上可以通过ip命令复现docker的网络隔离。
linux 网络命名空间管理:ip命令
ip netns help 查看命令
ip link 挪网络设备
创建命名空间
ip netns add r1
ip netns add r2
ip netns exec r1 ifconfig -a
ip netns exec r2 ifconfig -a
命名空间默认没有网卡,只有一个lo设备。sit0是ipv6的适配设备。
[email protected]:~$ sudo ip netns exec r1 ifconfig -a
lo: flags=8<LOOPBACK> mtu 65536
loop txqueuelen 1000 (Local Loopback)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
sit0: flags=128<NOARP> mtu 1480
sit txqueuelen 1000 (IPv6-in-IPv4)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
ip link add 创建虚拟网卡
ip link add name veth1.1 type veth peer name veth1.2
两个网卡在默认空间。
执行ifconfig 会发现并没网卡。默认创建的网卡是down状态。
执行:ifconfig -a,列表如下。
...
veth1.1: flags=4098<BROADCAST,MULTICAST> mtu 1500
ether 8a:53:6c:29:09:b6 txqueuelen 1000 (Ethernet)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
veth1.2: flags=4098<BROADCAST,MULTICAST> mtu 1500
ether 76:bd:2d:4d:f2:a4 txqueuelen 1000 (Ethernet)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
可以通过ip命令查看当前的网卡:ip link sh
其中包括了所有的网卡。
...
6: [email protected]: <BROADCAST,MULTICAST,M-DOWN> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
link/ether 76:bd:2d:4d:f2:a4 brd ff:ff:ff:ff:ff:ff
7: [email protected]: <BROADCAST,MULTICAST,M-DOWN> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
link/ether 8a:53:6c:29:09:b6 brd ff:ff:ff:ff:ff:ff
新创建的网卡在r1和r2命名空间不可见。
执行下面命令,看不到网卡veth1.1和veth1.2
ip netns exec r1 ifconfig -a
ip netns exec r2 ifconfig -a
网卡在命名空间迁移
将网卡放到 r1中
ip link set dev veth1.1 netns r1
在默认的命名空间,查看网卡,发现已经看不到网卡veth1.1:
[email protected]:~$ sudo ip link sh
...
6: [email protected]: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
link/ether 76:bd:2d:4d:f2:a4 brd ff:ff:ff:ff:ff:ff link-netns r1
在r1中查看网卡,发现虚拟网卡已经在r1中。
[email protected]:~$ sudo ip netns exec r1 ifconfig -a
lo: flags=8<LOOPBACK> mtu 65536
loop txqueuelen 1000 (Local Loopback)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
sit0: flags=128<NOARP> mtu 1480
sit txqueuelen 1000 (IPv6-in-IPv4)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
veth1.1: flags=4098<BROADCAST,MULTICAST> mtu 1500
ether 8a:53:6c:29:09:b6 txqueuelen 1000 (Ethernet)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
网络连通性
目前的网络拓扑:r1和默认空间通过veth1.1—veth1.2关联。
分别启动r1中的veth1.1 和默认空间的veth1.2 。
sudo ip netns exec r1 ifconfig veth1.1 10.1.0.1/24 up
sudo ifconfig veth1.2 10.1.0.2/24 up
在r1测试连通性:
[email protected]:~$ sudo ip netns exec r1 ping 10.1.0.2
PING 10.1.0.2 (10.1.0.2) 56(84) bytes of data.
64 bytes from 10.1.0.2: icmp_seq=1 ttl=64 time=0.281 ms
64 bytes from 10.1.0.2: icmp_seq=2 ttl=64 time=0.029 ms
64 bytes from 10.1.0.2: icmp_seq=3 ttl=64 time=0.044 ms
64 bytes from 10.1.0.2: icmp_seq=4 ttl=64 time=0.039 ms
将veth1.2迁移到r2中:
sudo ip link set dev veth1.2 netns r2
sudo ip netns exec r2 ifconfig veth1.2 10.1.0.2/24 up
[email protected]:~$ sudo ip netns exec r2 ifconfig
veth1.2: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 10.1.0.2 netmask 255.255.255.0 broadcast 10.1.0.255
inet6 fe80::74bd:2dff:fe4d:f2a4 prefixlen 64 scopeid 0x20<link>
ether 76:bd:2d:4d:f2:a4 txqueuelen 1000 (Ethernet)
RX packets 19 bytes 1522 (1.5 KB)
RX errors 0 dropped 2 overruns 0 frame 0
TX packets 25 bytes 1998 (1.9 KB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
测试r1和r2的连通性:
[email protected]:~$ sudo ip netns exec r1 ping 10.1.0.2
PING 10.1.0.2 (10.1.0.2) 56(84) bytes of data.
64 bytes from 10.1.0.2: icmp_seq=1 ttl=64 time=0.050 ms
64 bytes from 10.1.0.2: icmp_seq=2 ttl=64 time=0.070 ms
64 bytes from 10.1.0.2: icmp_seq=3 ttl=64 time=0.104 ms
[email protected]:~$ sudo ip netns exec r2 ping 10.1.0.1
PING 10.1.0.1 (10.1.0.1) 56(84) bytes of data.
64 bytes from 10.1.0.1: icmp_seq=1 ttl=64 time=0.048 ms
64 bytes from 10.1.0.1: icmp_seq=2 ttl=64 time=0.075 ms
设置网卡信息
ip netns exec r1 ip link set dev veth1.2 name eth0
ip netns exec r1 ifconfig -a
docker网络模型
封闭容器 只有lo设备
docker run --name t1 -it --network none --rm busybox:1.31.1
ifconfig 一个网卡 lo
[email protected]:~$ docker run --name t1 -it --network none --rm busybox:1.33.1
/ # ifconfig
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
UP LOOPBACK RUNNING MTU:65536 Metric:1
RX packets:0 errors:0 dropped:0 overruns:0 frame:0
TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:0 (0.0 B) TX bytes:0 (0.0 B)
/ #
桥接容器
docker run --name t1 -it --rm busybox:1.31.1
ifconfig 两个网卡 lo, eth0
[email protected]:~$ docker run --name t1 -it --rm busybox:1.33.1
/ # ifconfig
eth0 Link encap:Ethernet HWaddr 02:42:AC:11:00:02
inet addr:172.17.0.2 Bcast:172.17.255.255 Mask:255.255.0.0
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:11 errors:0 dropped:0 overruns:0 frame:0
TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:962 (962.0 B) TX bytes:0 (0.0 B)
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
UP LOOPBACK RUNNING MTU:65536 Metric:1
RX packets:0 errors:0 dropped:0 overruns:0 frame:0
TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:0 (0.0 B) TX bytes:0 (0.0 B)
docker run --name t1 -it --network bridge --rm busybox:1.31.1
ifconfig 两个网卡 lo, eth0,和默认的情况一样。
hostname为容器的id
/ # hostname
92b72be55875
设置主机名:
docker run --name t1 -it --network bridge -h t1.com --rm busybox:1.31.1
hostname 显示:t1.com
[email protected]:~$ docker run --name t1 -it --network bridge -h t1.com --rm busybox:1.33.1
/ # hostname
t1.com
/ #
域名解析:
查看hosts可以看到,容器自己的ip和主机名做了映射:
cat /etc/hosts
127.0.0.1 localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.17.0.2 t1.com t1
resolv.conf中使用宿主机作为dns
cat /etc/resolv.conf
# DNS requests are forwarded to the host. DHCP DNS options are ignored.
nameserver 192.168.65.5
nslookup -type=A www.baidu.com
Server: 192.168.65.5
Address: 192.168.65.5:53
Non-authoritative answer:
www.baidu.com canonical name = www.a.shifen.com
Name: www.a.shifen.com
Address: 110.242.68.4
Name: www.a.shifen.com
Address: 110.242.68.3
自定义dns主机:
docker run --name t1 -it --network bridge -h t1.com --dns 114.114.114.114 --rm busybox:1.31.1
cat /etc/resolv.conf 包含114
添加hosts:
docker run --name t1 -it --network bridge -h t1.com --add-host www.baidu.com:1.1.1.1 --rm busybox:1.31.1
cat /etc/hosts
joined容器 容器间共享网络
docker run --name b1 -it --rm busybox
ifconfig
docker run --name b2 -it --network container:b1 --rm busybox
ifconfig 结果和b1的相同
宿主机模式 容器直接使用主机网络
docker run --name b1 --network host -it --rm busybox
ifconfig 同主机
注意:wsl2不支持宿主机模式。
上一篇: 自定义Toast 显示文字和图片
下一篇: 土豆发芽吃下去身体会有哪些危害呢