• 网站配置了Cloudflare代理后,如何配置Nginx获取的真实客户端IP地址?


    网站配置了Cloudflare代理后,如何配置Nginx获取的真实客户端IP地址?

    这是一个很简单的问题,如何在后台获取真实的访问者IP地址? 网站为了避免有些不怀好意的访问者,不得不自动分析一下客户端访问信息,比如同一个IP一秒钟访问了一千次,正常人哪有这么快的手速,直接认定为程序所为(恶意攻击、爬虫等),今天分享下如何在日志中记录访问者的真实IP地址,以及如何配置一些简单的防止访问频率过高的限制。

    请添加图片描述

    本文获取IP地址方法仅对 Cloudflare代理 有效,其他代理如何解决需要阅读其官方文档,原理应该是类似的。

    接下来就分享一下具体的配置过程,带大家了解下配置过程,最后还会分享给大家的自动化处理Bash脚本,帮你你省去了自己编写脚本的时间了。

    第一步:获取代理IP段信息

    Cloudflare提供了其所有代理主机的IP段(ipv4/ipv6),我们需要提前获取这些IP段来识别哪些访问是通过Cloudflare发送到服务器的。

    Cloudflare提供的获取方式如下:

    • IPv4地址段: https://www.cloudflare.com/ips-v4
    • IPv6地址段: https://www.cloudflare.com/ips-v4

    比如,我们使用如下命令获取ipv4段信息:

    $ curl https://www.cloudflare.com/ips-v4
    173.245.48.0/20
    103.21.244.0/22
    ....
    131.0.72.0/22
    
    • 1
    • 2
    • 3
    • 4
    • 5

    如果需要IPv6地址段,方法同理的。

    第二步:生成nginx配置信息

    nginx配置文件支持模块化导入,因此我们只需要单独将 Cloudflare配置内容生成一个配置文件即可,不需要额外修改nginx的其他配置文件。

    Nginx对应的配置格式如下:

    $ cat /etc/nginx/conf.d/cloudflare.conf
    
    set_real_ip_from 173.245.48.0/20;
    set_real_ip_from 103.21.244.0/22;
    set_real_ip_from 103.22.200.0/22;
    set_real_ip_from 103.31.4.0/22;
    ...
    set_real_ip_from 2405:b500::/32;
    set_real_ip_from 2405:8100::/32;
    set_real_ip_from 2a06:98c0::/29;
    set_real_ip_from 2c0f:f248::/32;
    
    real_ip_header X-Forwarded-For;
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14

    因此,我们按照上面格式生成对应配置即可, 最后获取真实IP地址的是最后一行real_ip_header,可以有如下两种方法:

    # real_ip_header CF-Connecting-IP;
    real_ip_header X-Forwarded-For;
    
    • 1
    • 2

    这里的X-Forwarded-For格式是这样的:

    X-Forwarded-For: client1, proxy1, proxy2
    
    • 1

    其中的client1就是真实的访问者IP地址,而proxy1proxy2都是中间经过的代理转发节点,这里有个匿名代理的知识点,简单说一下:

    • 普通代理: 不匿名,可以通过X-Forwarded-For字段获取真实IP地址
    • 高匿名代理: X-Forwarded-For 只包含代理服务器地址,没有客户端地址,这样就无法得知真实的访问者IP地址了。

    第三步:脚本自动化生成配置

    接下来,我们编写脚本,自动化这个配置文件生成的过程,因为Cloudflare的IP段是定期更新的,我们也要定期更新这个配置。

    #!/usr/bin/env bash
    # 功能: 生成 cloudflare 代理IP列表,用户配置nginx获取客户端真实IP地址
    
    cf_ipv4="https://www.cloudflare.com/ips-v4"
    cf_ipv6="https://www.cloudflare.com/ips-v6"
    mod_cffile="/etc/nginx/conf.d/cloudflare.conf"
    
    get_cfipinfo() {
        # 生成nginx配置记录格式: set_real_ip_from 103.21.244.0/22;
        curl $cf_ipv4 2>/dev/null | grep -v '#' | grep -v '^$' | sed 's/^/set_real_ip_from /g;s/$/;/g'
        curl $cf_ipv6 2>/dev/null | grep -v '#' | grep -v '^$' | sed 's/^/set_real_ip_from /g;s/$/;/g'
        
        echo
        # echo "real_ip_header CF-Connecting-IP;"
        echo "real_ip_header X-Forwarded-For;"
        echo
    }
    
    get_cfipinfo  | tee $mod_cffile
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20

    脚本有了,定期执行就靠cron调度来帮助了。

    下面是一个调度示例(每月15日 0点更新一次):

    # 更新 CF 代理IP段并重新加载nginx服务(nginx -t 检测配置正确了才会重新加载)
    0 0 15 * * sh /path/to/you-script.sh >/dev/null 2>&1 &&  nginx -t && systemctl reload nginx
    
    
    • 1
    • 2
    • 3

    关于nginx配置

    毕竟每个人的nginx服务安装方法、编译选项不可能一样,想要获取真实IP需要http-real-ip功能支持,两种选择:获取支持此功能的安装包或者自己编译源代码获取此功能支持。

    问题一:如何判断自己的nginx服务支持http-real-ip功能?

    执行下面命令来判断:

    $ nginx -V 2>&1 | grep -i http_realip_module
    configure arguments: --prefix=/usr/ ... 
    --without-poll_module ... --with-http_v2_module `--with-http_realip_module` --with-http_addition_module ...
    
    
    • 1
    • 2
    • 3
    • 4

    检测编译选项中携带了--with-http_realip_module就说明可以获取真实客户端IP了。

    问题二:生成了 cloudflare.conf后nginx.conf如何自动识别并生效?

    可以在nginx.conf中的http配置块儿中找到类似下面的配置:

    http {
    
        ....
    	#gzip  on;
    
        include conf.d/*.conf;
    
    
        # vhost servers
        include vhosts.d/*.conf;
    
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13

    其中, include conf.d/*.conf;这行会自动导入conf.d(提示:你的nginx可能使用其他目录)目录下的*.conf结尾的文件配置,这些配置会适用于当前nginx运行的所有的Web服务。

    最后

    上面介绍的文字比较多,目的为了让大家理解,难免有些赘述,已经掌握的朋友忽略即可。

  • 相关阅读:
    猿创征文丨学C/C++的进来看看---这三种经典数组笔试题你都会做吗?
    vue三个点…运算符时报错 Syntax Error: Unexpected token
    [JavaScript]递归,深浅拷贝,处理this指向,异常处理
    C数据结构:树和森林存储方式与遍历方式
    服务器中jdk、mysql的安装配置,以及linux一些使用的操作
    Git 02: git管理码云代码仓库 + IDEA集成使用git
    stack, queue 模拟与用法
    R语言python时间序列处理
    探索人工智能领域——30个名词详解
    有意识的神经网络之对比网络层和后意识层 加入em
  • 原文地址:https://blog.csdn.net/dragonballs/article/details/126345175