网络爬虫基本就由如下部分组成:
程序入口
请求模块
数据解释
下面我们来看一下如何使用nodejs实现网络爬虫。
程序入口
开始配置和初始化commander
首先要在package.json添加如下节点,表示注册了一个命令行 "grab"。
"bin": { "grab": "bin/grab.js" },
接着在grab.js开始定义commander,最后我们就可以这样执行命令行:"grab baidu <内容>",当然可以用bd简写代替baidu,知乎的定义和百度是一样,这里不再重复介绍了。
program // .allowUnknownOption()//不报错误 .version('0.0.1').usage('这是我的网络爬虫程序
请求模块
https模块发起请求主要有两种方式,这里稍微封装了下:
1、get方式,主要针对的是简单的请求,只需要传递url发起get请求。知乎的调用这个就可以了。
function get(url, callback) { return https.get(url, function(response) { var body = ''; response.on('data', function(data) { body += data; }); response.on('end', function() { callback(body); }); }); }
2、querst方式,不但可以发起get请求,也可以发起post请求,还可以修改端口,请求header。这个主要是针对限制比较多的百度爬虫。
function request(options, callback) { // var postData = qs.stringify({}); var body, req = https.request(options, (res) = >{ console.log('STATUS: ' + res.statusCode); // console.log('HEADERS: ' + JSON.stringify(res.headers)); res.setEncoding('utf8'); res.on('data', function(chunk) { body += chunk; }); res.on('end', function() { callback(body) }); }); req.on('error', function(e) { console.log('problem with request: ' + e.message); }); // write data to request body // req.write(postData); req.end(); } function baiduRequset(pageNo, pageSize, keyword) { var path = '/s?' + qs.stringify({ ie: 'utf-8', f: 8, rsv_bp: 1, tn: 'baidu', rn: pageSize, pn: pageNo * pageSize, wd: keyword }), options = { hostname: 'www.baidu.com', port: 443, path: path, method: 'GET', headers: { 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/61.0.3163.100 Safari/537.36' } }; request(options, function(body) { saveFile(pageNo, keyword, body); showBaiduResult(pageNo, body); }); }
数据解释
抓取数据之后,我们需要做的就是调用cheerio,以jquery获取dom内容的方式获取结果,并显示出来,当然也可以保存文件或数据库。
/** * 显示结果 * @param {[type]} pageNo [description] * @param {[type]} body [description] * @return {[type]} [description] */ function showBaiduResult(pageNo, body) { var title, summary, link, reg = /<[^<>]+>/g, $ = cheerio.load(body, { decodeEntities: false }); $('#content_left .result').each(function(i, item) { var $a = $(item).find('h3 a'); title = $a.html(); link = $a.attr('href'); summary = $(item).find('.c-abstract').html(); if (title) { console.log(`第$ { pageNo + 1 }页第$ { i + 1 }条`); console.log(`link: $ { link }`.green); // console.log(`title: ${title}`); console.log('title: '); ouputColor(title); if (summary) { // console.log(`summary: ${summary}`); console.log('summary: '); ouputColor(summary); } } console.log('------------------------------'); console.log(''); }); } // 知乎 exports.zhihuSearch = function(keyword, cb) { get('https://www.zhihu.com/search?type=content&q=' + keyword, function(content) { var title, summary; var $ = cheerio.load(content, { decodeEntities: false }); saveFile(0, keyword, content); $('.list .item').each(function(i, item) { title = $(item).find('.js-title-link').html(); summary = $(item).find('.summary').html(); if (title) { // title=(''+title).replace(/<[^<>]+>/g,''); // summary=(''+summary).replace(/<.+>/g,''); console.log('title: '); ouputColor(title); if (summary) { console.log('summary: '); ouputColor(summary); } } console.log('------------------------------'); console.log(''); }); }); };
执行爬虫
功能完成后,先试验一下抓取知乎的内容
grab zh webgl
抓取到的html文件保存在download文件夹,同时在命令行显示抓取结果。
以上就是nodejs如何爬虫?的详细内容,更多请关注易知道|edz.cc其它相关文章!