iptables 层面如何做到判断 header 来做反向代理? - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
Distributions
Ubuntu
Fedora
CentOS
中文资源站
网易开源镜像站
herozzm
V2EX    Linux

iptables 层面如何做到判断 header 来做反向代理?

  •  
  •   herozzm 2021-05-08 21:53:27 +08:00 4618 次点击
    这是一个创建于 1683 天前的主题,其中的信息可能已经有所发展或是发生改变。

    正常情况下,可以用 iptables -t nat -A PREROUTING ... 来实现反向代理的,但是这个层面是无法判断 header 的,那么有其他办法吗?

    需求是只允许带有某个 header 的请求反向代理成功,其他一律拒绝

    27 条回复    2021-05-10 11:28:21 +08:00
    AngryPanda
        1
    AngryPanda  
       2021-05-08 21:58:33 +08:00 via iPhone   1
    应用层数据,nginx 就能实现了
    herozzm
        2
    herozzm  
    OP
       2021-05-08 22:00:59 +08:00
    @AngryPanda 就是不想转到 nginx 去处理啊,端口实在太多,有上百千个端口到 nginx? nginx 貌似不能简单绑定多个端口去做处理,都是 listen 单个端口去做判断
    seerhut
        3
    seerhut  
       2021-05-08 22:14:03 +08:00
    很久以前的确有人给 kernel 做 7 层的 filter,但似乎并没有正式并入内核,需要手动 patch,近几年似乎大家对内核空间中做 7 层处理没什么兴趣了,毕竟 dpdk 啥的让上层处理报文效率相当不错了。你这个需求是不是可以让 iptables 把包都扔给本机的 ng 一个端口上,再让 ng 处理 7 层?
    typeaudit
        4
    typeaudit  
       2021-05-08 22:14:28 +08:00 via iPhone
    你需要的或许是一个 API 网关。
    billlee
        5
    billlee  
       2021-05-08 23:18:27 +08:00
    @herozzm 你还要拦截非 80 端口的吗?
    herozzm
        6
    herozzm  
    OP
       2021-05-08 23:24:12 +08:00
    @billlee 是的
    billlee
        7
    billlee  
       2021-05-08 23:36:00 +08:00
    你的需求讲的很不清楚。拦截所有端口,如果拦下来后发现不是 HTTP 协议,那是要放行还是阻断?

    我觉得内核里解析 HTTP 就不要想了,但有很多方案可以在内核把流量重定向到用户空间进程,比如 iptables TPROXY, tun2socks
    herozzm
        8
    herozzm  
    OP
       2021-05-08 23:49:08 +08:00
    @billlee 我要拦截指定端口的 tcp 访问,然后判断其 header 中某个参数,符合条件就放行(反向代理),我现在用 iptables 将指定的几百个端口都转到了 nginx 的某个端口,然后在 nginx 里面去获取 header 来做反向代理,已经实现了,iptables 层面感觉很难做
    dangyuluo
        9
    dangyuluo  
       2021-05-09 00:29:54 +08:00
    自己写一个 Module ?杀鸡用牛刀的感觉
    learningman
        10
    learningman  
       2021-05-09 01:10:39 +08:00 via Android
    我琢磨过这个,答案是可行,但是巨麻烦。
    因为 iptables 操作的是 IP 包,你得拆两层才能拿到应用层数据,而且有可能的网卡分包
    fkdog
        11
    fkdog  
       2021-05-09 02:20:34 +08:00
    iptables 是工作在网络层,怎么可能管的到应用层的 http 协议。
    你需要一个应用层的防火墙
    herozzm
        12
    herozzm  
    OP
       2021-05-09 02:25:11 +08:00 via Android
    @fkdog filter 可以得到的
    tony601818
        13
    tony601818  
       2021-05-09 05:53:36 +08:00
    > 你需要的或许是一个 API 网关。

    +1 可以看看 Netflix 开源的 Zuul
    gam2046
        14
    gam2046  
       2021-05-09 07:04:40 +08:00
    这应该是 7 层干的事情,网络层去搞,非常麻烦,要不你统一在目标应用上加前置代理,由前置代理决定出口,如果目标应用不提供使用代理的功能,就套上 proxychains,这相对来说容易实现,成本也低。

    而你要分析 HTTP 头,那注定不能是 HTTPS,除非客户端信任你的自签证书,也就是说本身你的应用场景应该就是可控的场景,而不是针对任意第三方,所以加代理可能是比较容易的。
    yaxin
        15
    yaxin  
       2021-05-09 07:53:31 +08:00 via iPhone
    iptables 将特定端口数据转发到 nginx 处理就行了吧
    xuanbg
        16
    xuanbg  
       2021-05-09 08:01:41 +08:00   1
    7 层的事情就应该在 7 层处理,无论它有多少问题。你妄图在 4 层处理 7 层的事情,只会导致更多的问题。
    ElmerZhang
        17
    ElmerZhang  
       2021-05-09 10:48:37 +08:00
    iptables 就不是用来干 7 层的事情的,用 haproxy 或者 nginx 吧
    wangritian
        18
    wangritian  
       2021-05-09 13:57:25 +08:00
    赞同很多人提到的网络层不要干应用层的事,我好奇的是为什么一个 http 服务器需要几百个端口?统一到 80 然后通过 Host 分配二级域名做虚拟主机不可以吗
    PolarBears
        19
    PolarBears  
       2021-05-09 14:45:56 +08:00
    @wangritian 可能是想做透明代理?
    herozzm
        20
    herozzm  
    OP
       2021-05-09 17:15:27 +08:00
    @wangritian 没有域名,ip+端口 访问服务这不是正常的操作吗?
    LGA1150
        21
    LGA1150  
       2021-05-09 17:24:52 +08:00 via Android
    iptables nat 表只能匹配到新连接的包,对于 TCP 来说就是 SYN,看不到应用层的数据。

    你可能要找的是 ipvs
    Lemeng
        22
    Lemeng  
       2021-05-09 17:35:26 +08:00
    也是来学习的
    wangritian
        23
    wangritian  
       2021-05-09 17:44:40 +08:00
    @PolarBears 有可能,只允许定制的客户端访问这些端口

    @herozzm 一个服务这样做是正常的,几百个就应该在 7 层管理了,除非是特殊需求
    GG668v26Fd55CP5W
        24
    GG668v26Fd55CP5W  
       2021-05-09 17:53:41 +08:00 via iPhone
    http 明文传输是肯定是可以的,好像以前做过,https 理论上也可以,需要读取私钥或者信任证书,类似 Wireshark 的抓包。但我觉得还是应该在应用层解决比较好
    xenme
        25
    xenme  
       2021-05-09 17:59:19 +08:00 via iPhone
    直接 iptables 接管所有流量转发到 nginx,然后再 nginx 处理呗。透明代理现在都是这种思路
    GG668v26Fd55CP5W
        26
    GG668v26Fd55CP5W  
       2021-05-09 18:07:06 +08:00
    哦,以前做的是拦截某个 header 的 http 请求,比如 X-Forwarded-For

    iptables -I INPUT 1 -p tcp --dport 80 -m string --algo bm --string 'X-Forwarded-For:' -j DROP

    firewall-cmd --direct --add-rule ipv4 filter INPUT_direct 10 -p tcp --dport 80 -m string --algo bm --string 'X-Forwarded-For:' -j DROP
    julyclyde
        27
    julyclyde  
       2021-05-10 11:28:21 +08:00
    你都明知道不存在了还问啥啊
    用-m match 处理并不能保证结果正确
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     906 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 28ms UTC 22:13 PVG 06:13 LAX 14:13 JFK 17:13
    Do have faith in what you're doing.
    ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86