使用Puppeteer进行数据抓取(四)——图片下载

大多数情况下,图片获取并不是很困难的事情,获取图片的url,然后模拟浏览器请求即可。但是,有的时候这种方法往往无法生效,常见的情形有:

  1. 动态图片,每次获取都是一个新的,例如图片验证码,重新获取时是一个新的验证码图片,已经失去了效果了。
  2. 动态上下文,有的网站为了反爬虫,获取图片时要加上其动态生成的cookie才行。

这些情况下,使用puppeteer驱动chrome浏览器能看到图片,但获取url后单独请求时,要么获取到的图片无效,要么获取不到图片。本文这里就简单的介绍下一些十分通用且有效的下载这些图片的方法。

截图:

截图是一种非常简单除暴的方法,大多数的时候也是最方便有效的。特别是对于验证码之类的动态生成的图片,这些验证码获取原始图片往往需要一定时间的分析,但chrome能直接截取渲染后生成的图片,直接跳过了分析过程,十分方便。

这里以专利检索及分析网为例,截取它登陆的验证码。

  

首先用devtool分析其selector path。

发现其为"#codePic",接下来的操作就非常简单了

await page.goto(‘http://www.pss-system.gov.cn/sipopublicsearch/portal/uiIndex.shtml‘);

const image = await page.waitForSelector(‘#codePic‘);
await image.screenshot({
    path: ‘验证码.png‘,
    omitBackground: false
});

这里用的并不是page.screenshot,因为那样对整个页面截图了,而是首先获取验证码图片的ElementHandle,然后调用ElementHandle.screenshot只对该元素截图。

这种方式非常简单有效,但由于是通过渲染的方式获取的数据,还是丢失了原始信息的,例如,svg图片就丢失了矢量信息了。

从缓存中读取

另外一种思路是直接从chrome缓存中的数据读取图片数据,就像chrome dev tool的source tab中的那样

  

这个功能在puppeteer中并没有封装,在dev protocol中是有的,它主要涉及到如下两个api:

Page.getResourceTree

它可以用来获取资源树,就像上图左边所示:

Page.getResourceContent

它可以用来获取资源内容,它需要两个参数,frameid和url。frameid可以从page中获取,url必须是前面getResourceTree中获取的url。

虽然puppeteer没有封装这两个函数的功能,但还是有一个私有接口page._client.send可以发送原始dev protocol指令。这里我们可以简单的封装一下:

async function getResourceTree(page) {
    var resource = await page._client.send(‘Page.getResourceTree‘);
    return resource.frameTree;
}

const assert = require(‘assert‘);
async function getResourceContent(page, url) {
    const { contentbase64Encoded } = await page._client.send(
        ‘Page.getResourceContent‘,
        { frameId: String(page.mainFrame()._id), url },
    );
    assert.equal(base64Encoded, true);
    return content;
};

此时就说明我们可以利用前面的api获取该图片了。

const fs = require(‘fs‘);

await page.waitForSelector(‘#codePic‘);
const url = await page.$eval(‘#codePic‘, i => i.src);
const content = await getResourceContent(pageurl);
const contentBuffer = Buffer.from(content, ‘base64‘);
fs.writeFileSync(‘验证码.png‘, contentBuffer, ‘base64‘);

这种方式并不限于只获取图片,也可以获取原始的js,svg之类的资源。

原文地址:https://www.cnblogs.com/TianFang/p/9064409.html

时间: 2024-10-09 11:23:20

使用Puppeteer进行数据抓取(四)——图片下载的相关文章

使用Puppeteer进行数据抓取(二)——Page对象

page对象是puppeteer最常用的对象,它可以认为是chrome的一个tab页,主要的页面操作都是通过它进行的.Google的官方文档详细介绍了page对象的使用,这里我只是简单的小结一下. 客户端模拟 页面模拟设置相关函数有如下几个, page.setViewport: 设置视图大小 page.setUserAget: 设置UserAgent page.SetCookie: 设置Cookie 另外,也可以使用emulate函数提供快捷设置,puppeteer/DeviceDescript

使用Puppeteer进行数据抓取(三)——简单的示例

本文以一个示例简单的介绍一下puppeteer的用法,我们的目的是:获取我博客上的文章的前十页的所有随笔的标题和链接.由于puppeteer本身是自动化chorme,因此这里我们的步骤和手动操作浏览器差不多: 打开chrome,跳转到博客首页 获取所有博客标题信息 点击下一页按钮,跳转到下一页 重复2.3两步,直到所有信息采集完毕 获取信息 采集过程中比较麻烦的一步就是信息的采集,和传统采集html后解析的方式不同的时,由于chrome本身有完整的js引擎,因此我们采用注入一段js,利用该js采

抓取服务器图片下载到本地

Sample code: import org.apache.http.Header; import org.apache.http.HttpResponse; import org.apache.http.HttpStatus; import org.apache.http.client.ClientProtocolException; import org.apache.http.client.HttpClient; import org.apache.http.client.methods

第四章爬虫进阶之动态网页数据抓取

动态网页数据抓取 什么是AJAX: AJAX(Asynchronouse JavaScript And XML)异步JavaScript和XML.过在后台与服务器进行少量数据交换,Ajax 可以使网页实现异步更新.这意味着可以在不重新加载整个网页的情况下,对网页的某部分进行更新.传统的网页(不使用Ajax)如果需要更新内容,必须重载整个网页页面.因为传统的在传输数据格式方面,使用的是XML语法.因此叫做AJAX,其实现在数据交互基本上都是使用JSON.使用AJAX加载的数据,即使使用了JS,将数

Phantomjs+Nodejs+Mysql数据抓取(1.数据抓取)

概要: 这篇博文主要讲一下如何使用Phantomjs进行数据抓取,这里面抓的网站是太平洋电脑网估价的内容.主要是对电脑笔记本以及他们的属性进行抓取,然后在使用nodejs进行下载图片和插入数据库操作. 先进行所有页面的内容进行抓取 var page =require('webpage').create(); var address='http://product.pconline.com.cn/server/'; var fs = require('fs'); var mypath = 'ver

关于“淘宝爆款”的数据抓取与数据分析

本文为younghz原创,文章链接为:http://blog.csdn.net/u012150179/article/details/37306629 这个问题最初是源于我在知乎上一个回答(http://www.zhihu.com/question/24368542/answer/27579662),涉及了两个方面:数据抓取和数据分析. 1.数据爬取 爬取对象:淘宝"连衣裙 夏"的搜索结果. 爬取对象的选择分析我在文章中也有提及. 工具:Scrapy. 代码:我把当时实现的代码放在了G

网页数据抓取(B/S)

C# 抓取网页内容(转) 1.抓取一般内容 需要三个类:WebRequest.WebResponse.StreamReader 所需命名空间:System.Net.System.IO 核心代码: 1 WebRequest request = WebRequest.Create("http://www.cftea.com/"); 2 WebResponse response = request.GetResponse(); 3 StreamReader reader = new Stre

Phantomjs+Nodejs+Mysql数据抓取(2.抓取图片)

概要 这篇博客是在上一篇博客Phantomjs+Nodejs+Mysql数据抓取(1.抓取数据) http://blog.csdn.net/jokerkon/article/details/50868880 后进行的第二部分,请各位读者在看这篇博客之前先浏览上一篇,因为这里面有部分代码会沿用到上一部分的抓取结果. 好,现在开始正式的抓取图片的讲解 首先,我们先来看看代码: var page =require('webpage').create(); var address='http://pro

数据抓取的艺术(三):抓取Google数据之心得

本来是想把这部分内容放到前一篇<数据抓取的艺术(二):数据抓取程序优化>之中.但是随着任务的完成,我越来越感觉到其中深深的趣味,现总结如下: (1)时间     时间是一个与抓取规模相形而生的因素,数据规模越大,时间消耗往往越长.所以程序优化变得相当重要,要知道抓取时间越长,出错的可能性就越大,这还不说程序需要人工干预的情境.一旦运行中需要人工干预,时间越长,干预次数越多,出错的几率就更大了.在数据太多,工期太短的情况下,使用多线程抓取,也是一个好办法,但这会增加程序复杂度,对最终数据准确性产