Linux nftables防火墙配置实战:规则编写与流量过滤策略

iptables 作为 Linux 默认防火墙工具已有二十余年历史,但其规则匹配效率随规则数量增长急剧下降,且多表多链的跳转逻辑难以维护。nftables 作为 iptables 的继任者,通过统一语法、原生集合并发支持和更高效的数据结构,成为现代 Linux 服务器防火墙配置的首选方案。本文从规则编写到生产部署,给出 nftables 完整配置实战。

nftables与iptables的核心差异

nftables 在 Linux 3.13 内核引入,通过 nft 命令行工具替代 iptablesip6tablesarptablesebtables 四套工具。底层使用 netlink 接口与内核通信,规则在用户空间编译为字节码后注入内核虚拟机执行,避免了 iptables 每条规则单独系统调用的开销。

关键改进包括:原生支持集合(Set)和字典(Map)类型,一条规则可匹配数千个 IP 而无需逐条展开;支持命名集合持久化和动态更新;规则语法支持变量、匿名集合和连接追踪状态匹配;表和链可自定义,不再受限于 iptables 固定的 filter/nat/mangle/raw 表结构。

nftables基础语法与表链配置

创建一个基本的防火墙表和链:

# 创建 inet 类型的表(同时处理 IPv4 和 IPv6)
nft add table inet firewall

# 创建 input 链,类型为 filter,挂钩到网络入站路径
nft 'add chain inet firewall input { type filter hook input priority 0; policy drop; }'

# 允许已建立连接的流量(连接追踪)
nft add rule inet firewall input ct state established,related accept

# 允许回环接口流量
nft add rule inet firewall input iifname "lo" accept

# 允许 SSH 访问(限速防暴力破解)
nft add rule inet firewall input tcp dport 22 ct state new limit rate 5/minute accept

# 允许 HTTP 和 HTTPS
nft add rule inet firewall input tcp dport { 80, 443 } accept

# 允许 ICMP(ping)
nft add rule inet firewall input icmp type echo-request accept
nft add rule inet firewall input icmpv6 type echo-request accept

# 默认拒绝其他流量(已在链定义中设置 policy drop)

上述配置实现了基本的服务器防火墙:放行已建立连接、回环接口、SSH(带限速)、Web 服务和 ICMP,其余流量默认丢弃。policy drop 作为兜底策略确保未匹配规则的流量不会被放行。

nftables集合与动态IP管理

nftables 的集合功能是相较 iptables 最大的优势之一。维护一个 IP 白名单集合,支持运行时动态增删:

# 创建命名集合
nft add set inet firewall whitelist { type ipv4_addr \; flags interval \; }

# 批量添加 IP 段到集合
nft add element inet firewall whitelist { 10.0.0.0/8, 192.168.1.0/24, 172.16.5.10 }

# 使用集合匹配规则
nft add rule inet firewall input ip saddr @whitelist accept

# 运行时动态添加单个 IP
nft add element inet firewall whitelist { 203.0.113.50 }

# 运行时删除 IP
nft delete element inet firewall whitelist { 203.0.113.50 }

flags interval 启用区间匹配,支持 CIDR 网段。集合内部使用红黑树存储,即使包含数万个 IP 条目,匹配复杂度仍为 O(log n),远优于 iptables 逐条匹配的 O(n)。

结合连接追踪实现自动封禁可疑 IP:

# 创建封禁集合(带超时自动清除)
nft add set inet firewall blacklist { type ipv4_addr \; flags timeout \; timeout 1h \; }

# 检测到端口扫描行为时自动加入封禁集合
nft add rule inet firewall input tcp dport 1-65535 ct state new limit rate 10/minute burst 20 packets accept
nft add rule inet firewall input tcp dport 1-65535 ct state new update @blacklist { ip saddr limit rate 10/minute } drop

# 封禁集合中的 IP 直接丢弃
nft add rule inet firewall input ip saddr @blacklist drop

timeout 1h 让被封禁的 IP 一小时后自动从集合移除,避免长期占用内存。update @blacklist 语法在匹配到异常流量时自动将源 IP 写入封禁集合。

nftables NAT转发与端口映射配置

nftables 的 NAT 配置通过 nat 类型的链实现:

# 创建 NAT 表
nft add table ip nat

# 创建 prerouting 链(端口映射/目的地址转换)
nft 'add chain ip nat prerouting { type nat hook prerouting priority -100; }'

# 创建 postrouting 链(源地址转换/伪装)
nft 'add chain ip nat postrouting { type nat hook postrouting priority 100; }'

# 将外部 8080 端口映射到内网 192.168.1.100:80
nft add rule ip nat prerouting tcp dport 8080 dnat to 192.168.1.100:80

# 内网通过公网网卡访问外网(MASQUERADE)
nft add rule ip nat postrouting oifname "eth0" ip saddr 192.168.1.0/24 masquerade

# 固定 SNAT(指定出口 IP)
nft add rule ip nat postrouting oifname "eth0" ip saddr 10.0.0.0/8 snat to 203.0.113.1

MASQUERADE 适用于动态获取出口 IP 的场景(如 DHCP),SNAT 适用于固定公网 IP。二者区别在于 MASQUERADE 每次连接都查询出口 IP,SNAT 直接使用指定地址,性能略优。

nftables规则持久化与生产部署

nftables 规则默认存储在内存中,重启后丢失。持久化方案:

# 将当前规则导出到文件
nft list ruleset > /etc/nftables.conf

# 设置开机自动加载
systemctl enable nftables
systemctl start nftables

# /etc/nftables.conf 文件格式示例
cat > /etc/nftables.conf << 'EOF'
#!/usr/sbin/nft -f
flush ruleset

table inet firewall {
    set whitelist {
        type ipv4_addr
        flags interval
        elements = { 10.0.0.0/8, 192.168.1.0/24 }
    }

    chain input {
        type filter hook input priority 0; policy drop;
        ct state established,related accept
        iifname "lo" accept
        ip saddr @whitelist accept
        tcp dport { 80, 443 } accept
        tcp dport 22 ct state new limit rate 5/minute accept
        icmp type echo-request accept
    }

    chain forward {
        type filter hook forward priority 0; policy drop;
        ct state established,related accept
        iifname "eth1" oifname "eth0" accept
    }
}
EOF

使用 flush ruleset 确保每次加载前清空旧规则,避免规则叠加冲突。文件首行 #!/usr/sbin/nft -f 使其可直接作为脚本执行,方便调试。

nftables性能监控与规则调试

查看规则匹配计数器,定位未生效的规则:

# 查看所有规则及匹配计数
nft list ruleset -a

# 查看指定链的规则及计数器
nft list chain inet firewall input -a

# 为规则添加计数器(调试用)
nft add rule inet firewall input tcp dport 443 counter accept

# 实时监控规则匹配
nft monitor trace

counter 关键字在规则中插入计数器,可查看该规则匹配的数据包数和字节数。nft monitor trace 实时输出数据包经过规则链的匹配过程,是排查规则不生效的有效工具。生产环境中,建议在高频规则上添加计数器,结合 Prometheus 抓取实现防火墙流量可视化监控。

原创文章,作者:小编,如若转载,请注明出处:https://www.yunthe.com/linuxnftables-fang-huo-qiang-pei-zhi-shi-zhan-gui-ze-bian/

(0)
小编小编
上一篇 1天前
下一篇 1天前

相关推荐