Docker --- 网络模式

1. 概述

1.1 是什么?

1.2 Docker 未启动时,本机的网络情况

virbr0

在CentOS7的安装过程中,如果有选择相关虚拟化的服务安装系统后,启动网卡时会发现有一个以网桥连接的私网地址的virbr0网卡(virbr0网卡:它还有一个固定的默认IP地址:192.168.122.1),是做虚拟机网桥的使用,其作用是为连接其上的虚拟网卡提供NAT访问外网的功能

之前用虚拟机安装Linux时,勾选安装系统的时候附带了libvirt服务才会生成的一个东西,如果不需要刻意直接将libvirtd服务卸载

yum remove libvirt-libs.x86_64

1.3 Docker 启动后,本机的网络情况

出现了新的名为 docker0 的虚拟网桥

1.4 能干嘛

1. 容器之间的互联和通信以及端口映射
2. 容器IP变动时可以通过服务名直接网络通信而不受影响

1.5 容器 宕机/删除,IP地址的变化

容器每次启动和停止时,IP地址都会发生变化

2. 网络操作命令

2.1 查看 Docker 所有的网络

# bridge 网桥模式 , host 主机模式
docker network ls

2.2 查看网络源数据

docker network inspect 网络名

# 只看名字
docker network inspect | grep name

2.3 创建网络

# 不指定网络模式默认为 bridge
docker network create 网络名

2.4 删除网络

docker network rm 网络名

3. 网络模式

3.1 bridge (虚拟网桥,默认)

为每一个容器分配、设置IP等,并将容器连接到一个 docker0

1. 命令

--network bridge  # 默认使用docker0
-net bridge

2. docker0

1. 理论

Docker 服务默认会创建一个 docker0 网桥(其上有一个 docker0 内部接口),该桥接网络的名称为docker0, 它在内核层连通了其他的物理或虚拟网卡,这就将所有容器和本地主机都放到了同一个物理网络. Docker默认指定了 docker0 接口的IP地址和子网掩码,让主机和容器之间可以通过网桥相互通信

1. Docker 使用Linux桥接,在宿主机虚拟一个Docker容器网桥(docker0),Docker启动一个容器时会根据Docker网桥的网段分配给容器一个IP地址,成为Contaiiner-IP,同时Docker网桥时每个容器的默认网关,因为在同一宿主机内的容器都接入同一个网桥,这样容器之间就可以通过容器的Container-IP直接通信

2. docker run 的时候,没有指定network的话默认使用的网桥模式就是birdge,使用的就是docker0. 在宿主机ifcong,就可以看到docker0和自己create的networketh0,eth1,eth2....代表网卡一,网卡二,网卡三....lo代表127.0.0.1,即localhost,inet addr 用来表示网卡的IP地址

3. 网桥 docker0 创建一对对虚拟设备接口,一个叫veth,另一个叫eth0,成对匹配

1. 整个宿主机的网桥模式都是docker0, 类似一个交换机有一对接口,每个接口叫veth,在本地主机和容器内分别创建一个虚拟接口,并让他们彼此连通(这样的一对接口叫做veth pair)

2. 每个容器实例内部也有一块网卡,每个接口叫做eth0

3. docker0上面的每个veth匹配某个容器实例内部的eth0,两两配对,一一匹配

通过上述,将宿主机上的所有容器都连接到这个内部网络上,两个容器在同一网络下,会从这个网关下各自拿到分配的IP,此时两个容器的网络是互通的

2. 容器启动后的网络情况

启动两个容器后,宿主机上会出现两个网卡

宿主机的网络情况,veth 23 对应 eth022

容器内部的网络情况,eth0 22对应 veth23

容器内部的网络情况,eth0 24对应 veth25

3.2 host (主机模式)

容器将不会虚拟出自己的网卡,配置自己的IP等,而是使用宿主机的IP和端口

1. 命令

--network host  
-net host

docker run -d -p 8083:8080 --network host --name tomcat83 billygoo/tomcat8-jdk8

2. 会出现警告信息

原因

docker 启动时指定 --network=host 或 -net=host,如果还指定了-p端口映射,那这个时候就会有此警告,并且使用了-p指定端口也不会再起作用,而是用的tomcat的默认端口8080,如有重复则会递增8081...

解决办法

使用docker 的其他网络模式,如 --network=bridge,或者直接无视此警告,或者在启动容器时,不指定端口

3. 如何访问tomcat呢?

# 如果 8080 被其他服务占用则会递增
宿主机的IP:8080

3.3 none (无对外网络,只有本地回环)

容器有独立的 Network namspace,但没有对其进行任何网络设置,如分配 veth pair和网桥连接,IP等

命令

--network none 
-net none

3.4 container (容器模式)

新创建的容器不会创建自己的网卡和配置自己的IP,而是和一个指定的容器共享IP、端口范围等,同样,两个容器除了网络方面是共享的,其他如文件系统,进程列表依然还是隔离的

命令

--network container:容器名/容器ID  
-net container:容器名/容器ID  

错误案例

# 先启动一个容器
docker run -d -p 8085:8080 --name tomcat85 billygoo/tomcat8-jdk8

# 指定使用8085的ip和端口
docker run -d -p 8086:8080 --network container:tomcat85 --name tomcat86 billygoo/tomcat8-jdk8

报错

原因

相当于 tomcat85 和 tomcat86共用同一个IP和端口,导致端口冲突

正确案例,不指定端口

# 先启动一个容器
docker run -d  --name tomcat85 billygoo/tomcat8-jdk8

# 指定使用8085的ip和端口
docker run -d  --network container:tomcat85 --name tomcat86 billygoo/tomcat8-jdk8

3.5 自定义桥接网络 (使用最多)

自定义网络本身就维护好了主机名和IP的对应关系,用以保证IP和服务名都能ping通

1. 使用前

1. 用网桥模式,启动两个容器

docker run -d -p 8081:8080 --name tomcat81 billygoo/tomcat8-jdk8

docker run -d -p 8082:8080 --name tomcat82 billygoo/tomcat8-jdk8

2. 进入两个容器内相互ping IP地址,查看到可以ping通

# 查看 IP 地址
ip addr

# 172.17.0.3 ping 172.17.0.2
ping 172.17.0.2

# 172.17.0.2 ping 172.17.0.3
ping 172.17.0.3

3. 两个容器内相互ping 服务名,查看到无法ping通

# tomcat81 ping tomcat82
ping tomcat82

# tomcat82 ping tomcat81
ping tomcat81

4. 结论

可以看到 ping 服务名是ping不通的,但是每次容器启停时,容器的IP地址都会变化,如果按照IP地址访问其他容器的话,就会访问到错误的容器,导致服务不可用

2. 使用后

自定义桥接网络,默认使用的是桥接网络 bridge

1. 创建自定义网络

docker network create tomcat_network

2. 将容器加入到自定义网络中

docker run -d -p 8081:8080 --network tomcat_network --name tomcat81 billygoo/tomcat8-jdk8

docker run -d -p 8082:8080 --network tomcat_network --name tomcat82 billygoo/tomcat8-jdk8

3. 进入两个容器内相互ping IP地址,查看到可以ping通

# 查看 IP 地址
ip addr

# 172.17.0.3 ping 172.17.0.2
ping 172.17.0.2

# 172.17.0.2 ping 172.17.0.3
ping 172.17.0.3

4. 两个容器内相互ping 服务名,查看到也可以ping通

# tomcat81 ping tomcat82
ping tomcat82

# tomcat82 ping tomcat81
ping tomcat81
posted @ 2024-02-21 16:35  河图s  阅读(79)  评论(0)    收藏  举报