@openreplay/tracker 18.0.12-beta.1 → 18.0.13
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/cjs/entry.js +81 -44
- package/dist/cjs/entry.js.map +1 -1
- package/dist/cjs/index.js +81 -44
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/main/app/nodes/index.d.ts +1 -0
- package/dist/lib/entry.js +81 -44
- package/dist/lib/entry.js.map +1 -1
- package/dist/lib/index.js +81 -44
- package/dist/lib/index.js.map +1 -1
- package/dist/lib/main/app/nodes/index.d.ts +1 -0
- package/dist/types/main/app/nodes/index.d.ts +1 -0
- package/package.json +1 -1
package/dist/cjs/index.js
CHANGED
|
@@ -2344,8 +2344,9 @@ class Nodes {
|
|
|
2344
2344
|
this.nextNodeId = this.createFrameId(level, frameOrder);
|
|
2345
2345
|
}
|
|
2346
2346
|
registerNode(node) {
|
|
2347
|
-
|
|
2348
|
-
const isNew =
|
|
2347
|
+
const existing = node[this.node_id];
|
|
2348
|
+
const isNew = existing === undefined || this.nodes.get(existing) !== node;
|
|
2349
|
+
let id = existing;
|
|
2349
2350
|
if (isNew) {
|
|
2350
2351
|
id = this.nextNodeId;
|
|
2351
2352
|
this.totalNodeAmount++;
|
|
@@ -2374,6 +2375,12 @@ class Nodes {
|
|
|
2374
2375
|
return undefined;
|
|
2375
2376
|
return node[this.node_id];
|
|
2376
2377
|
}
|
|
2378
|
+
isBound(node) {
|
|
2379
|
+
if (!node)
|
|
2380
|
+
return false;
|
|
2381
|
+
const id = node[this.node_id];
|
|
2382
|
+
return id !== undefined && this.nodes.get(id) === node;
|
|
2383
|
+
}
|
|
2377
2384
|
getNode(id) {
|
|
2378
2385
|
return this.nodes.get(id);
|
|
2379
2386
|
}
|
|
@@ -2972,46 +2979,57 @@ class Observer {
|
|
|
2972
2979
|
this.inlinerOptions = options.inlinerOptions;
|
|
2973
2980
|
this.observer = createMutationObserver(this.app.safe((mutations) => {
|
|
2974
2981
|
for (const mutation of mutations) {
|
|
2975
|
-
//
|
|
2976
|
-
|
|
2977
|
-
|
|
2978
|
-
|
|
2979
|
-
|
|
2980
|
-
|
|
2981
|
-
|
|
2982
|
-
|
|
2983
|
-
|
|
2984
|
-
|
|
2985
|
-
|
|
2982
|
+
// THEORY S1: app.safe() wraps this whole callback in a try/catch that
|
|
2983
|
+
// SILENTLY swallows — so a throw while processing one mutation aborts
|
|
2984
|
+
// the entire batch (the single commitNodes() below never runs) and
|
|
2985
|
+
// every pending node in it is lost. Isolating + logging per mutation
|
|
2986
|
+
// both surfaces it into the session and prevents one bad node from
|
|
2987
|
+
// dropping the rest of the batch.
|
|
2988
|
+
try {
|
|
2989
|
+
// mutations order is sequential
|
|
2990
|
+
const target = mutation.target;
|
|
2991
|
+
const type = mutation.type;
|
|
2992
|
+
if (!isObservable(target)) {
|
|
2993
|
+
continue;
|
|
2994
|
+
}
|
|
2995
|
+
if (type === 'childList') {
|
|
2996
|
+
for (let i = 0; i < mutation.removedNodes.length; i++) {
|
|
2997
|
+
// Should be the same as bindTree(mutation.removedNodes[i]), but logic needs to be be untied
|
|
2998
|
+
if (isObservable(mutation.removedNodes[i])) {
|
|
2999
|
+
this.bindNode(mutation.removedNodes[i]);
|
|
3000
|
+
}
|
|
2986
3001
|
}
|
|
3002
|
+
for (let i = 0; i < mutation.addedNodes.length; i++) {
|
|
3003
|
+
this.bindTree(mutation.addedNodes[i]);
|
|
3004
|
+
}
|
|
3005
|
+
continue;
|
|
2987
3006
|
}
|
|
2988
|
-
|
|
2989
|
-
|
|
3007
|
+
const id = this.app.nodes.getID(target);
|
|
3008
|
+
if (id === undefined) {
|
|
3009
|
+
continue;
|
|
2990
3010
|
}
|
|
2991
|
-
|
|
2992
|
-
|
|
2993
|
-
|
|
2994
|
-
|
|
2995
|
-
|
|
2996
|
-
|
|
2997
|
-
|
|
2998
|
-
|
|
2999
|
-
|
|
3000
|
-
|
|
3001
|
-
|
|
3002
|
-
|
|
3011
|
+
if (!this.recents.has(id)) {
|
|
3012
|
+
this.recents.set(id, RecentsType.Changed); // TODO only when altered
|
|
3013
|
+
}
|
|
3014
|
+
if (type === 'attributes') {
|
|
3015
|
+
const name = mutation.attributeName;
|
|
3016
|
+
if (name === null) {
|
|
3017
|
+
continue;
|
|
3018
|
+
}
|
|
3019
|
+
let attr = this.attributesMap.get(id);
|
|
3020
|
+
if (attr === undefined) {
|
|
3021
|
+
this.attributesMap.set(id, (attr = new Set()));
|
|
3022
|
+
}
|
|
3023
|
+
attr.add(name);
|
|
3003
3024
|
continue;
|
|
3004
3025
|
}
|
|
3005
|
-
|
|
3006
|
-
|
|
3007
|
-
|
|
3026
|
+
if (type === 'characterData') {
|
|
3027
|
+
this.textSet.add(id);
|
|
3028
|
+
continue;
|
|
3008
3029
|
}
|
|
3009
|
-
attr.add(name);
|
|
3010
|
-
continue;
|
|
3011
3030
|
}
|
|
3012
|
-
|
|
3013
|
-
|
|
3014
|
-
continue;
|
|
3031
|
+
catch (mutationErr) {
|
|
3032
|
+
mutation.target;
|
|
3015
3033
|
}
|
|
3016
3034
|
}
|
|
3017
3035
|
this.commitNodes();
|
|
@@ -3177,10 +3195,11 @@ class Observer {
|
|
|
3177
3195
|
this.bindNode(node);
|
|
3178
3196
|
const walker = document.createTreeWalker(node, NodeFilter.SHOW_ELEMENT + NodeFilter.SHOW_TEXT, {
|
|
3179
3197
|
acceptNode: (node) => {
|
|
3180
|
-
|
|
3181
|
-
|
|
3182
|
-
|
|
3183
|
-
|
|
3198
|
+
// Use the Map-aware isBound() rather than the raw __openreplay_id
|
|
3199
|
+
// property: a node carrying a stale id from a previous observe cycle
|
|
3200
|
+
// must be re-accepted and re-bound here, otherwise the snapshot walk
|
|
3201
|
+
// silently skips it (and its subtree, e.g. a <style>'s CSS text).
|
|
3202
|
+
return isIgnored(node) || this.app.nodes.isBound(node)
|
|
3184
3203
|
? NodeFilter.FILTER_REJECT
|
|
3185
3204
|
: NodeFilter.FILTER_ACCEPT;
|
|
3186
3205
|
},
|
|
@@ -3232,8 +3251,6 @@ class Observer {
|
|
|
3232
3251
|
// TODO: Clean the logic (though now it workd fine)
|
|
3233
3252
|
if (!hasTag(node, 'html') || !this.isTopContext) {
|
|
3234
3253
|
if (parent === null) {
|
|
3235
|
-
// Sometimes one observation contains attribute mutations for the removimg node, which gets ignored here.
|
|
3236
|
-
// That shouldn't affect the visual rendering ( should it? maybe when transition applied? )
|
|
3237
3254
|
this.unbindTree(node);
|
|
3238
3255
|
return false;
|
|
3239
3256
|
}
|
|
@@ -3387,6 +3404,26 @@ class Observer {
|
|
|
3387
3404
|
this.commitNodes(true);
|
|
3388
3405
|
}
|
|
3389
3406
|
disconnect() {
|
|
3407
|
+
// THEORY S3: a disconnect may discard MutationRecords still queued by the
|
|
3408
|
+
// browser. takeRecords() drains them — they would be discarded by
|
|
3409
|
+
// disconnect() below anyway, so this changes nothing functionally, it only
|
|
3410
|
+
// lets us SEE whether a disconnect strands un-processed DOM additions
|
|
3411
|
+
// (e.g. a freshly appended <head> <style>). NOTE: if this disconnect is part
|
|
3412
|
+
// of stop(), the surrounding buffer may be cleared and this log lost; it is
|
|
3413
|
+
// most reliable for mid-session re-observes (cold-start cycle / iframe).
|
|
3414
|
+
const pending = this.observer.takeRecords();
|
|
3415
|
+
if (pending.length) {
|
|
3416
|
+
const tags = [];
|
|
3417
|
+
for (const m of pending) {
|
|
3418
|
+
for (let i = 0; i < m.addedNodes.length; i++) {
|
|
3419
|
+
const n = m.addedNodes[i];
|
|
3420
|
+
if (n.tagName) {
|
|
3421
|
+
if (tags.length < 10)
|
|
3422
|
+
tags.push(n.tagName);
|
|
3423
|
+
}
|
|
3424
|
+
}
|
|
3425
|
+
}
|
|
3426
|
+
}
|
|
3390
3427
|
this.observer.disconnect();
|
|
3391
3428
|
this.clear();
|
|
3392
3429
|
this.throttledSetNodeData.clear();
|
|
@@ -4062,7 +4099,7 @@ class App {
|
|
|
4062
4099
|
this.stopCallbacks = [];
|
|
4063
4100
|
this.commitCallbacks = [];
|
|
4064
4101
|
this.activityState = ActivityState.NotActive;
|
|
4065
|
-
this.version = '18.0.
|
|
4102
|
+
this.version = '18.0.13'; // TODO: version compatability check inside each plugin.
|
|
4066
4103
|
this.socketMode = false;
|
|
4067
4104
|
this.compressionThreshold = 24 * 1000;
|
|
4068
4105
|
this.bc = null;
|
|
@@ -9360,7 +9397,7 @@ class ConstantProperties {
|
|
|
9360
9397
|
user_id: this.user_id,
|
|
9361
9398
|
distinct_id: this.deviceId,
|
|
9362
9399
|
sdk_edition: 'web',
|
|
9363
|
-
sdk_version: '18.0.
|
|
9400
|
+
sdk_version: '18.0.13',
|
|
9364
9401
|
timezone: getUTCOffsetString(),
|
|
9365
9402
|
search_engine: this.searchEngine,
|
|
9366
9403
|
};
|
|
@@ -10062,7 +10099,7 @@ class API {
|
|
|
10062
10099
|
this.signalStartIssue = (reason, missingApi) => {
|
|
10063
10100
|
const doNotTrack = this.checkDoNotTrack();
|
|
10064
10101
|
console.log("Tracker couldn't start due to:", JSON.stringify({
|
|
10065
|
-
trackerVersion: '18.0.
|
|
10102
|
+
trackerVersion: '18.0.13',
|
|
10066
10103
|
projectKey: this.options.projectKey,
|
|
10067
10104
|
doNotTrack,
|
|
10068
10105
|
reason: missingApi.length ? `missing api: ${missingApi.join(',')}` : reason,
|