我正在嘗試為網(wǎng)站建立使用者重播會話功能,並且我正在使用 rrweb 庫來做到這一點。
這個庫的作用是在記錄時:它捕獲網(wǎng)頁中的所有事件,我可以通過將它們存儲在array
中來保存這些事件,當我想重播會話時,我只需將array
傳遞給重播函數(shù),該函數(shù)處理會話重播。
目前出於測試目的,我將此數(shù)組保存在我的sessionStorage
中,每次發(fā)出新事件時,我都會獲取array
然後將該新事件推送到其中,然後再次將sessionStorage
保存在我的sessionStorage
中,如下所示:< /p>
rrweb.record({ emit(event) { const sessions = JSON.parse(sessionStorage.getItem('sessions')) || []; sessions.push(event); sessionStorage.setItem('sessions', JSON.stringify(sessions)); }, });
但是,對於生產(chǎn),我不想將該數(shù)組保存在我的sessionStorage
中,然後在每次發(fā)出新事件時更新它,而是將該array
保存在在我的資料庫中,並且我想調(diào)用保存array
的函數(shù)當用戶 退出
或用戶決定關(guān)閉網(wǎng)站時(例如按X
按鈕),一次到我的資料庫.
第一部分- 當使用者logs out
- 非常簡單,我只需在logout
按鈕上新增一個eventListener
,這是第二部分- 當用戶決定關(guān)閉網(wǎng)站時- 這讓我有些頭痛.
我知道有beforeUnload
事件,但是經(jīng)過快速搜尋後,我清楚地意識到它是不可靠的,所以基本上我正在尋找的是一種可靠的方法來確定用戶何時關(guān)閉我的網(wǎng)站,以便我可以觸發(fā)async函數(shù)
會將array
儲存到我的資料庫中。
以下是我對如何減輕 beforeunload
事件的不可靠性的想法:
sessions
陣列中的目前條目數(shù)。假設我們正在討論您希望重播的單一頁面,則可以將此計數(shù)儲存為 JavaScript 變數(shù) eventCount
。更好的是從伺服器端表中獲取計數(shù),以防由於某種原因上次關(guān)閉頁面時未能成功保存所有記錄的事件。 N
秒呼叫一次函數(shù) checkEvents
(您必須決定呼叫此函數(shù)的頻率)setInterval
方法。此函數(shù)將查看目前事件計數(shù)(變數(shù)newCount
),如果大於目前eventCount
值,則Navigator sendBeacon
方法可用於向伺服器發(fā)送請求,傳遞所有自上次呼叫以來新增的事件(即JSON.stringify(sessions.slice(eventCount, newCount))
,並且當請求完成時分配eventCount = newCount
if newCount
為> eventCount
。請注意,當非同步sendBeacon
請求運行時,可能會產(chǎn)生新事件,這就是我們更新事件計數(shù)的原因使用newCount
而不是sessions
陣列的目前大小。beforeunload
和unload
事件不可靠,因此我們使用visibiltychanged
事件(如果瀏覽器支援),當新的可見性狀態(tài)為「隱藏」時,我們會更新伺服器。該文件討論了導致觸發(fā)此事件的使用者操作(不僅僅是在關(guān)閉頁面時)。但是,如果瀏覽器不支援此事件,則 pagehide 事件。 Navigator.sendBeacon
方法的文檔中沒有討論是否可以有多個並發(fā)請求。假設可能存在(這是一個非同步呼叫),則在 sendBeacon
請求目前正在進行時,由於 setInterval 的原因,使用者可能會決定離開頁面或關(guān)閉頁面。調(diào)用。然後,您發(fā)布此請求的伺服器 URL 可能應該在執(zhí)行插入時鎖定表,以便對該 URL 的任何後續(xù) POST 都會阻塞,直到前一個完成。如果您的表使用某種序號作為主鍵,我建議的另一個解決方案是將傳遞的第一個事件的起始數(shù)組索引傳遞給伺服器,並且伺服器將使用它來明確設定每個事件的序列號插入事件。然後可以運行並發(fā)更新,而不必鎖定整個表。