当前位置: 首页 > news >正文

零基础学Docker(7)--Docker网络

1. docker0

我们运行:ip addr 命令

可以看到有三个,lo代表的是我们的环回接口,eth0代表我们的物理网卡接口,docker0则代表docker的虚拟网桥接口,安装docker就会有这个。

当容器以默认的bridge网络模式启动时,Docker 会自动创建一对veth pair(虚拟网卡对),一端连接到容器内部作为容器的网卡(比如eth0),另一端则连接到docker0网桥上。 这就相当于把容器 “接入” 到了docker0这个虚拟的网络交换机上。

这里我启动了一个tomcat,可以看到多了一对veth pair,同时我们进入tomcat内部执行ip addr:

可以看到两边是对应的,接下来我们重点介绍容器是如何通信的:

2. 容器与外部如何通信

宿主机物理网卡 eth0 的 IP 为 172.24.10.23(外部可访问的宿主机地址);
容器启动时做了端口映射:docker run -d -p 8080:8080 tomcat(宿主机 8080 端口映射到容器 8080 端口);
容器内网卡为 eth0@if113,IP 为 172.17.0.2(docker0 网桥分配的私有 IP);
宿主机侧与容器配对的虚拟网卡为 veth45f915f@if112(挂在 docker0 网桥上,docker0 网关 IP 为 172.17.0.1)。
完整流程:外部 → 容器

  1.  外部请求发送到宿主机:外部设备(如用户电脑)通过网络向 172.24.10.23:8080 发送 HTTP 请求。该请求首先到达宿主机的物理网卡 eth0(因为 172.24.10.23 是 eth0 绑定的 IP 地址)。
  2. 宿主机内核接收并识别端口映射规则:宿主机内核的 TCP/IP 协议栈接收请求,解析目标地址为 172.24.10.23:8080。Docker 启动时已通过 iptables 和 netfilter 在内核中注册规则:将宿主机 8080 端口的流量转发到容器的 172.17.0.2:80。内核匹配到该规则,确定 “这是发给容器的流量”,准备转发。
  3. 流量从宿主机物理网卡转发到 docker0 网桥:内核根据转发规则,将流量从物理网卡 eth0 转发到 docker0 网桥(docker0 的 IP 为 172.17.0.1,是容器网络的网关)。此时通过 DNAT(目的地址转换),流量的目标 IP 从 172.24.10.23 转换为容器私有 IP 172.17.0.2,目标端口从 8080 转换为容器内的 80 端口。
  4. docker0 网桥将流量转发到容器的虚拟网卡:docker0 网桥作为虚拟交换机,维护着 MAC 地址表,记录了 172.17.0.2(容器 IP)与宿主机侧虚拟网卡 veth45f915f@if112 的 MAC 地址对应关系。docker0 查找表中 172.17.0.2 对应的端口(即 veth45f915f@if112),将流量转发到该虚拟网卡。
  5. 流量进入容器内部:veth45f915f@if112 是 veth pair 虚拟网卡对的宿主机侧接口,其配对的另一端是容器内的 eth0@if113 网卡。流量通过 veth pair 从 veth45f915f@if112 传递到容器内的 eth0@if113。
  6. 容器内应用接收请求:容器独立的网络命名空间接收 eth0@if113 传来的流量,解析目标地址为 172.17.0.2:80。容器内运行的tomcat 应用正监听 8080 端口,最终接收并处理该请求。

这个流程反过来就算容器内部到外部的通信流程

3. 容器间通信

前提场景
宿主机上有两个容器:
容器 A:IP 为 172.17.0.2,虚拟网卡对应宿主机侧 vethA(挂在 docker0 上);
容器 B:IP 为 172.17.0.3,虚拟网卡对应宿主机侧 vethB(挂在 docker0 上);
docker0 网桥 IP 为 172.17.0.1,维护着 MAC 地址表(记录 172.17.0.2 → vethA 的 MAC、172.17.0.3 → vethB 的 MAC);
容器 A 内的应用(如客户端)向容器 B 内的应用(如监听 80 端口的服务器)发送请求。

