MarkAll 导入豆瓣数据 —— Node.js 写爬虫

  1. 前言
  2. 过程
    1. 问题一. 请求
    2. 问题二. 异步
    3. 问题三. 写入
    4. 问题四.
  3. 结尾

前言

markAll ——想做个本地标记应用

https://github.com/hqweay/MarkAll/releases/tag/0.0.2

虽然之前用 Python 写过一个简单的爬虫,但是因为我想把爬数据和导入数据这两个步骤稍微整合一下,而由于 py 依赖它的运行环境,所以整合起来比较麻烦——要么在项目里带上 Python 运行环境、要么要求使用者本地有运行环境,感觉不好做。

由于 Electron 基于 Node.js,就冒出了用 Node.js 来重写一下爬虫这个思路。

最后效果达到了,可以把豆瓣用户看过的电影导入进来。

至于想看,以及书籍标记之类的,因为它们在豆瓣网页里的结构差不多,要做的话只需要稍微改一下获取节点应该就阔以了,便没继续做。

过程

没想象中简单,因为「js 天生异步」。这种特性一遇到爬虫这种执行步骤有严格先后顺序(同步执行)的程序,就很麻烦。

从整体来看,至少有「获取数据」、「存入数据」这样两个模块。而存取数据肯定必须放在获取数据之后。

由于我半桶水都不到,之前没专门了解过,只是有了需求就搜索解决方案——大概率只找到一个入门方案,自己还要想办法做到实现自己需求。花费了不少功夫。

看得这篇文章 : 【NodeJS】爬虫之cheerio抓取网页数据

文章中主要用到三个模块。

express、superagent、cheerio。

express 用于提供一个服务器环境,electron 已经有了,所以我这儿不用它。

superagent 用于发起网络请求。

cheerio 用于解析网页。

思路很清晰:superagent 发起请求,cheerio 解析返回的网页,获取网页里的元素并存下来。

不过我的需求比这稍微复杂一点…

文档 :

[译] SuperAgent中文使用文档

通读cheerio API

问题一. 请求

爬取的数据很有多页,所以需要循环调用 superagent 发起请求。

首先,怎么判断爬取到最后一页了呢?

访问完所有页面后,还会尝试获取一个不存在的页面,只要在获取这个不存在的页面时做判断然后跳出循环就好啦!

也没这么简单…

具体地光说也解释不清楚,晓得有这么个问题就行了。

其次,js 中 while 是异步的。

再其次,js 没有 sleep() 这类方法。(我爬了几次就被 302 了

后来使用了 setInternal(),循环定时调用。

问题二. 异步

强制同步执行,可以使用 Promise、 async…

async 底层还是使用的 Promise。

具体我没系统往下了解,大概知道这么个就行了。虽然最后效果达到了,其实我并不是很清楚逻辑…

问题三. 写入

以 json 格式写入本地文件。

又遇到问题:是一条数据一条数据地写入,还是把获取的数据存入一个数组,等获取完了一并写入呢?

最后选择获取完后把数组写入本地文件,因为使用的读写数据的模块 fs-extra 有把数据直接以 json 格式写入本地的 api,如果一条数据一条数据地写入,就需要自己自己以字符串的形式写入,并自己控制格式…太麻烦了。真的,麻烦…

问题四.

我因为一开始想得太过于沙雕,一心解耦。这里把数据爬下来后,另一个模块又要读取这里的数据,把数据加载到 MarkAll 上…

这两个步骤间又需要同步执行…

而其实每个步骤内部也涉及一些又先后顺序的操作…

太麻烦了…我晕。

结尾

其次没啥东西了,这篇文纯属吐吐槽…

文章标题:MarkAll 导入豆瓣数据 —— Node.js 写爬虫

文章字数:983

本文作者:禾七

发布时间:2019-06-17, 00:00:00

最后更新:2020-01-01, 20:34:21

原始链接:https://leay.net/2019/06/17/nodejs/

版权声明: "署名-非商用-相同方式共享 4.0" 转载请保留原文链接及作者。

目录