这个爬虫在Referer设置上和其它爬虫相比有特殊性。代码:

  1. //======================================================
  2. // mimimn图片批量下载Node.js爬虫1.00
  3. // 2017年11月15日
  4. //======================================================
  5.  
  6. // 内置http模块
  7. var https=require("https");
  8.  
  9. // 内置文件处理模块,用于创建目录和图片文件
  10. var fs=require('fs');
  11.  
  12. // cheerio模块,提供了类似jQuery的功能,用于从HTML code中查找图片地址和下一页
  13. var cheerio = require("cheerio");
  14.  
  15. // 请求参数JSON。http和https都有使用
  16. var options;
  17.  
  18. // request请求
  19. var req;
  20.  
  21. // 图片数组,找到的图片地址会放到这里
  22. var pictures=[];
  23.  
  24. //--------------------------------------
  25. // 爬取网页,找图片地址,再爬
  26. // pageUrl sample:https://www.mimimn.com/files/38/3832.html
  27. // pageUrl sample:https://www.mimimn.com/files/37/3775.html
  28. //--------------------------------------
  29. function crawl(pageUrl){
  30. console.log("Current page="+pageUrl);
  31.  
  32. // 得到hostname和path
  33. var currUrl=pageUrl.replace("https://","");
  34. var pos=currUrl.indexOf("/");
  35. var hostname=currUrl.slice(0,pos);
  36. var path=currUrl.slice(pos);
  37. //console.log("hostname="+hostname);
  38. //console.log("path="+path);
  39.  
  40. // 初始化options
  41. options={
  42. hostname:hostname,
  43. port:443,
  44. path:path,// 子路径
  45. method:'GET',
  46. };
  47.  
  48. req=https.request(options,function(resp){
  49. var html = [];
  50.  
  51. resp.on("data", function(data) {
  52. html.push(data);
  53. })
  54. resp.on("end", function() {
  55. var buffer = Buffer.concat(html);
  56. var body=buffer.toString();
  57. //console.log(body);
  58.  
  59. var $ = cheerio.load(body);
  60. var picCount=0;
  61.  
  62. // 找图片放入数组
  63. $(".text-center a img").each(function(index,element){
  64. var picUrl=$(element).attr("src");
  65. //console.log(picUrl);
  66.  
  67. if(picUrl.indexOf('.jpg')!=-1){
  68. pictures.push(picUrl);
  69. picCount++;
  70. }
  71. })
  72. console.log("找到图片"+picCount+"张.");
  73.  
  74. // 找下一页
  75. var htmls=[];
  76. var currIndex=-1;
  77. $(".pagination ul li").each(function(index,element){
  78. var text=$(element).html();
  79. //console.log(text);
  80. htmls.push(text);
  81.  
  82. var cls=$(element).attr("class");
  83. if(cls=='active'){
  84. currIndex=index;
  85. }
  86. })
  87.  
  88. //console.log("htmls.length="+htmls.length);
  89. //console.log("currIndex="+currIndex);
  90.  
  91. if((htmls.length-1)==currIndex){
  92. console.log(pageUrl+"已经是最后一页了.");
  93. download(pictures);
  94. }else{
  95. var text=htmls[currIndex+1];
  96. var start=text.indexOf("\"");
  97. var end=text.lastIndexOf("\"");
  98. var nextPageUrl=text.slice(start+1,end);
  99. //console.log("下一页是"+nextPageUrl);
  100. crawl(nextPageUrl);
  101. }
  102.  
  103. }).on("error", function() {
  104. console.log("获取失败")
  105. })
  106. });
  107.  
  108. // 超时处理
  109. req.setTimeout(5000,function(){
  110. req.abort();
  111. });
  112.  
  113. // 出错处理
  114. req.on('error',function(err){
  115. if(err.code=="ECONNRESET"){
  116. console.log('socket端口连接超时。');
  117. }else{
  118. console.log('请求发生错误,err.code:'+err.code);
  119. }
  120. });
  121.  
  122. // 请求结束
  123. req.end();
  124. }
  125.  
  126. //--------------------------------------
  127. // 下载图片
  128. //--------------------------------------
  129. function download(pictures){
  130. var folder='pictures('+getNowFormatDate()+")";
  131. // 创建目录
  132. fs.mkdir('./'+folder,function(err){
  133. if(err){
  134. console.log("目录"+folder+"已经存在");
  135. }
  136. });
  137.  
  138. var total=0;
  139. total=pictures.length;
  140. console.log("总计有"+total+"张图片将被下载.");
  141. appendToLogfile(folder,"总计有"+total+"张图片将被下载.\n");
  142. for(var i=0;i<pictures.length;i++){
  143. var picUrl=pictures[i];
  144. downloadPic(picUrl,folder);
  145. }
  146. }
  147.  
  148. //--------------------------------------
  149. // 写log文件
  150. //--------------------------------------
  151. function appendToLogfile(folder,text){
  152. fs.appendFile('./'+folder+'/log.txt', text, function (err) {
  153. if(err){
  154. console.log("不能书写log文件");
  155. console.log(err);
  156. }
  157. });
  158. }
  159.  
  160. //--------------------------------------
  161. // 取得当前时间
  162. //--------------------------------------
  163. function getNowFormatDate() {
  164. var date = new Date();
  165. var seperator1 = "-";
  166. var seperator2 = "_";
  167. var month = date.getMonth() + 1;
  168. var strDate = date.getDate();
  169. if (month >= 1 && month <= 9) {
  170. month = "0" + month;
  171. }
  172. if (strDate >= 0 && strDate <= 9) {
  173. strDate = "0" + strDate;
  174. }
  175. var currentdate =date.getFullYear() + seperator1 + month + seperator1 + strDate
  176. + " " + date.getHours() + seperator2 + date.getMinutes()
  177. + seperator2 + date.getSeconds();
  178. return currentdate;
  179. }
  180.  
  181. //--------------------------------------
  182. // 下载单张图片
  183. // picUrl sample:https://mi.uz0.net/20171029/1509249915gi25.jpg
  184. //--------------------------------------
  185. function downloadPic(picUrl,folder){
  186. console.log("图片:"+picUrl+"下载开始");
  187.  
  188. // 得到hostname,path和port
  189. var currUrl=picUrl.replace("https://","");
  190. var pos=currUrl.indexOf("/");
  191. var hostname=currUrl.slice(0,pos);
  192. var path=currUrl.slice(pos);
  193.  
  194. //console.log("hostname="+hostname);
  195. //console.log("path="+path);
  196.  
  197. var picName=currUrl.slice(currUrl.lastIndexOf("/"));
  198.  
  199. // 初始化options
  200. options={
  201. hostname:hostname,
  202. port:443,
  203. path:path,// 子路径
  204. method:'GET',
  205. // HTTP请求中有一个referer的报文头,用来指明当前流量的来源参考页.
  206. headers:{
  207. 'Referer':'https://www.mimimn.com',// 设置Referer,没有这一步图片下载不下来,因为网站用Rederer做了低端的图片防盗链
  208. }
  209.  
  210. };
  211.  
  212. req=https.request(options,function(resp){
  213. var imgData = "";
  214. resp.setEncoding("binary");
  215.  
  216. resp.on('data',function(chunk){
  217. imgData+=chunk;
  218. });
  219.  
  220. resp.on('end',function(){
  221.  
  222. // 创建文件
  223. var fileName="./"+folder+picName;
  224. fs.writeFile(fileName, imgData, "binary", function(err){
  225. if(err){
  226. console.log("[downloadPic]文件"+fileName+"下载失败.");
  227. console.log(err);
  228. appendToLogfile(folder,"文件 "+picUrl+" 下载失败.\n");
  229. }else{
  230. appendToLogfile(folder,"文件 "+picUrl+" 下载成功.\n");
  231. console.log("文件"+fileName+"下载成功");
  232. }
  233. });
  234. });
  235. });
  236.  
  237. // 超时处理
  238. req.setTimeout(7500,function(){
  239. req.abort();
  240. });
  241.  
  242. // 出错处理
  243. req.on('error',function(err){
  244. if(err){
  245. console.log('[downloadPic]文件'+picUrl+"下载失败,"+'因为'+err);
  246. appendToLogfile(folder,"文件"+picUrl+"下载失败.\n");
  247. }
  248. });
  249.  
  250. // 请求结束
  251. req.end();
  252. }
  253.  
  254. //--------------------------------------
  255. // 程序入口
  256. //--------------------------------------
  257. function getInput(){
  258.  
  259. process.stdout.write("\033[35m 请输入第一页URL:\033[039m"); //紫色
  260. process.stdin.resume();
  261. process.stdin.setEncoding('utf8');
  262.  
  263. process.stdin.on('data',function(text){
  264. process.stdin.end();// 退出输入状态
  265. crawl(text.trim());// trim()是必须的!
  266. });
  267. }
  268.  
  269. // 调用getInput函数,程序开始
  270. getInput();

