node网络爬虫
emer 发布于 2019-11-21 16:32 1907 次阅读
第一步:引入所需要的第三方包 const cheerio = require('cheerio'); const fs = require('fs'); // node.js自带的写模块,后面会用来将爬好的数据写到你的根文件夹中 const Nightmare = require('nightmare'); const nightmare = Nightmare({show: true}); // show:true 显示内置模拟浏览器 var newsList = [] // 用来存新闻数据 复制代码第二步:使用nightmare来爬取目标网页的数据到控制台来 nightmare工具 API介绍:github.com/segmentio/n… nightmare .goto('https://www.toutiao.com/') .wait(6000) // 6000 的意思是当模拟浏览器打开后会等待6秒再爬取页面数据,有这段时间就可以做你想要的动态加载操作 .evaluate(() => document.querySelector("div.feed-infinite-wrapper").innerHTML) // 这里一定要取到你想要爬取数据区域的容器的类名 .then(htmlStr => { newsListData = getnewsList(htmlStr) // getnewsList() 函数将执行对原始数据的选择和处理 newsListData = JSON.stringify(newsListData) // 将数据转化为字符串,以便进行fs写文件操作 fs.writeFile("newsListData.json", newsListData, "utf-8", (error) => { //监听错误,如正常输出,则打印null if (error == null) { console.log("恭喜您,newsListData数据爬取成功!)"); } }) }) .catch(error => { console.log(`数据抓取失败 - ${error}`); }) 复制代码值得说的一点是: es7的 async/await据说是异步编程的终级解决方案,它可以让我们以同步的思维方式来进行异步编程。es6的 Promise解决了异步编程的“回调地狱”,async/await同时使异步流程控制变得友好而有清晰,有兴趣的同学可以去了解学习一下,真的很好用。 第三步:封装getnewsList()处理原始数据 let getnewsList = (res) => { if (res) { let $ = cheerio.load(res); $('ul li').each(function (index, item) { if ($(item).children().attr('class') === 'no-mode') { let titem = $(item).children('.no-mode').children('.title-box'); let fitem = $(item).children('.no-mode').children('.footer-bar'); let news1 = { title_href: titem.children().attr('href'), // attr('属性') 可以取到对应属性的值,包括行内样式的值 title_text: titem.children().text(), // text() 取到文本内容 tag_href: fitem.children('.footer-bar-left').children('.tag').attr('href'), tag_text: fitem.children('.footer-bar-left').children('.tag').text(), mediaAvatar_href: fitem.children('.footer-bar-left').children('.media-avatar').attr('href'), mediaAvatar_imgsrc: fitem.children('.footer-bar-left').children('.media-avatar').children().first().attr('src'), source1_href: fitem.children('.footer-bar-left').children('.source').first().attr('href'), source1_text: fitem.children('.footer-bar-left').children('.source').first().text(), source2_href: fitem.children('.footer-bar-left').children('.source').last().attr('href'), source2_text: fitem.children('.footer-bar-left').children('.source').last().text(), time_text: fitem.children('.footer-bar-left').children('span').text() } newsList.push(news1) } else { let litem = $(item).children('.single-mode').children('.single-mode-lbox'); let ritem = $(item).children('.single-mode').children('.single-mode-rbox').children('.single-mode-rbox-inner'); let news2 = { img_href: litem.children('.img-wrap').attr('href'), img_src: litem.children('.img-wrap').children().attr('src'), title_href: ritem.children('.title-box').children().attr('href'), title_text: ritem.children('.title-box').children().text(), tag_href: ritem.children('.footer-bar').children('.footer-bar-left').children('.tag').attr('href'), tag_text: ritem.children('.footer-bar').children('.footer-bar-left').children('.tag').text(), mediaAvatar_href: ritem.children('.footer-bar').children('.footer-bar-left').children('.media-avatar').attr('href'), mediaAvatar_imgsrc: ritem.children('.footer-bar').children('.footer-bar-left').children('.media-avatar').children().attr('src'), source1_href: ritem.children('.footer-bar').children('.footer-bar-left').children('.source').first().attr('href'), source1_text: ritem.children('.footer-bar').children('.footer-bar-left').children('.source').first().text(), source2_href: ritem.children('.footer-bar').children('.footer-bar-left').children('.source').last().attr('href'), source2_text: ritem.children('.footer-bar').children('.footer-bar-left').children('.source').last().text(), time_text: ritem.children('.footer-bar').children('.footer-bar-left').children('span').text() } newsList.push(news2) } }) return newsList } else { console.log('无数据传入!') return } }