偷偷摘套内射激情视频,久久精品99国产国产精,中文字幕无线乱码人妻,中文在线中文a,性爽19p

前端如何靜悄悄錄制用戶的操作過程,靜悄悄上傳到服務(wù)器

開發(fā) 項目管理
公司有很多的項目,但是并不是每一個項目都很重要,其實重要的項目就那么幾個,上面也是很重視這幾個項目,尤其是對一些生產(chǎn)問題的關(guān)注度很高。

背景

公司有很多的項目,但是并不是每一個項目都很重要,其實重要的項目就那么幾個,上面也是很重視這幾個項目,尤其是對一些生產(chǎn)問題的關(guān)注度很高。

這幾天上面交代下來了,需要對這些項目做一些用戶行為的記錄,主要是為了更好地還原用戶在某一個時間點的操作過程

圖片

注意點

想要完成這個需求,仔細想了一下,需要注意幾個點:

  • 跨框架使用:這些項目有vue、angular、react,需要都能適用
  • 能錄制用戶行為:能把用戶在頁面上的操作錄制下來
  • 能回放錄制:如果不能回放,那么這個錄制就無意義了
  • 用戶無感知:必須做到用戶無感知才行

思考 & 技術(shù)方案

說到前端視頻的錄制,我們會想到 webRTC 這個技術(shù),他能做到錄制屏幕的效果,但是通過 webRTC 去完成這個方案的話,有幾個缺點:

  • 做不到用戶無感知,需要用戶同意才能錄制
  • 錄制的視頻太大了,太占內(nèi)存了
  • 學(xué)習(xí)成本比較高,這也是原因之一

那怎么才能做到:

  • 用戶無感知
  • 不錄制視頻

其實只要不錄制視頻了,那么用戶肯定就無感知,因為一旦要錄視頻,瀏覽器肯定要詢問用戶同意不同意。

所以我們選擇了另一個方案 rrweb,一個用來錄制用戶頁面行為的庫~

rrweb

rrweb 是 record and replay the web 的簡寫,旨在利用現(xiàn)代瀏覽器所提供的強大 API 錄制并回放任意 web 界面中的用戶操作。

效果展示

圖片

基本使用

我們先定義好 html 結(jié)構(gòu),三個按鈕

  • 錄制:點擊開始錄制
  • 回放:點擊開始回放
  • 返回:點擊重新再來

還有一個 replayer ,用來當(dāng)做回放的容器

<template>
  <div class="main">
    <div >
      <el-button @click="record">錄制</el-button>
      <el-button @click="replay">回放</el-button>
      <el-button @click="reset">返回</el-button>
    </div>
    <div v-if="!showReplay">
      <div>
        <el-input style="width: 300px" v-model="value" />
      </div>
      <div>
        <el-button>按鈕1</el-button>
      </div>
      <div>
        <el-button>按鈕2</el-button>
      </div>
      <div>
        <el-button>按鈕3</el-button>
      </div>
    </div>
    <div ref="replayer"></div>
  </div>
</template>

我們需要先安裝兩個包:npm i rrweb rrwebPlayer

  • rrweb:用來錄制網(wǎng)頁的
  • rrwebPlayer:用來回放的

rrweb擁有一個 record 函數(shù)來進行錄制操作,并可傳入配置,emit屬性就是用戶操作的監(jiān)聽函數(shù),接收一個參數(shù)event,這個參數(shù)是什么,我們后面會說~

然后我們定義三個函數(shù):

  • record:錄制函數(shù)
  • replay:回放函數(shù)
  • reset:返回/重置函數(shù)
const rrweb = require("rrweb");
import rrwebPlayer from "rrweb-player";

const events = ref([]);
const stopFn = ref(null);
const showReplay = ref(false);
const replayer = ref(null)

const record = () => {
  console.log("開始錄制");
  stopFn.value = rrweb.record({
    emit: (event) => {
      events.value.push(event);
    },
    // 支持錄制canvas
    recordCanvas: true,
    collectFonts: true,
  });
};
const replay = () => {
  stopFn.value();
  showReplay.value = true;
  new rrwebPlayer({
    // 可以自定義 DOM 元素
    target: replayer.value,
    // 配置項
    props: {
      // 傳入events
      events: events.value,
    },
  });
};
const reset = () => {
  showReplay.value = false;
  events.value = []
};

錄的是視頻嗎?