关于Referer设置的参考文章如下:

http://blog.csdn.net/u011250882/article/details/49679535

https://www.cnblogs.com/rubylouvre/p/3541411.html

http://blog.csdn.net/fishmai/article/details/52388840

https://www.cnblogs.com/bukudekong/p/3829852.html

https://zhidao.baidu.com/question/1832550088624773020.html

2017年11月15日05:19:50

Node.js mimimn图片批量下载爬虫 1.00的更多相关文章

  1. Node.js mzitu图片批量下载爬虫1.00

    又攻下一座山头. //====================================================== // mzitu图片批量下载爬虫1.00 // 2017年11月19 ...

  2. Node.js 4493图片批量下载爬虫1.00

    这个爬虫依然需要iconv转码,想不到如今非utf8的网页还这么多.另外此网页找下一页的方式比较异常,又再次借助了正则表达式. 代码如下: //============================ ...

  3. Node.js monly图片批量下载爬虫1.00

    此爬虫又用到了iconv转码,代码如下: //====================================================== // mmonly图片批量下载爬虫1.00 ...

  4. Node.js m03122图片批量下载爬虫1.00

    //====================================================== // m03122图片批量下载爬虫1.00 // 2017年11月18日 //==== ...

  5. Node.js mm131图片批量下载爬虫1.00 iconv协助转码

    //====================================================== // mm131图片批量下载爬虫1.00 // 2017年11月15日 //===== ...

  6. Node.js nvshens图片批量下载爬虫 1.00

    //====================================================== // www.nvshens.com图片批量下载Node.js爬虫1.00 // 此程 ...

  7. Node.js mm131图片批量下载爬虫1.01 增加断点续传功能

    这里的断点续传不是文件下载时的断点续传,而是指在爬行页面时有时会遇到各种网络中断而从中断前的页面及其数据继续爬行的过程,这个过程和断点续传原理上相似故以此命名.我的具体做法是:在下载出现故障或是图片已 ...

  8. Node.js abaike图片批量下载爬虫1.02

    //====================================================== // abaike图片批量下载爬虫1.02 // 用最近的断点续传框架改写原有1.01 ...

  9. Node.js nvshens图片批量下载爬虫1.01

    //====================================================== // nvshens图片批量下载爬虫1.01 // 用最近的断点续传框架改写原有1.0 ...

