关于热图

在网站分析行业中,网站热图能够很好的反应用户在网站的操作行为,具体分析用户的喜好,对网站进行针对性的优化,一个热图的例子(来源于ptengine)

上图中能很清晰的看到用户关注点在那,我们不关注产品中热图的功能如何,本篇文章就热图的实现做一下简单的分析和总结。

热图主流的实现方式

一般实现热图显示需要经过如下阶段:

  1. 获取网站页面
  2. 获取经过处理后的用户数据
  3. 绘制热图

    本篇主要聚焦于阶段1来详细的介绍一下主流的在热图中获取网站页面的实现方式
  4. 使用iframe直接嵌入用户网站
  5. 抓取用户页面保存到本地,通过iframe嵌入本地资源(所谓本地资源这里认为是分析工具这一端)

两种方式各有各的优缺点,首先第一种直接嵌入用户网站,这个有一定的限制条件,比如如果用户网站为了防止iframe劫持,不允许iframe嵌套(设置meta X-FRAME-OPTIONS 为sameorgin 或者直接设置http header ,甚至直接通过js来控制

if(window.top !== window.self){ window.top.location = window.location;}

),这种情况下就需要客户网站做一部分工作才可以被分析工具的iframe加载,使用起来不一定那么方便,因为并不是所有的需要检测分析的网站用户都可以管理网站的。

第二种方式,直接抓取网站页面到本地服务器,然后浏览的是本机服务器上抓取的页面,这种情况下页面已经过来了,我们就可以为所欲为了,首先我们绕过了X-FRAME-OPTIONS 为sameorgin的问题,只需要解决js控制的问题,对于抓取的页面来说,我们可以通过特殊的对应来处理(比如移除对应的js控制,或者添加我们自己的js);但是这种方式也有很多的不足:1、无法抓取spa页面,无法抓取需要用户登录授权的页面,无法抓取用户设置了白明白的页面等等。

两种方式都存在https 和 http资源由于同源策略引起的另一个问题,https站无法加载http资源,所以如果为了最好的兼容性,热图分析工具需要被应用http协议,当然具体可以根据访问的客户网站而具体分站优化。

抓取网站页面如何优化

这里我们针对抓取网站页面遇到的问题基于puppeteer做一些优化,提高抓取成功的概率,主要优化以下两种页面:

  1. spa页面

    spa页面在当前页算是主流了,但是它总所周知的是其对搜索引擎的不友好;通常的页面抓取程序其实就是一个简单的爬虫,其过程通常都是发起一个http get 请求到用户网站(应该是用户网站服务器)。这种抓取方式本身就会有问题问题,首先,直接请求的是用户服务器,用户服务器对非浏览器的agent 应该会有很多限制,需要绕过处理;其次,请求返回的是原始内容,需要在浏览器中通过js渲染的部分无法获取(当然,在iframe嵌入后,js执行还是会再一定程度上弥补这个问题),最后如果页面是spa页面,那么此时获取的只是模板,在热图中显示效果非常不友好。

    针对这种情况,如果基于puppeteer来做,流程就变成了

    puppeteer启动浏览器打开用户网站-->页面渲染-->返回渲染后结果,简单的用伪代码实现如下:
const puppeteer = require('puppeteer');

async getHtml = (url) =>{
const browser = await puppeteer.launch();
const page = await browser.newPage();
await page.goto(url);
return await page.content();
}

这样我们拿到的内容就是渲染后的内容,无论页面的渲染方式如何(客户端渲染抑或服务端)

需要登录的页面

对于需要登录页面其实分为多种情况:

  • 需要登录才可以查看页面,如果没有登录,则跳转到login页面(各种管理系统)

    对于这种类型的页面我们需要做的就是模拟登录,所谓模拟登录就是让浏览器去登录,这里需要用户提供对应网站的用户名和密码,然后我们走如下的流程:

    访问用户网站-->用户网站检测到未登录跳转到login-->puppeteer控制浏览器自动登录后跳转到真正需要抓取的页面,可用如下伪代码来说明:
const puppeteer = require("puppeteer");
async autoLogin =(url)=>{
const browser = await puppeteer.launch();
const page =await browser.newPage();
await page.goto(url);
await page.waitForNavigation(); //登录
await page.type('#username',"用户提供的用户名");
await page.type('#password','用户提供的密码'); await page.click('#btn_login'); //页面登录成功后,需要保证redirect 跳转到请求的页面
await page.waitForNavigation(); return await page.content();
}
  • 登录与否都可以查看页面,只是登录后看到内容会所有不同 (各种电商或者portal页面)

这种情况处理会比较简单一些,可以简单的认为是如下步骤:

通过puppeteer启动浏览器打开请求页面-->点击登录按钮-->输入用户名和密码登录 -->重新加载页面

基本代码如下图:

const puppeteer = require("puppeteer");
async autoLoginV2 =(url)=>{
const browser = await puppeteer.launch();
const page =await browser.newPage();
await page.goto(url); await page.click('#btn_show_login'); //登录
await page.type('#username',"用户提供的用户名");
await page.type('#password','用户提供的密码'); await page.click('#btn_login'); //页面登录成功后,是否需要reload 根据实际情况来确定
await page.reload(); return await page.content();
}

总结

明天总结吧,今天下班了。

补充(还昨天的债):基于puppeteer虽然可以很友好的抓取页面内容,但是也存在这很多的局限

  1. 抓取的内容为渲染后的原始html,即资源路径(css、image、javascript)等都是相对路径,保存到本地后无法正常显示,需要特殊处理(js不需要特殊处理,甚至可以移除,因为渲染的结构已经完成)
  2. 通过puppeteer抓取页面性能会比直接http get 性能会差一些,因为多了渲染的过程
  3. 同样无法保证页面的完整性,只是很大的提高了完整的概率,虽然通过page对象提供的各种wait 方法能够解决这个问题,但是网站不同,处理方式就会不同,无法复用。

