我有以下设置:
如何允许docker bridgenetworking上的docker容器与tun0networking上的openvpn客户端进行通信?
我希望能够以透明方式在docker1(10.10.0.3)和连接到vpn(172.19.0.x范围)的客户端之间进行基于tcp的通信。
我需要在docker(networking / iptables / …)端和主机上设置什么(iptables?)

我一直在使用Kyle Manna的非常好的Docker容器( https://github.com/kylemanna/docker-openvpn )。 我使用所谓的“偏执”文档来设置我的OpenVPN服务器,但在我看来,这应该是标准的方式,而不是偏执的方式。
为了允许在选定的Docker容器和VPN客户端之间进行双向连接,您需要创build一个Dockernetworking,在该networking上您将附加允许VPN客户端访问的容器。 VPN服务器将成为这些容器之一。
VPN服务器应该configurationclient-to-client , topology subnet , dev tun0 (或其他tun设备),并push "route <docker net IP> <docker net mask>" 。
应将VPN服务器的主机configuration为支持将IP数据包从一个子网转发到另一个子网。 这意味着将sysctl ip_forward设置为1(应该是这种情况,如果你有Docker安装的话),允许来自tun设备的数据包通过iptables FORWARD链并设置正确的路由。 这可以用这些命令来总结:
$ sudo sysctl -w net.ipv4.ip_forward=1 $ sudo iptables -A FORWARD -i tun+ -j ACCEPT $ sudo ip route add 192.168.255.0/24 via <IP address of OpenVPN server container>
无论如何,这里是我用来设置服务器的选项:
$ docker run --rm --net=none -it -v $PWD/files/openvpn:/etc/openvpn kylemanna/openvpn:2.4 ovpn_genconfig -u udp://<FQDN> -N -d -c -p "route <docker net IP> <docker net range>" -e "topology subnet"
这应该生成一个服务器configuration文件类似于:
server 192.168.255.0 255.255.255.0 verb 3 key /etc/openvpn/pki/private/vpn.example.com.key ca /etc/openvpn/pki/ca.crt cert /etc/openvpn/pki/issued/vpn.example.com.crt dh /etc/openvpn/pki/dh.pem tls-auth /etc/openvpn/pki/ta.key key-direction 0 keepalive 10 60 persist-key persist-tun proto udp # Rely on Docker to do port mapping, internally always 1194 port 1194 dev tun0 status /tmp/openvpn-status.log user nobody group nogroup client-to-client ### Push Configurations Below push "dhcp-option DNS 8.8.8.8" push "route 172.20.20.0 255.255.255.0" ### Extra Configurations Below topology subnet
现在我将举一个具体的例子。 在这个例子中,我将在主机vpn.example.com上的Docker中运行上面提到的OpenVPN服务器。 这个容器连接到Dockernetworkingdocker-net-vpn。 这里是命令(在这个例子中,我直接在服务器上生成服务器configuration,我跳过CA生成,请按照上述提到项目的偏执性文档):
$ docker network create --attachable=true --driver=bridge --subnet=172.20.20.0/24 --gateway=172.20.20.1 docker-net-vpn $ docker run --rm --net=none -it -v $PWD/files/openvpn:/etc/openvpn kylemanna/openvpn:2.4 ovpn_genconfig -u udp://vpn.example.com -N -d -c -p "route 172.20.20.0 255.255.255.0" -e "topology subnet" $ docker run --detach --name openvpn -v $PWD/files/openvpn:/etc/openvpn --net=docker-net-vpn --ip=172.20.20.2 -p 1194:1194/udp --cap-add=NET_ADMIN kylemanna/openvpn:2.4 $ sudo sysctl -w net.ipv4.ip_forward=1 $ sudo iptables -A FORWARD -i tun+ -j ACCEPT $ sudo ip route add 192.168.255.0/24 via 172.20.20.2
第一个命令创build一个专门的新Dockernetworking,它定义一个新的子网。 我们将把OpenVPN服务器连接到这个networking。
第二个使用第一个命令中定义的子网创buildOpenVPNconfiguration。
第三个创buildOpenVPN服务器。 它连接到新创build的Dockernetworking,并使用修复IP。
第四和第五个命令configurationIP转发。
最后一条命令通过OpenVPN容器固定IP为VPN客户端configuration添加一条新路由。
注意
我还没有尝试过,但是应该可以限制iptables的FORWARD规则。 Dockernetworking的创build创build了一个新的桥接设备。 这个网桥被命名为br-<ID> ,ID是DockernetworkingID的前12个字符。 这个ID可以通过docker network inspect -f '{{.Id}}' docker-net-vpn | cut -b-12 docker network inspect -f '{{.Id}}' docker-net-vpn | cut -b-12 。 因此,下面的命令可能更具限制性(安全性更好),但是仍然应该允许我们的stream量被路由:
$ NET_VPN_BRIDGE="br-$(docker network inspect -f '{{.Id}}' docker-net-vpn | cut -b-12)" $ sudo iptables -A FORWARD -i tun+ -o ${NET_VPN_BRIDGE} -j ACCEPT