Docker
在创建容器的时候,可以使用--net
选项指定容器的的网络模式。
网络模式
Docker
支持4种网络模式供大家选择:
- host模式,使用
- -net=host
指定。 - container模式,使用
- -net=container:NAME_or_ID
指定。 - none模式,使用
- -net=none
指定。 - bridge模式,使用
- -net=bridge
指定,默认设置。
host模式
众所周知,Docker
使用了Linux
的Namespaces
技术来进行资源隔离,如PID Namespace
隔离进程,Mount Namespace
隔离文件系统,Network Namespace
隔离网络等。一个Network Namespace
提供了一份独立的网络环境,包括网卡、路由、Iptable规则等都与其他的Network Namespace
隔离。一个Docker
容器一般会分配一个独立的Network Namespace
。但如果启动容器的时候使用host
模式,那么这个容器将不会获得一个独立的Network Namespace
,而是和宿主机共用一个Network Namespace
。容器将不会虚拟出自己的网卡,配置自己的IP
等,而是使用宿主机的IP
和端口。
例如,我们在10.10.101.105/24
的机器上用host
模式启动一个含有web
应用的Docker
容器,监听tcp80
端口。当我们在容器中执行任何类似ifconfig
命令查看网络环境时,看到的都是宿主机上的信息。而外界访问容器中的应用,则直接使用10.10.101.105:80
即可,不用任何NAT
转换,就如直接跑在宿主机中一样。但是,容器的其他方面,如文件系统、进程列表等还是和宿主机隔离的。
container模式
在理解了host
模式后,这个模式也就好理解了。这个模式指定新创建的容器和已经存在的一个容器共享一个Network Namespace
,而不是和宿主机共享。新创建的容器不会创建自己的网卡,配置自己的IP
,而是和一个指定的容器共享IP、端口范围等。同样,两个容器除了网络方面,其他的如文件系统、进程列表等还是隔离的。两个容器的进程可以通过lo网卡设备通信。
none模式
这个模式和前两个不同。在这种模式下,Docker
容器拥有自己的Network Namespace
,但是,并不为Docker
容器进行任何网络配置。也就是说,这个Docker
容器没有网卡、IP、路由等信息。需要我们自己为Docker
容器添加网卡、配置IP
等。
bridge模式
bridge
模式是Docker
默认的网络设置,此模式会为每一个容器分配Network Namespace
、设置IP
等,并将一个主机上的Docker
容器连接到一个虚拟网桥上。
bridge模式的拓扑
当Docker server
启动时,会在主机上创建一个名为docker0
的虚拟网桥,此主机上启动的Docker
容器会连接到这个虚拟网桥上。虚拟网桥的工作方式和物理交换机类似,这样主机上的所有容器就通过交换机连在了一个二层网络中。接下来就要为容器分配IP了,Docker
会从RFC1918
所定义的私有IP
网段中,选择一个和宿主机不同的IP地址和子网分配给docker0
,连接到docker0
的容器就从这个子网中选择一个未占用的IP使用。如一般Docker
会使用172.17.0.0/16
这个网段,并将172.17.42.1/16
分配给docker0
网桥(在主机上使用ifconfig
命令是可以看到docker0
的,可以认为它是网桥的管理接口,在宿主机上作为一块虚拟网卡使用)。单机环境下的网络拓扑如下,主机地址为10.10.101.105/24
。
默认模式
安装完Docker
的时候,会自动创建三个网络。使用docker network ls
命令可以查看这些网络:
docker network ls |
这三个网络都建在Docker
中。运行容器时,可以使用该--network
标志来指定容器应连接到的网络。
默认网桥
Docker
服务启动后默认会创建一个 docker0
网桥(其上有一个 docker0
内部接口),它在内核层连通了其他的物理或虚拟网卡,这就将所有容器和本地主机都放到同一个物理网络。
Docker
默认指定了 docker0
接口 的 IP
地址和子网掩码,让主机和容器之间可以通过网桥相互通信,它还给出了 MTU
(接口允许接收的最大传输单元),通常是 1500 Bytes
,或宿主主机网络路由上支持的默认值。这些值都可以在服务启动的时候进行配置。
bridge
所有Docker
主机上都存在默认网络。如果您不指定其他网络,则新的容器会自动连接到默认bridge
网络。
使用docker network inspect
命令可以查看相关的网络信息:
docker network inspect 75b73b341642 |