爬虫(Spider),反爬虫(Anti-Spider),反反爬虫(Anti-Anti-Spider)

爬虫(Spider),反爬虫(Anti-Spider),反反爬虫(Anti-Anti-Spider),这之间的斗争恢宏壮阔...

Day 1
小莫想要某站上所有的电影,写了标准的爬虫(基于HttpClient库),不断地遍历某站的电影列表页面,根据 Html 分析电影名字存进自己的数据库。
这个站点的运维小黎发现某个时间段请求量陡增,分析日志发现都是 IP(1.1.1.1)这个用户,并且 useragent 还是 JavaClient1.6 ,基于这两点判断非人类后直接在Nginx 服务器上封杀。

Day 2
小莫电影只爬了一半,于是也针对性的变换了下策略:1. useragent 模仿百度("Baiduspider..."),2. IP每爬半个小时就换一个IP代理。
小黎也发现了对应的变化,于是在 Nginx 上设置了一个频率限制,每分钟超过120次请求的再屏蔽IP。 同时考虑到百度家的爬虫有可能会被误伤,想想市场部门每月几十万的投放,于是写了个脚本,通过 hostname 检查下这个 ip 是不是真的百度家的,对这些 ip 设置一个白名单。

Day 3
小莫发现了新的限制后,想着我也不急着要这些数据,留给服务器慢慢爬吧,于是修改了代码,随机1-3秒爬一次,爬10次休息10秒,每天只在8-12,18-20点爬,隔几天还休息一下。
小黎看着新的日志头都大了,再设定规则不小心会误伤真实用户,于是准备换了一个思路,当3个小时的总请求超过50次的时候弹出一个验证码弹框,没有准确正确输入的话就把 IP 记录进黑名单。

Day 4
小莫看到验证码有些傻脸了,不过也不是没有办法,先去学习了图像识别(关键词 PIL,tesseract),再对验证码进行了二值化,分词,模式训练之后,识别了小黎的验证码(关于验证码,验证码的识别,验证码的反识别也是一个恢弘壮丽的斗争史,这里先不展开....),之后爬虫又跑了起来。
小黎是个不折不挠的好同学,看到验证码被攻破后,和开发同学商量了变化下开发模式,数据并不再直接渲染,而是由前端同学异步获取,并且通过 js 的加密库生成动态的 token,同时加密库再进行混淆(比较重要的步骤的确有网站这样做,参见微博的登陆流程)。

Day5
混淆过的加密库就没有办法了么?当然不是,可以慢慢调试,找到加密原理,不过小莫不准备用这么耗时耗力的方法,他放弃了基于 HttpClient的爬虫,选择了内置浏览器引擎的爬虫(关键词:PhantomJS,Selenium),在浏览器引擎中js 加密脚本算出了正确的结果,又一次拿到了对方的数据。
小黎:.....

爬虫与发爬虫的斗争还在继续。
不过实际应用时候,一般大家做到根据 IP 限制频次就结束了,除非很核心的数据,不会再进行更多的验证,毕竟工程的问题一半是成本的问题。

至于高效部分,一些 Tips:
1.尽量减少请求次数,能抓列表页就不抓详情页
2.不要只看 Web 网站,还有 App 和 H5,他们的反爬虫措施一般比较少
3.如果真的对性能要求很高,可以考虑多线程(一些成熟的框架如 scrapy都已支持),甚至分布式

时间: 2024-10-01 05:23:08

爬虫(Spider),反爬虫(Anti-Spider),反反爬虫(Anti-Anti-Spider)的相关文章

反调试手法之CreateProcess反调试

反调试手法之CreateProcess反调试 在学习Win32 创建进程的时候.我们发现了有一个进程信息结构体. STARTUPINFO. 这个结构体可以实现反调试. 具体CreateProcess可以参考上一篇博客.:  https://www.cnblogs.com/iBinary/p/9571577.html 一丶实现反调试需要的东西. 假设我们要实现反调试. 那么我们需要一个API GetStartupInfo (STARTUPINFO) 使用此API可以在进程启动的时候获取启动信息结构

一个咸鱼的python爬虫之路(五):scrapy 爬虫框架

介绍一下scrapy 爬虫框架 安装方法 pip install scrapy 就可以实现安装了.我自己用anaconda 命令为conda install scrapy. 1 Engine从Spider处获得爬取请求(Request)2Engine将爬取请求转发给Scheduler,用于调度 3 Engine从Scheduler处获得下一个要爬取的请求4 Engine将爬取请求通过中间件发送给Downloader5 爬取网页后,Downloader形成响应(Response)通过中间件发给En

第三百四十一节,Python分布式爬虫打造搜索引擎Scrapy精讲—编写spiders爬虫文件循环抓取内容—

