参考链接:阮一峰日志Nginx 限制某一ip的访问频率

在帮同事做一个小程序后端项目,因为有些许的流量,或者其他种种原因,被别人发起了 DDOS,所以想着把处理过程记录下来。

DDOS 是什么

首先还是先介绍一下 DDOS 吧,在维基百科中这样介绍:拒绝服务攻击(denial-of-service attack)简称 DDOS,是网络攻击的其中一种方法,其目的就是耗尽服务资源,让正常用户无法进行正常访问服务。其攻击方式有:带宽消耗型、资源耗尽型,都是消耗你的资源。 说白了就是攻击方不想让其他用户正常访问你的服务,降低你的流量。

带宽扩容

在一开始我还没有意识到对方对我的服务器发起了 DDOS ,因为那段时间的流量很多,对我的服务器(1G 1核 带宽1M)来说可以算是非常大了,那段时间经常带宽占满,我以为是流量大造成的,还升级了带宽进行应对这样的流量(年轻呀)。我用的是阿里云的服务器,在控制台看到流量走势,基本经常飙满,以后要长个心眼,要根据具体流量以及流量的大量涌入的时间来判断是否被恶意攻击。

因为特殊情况,把服务部署在我服务器上,后来同事把服务器准备好后,我就想着把服务迁过去了,不想我服务器配置过低,拖累别人的服务政策使用。

HTTP 拦截

把服务迁移过去后,还是有大量的流量涌入,当时就想着被恶意攻击了,然后就去看了访问日志,果然,发现排前几名的访问次数达到数十万甚至更多,可以通过以下命令进行查看 Nginx 的访问日志

1
awk '{print $1}' log file path | sort | uniq -c | sort -nr -k1 | head -n 10

然后把前几名的 ip 通过 iptables 进行限制,本着宁可误封一个,也不愿意放过一个恶意用户的态度,把前十名的全封了,过几分钟后观察控制台的流量走势,流量马上就降下去了。这也验证了我的想法,被人恶意攻击了。可以使用以下命令通过 iptables 对某一 ip 进行封禁。

1
iptables -I INPUT -s *.*.*.* -j DROP

后来他们又换了很多 ip 进行 DDOS,所以以上的方法还是不行,如果一个一个的封,那会很费力,还费时。我看了下 Nginx 的访问机制,发现可以通过 Nginx 的访问机制进行限制 ip 的访问频率。

nginx.conf 中加入以下配置

1
limit_req_zone $binary_remote_addr zone=one:10m rate=2r/s;

定义一个 one 的 limit_req_zone 用来存储 session,后面的 10M 是使用的内存大小,以 $binary_remote_addr 为 key,每秒的请求数为 2 的访问频率进行访问限制,这样不会影响正常的用户使用,也会限制恶意用户的大量请求。

site.conf site 配置文件下加入以下配置

1
limit_req zone=one burst=5;

设置rate=2r/s每秒请求数为2个,漏桶数burst为5个,brust的意思就是,如果第1秒、2,3,4秒请求为2个,第5秒的请求为7个是被允许的,可以理解为2+5,如果超过限制,服务器会返回 503 。从配置完 Nginx 到现在还是没有再出现过被 DDOS 的情况。

对服务进行备份

可以给出一个静态页面,不会让用户觉得服务挂了,可以告诉用户服务正在维护,啥啥的。