完整流程:容器 A → 容器 B

  1. 容器 A 内应用发起请求:容器 A 内的应用生成请求,目标地址为容器 B 的 IP 和端口 172.17.0.3:80,源地址为容器 A 自身 IP 172.17.0.2:随机端口。请求首先进入容器 A 的网络栈,通过容器 A 内的 eth0 网卡发送。
  2. 容器 A 解析目标 MAC 地址:容器 A 的网络栈判断目标 IP 172.17.0.3 与自身 IP 172.17.0.2 属于同一网段(172.17.0.0/16),因此需要通过 ARP 协议获取容器 B 的 MAC 地址:容器 A 发送 ARP 请求(广播帧):谁有 172.17.0.3 的 IP?请回复我(172.17.0.2)的 MAC 地址;该 ARP 请求通过容器 A 的 eth0 发送到宿主机侧的 vethA,再传递到 docker0 网桥。
  3. docker0 网桥转发 ARP 请求:docker0 网桥收到 ARP 广播帧后,会向除 vethA 外的所有端口(包括 vethB)广播该请求(因为 ARP 是二层广播,需全网段询问)。容器 B 的宿主机侧虚拟网卡 vethB 收到 ARP 请求,发现目标 IP 172.17.0.3 是自己的 IP,于是通过 vethB 向 docker0 网桥回复 ARP 响应:172.17.0.3 的 MAC 地址是 XX:XX:XX:XX:XX:XX(容器 B 内 eth0 的 MAC)。
  4. 容器 A 缓存 MAC 地址并发送数据:docker0 网桥将容器 B 的 ARP 响应转发给 vethA,再传递到容器 A 的 eth0。容器 A 收到响应后,将 172.17.0.3 → 容器 B 的 MAC 记录到本地 ARP 缓存表,然后生成数据帧(源 MAC:容器 A 的 MAC,目标 MAC:容器 B 的 MAC,封装 TCP 数据 172.17.0.3:80),通过 eth0 发送。
  5. docker0 网桥转发数据帧到容器 B:容器 A 的数据帧通过 vethA 传递到 docker0 网桥,docker0 查找自身 MAC 地址表,发现 172.17.0.3 对应的端口是 vethB,于是将数据帧直接转发到 vethB。
  6. 容器 B 接收并处理请求:vethB 将数据帧传递到容器 B 内的 eth0 网卡,容器 B 的网络栈解析数据帧,确认目标 IP 和端口 172.17.0.3:80 匹配自身监听的应用,最终由容器 B 内的应用(如服务器)接收并处理请求。

4. --link

容器启动时会被分配动态 IP(如 172.17.0.x),且 IP 可能随容器重启变化。

--link 允许一个容器(被链接容器)被另一个容器(发起链接的容器)通过别名访问,无需依赖动态 IP。例如:docker run --link db:mysql app,则 app 容器可直接通过 mysql 这个别名访问 db 容器,无需知道其 IP。

使用 --link 时,Docker 会自动在发起链接的容器中:
添加被链接容器的信息到 /etc/hosts 文件(如 172.17.0.3 mysql db),实现域名解析。
注入被链接容器的环境变量(如 MYSQL_PORT_3306_TCP、MYSQL_ENV_* 等),方便获取对方的网络信息(端口、环境变量等)。

docker run -d -p 8094:8080 --name mytomcat4 --link mytomcat1 diytomcat:1.0;

注意这个配置是单项的,也就是只能mytomcat4通过mytomcat1来访问mytomcat1,因为其原理是通过在本地host文件 添加 ip到mytomcat1的映射

5.自定义网络

在 Docker 中,自定义网络是一种更灵活、更安全的容器间通信方式,相比早期的 --link 机制,它支持动态 DNS 解析、网络隔离和更灵活的配置,是现代 Docker 网络的最佳实践。

为什么需要自定义网络

  • 默认的 bridge 网络(Docker 安装时自动创建)功能有限,不支持容器名直接通信(需依赖 --link)。
  • 自定义网络可实现容器间通过名称 / 别名通信(内置 DNS 服务),无需依赖 IP 或 --link。
  • 可隔离不同业务的容器(如数据库网络、应用网络分开),提高安全性。
5.1 创建自定义网络
docker network create [选项] 网络名称

