爬虫的技术问题

一、JS加密如何突破

  1. 熟练掌握 Chrome 的开发者工具的各个功能,Elements,Network,Source
  2. 认真观察,善于思考,Network 查看加载流程,找可疑的 xhr 请求,设置 xhr 断点,通过 CallStack 回溯 js 执行过程,边回溯便查看上下文代码。能读懂 js 代码,知道 js 的相关知识,比如 js 里面的 window 变量
  3. 以上是通过 debug js 找到 js 加密解密的代码,然后通过 Python 重新实现,这个过程很长,可能消耗你几天的时间,一旦网站改变一下 js 算法你的 Python 实现就不能使用了。
  4. 用 selenium 可简单突破,并且网站随便改都无所谓。唯一遗憾的是,selenium 的运行效率较差。但是,作为一个能用 js 加密来保护数据的网站,单价的运行效率应该足以满足网站的访问频率限制。这时候,更多的思考是如何增加资源(IP、账号)来提高抓取效率

二、多线程、协程、多进程的选择

  1. 爬虫是 IO 密集型任务,大部分时间花在网络访问上,所以多进程不适合网络爬虫,而多线程、异步 IO 协程更适合,而异步 IO 是最适合的,它相比多线程,协程间的切换代价更小,我们提倡使用异步 IO 而非多线程。异步 IO 的模块主要是:aysncio,aiohttp,aiomysql等
  2. 网页爬下来后从中提取想要的数据是 CPU 密集型的,这时候可以用多线程并步提取。
  3. 我们推荐的爬虫策略是,爬虫只管爬,把爬下来的 html 保存起来,存到数据库。然后单独写提取数据的提取器。好处是,提取不影响爬取,爬的效率更高,并且提取程序可以随时修改,有新的提取需求时不需要重新抓取。比如,最初写爬虫时只想抓取网页中的两项数据,运行一段时间后,发现另外 3 项数据也很有用,如果保存了 html,只需要改改提取器重新跑一遍就好了。

三、如果想要保留加粗或者图片原始位置,只能通过挖掘规律再写正则表达式来针对性处理吗?

网页数据提取的主要两种方法:正则表达式,xpath。通过 xpath 可以获取某个 html 标签节点。比如,一篇 blog 网页,它的主体内容都在某个标签里面,可能是某个 div。用 xpath 得到这个 div,转换为 html,就是包含了格式及其图片的部分,你保存这段 html 代码而纯文本就好了。

四、爬虫的增量爬取、断点续爬、去重等分享一下你的经验

  1. 通过网址池的概念去管理所有的 url
  2. 增量爬取就是补充下载已经下载过的,让网址池记住那些已经下载过的 url
  3. 断点续爬,就是场次还没有爬取的 url 这次接着爬,还是让网址池记住那些还没被爬取的 url
  4. 爬虫的去重,让网址池记录 url 的状态以避免重复爬取。

五、爬虫的部署问题,在公司是不是分布式爬虫系统比较多涉及部署问题

爬虫的部署,不一定是分布式的。大规模的爬虫,突破了目的网站限制的爬虫才会涉及到分布式,分布式的好处是抓取速度提高,但是管理会比较复杂。

六、网页的自动解析

这个话题就包含很多子任务了:怎么自动抽取文章的内容,如何处理各种各样的时间格式,怎样处理翻页

  1. 文章内容的提取,基本的是每种网页建立一个提取模板(正则表达式),好处是提取精准,坏处是工作量大,一旦稍微改版就失败。通过算法建立单一提取程序,基本上都可以提取,但是可能会有写杂质,比如文末的相关阅读。好处是,一劳永逸,不受改版限制
  2. 时间的提取,除了正则表达式之外似乎没有特别有效的方法。
  3. 翻页的话,如果只是抓取,如何在提取内容时要把多页内容合并成一个网页,那就需要特别处理。

七、爬新闻类的网站时,如何做好同一个新闻,各网站相互转载,爬取时文本去重

比较著名的算法是,Google 的 simhash,但具体实践中比较复杂。网传百度的做法是把文章的最长一句话(或多句)做 hash,这个 hash 值就是文章唯一性代表(指纹),这个方法准确率很高,但是召回率比较低,一旦这最长的几句话改一个字就不能召回;我改进了该方法,对 n 句 最长的话分别做 hash,一个文章由 n 个指纹(例如人的是个指头指纹都不一样)确定唯一性。准确率和召回率都还不错。

八、异步爬虫的涉及

  1. 一个好的 url 管理策略,参考这两篇文章:https://www.yuanrenxue.com/crawler/news-crawler-urlpool.html
    网址池是一个“生产者-消费者”模型,爬虫从中取出 url 去下载,下载的 html 中提取新的 url 放入池中,告诉 url 池刚取出的 url 是否下载成功;再从池中取出 url 进行 下载 url 是否下载成功。url 池是核心部件,它记录 url 的不同状态:
    (a) 下载成功
    (b) 下载失败 n 次
    (c) 正在下载
    每次往池子添加 url 时都要检查 url 在池中的状态,避免重复下载
  2. 一个好的异步协程管理策略,可以参考下面这个链接https://www.yuanrenxue.com/crawler/news-crawler-asyncio.html
    每次从 urlpool 中提取 n 个 url,生成 n 个异步下载的协程,通过一个变量记录协程的个数(也就是正在下载网页的个数)

