You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

如何让Docker容器使用Wireguard子网内的独立IP与NAT后的Wireguard节点通信

如何让Docker容器使用Wireguard子网内的独立IP与NAT后的Wireguard节点通信

我来帮你捋清楚这个问题的解决逻辑——你之前踩的坑核心是Docker桥接网络和Wireguard接口用了完全重叠的子网,导致服务器的路由表彻底混乱,不知道该把容器的数据包往哪发。

先复盘下你之前的问题:

  • 用默认Docker桥接时,容器发往Wireguard节点的请求会被SNAT成服务器的Wireguard IP(192.168.60.1),节点那边根本分不清是哪个容器来的请求
  • 后来你手动创建了同子网的Docker桥(192.168.60.0/24),结果服务器上同时有wg1和Docker桥两个接口都声称自己管这个子网的路由,系统直接懵了,数据包自然发不出去

下面是经过验证的解决步骤:

1. 拆分重叠子网,避免路由冲突

把Wireguard和Docker桥的子网分成两个不重叠的小范围,比如:

  • Wireguard接口用 192.168.60.1/28(这个子网覆盖192.168.60.1~192.168.60.15)
  • Docker桥用 192.168.60.16/28(覆盖192.168.60.16~192.168.60.31)

2. 更新Wireguard配置

服务器端(wg1)配置

修改对应的Wireguard配置文件(比如/etc/wireguard/wg1.conf):

[Interface]
PrivateKey = *** REDACTED ***
ListenPort = 51821
Address = 192.168.60.1/28

[Peer]
PublicKey = *** REDACTED ***
AllowedIPs = 192.168.60.2/32, 192.168.60.16/28  # 新增Docker桥子网,让节点能接收容器的数据包

NAT后的Wireguard节点配置

修改节点的Wireguard配置:

[Interface]
PrivateKey = *** REDACTED ***
Address = 192.168.60.2/32

[Peer]
PublicKey = *** REDACTED ***
AllowedIPs = 192.168.60.0/28, 192.168.60.16/28  # 包含两个子网,确保能和服务器、容器通信

改完后记得重启两边的Wireguard服务:wg-quick down wg1 && wg-quick up wg1

3. 创建禁用SNAT的Docker桥接网络

用这条命令创建Docker网络,关键是禁用地址伪装,这样容器的真实IP会被保留:

docker network create --driver=bridge --subnet=192.168.60.16/28 --opt com.docker.network.bridge.enable_ip_masquerade=false my-net

4. 启动容器测试

给容器分配子网内的固定IP,比如:

docker run -it --rm --network=my-net --ip=192.168.60.18 alpine

现在从这个容器ping 192.168.60.2,节点那边看到的源IP就是192.168.60.18,完美区分不同容器的请求!

为什么这样能解决问题?

  • 拆分子网后,服务器的路由表会明确:192.168.60.0/28的流量走wg1接口,192.168.60.16/28的流量走Docker桥,不会再出现路由冲突
  • 禁用enable_ip_masquerade后,Docker不会把容器的源IP替换成服务器的IP,保证容器的独立IP能被Wireguard节点识别到

备注:内容来源于stack exchange,提问作者sven

火山引擎 最新活动