常用选项:

  • --driver:指定网络驱动(默认 bridge,适用于单机容器通信;其他如 overlay 用于跨主机通信)。
  • --subnet:指定子网网段(如 192.168.0.0/16),不指定则自动分配。
  • --gateway:指定网关 IP(如 192.168.0.1)。

创建一个名为my-net的桥接网络

docker network create my-net

示例(指定子网和网关):

docker network create --driver bridge --subnet 192.168.100.0/24 --gateway 192.168.100.1 my-net

可以通过 docker network ls查看所有网络

  • bridge是 Docker 默认的网络驱动,即docker0所使用的
  • host代表使用宿主机网络,这意味着容器和主机共享相同的 IP 地址和端口空间,容器内监听的端口不能与主机上已占用的端口冲突。
  • none代表无网络模式,在不需要进行网络通信的场景,比如一些只需要在容器内执行计算任务,不需要对外提供服务,也不需要从外部获取数据的批处理任务容器。
5.2让容器加入自定义网络

创建容器时加入:用 --network 指定网络,--network-alias 可设置容器在该网络中的别名(可选)。

# 创建容器 tomcat1 加入 my-net 网络
docker run -d --name tomcat1 --network my-net --network-alias mytomcat1 diytomcat:1.0# 创建容器 tomcat2 加入 my-net 网络
docker run -d --name tomcat2 --network my-net diytomcat:1.0

# 将已有的容器 tomcat3 加入 my-net 网络
docker network connect my-net tomcat3 

注意,一个容器是可以通过connect命令加入多个网络的,可以做到不同网络中的容器互通

5.3 容器间通信

加入同一自定义网络的容器,可直接通过容器名网络别名通信(无需 IP)。


自定义网络的优势

  • 自动 DNS 解析:容器名 / 别名直接映射到 IP,无需手动维护 hosts。
  • 网络隔离:不同网络的容器默认无法通信(除非手动连接),增强安全性。
  • 动态更新:容器重启后 IP 变化不影响通信(依赖名称解析)。
  • 支持多种驱动:除了单机的 bridge,还可通过 overlay 实现跨主机容器通信(配合 Swarm 或 Kubernetes)。
http://www.dtcms.com/a/458094.html

相关文章:

  • 网站关键词掉的很快中卫网站推广公司
  • 32套网站后台管理系统模板开发一款软件的费用
  • DVWA靶场之十五:授权绕过(Authorisation Bypass)
  • wordpress菜单参数设置seo线上培训机构
  • FPGA实现直流电机转速、电压、电流测量系统(基于EP4CE6F17C8 + INA226)
  • 【linux】 查看cpu占用前10的进程
  • 跨越银色浪潮:中国智慧养老的“无人区”探索与人性回归
  • 如何做网上私人彩票网站网站建站公司官网
  • 网站管理员功能网站推广的目的是什么
  • 网站建设书籍免费wordpress超精简主题
  • 上海市建设安全协会网站孟 侠上海网站建设优化公司
  • c++ 程序基础-变量赋值
  • 吴恩达机器学习课程(PyTorch 适配)学习笔记:2.3 PyTorch 工具与高效实现
  • 国内优秀的网站设计东营住房与城乡建设部网站
  • Spring原理揭秘--ApplicationContext初始化中的扩展点
  • wordpress 多站点主题php做视频网站有哪些
  • 南京手机网站制作中山古镇做网站的公司
  • 深圳市建设局质监站官方网站大数据营销方式有哪些
  • 深度学习-Kaggle实战1(房价预测)
  • 邢台高端网站建设公司wordpress 单页模板
  • 有设计师做的装修效果图的网站关于做营销型网站的建议
  • C#+WPF+Opencv模块化开发视觉对位系统
  • 网站专业优化公司广州工商学院门户网站
  • 贪心:Stall Reservations S
  • 商务网站怎么做wordpress模板 更换
  • 企业建设网站的目的wordpress路由与模板调用
  • 滕州住房和城乡建设局网站企业网站设计建设
  • C4D域功能深度解析:随机域、着色器域、声音域、公式域与Python域详解
  • SQL 面试题解析:如何用多表查询写用户订单统计?
  • 建设网站需要收费吗wordpress前台注册登录弹窗代码