Docker 绕过防火墙的端口映射问题
问题发现
早上检查服务器时发现他妈的数据库被黑了,排查后才想起防火墙端口忘记关闭。立即登录服务器关闭了防火墙对应端口
但远程测试时发现:端口居然还能连上!
问题原因

我的数据库服务是通过 Docker 启动的,这正是问题的根源。
Docker 默认把所有转发到容器的流量全部放行,无条件 ACCEPT
Docker 的 iptables 行为
Docker 默认会在系统 iptables 中自动添加 NAT/FORWARD 规则,将映射端口直接放行。外部流量会绕过 INPUT 链,因此即使防火墙(UFW)没有开放端口,也能访问容器服务。
当 Docker 启动容器并映射端口(如 -p 3307:3306)时,会自动执行以下操作:
- 在 NAT 表的
PREROUTING链添加 DNAT 规则,将宿主机端口转发到容器端口 - 在
FORWARD链添加 ACCEPT 规则,放行转发流量
流量路径分析
UFW 规则作用于 filter/INPUT 链,而外部访问 Docker 映射端口时,流量走的是:
1 | |
由于流量不经过 INPUT 链,所以即使 UFW 禁止了端口,Docker 映射的端口仍然可以被外部访问。
解决方案
方案一:禁止 Docker 自动管理 iptables(推荐)
编辑 Docker 配置文件:
1 | |
添加以下内容:
1 | |
重启 Docker 服务:
1 | |
这样防火墙(UFW、iptables)就能真正掌控端口访问,Docker 不再绕过 INPUT 链。
⚠️ 注意:禁用后需要手动配置容器网络的 NAT 规则,容器间通信和外部访问都需要自行管理。
方案二:使用 UFW-Docker 插件
安装 ufw-docker 脚本,让 UFW 能正确管理 Docker 端口:
1 | |
允许特定 IP 访问容器端口:
1 | |
常见坑排查清单
| 问题现象 | 可能原因 | 排查命令 |
|---|---|---|
| 防火墙关了端口还能访问 | Docker 绑定了 iptables | iptables -t nat -L -n |
| 容器无法访问外网 | 禁用 iptables 后未配置 NAT | iptables -t nat -A POSTROUTING -s 172.17.0.0/16 -j MASQUERADE |
| 容器间无法通信 | 网络模式或 FORWARD 链问题 | docker network ls |
| UFW 状态显示正常但不生效 | Docker 规则优先级更高 | iptables -L DOCKER-USER -n |
总结
Docker 默认的 iptables 管理机制虽然方便,但会绕过系统防火墙,带来安全隐患。生产环境建议:
- 敏感服务不要直接映射到公网,使用
127.0.0.1绑定 - 配置
iptables: false或使用 ufw-docker 插件 - 定期检查 iptables 规则:
iptables -L -n和iptables -t nat -L -n - 数据库等关键服务设置强密码,并限制访问 IP
安全无小事,别等被黑了才想起来补救。
Docker 绕过防火墙的端口映射问题
https://blog.newpon.top/2025/12/01/服务器端口拦截问题/