随机推荐

  1. 使用css让文字两端对齐

    text-align:justify; text-justify:distribute-all-lines; text-align-last:justify;可以让文字实现两端对齐

  2. Mac安装Maven

    1.从官网(https://maven.apache.org/download.cgi)下载 Maven 并解压. 2.配置环境 .  vim ~/.bash_profile export MAVEN ...

  3. bzoj 1443 二分图博弈

    这种两个人轮流走,不能走 走过的格子的大都是二分图博弈... #include<bits/stdc++.h> #define LL long long #define fi first # ...

  4. yum 安装

    可以有两种方式:1.sudo yum install 然后输入root密码2.su root,输入密码然后yum install

  5. Python开发基础-Day10生成器表达式形式、面向过程编程、内置函数部分

    生成器表达式形式 直接上代码 # yield的表达式形式 def foo(): print('starting') while True: x=yield #默认返回为空,实际上为x=yield No ...

  6. 【BFS】Pots

    [poj3414]Pots Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 16925   Accepted: 7168   ...

  7. 【SAM】BZOJ2882-工艺

    [题目大意] 求一个循环数列的最小表示法. [思路] 最小表示法的正解:★ SAM乱搞,和前面的POJ那道一样.然而MLE了,当作学习一下map的用法^ ^ map的使用方法(来源:☆) 一.map的 ...

  8. MYSQL复习笔记1-物理文件和系统架构

    date:20140101auth:Jin 一.物理组成(一) 日志文件参考:http://dev.mysql.com/doc/refman/5.1/en/server-logs.html1.错误日志 ...

  9. dns问题,QQ打得开,网页打不开

    dns问题,QQ打得开,网页打不开 ip4 dns 改为114.114.114.114. 原因有可能是路由出错之类的.114是默认的通用ip

  10. 图解SQL Server:聚集索引、唯一索引、主键

    http://www.cnblogs.com/chenxizhang/archive/2010/01/14/1648042.html