最近无意中查了一下网站日志,结果发现受到了大量非法拉取、大量漏洞攻击,好家伙!为了减少这些恶意行为,打算直接屏蔽其IP(通过对日志的相应编辑,看到部分IP能重复上千次!),由于我的网站套了Cloudflare,在nginx.conf中屏蔽某一IP并不能生效(我自己用手机测试的),上网搜了一些解决办法,选一种简单有效的方法记录一下。
网站受到非法拉取文件、进行漏洞攻击,以及恶意搜索引擎蜘蛛爬虫大量访问

说到获取真实IP,我们不难想到nginx的http realip module,就是当遇到IP是设定范围内的地址时,就逆向递归获取源目标的真实IP。对于Cloudflare CDN而言,也是遵从行业标准的,即使用X-Forwarded-For header 和 CF-Connecting-IP header 。Cloudflare的真实IP地址可以从这里获取Cloudflare IP addresses,当然我们也可以查看文本格式的Cloudflare的IP段:
https://www.cloudflare.com/ips-v4
https://www.cloudflare.com/ips-v6Copy
官方建议还是要定期更新这个IP范围的,以免范围改动影响使用效果。

一、自动更新脚本

#!/bin/bash

CLOUDFLARE_FILE_PATH=/etc/nginx/cloudflare_IP.conf
SH_SAVE_PATH=/root/shfiles

echo "#Cloudflare" > $CLOUDFLARE_FILE_PATH;
echo "" >> $CLOUDFLARE_FILE_PATH;

echo "# - IPv4" >> $CLOUDFLARE_FILE_PATH;
for i in `curl https://www.cloudflare.com/ips-v4`; do
    echo "set_real_ip_from $i;" >> $CLOUDFLARE_FILE_PATH;
done

echo "" >> $CLOUDFLARE_FILE_PATH;
echo "# - IPv6" >> $CLOUDFLARE_FILE_PATH;
for i in `curl https://www.cloudflare.com/ips-v6`; do
    echo "set_real_ip_from $i;" >> $CLOUDFLARE_FILE_PATH;
done

echo "" >> $CLOUDFLARE_FILE_PATH;
echo "real_ip_header CF-Connecting-IP;" >> $CLOUDFLARE_FILE_PATH;

# 方便打印时间到日志中
echo
echo `date +"%Y-%m-%d %H:%M:%S"`

# 更新cloudflare_IP.conf后要重新启动下Nginx,使其生效
cd $SH_SAVE_PATH
nginx -t && /etc/init.d/nginx restart

exit 0

将以上脚本保存到/root/shfiles/下,并测试下。输出文件内容如下:

输出内容

#Cloudflare

# - IPv4
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 141.101.64.0/18;
set_real_ip_from 108.162.192.0/18;
set_real_ip_from 190.93.240.0/20;
set_real_ip_from 188.114.96.0/20;
set_real_ip_from 197.234.240.0/22;
set_real_ip_from 198.41.128.0/17;
set_real_ip_from 162.158.0.0/15;
set_real_ip_from 104.16.0.0/12;
set_real_ip_from 172.64.0.0/13;
set_real_ip_from 131.0.72.0/22;

# - IPv6
set_real_ip_from 2400:cb00::/32;
set_real_ip_from 2606:4700::/32;
set_real_ip_from 2803:f800::/32;
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 CF-Connecting-IP;
real_ip_recursive on;

二、选出恶意IP

将网站日志(一般是access.log)中的内容按照IP出现的次序排序,并输出到文本中:

awk '{print $1}' /www/wwwlogs/access.log |sort |uniq -c|sort -n 2>&1 | tee -a /www/wwwlogs/blockip.conf

按照下图的格式调整blockip.conf文件。
blockip.conf

三、配置nginx.conf

找到网站的nginx.conf文件,在server中插入include /path/blockip.conf;,这里/path/就是blockip.conf的绝对路径。然后再执行下

nginx -t
/etc/init.d/nginx restart

没报错的话,就用手机测试下效果(可能需要清理下浏览器缓存),如果手机浏览器界面出现403等常见HTTP错误代码则表示没问题了。注意这里不要用电脑IP测试,否则很可能会导致无法通过Xshell等工具连接到服务器。我在测试时在站点的配置文件(如eonegh.com.conf)里面也加入include /path/blockip.conf;(如果没效果,可以考虑也在站点文件的server中加入。)

四、自动执行

crontab -e
# 每月28号的凌晨1点1分时候执行一次,并将结果输入到日志中
1 1 28 * * /root/shfiles/cf_realIP_update.sh  2>&1 | tee -a /www/wwwlogs/cf_realIP_update.sh.log

五、屏蔽蜘蛛爬虫

分析日志还可以看到大量的恶意搜索引擎蜘蛛爬虫大量访问网站,其实对服务器的影响不大,但对于一些服务器资源比较紧张的站点,还是把这些访问禁止掉吧,以减少服务器消耗。

