Docker安装的mysql限制ip访问
1.问题背景
docker安装了mysql服务,服务器为Redhat9,我们希望通过防火墙规则直接限制访问的来源ip,只允许特定ip进行访问,其余ip需要被禁止。
2.排查过程
1.首先尝试了通过firewalld方式添加对应的防火墙规则,
sudo firewall-cmd --add-rich-rule='rule family="ipv4" source address="0.0.0.0/0" port protocol="tcp" port="3306" reject'firewall-cmd --add-rich-rule='rule family="ipv4" source address="10.190.126.111" port protocol="tcp" port="3306" accept'sudo firewall-cmd --runtime-to-permanentsudo firewall-cmd --reload
添加后发现其余IP依然可以访问,firewalld并未起作用。
2.查找问题根源
sudo iptables -L -n | grep 3306
发现docker默认添加了3306端口的放行规则,虽然我在 firewalld 设置了规则,但Docker加的iptables规则优先级更高,所以导致直接放行了。
继续查看DOCKER-USER
sudo iptables -L DOCKER-USER --line-numbers
是 DOCKER-USER 链默认的第一条,意思是:
如果没有其他规则匹配,就RETURN返回,继续走INPUT链的逻辑。
RETURN 相当于 退出当前链,不继续匹配 DOCKER-USER 后续规则了。
➡️所以后续我们添加的自定义规则(比如 DROP、ACCEPT)一定要加在 RETURN 之前!
如果加在 RETURN 之后,就永远到不了你的规则了,因为前面已经 RETURN 了,后面的根本不会执行。
举个例子:
现在 DOCKER-USER链是这样的:
Chain DOCKER-USER (1 references)
num target prot opt source destination
1 RETURN all -- 0.0.0.0/0 0.0.0.0/0
如果我们要加规则,比如:
允许 10.161.238.15 访问3306,再全部拒绝其他IP。
我们需要这么加(保证在RETURN前):
iptables -I DOCKER-USER 1 -s 10.161.238.15 -p tcp --dport 3306 -j ACCEPT
iptables -I DOCKER-USER