赞
踩
目录
当项目大规模使用 Docker 时,容器通信的问题也就产生了。要解决容器通信问题,必须先了解很多关于网络的知识。Docker 作为目前最火的轻量级容器技术,有很多令人称道的功能,如 Docker 的镜像管理。然而,Docker 同样有着很多不完善的地方,网络方面就是 Docker 比较薄弱的部分。因此,我们有必要深入了解 Docker 的网络知识,以满足更高的网络需求。
默认网络
安装 Docker 以后,会默认创建三种网络,可以通过 docker network ls
查看。
- [root@localhost ~]# docker network ls
- cNETWORK ID NAME DRIVER SCOPE
- b2d0689a7644 bridge bridge local
- c598e7da9321 host host local
- 36391f761fe6 none null local
网络模式 | 简介 |
---|---|
none | 容器有独立的network namespace,但并没有对其进行任何网络设置, |
host | 容器将不会虚拟出自己的网卡,配置自动的IP等,而是使用宿主机的IP和端口 |
bridge | 为每一个容器分配,设置IP等,并将容器连接一个docker0虚拟网桥,默认为该模式 |
自定义网络 | 根据个人需要进行创建网络 |
none 网络模式是指禁用网络功能,只有 lo 接口 local 的简写,代表 127.0.0.1,即 localhost 本地环回接口。在创建容器时通过参数 --net none
或者 --network none
指定;
none网络就是什么都没有的网络,挂在这个网络下的容器除了lo,没有其他任何网卡了,是一个封闭的空间。
- [root@localhost ~]# docker run -it --network=none busybox
- / # ls
- bin dev etc home proc root sys tmp usr var
- / # ip a
- 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1
- 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
使用场景,一些对安全性要求高并且不需要联网的应用情况下可以使用none网络。比如某个容器的唯一用途是生成随机密码,就可以存放到none网络中,避免密码被窃取等。
采用 host 网络模式的 Docker Container,可以直接使用宿主机的 IP 地址与外界进行通信,若宿主机的 eth0 是一个公有 IP,那么容器也拥有这个公有 IP。同时容器内服务的端口也可以使用宿主机的端口,无需额外进行 NAT 转换;
- [root@localhost ~]# docker run -it --network host busybox
- / # ip a
- 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1
- 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 qlen 1000
- link/ether 00:0c:29:10:b7:cb brd ff:ff:ff:ff:ff:ff
- inet 192.168.2.5/24 brd 192.168.2.255 scope global ens33
- valid_lft forever preferred_lft forever
- inet6 fe80::20c:29ff:fe10:b7cb/64 scope link
- valid_lft forever preferred_lft forever
- 3: docker0: <NO-CARRIER,BROADCAST,MULTICAST,UP> mtu 1500 qdisc noqueue
- link/ether 02:42:48:47:28:8a 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:48ff:fe47:288a/64 scope link
- valid_lft forever preferred_lft forever
在容器中可以看到host的所有网卡,并且连hostname也是host的。host网络的使用场景又是什么呢? 直接使用docker host的网络最大的好处就是性能,如果容器对网络传输效率有较高要求,则可以选择host网络。当然不便之处就是牺牲一些灵活性,比如要考虑端口冲突问题,docker host 上已经使用的端口就不能再用了。
docker host的另一个用途是让容器可以直接配置host网络,比如某些跨host的网络解决方案,其本身也是以容器方式运行的,这些方案需要对网络进行配置,比如管理iptables。
下面我以nginx为例,来查看一些host网络的特性
[root@localhost ~]# docker run -it --network=host nginx
无需映射端口,就可以正常访问。
当然要关闭防火墙,或者开发80端口。
在该模式中,Docker 守护进程创建了一个虚拟以太网桥 docker0
,新建的容器会自动桥接到这个接口,附加在其上的任何网卡之间都能自动转发数据包。
docker安装时会创建一个命名为docker0的Linux bridge。如果不指定--network,创建的容器默认都会挂到docker0上。
- [root@localhost ~]# brctl show
- bridge name bridge id STP enabled interfaces
- docker0 8000.02424847288a no
当前docker0上没有任何其他网络设备,我们创建一个容器看看变化
- [root@localhost ~]# docker run -itd busybox
- 0fee2a50ff1136c302604c13b5b51a2b72d904268ff8d69df07a8d01a1c2c6a9
- [root@localhost ~]# brctl show
- bridge name bridge id STP enabled interfaces
- docker0 8000.02424847288a no vethe833331
一个新的网络接口vethe833331被挂载到了docker0上,vethe331aee3就是新创建容器的虚拟网卡
查看刚刚创建容器的网卡配置
- [root@localhost ~]# docker exec -it 0fee2a50ff11 /bin/sh
- / # ip a
- 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1
- 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,M-DOWN> mtu 1500 qdisc noqueue
- link/ether 02:42:ac:11:00:02 brd ff:ff:ff:ff:ff:ff
- inet 172.17.0.2/16 brd 172.17.255.255 scope global eth0
- valid_lft forever preferred_lft forever
- / # route -n
- Kernel IP routing table
- Destination Gateway Genmask Flags Metric Ref Use Iface
- 0.0.0.0 172.17.0.1 0.0.0.0 UG 0 0 0 eth0
- 172.17.0.0 0.0.0.0 255.255.0.0 U 0 0 0 eth0
原来briage网络配置的subnet就是172.17.0.0/16,并且网关是172.17.0.1。这个网关就是docker0.
- [root@localhost ~]# ifconfig docker0
- docker0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
- inet 172.17.0.1 netmask 255.255.0.0 broadcast 172.17.255.255
- inet6 fe80::42:48ff:fe47:288a prefixlen 64 scopeid 0x20<link>
- ether 02:42:48:47:28:8a txqueuelen 0 (Ethernet)
- RX packets 0 bytes 0 (0.0 B)
- RX errors 0 dropped 0 overruns 0 frame 0
- TX packets 5 bytes 438 (438.0 B)
- TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
除了none,host,bridge这三个自动创建的网络,用户也可以根据业务需要创建user-defined网络。
格式:
docker network create [OPTIONS] NETWORK
选项:
- --driver,-d:驱动程序管理网络,选项网络类型
- --gateway:主子网的IPv4或IPv6网关
- --subnet:CIDR格式的子网,表示一个网段
创建一个192.168.8.0网段的网卡,网关为192.168.8.254
- [root@localhost ~]# docker network create --driver bridge --gateway 192.168.8.254 --subnet 192.168.8.0/24 mynet1
- 37c8fcb1b7c93184f4efadac4cb849651b60738d1c3d667c3352a6e367a0a633
- [root@localhost ~]# brctl show
- bridge name bridge id STP enabled interfaces
- br-37c8fcb1b7c9 8000.024213041d24 no
- docker0 8000.02424847288a no vethe833331
- [root@localhost ~]# docker run -it --network mynet1 busybox
- / # ip a
- 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1
- 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
- 15: eth0@if16: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue
- link/ether 02:42:c0:a8:08:01 brd ff:ff:ff:ff:ff:ff
- inet 192.168.8.1/24 brd 192.168.8.255 scope global eth0
- valid_lft forever preferred_lft forever
- / # route -n
- Kernel IP routing table
- Destination Gateway Genmask Flags Metric Ref Use Iface
- 0.0.0.0 192.168.8.254 0.0.0.0 UG 0 0 0 eth0
- 192.168.8.0 0.0.0.0 255.255.255.0 U 0 0 0 eth0
显示一个或多个网络的详细信息
格式:
docker network inspect [OPTIONS] NETWORK [NETWORK...]
选项:
--format,-f:自定义格式输出
查看刚刚创建网卡详细信息
- [root@localhost ~]# docker network inspect mynet1
- [
- {
- "Name": "mynet1",
- "Id": "37c8fcb1b7c93184f4efadac4cb849651b60738d1c3d667c3352a6e367a0a633",
- "Created": "2023-07-11T22:04:40.965301103+08:00",
- "Scope": "local",
- "Driver": "bridge",
- "EnableIPv6": false,
- "IPAM": {
- "Driver": "default",
- "Options": {},
- "Config": [
- {
- "Subnet": "192.168.8.0/24",
- "Gateway": "192.168.8.254"
- }
- ]
- },
- "Internal": false,
- "Attachable": false,
- "Ingress": false,
- "ConfigFrom": {
- "Network": ""
- },
- "ConfigOnly": false,
- "Containers": {},
- "Options": {},
- "Labels": {}
- }
- ]
将容器连接到网络
格式:
docker network connect [OPTIONS] NETWORK CONTAINER
创建一个网络,进行添加到容器中
- [root@localhost ~]# docker network connect mynet02 041b95cd171e
- [root@localhost ~]# docker exec -it 041b95cd171e /bin/sh
- / # ip a
- 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1
- 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
- 20: eth0@if21: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue
- link/ether 02:42:c0:a8:08:01 brd ff:ff:ff:ff:ff:ff
- inet 192.168.8.1/24 brd 192.168.8.255 scope global eth0
- valid_lft forever preferred_lft forever
- 22: eth1@if23: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue
- link/ether 02:42:ac:12:00:02 brd ff:ff:ff:ff:ff:ff
- inet 172.18.0.2/16 brd 172.18.255.255 scope global eth1
- valid_lft forever preferred_lft forever
4.docker network rm
移除一个或多个网络
格式:
docker network rm NETWORK [NETWORK...]
选项:
--force,-f:强制删除网络
删除刚刚创建的网络
- [root@localhost ~]# docker network rm -f mynet1
- mynet1
- [root@localhost ~]# docker network rm -f mynet02
- mynet02
- [root@localhost ~]# docker network ls
- NETWORK ID NAME DRIVER SCOPE
- b2d0689a7644 bridge bridge local
- c598e7da9321 host host local
- 36391f761fe6 none null local
1.外部访问容器
网卡改为host模式
2.不同网段容器之间如何访问
为容器添加双网卡
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。