基于puppeteer模拟登录抓取页面的更多相关文章

  1. C# WebBrowser控件 模拟登录 抓取数据

    参考博客:C#中的WebBrowser控件的使用 参考博客:C#中利用WebBrowser控件,获得HTML源码 一.问题点: 1.模拟登录后,如果带有嵌套的iframe嵌套,不好读取iframe内容 ...

  2. CasperJS基于PhantomJS抓取页面

    CasperJS基于PhantomJS抓取页面 Casperjs是基于Phantomjs的,而Phantom JS是一个服务器端的 JavaScript API 的 WebKit. CasperJS是 ...

  3. php中CURL技术模拟登陆抓取数据实战,抓取某校教务处学生成绩。

    这两天有基友要php中curl抓取教务处成绩的源码,用于微信公众平台的开发.下面笔者只好忍痛割爱了.php中CURL技术模拟登陆抓取数据实战,抓取沈阳工学院教务处学生成绩. 首先,教务处登录需要验证码 ...

  4. php爬虫入门 - 登录抓取内容

    PHP 写爬虫 说实话我也想用Python的,毕竟人家招牌.无奈我Python还停留在看语法的阶段,实在太惭愧,鞭笞一下自己加油学习.这里用php的CURL库进行页面抓取. 同事使用的系统需要先登录, ...

  5. PHP爬虫入门--简单的登录抓取内容

    给同事写一个小工具,抓取月报表然后统计加工.第一反应是做一个爬虫把需要的表和图抓下来,这样就不用再自己去连数据库然后组织表格生成图片之类的. 以上为背景 PHP 写爬虫 说实话我也想用Python的, ...

  6. 爬虫抓取页面数据原理(php爬虫框架有很多 )

    爬虫抓取页面数据原理(php爬虫框架有很多 ) 一.总结 1.php爬虫框架有很多,包括很多傻瓜式的软件 2.照以前写过java爬虫的例子来看,真的非常简单,就是一个获取网页数据的类或者方法(这里的话 ...

  7. 搭建谷歌浏览器无头模式抓取页面服务,laravel->php->python->docker !!!

    背景: 公司管理系统需要获取企业微信页面的配置参数如企业名.logo.人数等信息并操作,来隐藏相关敏感信息并自定义简化企业号配置流程 第一版已经实现了扫码登录获取cookie,使用该cookie就能获 ...

  8. 用PHP抓取页面并分析

    在做抓取前,记得把php.ini中的max_execution_time设置的大点,不然会报错的.

  9. php抓取页面的几种方式

    在做一些天气预报或者RSS订阅的程序时,往往 需要抓取非本地文件,一般情况下都是利用php模拟浏览器的访问,通过http请求访问url地址, 然后得到html源代码或者xml数据,得到数据我们不能直接 ...

随机推荐

  1. UNIX环境高级编程——信号说明列表

    $ kill -l 1) SIGHUP 2) SIGINT 3) SIGQUIT 4) SIGILL 5) SIGTRAP 6) SIGABRT 7) SIGBUS 8) SIGFPE 9) SIGK ...

  2. Iterm2安装Zsh + Oh My Zsh+Solarized

    安装Oh My Zsh curl -L https://raw.github.com/robbyrussell/oh-my-zsh/master/tools/install.sh | sh 安装Zsh ...

  3. 程序员的软实力武器-star法则

    hhh 程序员的表达能力一直被诟病,尤其面试讲述自己的项目的时候 下面的star原则能够帮助你: 所谓STAR原则,即Situation(情景).Task(任务).Action(行动)和Result( ...

  4. [Ext.Net]动态生成控件(二)--js动态添加文本框

    转自:http://www.ext.net.cn/forum.php?mod=viewthread&tid=11931 点击一个按钮就出现一行控件,点击删除控件就可将一行控件删除,这是不是你一 ...

  5. 《java入门第一季》之面向对象匿名内部类面试题

    面试题一: /*         按照要求,补齐代码             interface Inter { void show(); }             class Outer { // ...

  6. 在android C/C++ native编程(ndk)中使用logcat

    最近在研究Android 2.2 源代码的C/C++层,需要对代码进行一些调试,但是奇怪的是,直接添加LOGD("XXXXXXXX");,使用logcat却看不到任何输出,换成LO ...

  7. 【Android 应用开发】Android中使用ViewPager制作广告栏效果 - 解决ViewPager占满全屏页面适配问题

    . 参考界面 : 携程app首页的广告栏, 使用ViewPager实现        自制页面效果图 : 源码下载地址: http://download.csdn.net/detail/han1202 ...

  8. windows下追踪路由

    追踪路由 tracert   目标ip/域名 测试两个ip是否畅通 ping    目标ip 在windows查看ip情况 ipconfig linux/unix下查看ip情况的使用 ifconfig

  9. Gradle 1.12用户指南翻译——第三十七章. OSGi 插件

    本文由CSDN博客万一博主翻译,其他章节的翻译请参见: http://blog.csdn.net/column/details/gradle-translation.html 翻译项目请关注Githu ...

  10. Objective-C的面向对象特性(二)

    在Objective-C语言中, 类别.类扩展(也称为匿名类别)以及协议是Objective-C 语言级别支持的模式,用来实现对类进行功能扩展. 一.类别--用来增加方法到已存在类 声明一个类别的语法 ...