我有一个绑定到
127.0.0.1:10080
的无根 podman 容器,我想将外部流量转发到端口 80
去那个容器,我一直无法完成:
[me@certvault ~]$ curl -sS http://127.0.0.1:10080 >/dev/null
[me@certvault ~]$ curl -sS http://127.0.0.1:80 >/dev/null
curl: (7) Failed to connect to 127.0.0.1 port 80: Connection refused
[me@certvault ~]$ sudo firewall-cmd --list-forward-ports
[me@certvault ~]$ sudo firewall-cmd --add-forward-port=port=80:proto=tcp:toport=10080:toaddr=127.0.0.1
success
[me@certvault ~]$ sudo firewall-cmd --list-forward-ports
port=80:proto=tcp:toport=10080:toaddr=127.0.0.1
[me@certvault ~]$ curl -sS http://127.0.0.1:80 >/dev/null
curl: (7) Failed to connect to 127.0.0.1 port 80: Connection refused
[me@certvault ~]$ curl -sS http://127.0.0.1:10080 >/dev/null
如您所见,除了将流量重定向到容器外,一切正常。如果我删除容器的限制和
127.0.0.1
的规则,一切正常,所以我认为基本设置和想法是可靠的。但是我不想仅仅为了将流量重定向到它而向世界公开容器自定义端口,而且这似乎没有必要。一旦外界到达端口80
,它甚至不需要知道端口10080
。
# sudo firewall-cmd --add-forward port=port=80:proto=tcp:toport=10080:toaddr=127.0.0.1
此命令为默认区域添加转发端口。这将为进入默认区域的流量转发端口,例如民众。这击中了 iptables/nftables 的
PREROUTING
链/钩子。
你的榜样
$ curl -sS http://127.0.0.1:10080 >/dev/null
大概是从运行 firewalld 的主机上执行的。因此,流量永远不会到达内核中的
PREROUTING
链/钩子。它会打OUTPUT
!
在另一台机器上尝试卷曲测试;不是运行 firewalld 的那个。
如果您希望它也能在运行 firewalld 的同一台机器上工作,那么可以使用 firewalld v1.1.0 或更高版本中的 policy 来实现。事实上,这就是 podman 的新网络插件 netavark 所做的。
# firewall-cmd --permanent --new-policy outputDNAT
# firewall-cmd --permanent --policy outputDNAT --add-ingress-zone HOST
# firewall-cmd --permanent --policy outputDNAT --add-egress-zone ANY
# firewall-cmd --permanent --policy outputDNAT --add-rich-rule 'rule family="ipv4" destination address="127.0.0.1" forward-port port="80" protocol="tcp" to-port="10080"'
# firewall-cmd --reload