爬虫的泛问题

一、爬虫的法律问题

  1. 最好不要去抓涉及到个人隐私的信息,比如个人的电话、地址、联系方式和个人征信等,还有就是涉及到一些版权的信息,比如图片。这些抓了之后,你用于商业之后就会犯法,或者拿这些数据做一些违法的行为都会被抓的。
  2. 去了解下刑法的 285 条 和 286 条,这两个都是和破坏计算机有关的。比如逆行,抓app的话,就需要反编译,这个一旦被举证,肯定会坐牢。没有抓你是没有举报你而已。
  3. 私下售卖数据也需要小心,因为别人买了你的数据,你不知道别人是拿来干什么的,用来别的非法的用途的都不要去卖给他。
  4. 最近国家也新出了一个爬虫规定,可以看看。

二、初学爬虫入门

  1. 学 requests 库,并会熟用,就可以说是简单地入门到爬虫了
  2. 在爬取的过程中你就会想到要解析,就会去查看有哪些解析方法,就有正则和 xpath,你就会又学这两个东西,在学习的过程中你就不会感觉到很枯燥。
  3. 把数据解析出来了,就需要存储数据,可以直接写到文本,可以写到数据库,这就会又去学习数据库相关知识,最后就能存储数据到数据库了。
  4. 最后你是能爬能解析能存了,但发现爬取的速度太慢了,有时候还会遇到错误,这是遇到反爬,你就又要去学习和反爬相关的知识,或者使用别的来提高爬取速度。
  5. 就是从一点一点地去做,在做的过程中,遇到问题了再来去学习,这样的话,你的收获感是最大的,而且你对他的印象也是最深刻的。

三、爬虫的后续发展路径

  1. 往爬虫高级发展,就是抓取过市面上 80% 的 app和网站,对每一个 app 或者网站都懂它的反爬,都知道相应的爬取策略,都有自己的方法论。而且能够日抓取数量到千万级以上,这种爬虫人才是很奇缺的。
  2. 可以去做自由职业,可以选择接外包,但是不要去接 一两千或者几百的,要接就只接万块以上的,要不改需求的时候就会折腾掉很多时间,得不偿失。怎么接呢?首先自己需要抓过市面上主流的大多数app,比如美团、大众点评,京东、淘宝、脉脉等,这些你都抓过,都已经把程序给写好了的,然后有人找你的时候就可以直接给数据给他看就可以交易了。
  3. 被动收入,做数据抽取和数据整合。数据抽取就是在一堆凌乱的数据中把需要的数据给提取出来。而数据整合就是把散放在各个不同网站上的相同类型的数据整合起来。比如:做微博的数据整合,早期没有记者这些东西实时跟踪明星的动态,但是一些路人在看见某个明星的时候就会发个照片或者视频到微博上,你就可以爬取这些数据,把某一个明星的动态整合起来凡在你的网站上,多人搜的时候就会有流量,有流量就会有收入。但是现在去做会涉及到图片版权的问题。

四、数据整合,涉及到 n 个网站的数据处理大致是什么形式的

这个没有办法完全使用技术实现,因为现阶段的自然语言处理技术还不是很好。
我自己的是通过机器来爬取网站的大量数据,然后自己再人工去筛选数据,这个需要花费大量的时间的,然后就把几个不同网页的数据自己整合成一段话之类的。

五、爬虫的简历应该如何写才不会石沉大海

  1. 简历不要写那种我会什么,会抓取什么,会什么策略,需要带上数字去描述,比如三天破解淘宝的 JS 加密,能设计出日抓千万级数据的爬虫架构,三天时间能够抓取淘宝1000网页
  2. 注意公司的招聘要求,别人上要求能抓取的网站,如果自己也能抓取的话,就必须要在简历上写出来,反正别人需要什么就尽可能多点写。
  3. 简历还需要有动词,要善于使用动词,比如说擅长、设计、主抓、什么负责人之类的。

六、爬虫进阶

  1. 抓取数据量级变大,就是往日抓千万级、过亿的数据上去抓。这个时候,你就会发现你之前用的东西都没有用了。因为之前你抓数据就一天抓个几万,觉得很容易,但需要你抓千万级的时候,这个时候再按之前那种抓法,就会发现自己的硬盘会爆,而且网络请求也会有大量的问题。
    这里就需要重新设计爬虫架构,这时就会有自己的设计理念在里面,就会涉及到任务的调度、分发,url 的存储等等,而且还需要很用心处理 http code,比如遇到 500 怎么办,遇到 400怎么办,这些都需要处理,而且还需要处理一些异常,不能让爬虫停止,考虑的东西都变多了好几倍。
  2. 在上升阶段,不需要去使用 scrapy 框架,因为很多原理自己都不懂,直接使用框架的话,就会少碰到很多细节问题,但是如果你熟悉 scrapy 框架的源代码的话,这是可以使用的,因为原理都懂了,不需要自己再造轮子了也行,不懂得话就需要自己实现一个,要不然工作三四年以后,再去应聘的话都需要会自己写一个爬虫框架,到时候什么都不会就惨了。
  3. 另一个进阶方向就是逆向, JS 逆向和 app 逆向,这些都是进阶必学的内容。
  4. 最后这两个都搞定了,就会遇到另外一些问题,比如需要考虑大规模的账号和 IP,这些也都是需要考虑的。当你拥有这两个东西的时候,就不会怕什么逆向之类的,因为都不需要了。

