准备文件
准备文件spider,文件目录如下 npm init 初始化package.json;
需要的模块
- http模块、fs模块都是内置的包
- 安装cheerio包,和request包(直接那么npm install)
开始编写脚本
在根目录下新建spider.js,加载包依赖
var http = require('http');
var fs = require('fs');
var cheerio = require('cheerio');
var request= require('request');
var i=0;
var url="http://gz.lianjia.com/zufang/";
//初始化url
function fetchPage(x){//封装了一层函数
console.log('start');
startRequest(x);
}
下面利用cheerio来解析html文档,筛选出需要的数据,这里cheerio的用法和jq好像基本上一样(挺简单的);把文字内容格式为类似json的key:val;用i来控制爬取内容的数量
function startRequest(x){
//采用http模块向服务器发起一次get请求
http.get(x,function(res){
var html='';//用来存储请求网页的整个html内容
var titles=[];
res.setEncoding('utf-8');//防止中文乱码
//监听data事件,每次取一块数据
res.on('data',function(chunk){
html+=chunk;
})
//监听end事件,如果整个网页的内容html都获取完毕,就执行回调函数
res.on('end',function(){
var $=cheerio.load(html);//采用cheerio模块来解析html
var pic_panel=$('.pic-panel a').eq(i).find('img');
var news_item = {
//获取租房的标题
title: $('.info-panel h2 a').eq(i).text().trim(),
//获取租房发布的时间
Time: $('.info-panel .price-pre').eq(i).text().trim(),
//获取租房的url
link: $(".info-panel h2 a").eq(i).attr('href'),
//获取租房价格
price: $('.info-panel .price span').eq(i).text().trim(),
//获取详细信息
msg: $('.where .region').eq(i).text().trim()+$('.where .zone span').eq(i).text().trim()+$('.where .meters').eq(i).text().trim(),
//i是用来判断获取了多少篇文章
i: i = i + 1,
};
console.log(news_item);
savedContent($,news_item);//存储内容
savedImg($,pic_panel);//存储图片
if (i <=20) {
fetchPage(url);
}
});
}).on('error', function (err) {
console.log(err);
});
}
下面连个函数是用来把数据保存到本地的,这里有个坑,一般图片是有防爬取链接的,比如这里我选择的事img的data-img而不是src,看一下链家的接口是把图片的src在页面load的时候再切换的
//该函数的作用:在本地存储所爬取的新闻内容资源
function savedContent($, news_title) {
var x = JSON.stringify(news_title);
//将新闻文本内容一段一段添加到/data文件夹下,并用新闻的标题来命名文件
fs.appendFile('./data/' + news_title.title + '.txt', x, 'utf-8', function (err) {
if (err) {
console.log(err);
}
});
}
//该函数的作用:在本地存储所爬取到的图片资源
function savedImg($,news_title) {
var img_title = news_title.attr('alt'); //获取图片的标题
if(img_title.length>35||img_title==""){
img_title="Null";}
var img_filename = img_title + '.jpg';
var img_src = news_title.attr('data-img'); //获取图片的url
console.log(img_src)
//采用request模块,向服务器发起一次请求,获取图片资源
request.head(img_src,function(err,res,body){
if(err){
console.log(err);
}
});
request(img_src).pipe(fs.createWriteStream('./image/'+img_title + '---' + img_filename)); //通过流的方式,把图片写到本地/image目录下,并用新闻的标题和图片的标题作为图片的名称。
}
最后执行函数
fetchPage(url); //主程序开始运行
这是爬取的图片 这是爬取的文档 这是爬取的文档内容
This work is licensed under a CC A-S 4.0 International License.