#禁垃圾蜘蛛
if ($http_user_agent ~* "CheckMarkNetwork|Synapse|Nimbostratus-Bot|Dark|scraper|LMAO|Hakai|Gemini|Wappalyzer|masscan|crawler4j|Mappy|Center|eright|aiohttp|MauiBot|Crawler|researchscan|Dispatch|AlphaBot|Census|ips-agent|NetcraftSurveyAgent|ToutiaoSpider|EasyHttp|Iframely|sysscan|fasthttp|muhstik|DeuSu|mstshash|HTTP_Request|ExtLinksBot|package|SafeDNSBot|CPython|SiteExplorer|SSH|MegaIndex|BUbiNG|CCBot|NetTrack|Digincore|aiHitBot|SurdotlyBot|null|SemrushBot|Test|Copied|ltx71|Nmap|DotBot|AdsBot|InetURL|Pcore-HTTP|PocketParser|Wotbox|newspaper|DnyzBot|redback|PiplBot|SMTBot|WinHTTP|Auto Spider 1.0|GrabNet|TurnitinBot|Go-Ahead-Got-It|Download Demon|Go!Zilla|GetWeb!|GetRight|libwww-perl|Cliqzbot|MailChimp|SMTBot|Dataprovider|XoviBot|linkdexbot|SeznamBot|Qwantify|spbot|evc-batch|zgrab|Go-http-client|FeedDemon|JikeSpider|Indy Library|Alexa Toolbar|AskTbFXTV|AhrefsBot|CrawlDaddy|CoolpadWebkit|Java|UniversalFeedParser|ApacheBench|Microsoft URL Control|Swiftbot|ZmEu|jaunty|Python-urllib|lightDeckReports Bot|YYSpider|DigExt|YisouSpider|HttpClient|MJ12bot|EasouSpider|LinkpadBot|Ezooms") {
    return 400;
    break;
}

#禁部分爬取工具
if ($http_user_agent ~* "crawl|curb|git|Wtrace|Scrapy" ) {
    return 400;
    break;
}

#UA 不全,十有八九不是正常访问,禁
if ($http_user_agent = "Mozilla") {
    return 400;
    break;
}

#UA 不全,十有八九不是正常访问,禁
if ($http_user_agent = "Mozilla/5\.0") {
    return 400;
    break;
}

#UA 不全,十有八九不是正常访问,禁
if ($http_user_agent = "Mozilla/4\.0") {
    return 400;
    break;
}

#禁IE6
if ($http_user_agent = "MSIE 6\.0") {
    return 400;
    break;
}

#禁止特殊请求方式
if ($request_method ~* "DELETE|OPTIONS" ) {
    return 400;
    break;
}

#禁特殊url,wp慎
location ~* (wp-login\.php|LICENSE|README\.md)$ {
    return 400;
    break;
}

#禁特殊url
location ~* ^/(cgi-bin|includes|plus|user|web|vendor|maccms|bitcoin|wallet|backup)/.*.(php|php5|html)$ {
    return 400;
    break;
}

#禁特殊后缀
location ~* \.(asp|aspx|htaccess|ini|sql|env|git|project|cgi)$ {
    return 400;
    break;
}

#禁压缩包
location ~* \.(tgz|bak|zip|rar|tar|gz|bz2|xz|tar.gz)$ {
    return 400;
    break;
}

#禁空 UA
if ($http_user_agent ~* ^$) {
    return 400;
    break;
}

#非 SSR 屏蔽
if ($http_user_agent ~* "python-requests" ) {
    return 400;
    break;
}

#禁特殊请求工具
if ($http_user_agent ~* "Wget|Curl" ) {
    return 400;
    break;
}

#禁特定请求方式
#if ($request_method ~* "POST|PUT" ) {
#    return 400;
#    break;
#}

复制以上内容,保存为kill_bots.conf,并在nginx.confeonegh.com.conf中的server中插入,类似于include /path/kill_bots.conf;。再执行下:

nginx -t
/etc/init.d/nginx restart

这个无法立即看到效果,等一段时间后查看access.log或者eonegh.com.log,若看到部分蜘蛛爬虫访问后返回非200的HTTP状态代码(一般是404403之类),就表示以上配置是已经生效的。
生效情况

实验环境:Ubuntu16.04,Nginx v1.18.0,Cloudflare,VPS

六、参考文件

1、CloudFlare CDN下Nginx正确获取真实IP教程 | 奶牛博客
2、GitHub - ergin/nginx-cloudflare-real-ip
3、NGINX,PHP获取Cloudflare传递的真实访客IP 配合宝塔面板防御CC攻击 防伪造IP
4、http协议的状态码——400,401,403,404,500,502,503,301,302等常见网页错误代码


本文标签:建站技巧杂烩总结安全