碰到的一个反爬场景,它吃光了对应机器的内存,导致应用服务也没法正常使用

作者: admin 分类: Scrapy 发布时间: 2020-06-23 19:35  阅读: 316 views

记起以前获取数据的时候碰到过一个情况,用光了机器的内存,导致应用服务都无法正常使用,所以这里简单记录一下。

场景描述


做一些数据的分析,所以要抓点数据进行测试。于是分析目标网站之后,进行简单的编码开始抓取。

抓取规则是获取n页列表的数据,然后解析列表中每个页面的数据,进行入库操作。大概不到100页,每页10条数据。总共小于1000个页面。

这里使用的是JAVA语言的webmagic框架。原理是:

下载页面 >>> 解析html >>> 入库

我这里的目标网站是js动态加载的,无法直接获取html,所以使用了selenium框架模拟用户操作进行抓取。

整个过程就分成了两个阶段,先是解析页面元素存到内存中,然后一次性提交到数据库中。

使用的是阿里云8G内存的机器。1000个页面肯定不在话下。所以编写好就发布上去了运行了。

问题暴露


开始运行的几天是没有问题的。一切正常,数据可以拿到做测试分析。

过了一两周,先是对应服务器收到报警,然后是服务器上的应用服务无法正常访问。
– ssh登录卡顿,最终登录上去后。
– 发现爬虫日志好像进入了一个死循环状态(从列表页获取了大量url进行抓取,无穷无尽)。
– 查看内存,发现已用尽。
– kill掉爬虫进程后,应用服务正常运行。

问题分析


前期测试正常,应该是没有触发反爬规则。后期的运行规则应该比较规律,所以触发了。

触发的点应该是进入了一个反爬页面,导致完全按照目标网站设定的规则执行。最终吃光内存。

问题设计


最有可能出现的地方,应该是分页栏这里。看如下代码(简易模仿)


<html> <head> <meta charset="utf-8"></head> <style> li { float:left; } td { text-align: center; } </style> <body> <table cellpadding="0" cellspacing="0" border="0" width="500"> <tr> <td >列表第一条数据</td></tr> <tr> <td >....</td></tr> <tr> <td >列表第n条数据</td></tr> <tr> <td ><hr></td></tr> <!-- 没有做处理的分页栏 --> <tr> <td> <ul> <li>第</li> <li><a href="https://www.deathearth.com/page/1">[1]</a></li> <li><a href="https://www.deathearth.com/page/2">[2]</a></li> <li><a href="https://www.deathearth.com/page/3">[3]</a></li> <li><a href="https://www.deathearth.com/page/4">[4]</a></li> <li><a href="https://www.deathearth.com/page/5">[5]</a></li> <li>页</li> </ul> </td> </tr> <tr> <td ><hr></td></tr> <!-- 做处理的分页栏 --> <tr> <td> <ul> <li>第</li> <li><a href="https://www.deathearth.com/page/1">[1]</a></li> <li><a href="https://www.deathearth.com/page/2">[2]</a></li> <li><a href="https://www.deathearth.com/page/3">[3]</a></li> <li><a href="https://www.deathearth.com/page/4">[4]</a></li> <li style="display:none;"><a href="death.page"></a></li> <li><a href="https://www.deathearth.com/page/5">[5]</a></li> <li>页</li> </ul> </td> </tr> </table> </body> </html>

界面如下:
效果界面

可以看到,两种分页栏的写法对于用户来说是没有任何影响的。但是对于程序来说差别就大了。如果没有判断好的话,可能就进入了death.page页面了。

这里应该可以有多种写法,因为可以用多种标签、样式来达到这样的目的。

问题触发


只要能看懂上面的代码,就应该知道怎么触发了。

  • 在分页栏随机出现
  • 判定可能是爬虫后,释放出这种代码

如果假设爬虫进入到 death.page路径后,也可以做多种的处理

  • 一次性返回大量的url(和正常页面html规则一致,但是数据为无效数据)。
  • 在该无效页面的分页栏做处理。页数在一个阈值内出现,让爬虫机器难以察觉是否为有效链接,每页的数据都是无效数据。

(注:这里应该注意的是,返回的html数据要和正常数据没有太大差别,具体数据可以做假。主要是迷惑爬虫,让它以为爬到了有效数据,造成混淆)

无数的假url,假数据慢慢的消耗爬虫服务器的资源。而且是逐渐暴露出来的。对于一些没有过多关注、有做监控的服务器来说,可能一些人就简单的重启一下继续用了吧。

防止

  • 可能有些网站是想搞死过来的爬虫服务器吧,也许目标网站放出这种代码是无差别对待的。这样是就要对html的解析做精确化判断。
- 什么标签是符合条件的,
- 什么样式是有危险的,
- 什么样的url规则可能是异常的,
- 而且要对异常产生的地方做记录,做排查,
- 对一些数据做临界值的判断。

可能有的很难发现,有的网站做的隐藏特别的好。所以,还是考察的一个细心度。代码本身是简单的,就看你观察的仔细不仔细了。


   原创文章,转载请标明本文链接: 碰到的一个反爬场景,它吃光了对应机器的内存,导致应用服务也没法正常使用

如果觉得我的文章对您有用,请随意打赏。您的支持将鼓励我继续创作!

发表评论

电子邮件地址不会被公开。 必填项已用*标注