七、IP 代理池的抓取,app 数据的抓取

  1. IP 代理池的话,肯定是需要付钱的,一般都使用 adsl,这个成本低。或者使用付费代理,这样才可以稳定去抓取。
  2. app 抓取的话,如果不会逆向的话可以去使用一些自动化测试工具,比如网易的 arits(可能拼错了),或者 appium 都可以。这些自动化测试工具最常用就是群控,当有足够的 ip 和账号的时候,就直接使用这个就行了,不需要再花费成本去逆向破解。

八、怎样算一个好爬虫

  1. 不触犯你抓取网站的屏蔽规则就是一个好爬虫。 当你触犯了,比如抓网站的时候需要了验证码,这都是因为你触犯了别人的屏蔽规则,账号和 ip 都被监控起来了,这样子就不是一个好的爬虫。
  2. 好的爬虫就是尽量减少触犯网站的屏蔽规则,要像一个人一样正常地爬取,这样就可以减少很多爬取时需要破解的麻烦。
  3. 我现在在爬数据之前就会先测试抓取极限,比如测试下 100s 内能访问多少次,如果到了 80 次就被封了,其实你有可能在第 70 次访问的时候就开始被监控了,这个时候为了让账号活得更久,我们就应该设置 100s 内爬取 40 次,为什么是 40 次呢,因为如果网站在某一时候遭到大量的爬虫的时候,会提高对爬虫的屏蔽,比如原来让你 100s 访问 80次,他就会有可能 100s 只能访问 60次 或者更高来避免爬虫,这时候我们如果设置次数太高的话,肯定会遭殃,但是设置少于他的抓取极限一倍时就不太可能被封。
    有时候一些公司会搞爬虫暗战,就会在晚上凌晨的时候,想搞一下竞争对手,让对手的爬虫都死掉,就有可能会去高频次地去抓取,尽而让他们提高下对爬虫的屏蔽,这样子竞争对手的爬取数据就会死掉。

9. 通过爬虫赚钱的一些套路

  1. 数据提炼型,比如做知乎粉丝、点赞数等排行榜,他是通过让别人关注公众号来回复知乎 id 返回 他是 大v 、小v 等等这些信息,这样子可以获得一些精准粉丝,以后就可以做流量生意。我们还可以去做抖音、微博、网易云之类的排行耪。
  2. 数据抽取型,通过爬取特定的数据来展示给特定的人群。比如前面所说的爬取微博上一些明星的动态,这些动态不是明星自己发的,而是粉丝在看见明星的时候发在微博上的,然后就可以爬取这些数据来展示给他们的粉丝看,流量也是很大的。
  3. 数据结构化,机构化一些没有版权的东西,比如公开的商标,专利等等。

10. 自己学习过程中的一些经验

  1. 主要就是两个,第一,要沉下心来,第二,要傻瓜化,就是没有那种讨巧的方法
  2. 工作的前三年需要将大部分的时间投入到工作上,投入到学习上,需要多学。还有傻瓜化,就是有些程序看不懂,就一行一行抄下来,再不懂,就一行行去打断点,就慢慢来。
  3. 编程的基础是绝对重要的,编程基础决定你编程的质量,基础不好,写的代码就有可能会有很多 bug。需要学习数据结构
  4. 英文,英文这个很重要,因为很多文档或者先进的技术资料都是英文的,所以需要看得懂。可以每天坚持去看一篇新闻报告,把不懂得新闻单词都给查下来,直到看懂,坚持一年之后,就会觉得都很容易了。这样子就可以很轻松和国外得技术人员沟通了。

11.反爬策略

  1. 改refere,改ua,cookie,注定访问 url 的顺序,还有就是需要先访问图片才可以去访问某个 url.
  2. 如果需要更换 IP,可以去买个智能路由器,然后自己实现下它的 adsl 拔号,这样也可以更换 ip,还有因为这些 IP 都是民用的,被封的概率也少一点。
  3. 改 refer,比如将它改成 百度,因为有些网站如果是直接进去的话,是需要登陆的,但是如果是先从百度搜索,再点击结果进去的,就不需要登陆,这是网站为了得到流量而做的做法,所以改了这个可以避免一些网站登陆。
  4. 改 cdn,还是改 dns,这个还是不太懂,
  5. 查看 robot 协议,有的网站会将整个网站的 html 网页都放在 robot 协议上,这样子我们直接访问这个,就可以节省很多请求,比如一些翻页反列表之类的。