最可靠方式是用 macvlan 驱动创建网络并指定 -o parent=eth1;需确保 eth1 up 状态,执行 docker network create -d macvlan --subnet=192.168.50.0/24 --gateway=192.168.50.1 -o parent=eth1 phys-eth1-net,容器启动时手动指定 ip 且不可用 -p 映射。

要让 Docker 容器的出网流量走指定的物理网卡(比如 eth1 而不是默认的 eth0),关键不是改路由或 iptables,而是让容器网络直接绑定到那张物理网卡——最可靠、最贴近实战的方式是用 macvlan 驱动创建网络,并明确指定 -o parent=eth1。
确认物理网卡可用且已就绪
先确保目标网卡(如 eth1)处于 UP 状态,且能正常收发包:
- 运行
ip link show eth1,确认状态为UP,没有NO-CARRIER - 若需 VLAN 透传,还需提前加载
8021q模块:modprobe 8021q - 如果该网卡已配置 IP(如用于宿主机管理),不影响 macvlan 使用;但建议将其 IP 移到子接口(如 eth1.100)或清空,避免地址冲突
创建基于指定网卡的 macvlan 网络
用 docker network create 命令绑定到目标物理接口。例如,让容器走 eth1 并接入 192.168.50.0/24 子网:
docker network create -d macvlan \--subnet=192.168.50.0/24 \--gateway=192.168.50.1 \-o parent=eth1 \phys-eth1-net
注意:这个网络不依赖 docker0,也不经过宿主机协议栈,容器发出的包会直接从 eth1 发出,源 MAC 是容器独占的虚拟 MAC,IP 是你分配的物理网段地址。
启动容器并指定 IP(推荐手动指定)
macvlan 网络通常不带内置 DHCP,所以启动时应显式指定 IP,确保它属于该子网且未被占用:
docker run -d --name web-srv \--net=phys-eth1-net \--ip=192.168.50.100 \-p 80:80 nginx
⚠️ 这里的 -p 在 macvlan 下**无效**(端口映射依赖 NAT,而 macvlan 绕过了宿主机网络栈)。如需对外暴露服务,应直接访问容器 IP(如 http://192.168.50.100),或在交换机/上游防火墙上做策略。
验证流量是否真从指定网卡发出
进容器检查出口接口和路由:
-
docker exec -it web-srv ip route→ 应显示默认路由指向192.168.50.1 dev eth0 -
docker exec -it web-srv cat /sys/class/net/eth0/nameif→ 应返回类似eth1@的 parent 关联信息 - 在宿主机上抓包:
tcpdump -i eth1 port 80,同时从容器 curl 外部地址,能看到请求帧从 eth1 发出
如果看到流量出现在 eth0 或 docker0 上,说明网络创建时 parent 写错了,或容器误用了 bridge 网络。











