zoukankan      html  css  js  c++  java
  • 简析hotjar录屏功能实现原理

    简析hotjar录屏功能实现原理

    众所周知,hotjar中录屏功能是其重要的一个卖点,看着很牛X酷炫的样子,今天就简单的分析一下其可能实现(这里只根据其请求加上个人理解分析,并不代表hotjar中真实实现必然如此)的原理。

    1、获取完整DOM内容

    如果要实现完整的录屏功能,在客户端在没有客户允许的前提下,目前是无法做到的,所以只能考虑在服务端来实现,在服务端实现的第一步,就必然需要重现客户端的渲染结果,此时需要完整的发送客户端内容到服务端,在服务端进行完整的渲染。

    从布玛的效果来看,获取DOM内容会涉及如下三个请求:

    请求1 用来判断该页面内容在服务端是否存在
    Request URL: https://in.hotjar.com/api/v1/sites/848493/pages/2338866123/content-id/34b2f50d09fbe08a4444e6691b1be779
    
    Request Method: GET
    Status Code: 200 
    
    //响应结果  
    {"exists": false}
    
    
    请求2 预检请求  没啥说的,应该都知道干啥的
    Request URL: https://in.hotjar.com/api/v1/sites/848493/url-hash/4f9e7b2f60ba35900e873ed12b1502ec/content
    Request Method: OPTIONS
    Status Code: 200 
    
    请求3 发送完整DOM内容
    Request URL: https://in.hotjar.com/api/v1/sites/848493/url-hash/4f9e7b2f60ba35900e873ed12b1502ec/content
    Request Method: POST
    Status Code: 200 
    
    Request Payload
    content: "{"docType":"<!DOCTYPE html>
    ","rootId":1,"childre" .......
    content_md5: "34b2f50d09fbe08a4444e6691b1be779"
    page_id: 2338866123
    page_url: "xxxxxxxxx.html"
    
    //响应结果
    {"page_content_id": 8784354270, "success": true}
    
    

    从请求3 中可以看到,content部分其实就是对完整html的json化,这部分内容比较长,只贴出部分内容。

    2、获取鼠标移动轨迹

    只是获取完整DOM内容只是第一步,在hotjar的录屏功能中,还有一个是获取鼠标运动轨迹,想要绘制运动轨迹,必然要知悉鼠标在时间轴上的位置信息,所以hotjar中,必然要采集鼠标在不同时间点的位置信息,这个可以通过其websocket 请求

    Request URL: wss://ws7.hotjar.com/api/v1/client/ws
    Request Method: GET
    Status Code: 101 Switching Protocols
    
    

    在ws 请求过程中,会有mouse-move数据包的发送,其基本结构如下:

    mouse_move: [{time: 106597, x: 215, y: 115}, {time: 106695, x: 181, y: 105}, {time: 106796, x: 134, y: 139},…]
    page_visit_id: 14777325238
    page_visit_key: "e9fa998e-5811-4d2f-81d2-bd296c7129af"
    

    其中可以看到mouse_move 数据结构中,包含了时间轴上不断变化的坐标值(x,y),有了基于时间轴的xy坐标,我们绘制内容就变的不那么复杂了。

    3、检测并发送DOM变化

    除了鼠标运行轨迹之外,用户在页面上的所有行为都会被完整的记录下来,页面的任何变化也都被记录了下来,如果需要在服务端完整的重新演化这种变化,那么需要把完整的变化结构发送到服务器,让服务端进行变化回溯,hotjar是通过ws中发送mutation发送这种结构包的,当然要发送这种结构包,首先要先观测DOM变化,这里也有一种简单的方式(暂时不确定hotjar的实现)HTML5 DOM4级MutatioObserver方法,可以检查页面中的DOM是否发生变化,大家可以做一下简单的测试:

    //选择目标观测节点
    let target = document.querySelector('目标节点选择器');
    
    // 创建观察者对象
    var observer = new window.MutationObserver(function(mutations) {
      mutations.forEach(function(mutation) {
        console.log(mutation);
      });    
    });
     
    // 观测项配置:
    var config = { attributes: true, childList: true }
     
    // 开始观测目标节点
    observer.observe(target, config);
    

    获取到变化的DOM结构(这种变化也是时序的变化,因为任何操作都可能导致变化,变化必然是有先后顺序的),然后通过ws发送到服务器,通过chrome network可以看到ws中mutation基本的包结构如下:

    mouse_move: [{time: 118994, x: 404, y: 135}]
    mutation: [{time: 118308,…}, {time: 118312,…}, {time: 118336, c: [{id: 7480,…}]}
    page_visit_id: 14777325238
    page_visit_key: "e9fa998e-5811-4d2f-81d2-bd296c7129af"
    

    里面包含了DOM节点变化,其中包含变化节点如何变化的(通过节点的所有attribute来应用)

    4、变化和轨迹回溯生成视频

    最后一切数据准备完毕,需要生成视频了,生成视频当然涉及很多的计算,因为要演化和回溯用户的所有操作,我猜可能的思路是这样的:

    1. 在服务器启动浏览器 并 启动录屏软件(录屏软件只是猜测可能有其它多种方式)
    2. 根据页面发送的完整DOM进行初始化内容展示
    3. 按照时序合并鼠标轨迹和mutation包数据
    4. 根据时间轴自动操作改变DOM
    5. 访次结束完成录制

    总结

    hotjar中还涉及到更多的细节实现,里面很多内容也并没有考虑,比如发送view_port report_content包等都没什么在文章中体现出来,但这些并不影响主线分析,另外因为只是简要分析,所以并不涉及实现细节,有兴趣的欢迎留言讨论。

  • 相关阅读:
    vim高级编辑(一)
    [每日一题] 11gOCP 1z0-052 :2013-09-5 runInstaller oracle of no swap
    ABAP 中 Table Control例子
    跟我一起学习ASP.NET 4.5 MVC4.0(四)
    跟我一起学习ASP.NET 4.5 MVC4.0(三)
    跟我一起学习ASP.NET 4.5 MVC4.0(二)
    跟我一起学习ASP.NET 4.5 MVC4.0(一)
    如何选择Html.RenderPartial和Html.RenderAction
    ASP.NET MVC4 Razor
    ADO.NET Entity Framework -Code Fisrt 开篇(一)
  • 原文地址:https://www.cnblogs.com/Johnzhang/p/9767304.html
Copyright © 2011-2022 走看看