@neroom/nevision 0.1.6 → 0.1.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -124,7 +124,6 @@ function NevisionRecorder({
124
124
  const stopFnRef = (0, import_react.useRef)(null);
125
125
  const chunkIndexRef = (0, import_react.useRef)(0);
126
126
  const eventStoreRef = (0, import_react.useRef)(null);
127
- const initializedRef = (0, import_react.useRef)(false);
128
127
  const onStartRef = (0, import_react.useRef)(onStart);
129
128
  const onErrorRef = (0, import_react.useRef)(onError);
130
129
  const samplingRef = (0, import_react.useRef)(sampling);
@@ -134,16 +133,16 @@ function NevisionRecorder({
134
133
  samplingRef.current = sampling;
135
134
  privacyRef.current = privacy;
136
135
  (0, import_react.useEffect)(() => {
137
- if (initializedRef.current) {
138
- return;
139
- }
140
- initializedRef.current = true;
136
+ let isActive = true;
141
137
  let intervalId;
138
+ let sessionStartTime = 0;
142
139
  const init = async () => {
143
140
  try {
144
141
  eventStoreRef.current = new EventStore();
145
142
  await retrySendPendingChunks(apiUrl);
143
+ if (!isActive) return;
146
144
  const { record } = await import("rrweb");
145
+ if (!isActive) return;
147
146
  const startResponse = await fetch(`${apiUrl}/public/recordings/start`, {
148
147
  method: "POST",
149
148
  headers: {
@@ -164,8 +163,10 @@ function NevisionRecorder({
164
163
  if (!startResponse.ok) {
165
164
  throw new Error(`Failed to start recording: ${startResponse.status}`);
166
165
  }
166
+ if (!isActive) return;
167
167
  const { sessionId } = await startResponse.json();
168
168
  sessionIdRef.current = sessionId;
169
+ sessionStartTime = Date.now();
169
170
  onStartRef.current?.(sessionId);
170
171
  const currentSampling = samplingRef.current;
171
172
  const currentPrivacy = privacyRef.current;
@@ -324,22 +325,27 @@ function NevisionRecorder({
324
325
  }
325
326
  };
326
327
  const endSession = (url, sessionId) => {
328
+ const durationMs = sessionStartTime > 0 ? Date.now() - sessionStartTime : 0;
327
329
  navigator.sendBeacon?.(
328
330
  `${url}/public/recordings/end`,
329
331
  new Blob(
330
- [JSON.stringify({ sessionId, siteId, apiKey })],
332
+ [JSON.stringify({ sessionId, durationMs })],
331
333
  { type: "application/json" }
332
334
  )
333
335
  );
334
336
  };
335
337
  init();
336
338
  return () => {
339
+ isActive = false;
337
340
  clearInterval(intervalId);
338
341
  stopFnRef.current?.();
339
342
  if (sessionIdRef.current) {
340
343
  sendChunk(apiUrl, sessionIdRef.current, true);
341
344
  endSession(apiUrl, sessionIdRef.current);
342
345
  }
346
+ sessionIdRef.current = null;
347
+ chunkIndexRef.current = 0;
348
+ eventsBufferRef.current = [];
343
349
  };
344
350
  }, [siteId, apiKey, apiUrl]);
345
351
  return null;
package/dist/index.mjs CHANGED
@@ -90,7 +90,6 @@ function NevisionRecorder({
90
90
  const stopFnRef = useRef(null);
91
91
  const chunkIndexRef = useRef(0);
92
92
  const eventStoreRef = useRef(null);
93
- const initializedRef = useRef(false);
94
93
  const onStartRef = useRef(onStart);
95
94
  const onErrorRef = useRef(onError);
96
95
  const samplingRef = useRef(sampling);
@@ -100,16 +99,16 @@ function NevisionRecorder({
100
99
  samplingRef.current = sampling;
101
100
  privacyRef.current = privacy;
102
101
  useEffect(() => {
103
- if (initializedRef.current) {
104
- return;
105
- }
106
- initializedRef.current = true;
102
+ let isActive = true;
107
103
  let intervalId;
104
+ let sessionStartTime = 0;
108
105
  const init = async () => {
109
106
  try {
110
107
  eventStoreRef.current = new EventStore();
111
108
  await retrySendPendingChunks(apiUrl);
109
+ if (!isActive) return;
112
110
  const { record } = await import("rrweb");
111
+ if (!isActive) return;
113
112
  const startResponse = await fetch(`${apiUrl}/public/recordings/start`, {
114
113
  method: "POST",
115
114
  headers: {
@@ -130,8 +129,10 @@ function NevisionRecorder({
130
129
  if (!startResponse.ok) {
131
130
  throw new Error(`Failed to start recording: ${startResponse.status}`);
132
131
  }
132
+ if (!isActive) return;
133
133
  const { sessionId } = await startResponse.json();
134
134
  sessionIdRef.current = sessionId;
135
+ sessionStartTime = Date.now();
135
136
  onStartRef.current?.(sessionId);
136
137
  const currentSampling = samplingRef.current;
137
138
  const currentPrivacy = privacyRef.current;
@@ -290,22 +291,27 @@ function NevisionRecorder({
290
291
  }
291
292
  };
292
293
  const endSession = (url, sessionId) => {
294
+ const durationMs = sessionStartTime > 0 ? Date.now() - sessionStartTime : 0;
293
295
  navigator.sendBeacon?.(
294
296
  `${url}/public/recordings/end`,
295
297
  new Blob(
296
- [JSON.stringify({ sessionId, siteId, apiKey })],
298
+ [JSON.stringify({ sessionId, durationMs })],
297
299
  { type: "application/json" }
298
300
  )
299
301
  );
300
302
  };
301
303
  init();
302
304
  return () => {
305
+ isActive = false;
303
306
  clearInterval(intervalId);
304
307
  stopFnRef.current?.();
305
308
  if (sessionIdRef.current) {
306
309
  sendChunk(apiUrl, sessionIdRef.current, true);
307
310
  endSession(apiUrl, sessionIdRef.current);
308
311
  }
312
+ sessionIdRef.current = null;
313
+ chunkIndexRef.current = 0;
314
+ eventsBufferRef.current = [];
309
315
  };
310
316
  }, [siteId, apiKey, apiUrl]);
311
317
  return null;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@neroom/nevision",
3
- "version": "0.1.6",
3
+ "version": "0.1.7",
4
4
  "description": "React SDK for NEROOM/NEVISION session recording",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",