第三百四十一节,Python分布式爬虫打造搜索引擎Scrapy精讲-编写spiders爬虫文件循环抓取内容- 编写spiders爬虫文件循环抓取内容 Request()方法,将指定的url地址添加到下载器下载页面,两个必须参数, 参数: url='url' callback=页面处理函数 使用时需要yield Request() parse.urljoin()方法,是urllib库下的方法,是自动url拼接,如果第二个参数的url地址是相对路径会自动与第一个参数拼接 # -*- coding:

学习《从零开始学Python网络爬虫》PDF+源代码+《精通Scrapy网络爬虫》PDF

学习网络爬虫,基于python3处理数据,推荐学习<从零开始学Python网络爬虫>和<精通Scrapy网络爬虫>. <从零开始学Python网络爬虫>是基于Python 3的图书,代码挺多,如果是想快速实现功能,这本书是一个蛮好的选择. <精通Scrapy网络爬虫>基于Python3,深入系统地介绍了Python流行框架Scrapy的相关技术及使用技巧. 学习参考: <从零开始学Python网络爬虫>PDF,279页,带目录,文字可复制: 配套

java爬虫系列第五讲-如何使用代理防止爬虫被屏蔽?

本文内容 1.分析一下爬虫存在的问题及解决方案 2.webmagic中代理的使用 3.目前市面上一些比较好用的代理服务器 存在的问题 我们在使用爬虫过程中,大多都会遇到这样的问题:突然某一天爬虫爬不到内容了,目标网站直接返回404或者其他错误信息,这说明我们的爬虫被目标网站给屏蔽了. 爬虫被屏蔽的原因 1.爬虫大量请求对对目标服务器造成了压力 2.爬虫采集目标网站有价值的内容到处传播,对目标网站造成了不良影响 出于以上原因,正常情况下目标网站会把爬虫屏蔽掉,这样直接导致我们开发的爬虫无法采集正确

第三百五十六节,Python分布式爬虫打造搜索引擎Scrapy精讲—scrapy分布式爬虫要点

第三百五十六节,Python分布式爬虫打造搜索引擎Scrapy精讲-scrapy分布式爬虫要点 1.分布式爬虫原理 2.分布式爬虫优点 3.分布式爬虫需要解决的问题

零基础自学Python 3开发网络爬虫(二): 用到的数据结构简介以及爬虫Ver1.0 alpha

上一回, 我学会了 用伪代码写出爬虫的主要框架; 用Python的urllib.request库抓取指定url的页面; 用Python的urllib.parse库对普通字符串转符合url的字符串. 这一回, 开始用Python将伪代码中的所有部分实现. 由于文章的标题就是"零基础", 因此会先把用到的两种数据结构队列和集合介绍一下. 而对于"正则表达式"部分, 限于篇幅不能介绍, 但给出我比较喜欢的几个参考资料. Python的队列 在爬虫程序中, 用到了广度优先搜

【爬虫】把抓到数据存起来——爬虫绝配mongodb

[爬虫]把抓到数据存起来--爬虫绝配mongodb 视频地址 抓取数据的方法,前面的课程该讲的都已经讲了,爬取下来数据只是第一步,第二步就是要先存起来.我们最容易想到的就是存文件里喽,python写文件之前的课程也已经讲过了.存到文件里当然是可以的,但是你是否想过,每次使用都要把整个文件打开,然后读取,实在是有点不geek啊. 所以我们通常会选择存进数据库,方便写入和读取数据,并且对于大部分情况而言,python数据结构中的dict足够我们去结构化抓取的数据,那么能把两者发挥到极致的神器就是--

Android 反编译与防止被反编译

泉贸软件工作室原创.原帖地址:http://www.svch0st.com/cont.asp?id=38 Android App使用Java语言进行开发,因此十分容易就可以被反编译出近乎原始的程式码.也因为这个特性,许多人在写Android App的时候会喜欢去反编译别人写好的程式,再挪为己用,虽然很不道德,但这也是一种有效提升软体开发速度的方法.但换个角度想,如果是自己写的程式码被盗走的话,这就对自己不太有利了,所以学习如何防止自己程式码被偷也是一个很重要的课题. Android App的安装

zoj 2526 反素数 附上个人对反素数性质的证明

反素数的定义:对于任何正整数,其约数个数记为,例如,如果某个正整数满足:对任意的正整 数,都有,那么称为反素数. 从反素数的定义中可以看出两个性质: (1)一个反素数的所有质因子必然是从2开始的连续若干个质数,因为反素数是保证约数个数为的这个数尽量小 (2)同样的道理,如果,那么必有 个人理解性证明: 对(1)假设不是从2开始,那么假设n的最小素因素是k,把k换成2,2的次数仍等于k的次数,得到N,可知,N<n,并且f(n)==f(N),与n是反素数矛盾 对(2)假设ti<tj   ti,tj