We are going to start coding!!
这个爬虫的想法很简单,对於每个 Block
,我们从第一个 Page
开始爬,直到最後一个。
对,就酱。
在这里,我们只需要处理一个问题:如何判定最後一页到了没?
我们的方法是:用「视觉」上的差异决定,因为网站本来就是做给人看的,所以爬虫最好也依人的「视角」去爬。
当你在看铁人赛文章列表时,从哪里可以看出这一页是不是最後一页?
没错,就是下面这条:
在这条页数条上,有两项能拿来当指标的东西:「当前页面标示」及「下一页按钮状态」。
在这里,我们选择以「当前页面标示」作为判定已经是最後一页的指标。
当我们在最後一页时,「当前页面标示」是没有下一项的:
好了,想法的部分大概都结束了,接下来来写程序吧!
相信各位都装了 Node.js 了吧?
现在让我们建立一个专案的资料夹,取你喜欢的名称即可,我自己取 iT_Crawler
。
然後至该资料夹内执行:
npm init -y
它就会自动建立好这个档案了:
接着安装需要的 Packages:
npm i node-fetch@2 jsdom
我们使用 node-fetch
来发送请求,接着用 jsdom
来解析。
使用 node-fetch@2
的原因是因为 node-fetch@3
只支援 esm,要用还得改 package.json
。
然後我们建立 index.js:
专案建立完成!
程序都写在 index.js 里喔。
先引入我们需要的 Packages,等等就可以在程序中用了。
const fs = require("fs");
const fetch = require("node-fetch");
const { JSDOM } = require("jsdom");
疑?我们刚刚没有安装 fs
这个 Package 啊,为什麽可以引用?
因为 fs
是 Node.js 内建的 Package,用来操作档案系统。
async function main() {
// 纪录程序开始时间
const START_TIME = new Date();
// 定义 iThelp 铁人赛网址及 Block 名称
const baseURL = "https://ithelp.ithome.com.tw/2021ironman/";
const types = ["contest", "self"];
// 爬取资料
const results = await Promise.all(types.map((type) => crawler(baseURL + type)));
// 整理资料,降维及排序
const data = results.reduce((a, b) => a.concat(b), []);
data.sort((a, b) => b.view - a.view || b.date[1] - a.date[1] || b.date[2] - a.date[2]);
// 储存资料
saveData(data);
// 纪录程序结束时间
const END_TIME = new Date();
// 计算程序执行时间
console.log(`Crawled ${data.length} Articles in ${((END_TIME - START_TIME) / 1000).toFixed(2)}s`);
}
之後执行时,我们的程序从 main 开始执行。
你可能会觉得奇怪, JavaScript 不需要定义 main 函式啊?
没错,但因为我们会用到 await
所以为了避免在 Top Level 用发生问题,我们就把主程序也写成一个函式 main,然後再执行它。
我们希望 main 会有几个功能:
相关程序码就如上方所示,程序码也几乎逐行用注解标示功能了,应该非常明了。
接着,我们只要再写 crawler
函式及 saveData
函式就好了。
就期待明天吧!
以 9/22 20:00 ~ 9/23 20:00 文章观看数增加值排名
+845
Day 1 无限手套 AWS 版:掌控一切的 5 + 1 云端必学主题
+678
Day 2 AWS 是什麽?又为何企业这麽需要 AWS 人才?
+668
Day 3 云端四大平台比较:AWS . GCP . Azure . Alibaba
+625
Day 4 网路宝石:AWS VPC Region/AZ vs VPC/Subnet 关系介绍
+619
Day 5 网路宝石:AWS VPC 架构 Routes & Security (上)
+606
Day 7 网路宝石:【Lab】VPC外网 Public Subnet to the Internet (IGW) (上)
+604
Day 6 网路宝石:AWS VPC 架构 Routes & Security (下)
+570
Day 8 网路宝石:【Lab】VPC外网 Public Subnet to the Internet (IGW) (下)
+569
Day 18 储存宝石:【Lab】S3 储存类别 & 生命周期管理 (下)
+568
Day 9 运算宝石:EC2 重点架构
今天中午 iThelp 被炸了(?) 所以没有 12:00 的资料 QQ,只好用 20:00 来代替。
<<: 【程序】论 Code Review 转生成恶役菜鸟工程师避免 Bad End 的 30 件事 - 10
>>: 【D9】厨具熟练後制作精致:使用历史资料的Kbar做MA(移动平均线)图
第十七天 各位点进来的朋友,你们好阿 小的不才只能做这个系列的文章,但还是希望分享给点进来的朋友,知...
先来谈谈IDE是什麽吧! IDE,Integrated Development Environmen...
今天要来试着使用Firebase的机器学习套件,点击左边的Machine Learning 可以看到...
昨天我们安装後有试跑一下 flutter run ,而今天我们就要来好好讲讲这个预设专案到底有什麽东...
v-on (事件绑定) v-on是用来绑定event事件的指令,就像之前javascript介绍过...