NodeJS学习(2)构建第一个爬虫
前言
一般来讲,提到爬虫,目前搭建也都喜欢使用python,不可否认,python确实有它方便的地方,上手简单,容易等等很多优点;
前一段时间也写了不少爬虫的文章,但是发现在爬取大量数据和存贮大量的数据时,只用python,效率确实不高。
毕竟虽然python也有多线程这些内容,但本质上它还是一个单线程的东东,在并发上,python的优势不是很明显。
从这篇文章开始,我写点NodeJS相关的爬虫文章,即是记录一下自己的的学习成果,也是分享。
正文
创建工程
创建自己的工作目录,然后构建工作环境如下:
E:\>mkdir myNodeJS
E:\>cd myNodeJS
E:\myNodeJS>mkdir firstSpider
E:\myNodeJS>cd firstSpider
E:\myNodeJS\firstSpider>npm init
在输入 npm init 之后, 会出现一些列询问的语句,可以暂时全部一路回车
This utility will walk you through creating a package.json file.
It only covers the most common items, and tries to guess sensible defaults.
See `npm help json` for definitive documentation on these fields
and exactly what they do.
Use `npm install <pkg>` afterwards to install a package and
save it as a dependency in the package.json file.
Press ^C at any time to quit.
package name: (firstspider)
version: (1.0.0)
description:
entry point: (index.js)
test command:
git repository:
keywords:
author:
license: (ISC)
About to write to E:\myNodeJS\firstSpider\package.json:
{
"name": "firstspider",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC"
}
Is this ok? (yes)
npm init 是在当前目录创建模块(也就是生成 package.json)其文件属性说明如下
- name - 包名。
- version - 包的版本号。
- description - 包的描述。
- homepage - 包的官网 url 。
- author - 包的作者姓名。
- contributors - 包的其他贡献者姓名。
- dependencies - 依赖包列表。如果依赖包没有安装,npm 会自动将依赖包安装在 node_module 目录下。
- repository - 包代码存放的地方的类型,可以是 git 或 svn,git 可在 Github 上。也就是你 Git 的仓库地址
- main - main 字段是一个模块ID,它是一个指向你程序的主要项目。就是说,如果你包的名字叫 express,然后用户安装它,然后require(“express”)。
- keywords - 关键字
这些内容现在都没有填写,不过可以在这个工程目录下的json文件(package.json)中去随时修改
安装库
安装必要的一些库,这里安装一些爬虫用到的两个库,一个request,一个cheerio
- request,跟python里request功能差不多。它的功能就是建立起对目标网页的链接,并返回相应的数据。是我们做爬虫获取数据的重要一步。
- cheerio的功能是用来操作 dom 元素的,他可以把 request 返回来的数据转换成可供 dom 操作的数据,更重要的 cheerio 的 api 跟 jquery 一样,用$来选取对应的dom结点,这样就可以想取啥就取啥,感谢强大的 DOM
安装命令如下
E:\myNodeJS\firstSpider>npm install cheerio
E:\myNodeJS\firstSpider>npm install request
主程序
到这里可以新建文件,写代码了。
新建一个 js 文件,如果是主入口文件名称应该注意和 package.json 中 entry point 一致。
这里我们新建一个 名为 onespider.js 的文件
建立依赖引用,代码如下
var request=require("request");
var cheerio=require("cheerio");
构建请求,获取百度主页的内容
request('https://www.baidu.com',function(err,result){
if(err){
console.log("请求错误:"+err);
return
}
console.log(result.body);
});
到这一步,大致的一个小爬虫就写完了,接下来,运行一下,看看跟预期中的效果一样不:
E:\myNodeJS\firstSpider>node onespider.js
程序运行之后,大致输出如下:
<!DOCTYPE html><!--STATUS OK-->
<html>
<head>
<meta http-equiv="content-type" content="text/html;charset=utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=Edge">
<link rel="dns-prefetch" href="//s1.bdstatic.com"/>
<link rel="dns-prefetch" href="//t1.baidu.com"/>
<link rel="dns-prefetch" href="//t2.baidu.com"/>
<link rel="dns-prefetch" href="//t3.baidu.com"/>
<link rel="dns-prefetch" href="//t10.baidu.com"/>
<link rel="dns-prefetch" href="//t11.baidu.com"/>
<link rel="dns-prefetch" href="//t12.baidu.com"/>
<link rel="dns-prefetch" href="//b1.bdstatic.com"/>
<title>百度一下,你就知道</title>
<link href="http://s1.bdstatic.com/r/www/cache/static/home/css/index.css" rel="stylesheet" type="text/css" />
<!--[if lte IE 8]><style index="index" >#content{height:480px\9}#m{top:260px\9}</style><![endif]-->
<!--[if IE 8]><style index="index" >#u1 a.mnav,#u1 a.mnav:visited{font-family:simsun}</style><![endif]-->
<script>var hashMatch = document.location.href.match(/#+(.*wd=[^&].+)/);if (hashMatch && hashMatch[0] && hashMatch[1]) {document.location.replace("http://"+location.host+"/s?"+hashMatch[1]);}var ns_c = function(){};</script>
<script>function h(obj){obj.style.behavior='url(#default#homepage)';var a = obj.setHomePage('//www.baidu.com/');}</script>
这样来看,第一个程序写的还算成功,如预期一样,拿到了我们想要的网页内容。
接下来执行第二部,处理拿到的网页数据
目的是获取一下网页的title,怎么找到titile在网页的位置?依然是借助与F12 工具在网页上简单的查看一下,这里刚才上面的输出其实已经看到了。
现在通过代码处理一下刚才获取到的网页内容,得到title:
//console.log(result.body);
var page=cheerio.load(result.body);
console.log(page('title').text());
然后输出如下:
E:\myNodeJS\firstSpider>node onespider.js
百度一下,你就知道
这样使用NodeJS 构建的第一个爬虫就这样完成了~
完整代码
var request=require("request"); //导入依赖
var cheerio=require("cheerio"); //导入依赖
request('http://www.baidu.com',function(err,result){
if(err){ //错误处理
console.log("请求错误:"+err);
return
}
//console.log(result.body); //直接输出结果
var page=cheerio.load(result.body); //将得到的网页内容重新交给cheerio处理
console.log(page('title').text()); //获取标题
});