基于nodejs 的多页面爬虫实例代码


Posted in NodeJs onMay 31, 2017

前言

前端时间再回顾了一下node.js,于是顺势做了一个爬虫来加深自己对node的理解。

主要用的到是request,cheerio,async三个模块

request

用于请求地址和快速下载图片流。 https://github.com/request/request

cheerio

为服务器特别定制的,快速、灵活、实施的jQuery核心实现.

便于解析html代码。 https://www.npmjs.com/package/cheerio

async

异步调用,防止堵塞。 http://caolan.github.io/async/

核心思路

  1. 用request 发送一个请求。获取html代码,取得其中的img标签和a标签。
  2. 通过获取的a表情进行递归调用。不断获取img地址和a地址,继续递归
  3. 获取img地址通过request(photo).pipe(fs.createWriteStream(dir + “/” + filename));进行快速下载。
function requestall(url) {

 request({

  uri: url,

  headers: setting.header

 }, function (error, response, body) {

  if (error) {

   console.log(error);

  } else {

   console.log(response.statusCode);

   if (!error && response.statusCode == 200) {

    var $ = cheerio.load(body);

    var photos = [];

    $('img').each(function () {

     // 判断地址是否存在

     if ($(this).attr('src')) {

      var src = $(this).attr('src');

      var end = src.substr(-4, 4).toLowerCase();

      if (end == '.jpg' || end == '.png' || end == '.jpeg') {

       if (IsURL(src)) {

        photos.push(src);

       }

      }

     }

    });

    downloadImg(photos, dir, setting.download_v);

    // 递归爬虫

    $('a').each(function () {

     var murl = $(this).attr('href');

     if (IsURL(murl)) {

      setTimeout(function () {

       fetchre(murl);

      }, timeout);

      timeout += setting.ajax_timeout;

     } else {

      setTimeout(function () {

       fetchre("http://www.ivsky.com/" + murl);

      }, timeout);

      timeout += setting.ajax_timeout;

     }

    })

   }

  }

 });

}

防坑

1.在request通过图片地址下载时,绑定error事件防止爬虫异常的中断。

2.通过async的mapLimit限制并发。

3.加入请求报头,防止ip被屏蔽。

4.获取一些图片和超链接地址,可能是相对路径(待考虑解决是否有通过方法)。

function downloadImg(photos, dir, asyncNum) {

 console.log("即将异步并发下载图片,当前并发数为:" + asyncNum);

 async.mapLimit(photos, asyncNum, function (photo, callback) {

  var filename = (new Date().getTime()) + photo.substr(-4, 4);

  if (filename) {

   console.log('正在下载' + photo);

   // 默认

   // fs.createWriteStream(dir + "/" + filename)

   // 防止pipe错误

   request(photo)

    .on('error', function (err) {

     console.log(err);

    })

    .pipe(fs.createWriteStream(dir + "/" + filename));

   console.log('下载完成');

   callback(null, filename);

  }

 }, function (err, result) {

  if (err) {

   console.log(err);

  } else {

   console.log(" all right ! ");

   console.log(result);

  }

 })

}

测试:

基于nodejs 的多页面爬虫实例代码

可以感觉到速度还是比较快的。

基于nodejs 的多页面爬虫实例代码 

完整地址。https://github.com/hua1995116/node-crawler/

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

NodeJs 相关文章推荐
nodejs获取本机内网和外网ip地址的实现代码
Jun 01 NodeJs
nodejs 实现模拟form表单上传文件
Jul 14 NodeJs
NodeJS学习笔记之MongoDB模块
Jan 13 NodeJs
Nodejs读取文件时相对路径的正确写法(使用fs模块)
Apr 27 NodeJs
nodejs利用ajax实现网页无刷新上传图片实例代码
Jun 06 NodeJs
Nodejs实现文件上传的示例代码
Sep 26 NodeJs
使用nodeJs来安装less及编译less文件为css文件的方法
Nov 20 NodeJs
NodeJs form-data格式传输文件的方法
Dec 13 NodeJs
nodejs结合Socket.IO实现的即时通讯功能详解
Jan 12 NodeJs
nodeJs实现基于连接池连接mysql的方法示例
Feb 10 NodeJs
nodejs实现用户登录路由功能
May 22 NodeJs
浅谈Node的内存泄露问题
May 06 NodeJs
详解nodeJS之路径PATH模块
May 31 #NodeJs
NodeJS实现微信公众号关注后自动回复功能
May 31 #NodeJs
nodejs操作mysql实现增删改查的实例
May 28 #NodeJs
详解nodejs微信jssdk后端接口
May 25 #NodeJs
mac下的nodejs环境安装的步骤
May 24 #NodeJs
Nodejs搭建wss服务器教程
May 24 #NodeJs
Nodejs中Express 常用中间件 body-parser 实现解析
May 22 #NodeJs
You might like
php mssql 时间格式问题
2009/01/13 PHP
php && 逻辑与运算符使用说明
2010/03/04 PHP
php简单的会话类代码
2011/08/08 PHP
Laravel框架实现的记录SQL日志功能示例
2018/06/19 PHP
jQuery get和post 方法传值注意事项
2009/11/03 Javascript
SlideView 图片滑动(扩展/收缩)展示效果
2010/08/01 Javascript
jquery ui resizable bug解决方法
2010/10/26 Javascript
Javascript代码在页面加载时的执行顺序介绍
2013/05/03 Javascript
简单的js图片轮换代码(js图片轮播)
2014/05/06 Javascript
JavaScript显示当前文档最后修改日期的方法
2015/03/19 Javascript
javascript实现捕捉键盘上按下的键
2015/05/05 Javascript
详解AngularJS中module模块的导入导出
2015/12/10 Javascript
深入浅析JavaScript中数据共享和数据传递
2016/04/25 Javascript
node.js插件nodeclipse安装图文教程
2020/10/19 Javascript
javascript基础语法——全面理解变量和标识符
2016/06/02 Javascript
node.js利用mongoose获取mongodb数据的格式化问题详解
2017/10/06 Javascript
原生js实现仿window10系统日历效果的实例
2017/10/31 Javascript
js实现简单数字变动效果
2017/11/06 Javascript
最后说说Vue2 SSR 的 Cookies 问题
2018/05/25 Javascript
JavaScript惰性载入函数实例分析
2019/03/27 Javascript
vue项目前端错误收集之sentry教程详解
2019/05/27 Javascript
layer扩展打开/关闭动画的方法
2019/09/23 Javascript
[41:52]2018DOTA2亚洲邀请赛3月29日小组赛B组Effect VS Secret
2018/03/30 DOTA
跟老齐学Python之玩转字符串(1)
2014/09/14 Python
numpy中的delete删除数组整行和整列的实例
2018/05/09 Python
python多行字符串拼接使用小括号的方法
2020/03/19 Python
使用django实现一个代码发布系统
2019/07/18 Python
Python MongoDB 插入数据时已存在则不执行,不存在则插入的解决方法
2019/09/24 Python
python实现tail实时查看服务器日志示例
2019/12/24 Python
基于OpenCV的网络实时视频流传输的实现
2020/11/15 Python
Mankind西班牙男士护肤品网站:购买皮肤护理、护发和剃须
2017/04/27 全球购物
匡威西班牙官网:Converse西班牙
2019/10/01 全球购物
Michael Kors英国官网:美国奢侈品品牌
2019/11/13 全球购物
如果NULL定义成#define NULL((char *)0)难道不就可以向函数传入不加转换的NULL了吗
2012/02/15 面试题
Shell如何接收变量输入
2012/09/24 面试题
毕业实习评语
2014/02/10 职场文书