我們之前說了:一旦要錄視頻,瀏覽器肯定要詢問用戶同意不同意。但是我們發(fā)現(xiàn)我們使用 rrweb 去錄制,瀏覽器并沒有詢問,做到了無感知~所以我們可以推斷出,rrweb 錄制的并不是視頻,那錄制的是什么呢?

我們其實可以試著去輸出一下剛剛的參數(shù) event 看看是什么

rrweb.record({
    emit: (event) => {
        // 輸出
+      console.log(event)
      events.value.push(event);
    },
});

圖片

我們可以看到這個event記錄的東西是當(dāng)前頁面的DOM結(jié)構(gòu),當(dāng)用戶操作頁面時,rrweb會將每一次的DOM結(jié)構(gòu)轉(zhuǎn)換成對象形式,通過 emit 函數(shù)的第一個參數(shù)輸出,我們使用一個數(shù)組去記錄這一次次的DOM結(jié)構(gòu),然后把它傳給rrweb-player,它能將這些DOM結(jié)構(gòu)按照先后順序,一個一個展示出來,自然就相當(dāng)于是視頻的展示效果了~

圖片

rrweb能記錄這些頁面的 DOM 行為:

  • 節(jié)點創(chuàng)建、銷毀
  • 節(jié)點屬性變化
  • 文本變化
  • 鼠標(biāo)移動
  • 鼠標(biāo)交互
  • 頁面或元素滾動
  • 視窗大小改變
  • 輸入

上傳 & 優(yōu)化

我們記錄的這些數(shù)據(jù),需要上傳到后端那邊去,方便后續(xù)在后臺管理系統(tǒng)里管理這些回放~

很多人會說這樣一直錄制,那豈不是數(shù)據(jù)量很大?所以我覺得只有在一些重要的頁面,才需要做錄制行為的操作,而不是每一個頁面都去做這樣的操作~

并且每次上傳需要一定的時間間隔,不能上傳太頻繁,不然瀏覽器壓力會增大~

const record = () => {
  console.log("開始錄制");
  stopFn.value = rrweb.record({
    emit: (event) => {
      events.value.push(event);
    },
    recordCanvas: true,
    collectFonts: true,
  });
};

const report = async () => {
  await reportRequest(events.value);
  events.value = [];
}

// 20s 去上傳一次
setInterval(report, 10 * 2000);

同時,雖然現(xiàn)在上傳的是DOM結(jié)構(gòu)的對象,大小遠遠比視頻小,但是其實還是不小的

圖片

所以我們需要采取措施,去壓縮一下數(shù)據(jù),壓縮后再進行上傳,這樣能降低服務(wù)器的壓力~我們可以使用packFn屬性來對錄制的數(shù)據(jù)進行壓縮,同時回放時也要用unpackFn去解碼

const record = () => {
  console.log("開始錄制");
  stopFn.value = rrweb.record({
    emit: (event) => {
      events.value.push(event);
    },
    recordCanvas: true,
    collectFonts: true,
+    packFn: rrweb.pack
  });
};

const replay = () => {
  stopFn.value();
  showReplay.value = true;
  new rrwebPlayer({
    // 可以自定義 DOM 元素
    target: replayer.value,
    // 配置項
    props: {
      // 傳入events
      events: events.value,
+      unpackFn: rrweb.unpack,
    },
  });
};

圖片

責(zé)任編輯:武曉燕 來源: 前端之神
相關(guān)推薦

2012-05-14 11:01:50

搜索引擎微軟

2013-08-14 10:03:56

微信支付

2024-09-09 11:14:31

降噪技術(shù)AR技術(shù)VR

2011-02-24 14:23:18

2009-12-11 17:29:22

Linux桌面

2009-12-29 10:44:19

2009-08-25 15:48:03

C#數(shù)組操作

2010-01-06 11:30:22

.NET Framew

2014-07-22 10:36:52

惡意程序小米手機

2015-06-19 14:07:53

免費WiFi北京

2010-05-27 15:11:44

MySQL保存

2010-05-17 13:28:15

MySQL 復(fù)制

2009-01-15 09:25:00

2010-03-30 12:50:42

Oracle存儲

2010-06-30 12:39:11

2025-03-24 07:15:00

WebWorkerWeb瀏覽器

2010-04-14 13:18:53

安裝無線適配器

2009-12-16 17:11:10

Fedora 掛載

2010-04-26 00:42:08

DNS負(fù)載均衡

2019-01-09 09:52:30

互聯(lián)網(wǎng)馬云馬化騰
點贊
收藏

51CTO技術(shù)棧公眾號