@openreplay/tracker 3.6.0-beta.0 → 3.6.2

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.
Files changed (126) hide show
  1. package/cjs/app/guards.d.ts +1 -2
  2. package/cjs/app/guards.js +3 -6
  3. package/cjs/app/index.d.ts +22 -24
  4. package/cjs/app/index.js +84 -85
  5. package/cjs/app/logger.js +3 -6
  6. package/cjs/app/nodes.js +0 -2
  7. package/cjs/app/observer/iframe_observer.d.ts +1 -1
  8. package/cjs/app/observer/iframe_observer.js +3 -3
  9. package/cjs/app/observer/observer.d.ts +3 -2
  10. package/cjs/app/observer/observer.js +52 -50
  11. package/cjs/app/observer/shadow_root_observer.d.ts +1 -1
  12. package/cjs/app/observer/shadow_root_observer.js +3 -3
  13. package/cjs/app/observer/top_observer.d.ts +2 -11
  14. package/cjs/app/observer/top_observer.js +23 -52
  15. package/cjs/app/sanitizer.d.ts +1 -1
  16. package/cjs/app/sanitizer.js +5 -5
  17. package/cjs/app/session.d.ts +2 -18
  18. package/cjs/app/session.js +6 -55
  19. package/cjs/app/ticker.d.ts +1 -1
  20. package/cjs/common/messages.d.ts +444 -0
  21. package/cjs/common/messages.js +794 -0
  22. package/cjs/common/types.d.ts +9 -0
  23. package/cjs/common/{interaction.js → types.js} +0 -0
  24. package/cjs/common/{interaction.d.ts → webworker.d.ts} +5 -5
  25. package/cjs/common/webworker.js +2 -0
  26. package/cjs/index.d.ts +10 -10
  27. package/cjs/index.js +37 -42
  28. package/cjs/modules/connection.d.ts +1 -1
  29. package/cjs/modules/connection.js +2 -2
  30. package/cjs/modules/console.d.ts +1 -1
  31. package/cjs/modules/console.js +21 -7
  32. package/cjs/modules/cssrules.d.ts +1 -1
  33. package/cjs/modules/cssrules.js +14 -18
  34. package/cjs/modules/exception.d.ts +3 -3
  35. package/cjs/modules/exception.js +20 -25
  36. package/cjs/modules/img.d.ts +1 -1
  37. package/cjs/modules/img.js +26 -39
  38. package/cjs/modules/input.d.ts +1 -1
  39. package/cjs/modules/input.js +21 -21
  40. package/cjs/modules/longtasks.d.ts +2 -0
  41. package/cjs/modules/longtasks.js +26 -0
  42. package/cjs/modules/mouse.d.ts +1 -1
  43. package/cjs/modules/mouse.js +43 -50
  44. package/cjs/modules/performance.d.ts +1 -1
  45. package/cjs/modules/performance.js +2 -2
  46. package/cjs/modules/scroll.d.ts +1 -1
  47. package/cjs/modules/scroll.js +7 -16
  48. package/cjs/modules/timing.d.ts +1 -1
  49. package/cjs/modules/timing.js +26 -14
  50. package/cjs/modules/viewport.d.ts +1 -1
  51. package/cjs/modules/viewport.js +4 -4
  52. package/cjs/utils.js +7 -7
  53. package/cjs/vendors/finder/finder.js +48 -53
  54. package/lib/app/guards.d.ts +1 -2
  55. package/lib/app/guards.js +2 -4
  56. package/lib/app/index.d.ts +22 -24
  57. package/lib/app/index.js +92 -93
  58. package/lib/app/logger.js +3 -6
  59. package/lib/app/nodes.js +0 -2
  60. package/lib/app/observer/iframe_observer.d.ts +1 -1
  61. package/lib/app/observer/iframe_observer.js +3 -3
  62. package/lib/app/observer/observer.d.ts +3 -2
  63. package/lib/app/observer/observer.js +53 -51
  64. package/lib/app/observer/shadow_root_observer.d.ts +1 -1
  65. package/lib/app/observer/shadow_root_observer.js +3 -3
  66. package/lib/app/observer/top_observer.d.ts +2 -11
  67. package/lib/app/observer/top_observer.js +27 -56
  68. package/lib/app/sanitizer.d.ts +1 -1
  69. package/lib/app/sanitizer.js +7 -7
  70. package/lib/app/session.d.ts +2 -18
  71. package/lib/app/session.js +6 -55
  72. package/lib/app/ticker.d.ts +1 -1
  73. package/lib/common/messages.d.ts +444 -0
  74. package/lib/common/messages.js +790 -0
  75. package/lib/common/tsconfig.tsbuildinfo +1 -1
  76. package/lib/common/types.d.ts +9 -0
  77. package/lib/common/{interaction.js → types.js} +0 -0
  78. package/lib/common/{interaction.d.ts → webworker.d.ts} +5 -5
  79. package/lib/common/webworker.js +1 -0
  80. package/lib/index.d.ts +10 -10
  81. package/lib/index.js +50 -55
  82. package/lib/modules/connection.d.ts +1 -1
  83. package/lib/modules/connection.js +2 -2
  84. package/lib/modules/console.d.ts +1 -1
  85. package/lib/modules/console.js +22 -8
  86. package/lib/modules/cssrules.d.ts +1 -1
  87. package/lib/modules/cssrules.js +15 -19
  88. package/lib/modules/exception.d.ts +3 -3
  89. package/lib/modules/exception.js +20 -25
  90. package/lib/modules/img.d.ts +1 -1
  91. package/lib/modules/img.js +28 -41
  92. package/lib/modules/input.d.ts +1 -1
  93. package/lib/modules/input.js +23 -23
  94. package/lib/modules/longtasks.d.ts +2 -0
  95. package/lib/modules/longtasks.js +23 -0
  96. package/lib/modules/mouse.d.ts +1 -1
  97. package/lib/modules/mouse.js +46 -53
  98. package/lib/modules/performance.d.ts +1 -1
  99. package/lib/modules/performance.js +3 -3
  100. package/lib/modules/scroll.d.ts +1 -1
  101. package/lib/modules/scroll.js +8 -17
  102. package/lib/modules/timing.d.ts +1 -1
  103. package/lib/modules/timing.js +28 -16
  104. package/lib/modules/viewport.d.ts +1 -1
  105. package/lib/modules/viewport.js +4 -4
  106. package/lib/utils.js +7 -7
  107. package/lib/vendors/finder/finder.js +48 -53
  108. package/package.json +10 -27
  109. package/.eslintignore +0 -8
  110. package/.prettierignore +0 -1
  111. package/cjs/app/messages.d.ts +0 -52
  112. package/cjs/app/messages.gen.d.ts +0 -57
  113. package/cjs/app/messages.gen.js +0 -494
  114. package/cjs/app/messages.js +0 -235
  115. package/cjs/common/messages.gen.d.ts +0 -382
  116. package/cjs/common/messages.gen.js +0 -62
  117. package/cjs/modules/adoptedStyleSheets.d.ts +0 -2
  118. package/cjs/modules/adoptedStyleSheets.js +0 -127
  119. package/lib/app/messages.d.ts +0 -52
  120. package/lib/app/messages.gen.d.ts +0 -57
  121. package/lib/app/messages.gen.js +0 -435
  122. package/lib/app/messages.js +0 -182
  123. package/lib/common/messages.gen.d.ts +0 -382
  124. package/lib/common/messages.gen.js +0 -59
  125. package/lib/modules/adoptedStyleSheets.d.ts +0 -2
  126. package/lib/modules/adoptedStyleSheets.js +0 -124
@@ -1,25 +1,24 @@
1
- import { JSException } from '../app/messages.gen.js';
1
+ import { JSException } from "../common/messages.js";
2
2
  import ErrorStackParser from 'error-stack-parser';
3
3
  function getDefaultStack(e) {
4
- return [
5
- {
4
+ return [{
6
5
  columnNumber: e.colno,
7
6
  lineNumber: e.lineno,
8
7
  fileName: e.filename,
9
- functionName: '',
10
- source: '',
11
- },
12
- ];
8
+ functionName: "",
9
+ source: "",
10
+ }];
13
11
  }
14
12
  export function getExceptionMessage(error, fallbackStack) {
15
13
  let stack = fallbackStack;
16
14
  try {
17
15
  stack = ErrorStackParser.parse(error);
18
16
  }
19
- catch (e) { }
20
- return JSException(error.name, error.message, JSON.stringify(stack));
17
+ catch (e) {
18
+ }
19
+ return new JSException(error.name, error.message, JSON.stringify(stack));
21
20
  }
22
- export function getExceptionMessageFromEvent(e, context = window) {
21
+ export function getExceptionMessageFromEvent(e) {
23
22
  if (e instanceof ErrorEvent) {
24
23
  if (e.error instanceof Error) {
25
24
  return getExceptionMessage(e.error, getDefaultStack(e));
@@ -30,10 +29,10 @@ export function getExceptionMessageFromEvent(e, context = window) {
30
29
  name = 'Error';
31
30
  message = e.message;
32
31
  }
33
- return JSException(name, message, JSON.stringify(getDefaultStack(e)));
32
+ return new JSException(name, message, JSON.stringify(getDefaultStack(e)));
34
33
  }
35
34
  }
36
- else if ('PromiseRejectionEvent' in context && e instanceof context.PromiseRejectionEvent) {
35
+ else if ('PromiseRejectionEvent' in window && e instanceof PromiseRejectionEvent) {
37
36
  if (e.reason instanceof Error) {
38
37
  return getExceptionMessage(e.reason, []);
39
38
  }
@@ -45,7 +44,7 @@ export function getExceptionMessageFromEvent(e, context = window) {
45
44
  catch (_) {
46
45
  message = String(e.reason);
47
46
  }
48
- return JSException('Unhandled Promise Rejection', message, '[]');
47
+ return new JSException('Unhandled Promise Rejection', message, '[]');
49
48
  }
50
49
  }
51
50
  return null;
@@ -55,17 +54,13 @@ export default function (app, opts) {
55
54
  captureExceptions: true,
56
55
  }, opts);
57
56
  if (options.captureExceptions) {
58
- function patchContext(context) {
59
- const handler = (e) => {
60
- const msg = getExceptionMessageFromEvent(e, context);
61
- if (msg != null) {
62
- app.send(msg);
63
- }
64
- };
65
- app.attachEventListener(context, 'unhandledrejection', handler);
66
- app.attachEventListener(context, 'error', handler);
67
- }
68
- app.observer.attachContextCallback(patchContext);
69
- patchContext(window);
57
+ const handler = (e) => {
58
+ const msg = getExceptionMessageFromEvent(e);
59
+ if (msg != null) {
60
+ app.send(msg);
61
+ }
62
+ };
63
+ app.attachEventListener(window, 'unhandledrejection', (e) => handler(e));
64
+ app.attachEventListener(window, 'error', (e) => handler(e));
70
65
  }
71
66
  }
@@ -1,2 +1,2 @@
1
- import type App from '../app/index.js';
1
+ import type App from "../app/index.js";
2
2
  export default function (app: App): void;
@@ -1,6 +1,6 @@
1
- import { timestamp, isURL } from '../utils.js';
2
- import { ResourceTiming, SetNodeAttributeURLBased, SetNodeAttribute } from '../app/messages.gen.js';
3
- import { hasTag } from '../app/guards.js';
1
+ import { timestamp, isURL } from "../utils.js";
2
+ import { ResourceTiming, SetNodeAttributeURLBased, SetNodeAttribute } from "../common/messages.js";
3
+ import { hasTag } from "../app/guards.js";
4
4
  function resolveURL(url, location = document.location) {
5
5
  url = url.trim();
6
6
  if (url.startsWith('/')) {
@@ -16,34 +16,19 @@ function resolveURL(url, location = document.location) {
16
16
  return location.origin + location.pathname + url;
17
17
  }
18
18
  }
19
- const PLACEHOLDER_SRC = 'https://static.openreplay.com/tracker/placeholder.jpeg';
19
+ const PLACEHOLDER_SRC = "https://static.openreplay.com/tracker/placeholder.jpeg";
20
20
  export default function (app) {
21
21
  function sendPlaceholder(id, node) {
22
- app.send(SetNodeAttribute(id, 'src', PLACEHOLDER_SRC));
22
+ app.send(new SetNodeAttribute(id, "src", PLACEHOLDER_SRC));
23
23
  const { width, height } = node.getBoundingClientRect();
24
- if (!node.hasAttribute('width')) {
25
- app.send(SetNodeAttribute(id, 'width', String(width)));
24
+ if (!node.hasAttribute("width")) {
25
+ app.send(new SetNodeAttribute(id, "width", String(width)));
26
26
  }
27
- if (!node.hasAttribute('height')) {
28
- app.send(SetNodeAttribute(id, 'height', String(height)));
27
+ if (!node.hasAttribute("height")) {
28
+ app.send(new SetNodeAttribute(id, "height", String(height)));
29
29
  }
30
30
  }
31
- const sendSrcset = function (id, img) {
32
- const { srcset } = img;
33
- if (!srcset) {
34
- return;
35
- }
36
- const resolvedSrcset = srcset
37
- .split(',')
38
- .map((str) => resolveURL(str))
39
- .join(',');
40
- app.send(SetNodeAttribute(id, 'srcset', resolvedSrcset));
41
- };
42
- const sendSrc = function (id, img) {
43
- const src = img.src;
44
- app.send(SetNodeAttributeURLBased(id, 'src', src, app.getBaseHref()));
45
- };
46
- const sendImgAttrs = app.safe(function () {
31
+ const sendImgSrc = app.safe(function () {
47
32
  const id = app.nodes.getID(this);
48
33
  if (id === undefined) {
49
34
  return;
@@ -55,44 +40,46 @@ export default function (app) {
55
40
  const resolvedSrc = resolveURL(src || ''); // Src type is null sometimes. - is it true?
56
41
  if (naturalWidth === 0 && naturalHeight === 0) {
57
42
  if (isURL(resolvedSrc)) {
58
- app.send(ResourceTiming(timestamp(), 0, 0, 0, 0, 0, resolvedSrc, 'img'));
43
+ app.send(new ResourceTiming(timestamp(), 0, 0, 0, 0, 0, resolvedSrc, 'img'));
59
44
  }
60
45
  }
61
46
  else if (resolvedSrc.length >= 1e5 || app.sanitizer.isMasked(id)) {
62
47
  sendPlaceholder(id, this);
63
48
  }
64
49
  else {
65
- sendSrc(id, this);
66
- sendSrcset(id, this);
50
+ app.send(new SetNodeAttribute(id, 'src', resolvedSrc));
51
+ if (srcset) {
52
+ const resolvedSrcset = srcset.split(',').map(str => resolveURL(str)).join(',');
53
+ app.send(new SetNodeAttribute(id, 'srcset', resolvedSrcset));
54
+ }
67
55
  }
68
56
  });
69
57
  const observer = new MutationObserver((mutations) => {
70
58
  for (const mutation of mutations) {
71
- if (mutation.type === 'attributes') {
59
+ if (mutation.type === "attributes") {
72
60
  const target = mutation.target;
73
61
  const id = app.nodes.getID(target);
74
62
  if (id === undefined) {
75
63
  return;
76
64
  }
77
- if (mutation.attributeName === 'src') {
78
- sendSrc(id, target);
65
+ if (mutation.attributeName === "src") {
66
+ const src = target.src;
67
+ app.send(new SetNodeAttributeURLBased(id, 'src', src, app.getBaseHref()));
79
68
  }
80
- if (mutation.attributeName === 'srcset') {
81
- sendSrcset(id, target);
69
+ if (mutation.attributeName === "srcset") {
70
+ const srcset = target.srcset;
71
+ app.send(new SetNodeAttribute(id, 'srcset', srcset));
82
72
  }
83
73
  }
84
74
  }
85
75
  });
86
- app.attachStopCallback(() => {
87
- observer.disconnect();
88
- });
89
76
  app.nodes.attachNodeCallback((node) => {
90
- if (!hasTag(node, 'IMG')) {
77
+ if (!hasTag(node, "IMG")) {
91
78
  return;
92
79
  }
93
- app.nodes.attachElementListener('error', node, sendImgAttrs.bind(node));
94
- app.nodes.attachElementListener('load', node, sendImgAttrs.bind(node));
95
- sendImgAttrs.call(node);
96
- observer.observe(node, { attributes: true, attributeFilter: ['src', 'srcset'] });
80
+ app.nodes.attachElementListener('error', node, sendImgSrc);
81
+ app.nodes.attachElementListener('load', node, sendImgSrc);
82
+ sendImgSrc.call(node);
83
+ observer.observe(node, { attributes: true, attributeFilter: ["src", "srcset"] });
97
84
  });
98
85
  }
@@ -1,4 +1,4 @@
1
- import type App from '../app/index.js';
1
+ import type App from "../app/index.js";
2
2
  declare type TextEditableElement = HTMLInputElement | HTMLTextAreaElement;
3
3
  export declare function getInputLabel(node: TextEditableElement): string;
4
4
  export declare const enum InputMode {
@@ -1,18 +1,18 @@
1
- import { normSpaces, IN_BROWSER, getLabelAttribute, hasOpenreplayAttribute } from '../utils.js';
2
- import { hasTag } from '../app/guards.js';
3
- import { SetInputTarget, SetInputValue, SetInputChecked } from '../app/messages.gen.js';
1
+ import { normSpaces, IN_BROWSER, getLabelAttribute, hasOpenreplayAttribute, } from "../utils.js";
2
+ import { hasTag } from "../app/guards.js";
3
+ import { SetInputTarget, SetInputValue, SetInputChecked } from "../common/messages.js";
4
4
  const INPUT_TYPES = ['text', 'password', 'email', 'search', 'number', 'range', 'date'];
5
5
  function isTextEditable(node) {
6
- if (hasTag(node, 'TEXTAREA')) {
6
+ if (hasTag(node, "TEXTAREA")) {
7
7
  return true;
8
8
  }
9
- if (!hasTag(node, 'INPUT')) {
9
+ if (!hasTag(node, "INPUT")) {
10
10
  return false;
11
11
  }
12
12
  return INPUT_TYPES.includes(node.type);
13
13
  }
14
14
  function isCheckable(node) {
15
- if (!hasTag(node, 'INPUT')) {
15
+ if (!hasTag(node, "INPUT")) {
16
16
  return false;
17
17
  }
18
18
  const type = node.type;
@@ -22,7 +22,7 @@ const labelElementFor = IN_BROWSER && 'labels' in HTMLInputElement.prototype
22
22
  ? (node) => {
23
23
  let p = node;
24
24
  while ((p = p.parentNode) !== null) {
25
- if (hasTag(p, 'LABEL')) {
25
+ if (hasTag(p, "LABEL")) {
26
26
  return p;
27
27
  }
28
28
  }
@@ -34,13 +34,13 @@ const labelElementFor = IN_BROWSER && 'labels' in HTMLInputElement.prototype
34
34
  : (node) => {
35
35
  let p = node;
36
36
  while ((p = p.parentNode) !== null) {
37
- if (hasTag(p, 'LABEL')) {
37
+ if (hasTag(p, "LABEL")) {
38
38
  return p;
39
39
  }
40
40
  }
41
41
  const id = node.id;
42
42
  if (id) {
43
- const labels = node.ownerDocument.querySelectorAll('label[for="' + id + '"]');
43
+ const labels = document.querySelectorAll('label[for="' + id + '"]');
44
44
  if (labels !== null && labels.length === 1) {
45
45
  return labels[0];
46
46
  }
@@ -50,13 +50,12 @@ export function getInputLabel(node) {
50
50
  let label = getLabelAttribute(node);
51
51
  if (label === null) {
52
52
  const labelElement = labelElementFor(node);
53
- label =
54
- (labelElement && labelElement.innerText) ||
55
- node.placeholder ||
56
- node.name ||
57
- node.id ||
58
- node.className ||
59
- node.type;
53
+ label = (labelElement && labelElement.innerText)
54
+ || node.placeholder
55
+ || node.name
56
+ || node.id
57
+ || node.className
58
+ || node.type;
60
59
  }
61
60
  return normSpaces(label).slice(0, 100);
62
61
  }
@@ -70,7 +69,7 @@ export default function (app, opts) {
70
69
  function sendInputTarget(id, node) {
71
70
  const label = getInputLabel(node);
72
71
  if (label !== '') {
73
- app.send(SetInputTarget(id, label));
72
+ app.send(new SetInputTarget(id, label));
74
73
  }
75
74
  }
76
75
  function sendInputValue(id, node) {
@@ -83,7 +82,8 @@ export default function (app, opts) {
83
82
  (inputMode === 0 /* Plain */ &&
84
83
  ((options.obscureInputNumbers && node.type !== 'date' && /\d\d\d\d/.test(value)) ||
85
84
  (options.obscureInputDates && node.type === 'date') ||
86
- (options.obscureInputEmails && (node.type === 'email' || !!~value.indexOf('@')))))) {
85
+ (options.obscureInputEmails &&
86
+ (node.type === 'email' || !!~value.indexOf('@')))))) {
87
87
  inputMode = 1 /* Obscured */;
88
88
  }
89
89
  let mask = 0;
@@ -97,7 +97,7 @@ export default function (app, opts) {
97
97
  value = '';
98
98
  break;
99
99
  }
100
- app.send(SetInputValue(id, value, mask));
100
+ app.send(new SetInputValue(id, value, mask));
101
101
  }
102
102
  const inputValues = new Map();
103
103
  const checkableValues = new Map();
@@ -135,7 +135,7 @@ export default function (app, opts) {
135
135
  }
136
136
  if (checked !== node.checked) {
137
137
  checkableValues.set(id, node.checked);
138
- app.send(SetInputChecked(id, node.checked));
138
+ app.send(new SetInputChecked(id, node.checked));
139
139
  }
140
140
  });
141
141
  });
@@ -146,9 +146,9 @@ export default function (app, opts) {
146
146
  return;
147
147
  }
148
148
  // TODO: support multiple select (?): use selectedOptions; Need send target?
149
- if (hasTag(node, 'SELECT')) {
149
+ if (hasTag(node, "SELECT")) {
150
150
  sendInputValue(id, node);
151
- app.attachEventListener(node, 'change', () => {
151
+ app.attachEventListener(node, "change", () => {
152
152
  sendInputValue(id, node);
153
153
  });
154
154
  }
@@ -159,7 +159,7 @@ export default function (app, opts) {
159
159
  }
160
160
  if (isCheckable(node)) {
161
161
  checkableValues.set(id, node.checked);
162
- app.send(SetInputChecked(id, node.checked));
162
+ app.send(new SetInputChecked(id, node.checked));
163
163
  return;
164
164
  }
165
165
  }));
@@ -0,0 +1,2 @@
1
+ import type App from "../app/index.js";
2
+ export default function (app: App): void;
@@ -0,0 +1,23 @@
1
+ import { LongTask } from "../common/messages.js";
2
+ ;
3
+ ;
4
+ export default function (app) {
5
+ if (!('PerformanceObserver' in window) || !('PerformanceLongTaskTiming' in window)) {
6
+ return;
7
+ }
8
+ const contexts = ["unknown", "self", "same-origin-ancestor", "same-origin-descendant", "same-origin", "cross-origin-ancestor", "cross-origin-descendant", "cross-origin-unreachable", "multiple-contexts"];
9
+ const containerTypes = ["window", "iframe", "embed", "object"];
10
+ function longTask(entry) {
11
+ let type = "", src = "", id = "", name = "";
12
+ const container = entry.attribution[0];
13
+ if (container != null) {
14
+ type = container.containerType;
15
+ name = container.containerName;
16
+ id = container.containerId;
17
+ src = container.containerSrc;
18
+ }
19
+ app.send(new LongTask(entry.startTime + performance.timing.navigationStart, entry.duration, Math.max(contexts.indexOf(entry.name), 0), Math.max(containerTypes.indexOf(type), 0), name, id, src));
20
+ }
21
+ const observer = new PerformanceObserver((list) => list.getEntries().forEach(longTask));
22
+ observer.observe({ entryTypes: ['longtask'] });
23
+ }
@@ -1,2 +1,2 @@
1
- import type App from '../app/index.js';
1
+ import type App from "../app/index.js";
2
2
  export default function (app: App): void;
@@ -1,8 +1,8 @@
1
- import { hasTag, isSVGElement, isDocument } from '../app/guards.js';
2
- import { normSpaces, hasOpenreplayAttribute, getLabelAttribute } from '../utils.js';
3
- import { MouseMove, MouseClick } from '../app/messages.gen.js';
4
- import { getInputLabel } from './input.js';
5
- function _getSelector(target, document) {
1
+ import { hasTag, isSVGElement } from "../app/guards.js";
2
+ import { normSpaces, hasOpenreplayAttribute, getLabelAttribute, } from "../utils.js";
3
+ import { MouseMove, MouseClick } from "../common/messages.js";
4
+ import { getInputLabel } from "./input.js";
5
+ function _getSelector(target) {
6
6
  let el = target;
7
7
  let selector = null;
8
8
  do {
@@ -10,10 +10,9 @@ function _getSelector(target, document) {
10
10
  return `#${el.id}` + (selector ? ` > ${selector}` : '');
11
11
  }
12
12
  selector =
13
- el.className
14
- .split(' ')
15
- .map((cn) => cn.trim())
16
- .filter((cn) => cn !== '')
13
+ el.className.split(' ')
14
+ .map(cn => cn.trim())
15
+ .filter(cn => cn !== '')
17
16
  .reduce((sel, cn) => `${sel}.${cn}`, el.tagName.toLowerCase()) +
18
17
  (selector ? ` > ${selector}` : '');
19
18
  if (el === document.body) {
@@ -25,23 +24,23 @@ function _getSelector(target, document) {
25
24
  }
26
25
  function isClickable(element) {
27
26
  const tag = element.tagName.toUpperCase();
28
- return (tag === 'BUTTON' ||
27
+ return tag === 'BUTTON' ||
29
28
  tag === 'A' ||
30
29
  tag === 'LI' ||
31
30
  tag === 'SELECT' ||
32
31
  element.onclick != null ||
33
- element.getAttribute('role') === 'button');
32
+ element.getAttribute('role') === 'button';
34
33
  //|| element.className.includes("btn")
35
- // MBTODO: intersept addEventListener
34
+ // MBTODO: intersect addEventListener
36
35
  }
37
- //TODO: fix (typescript is not sure about target variable after assignation of svg)
38
- function getTarget(target, document) {
36
+ //TODO: fix (typescript doesn't allow work when the guard is inside the function)
37
+ function getTarget(target) {
39
38
  if (target instanceof Element) {
40
- return _getTarget(target, document);
39
+ return _getTarget(target);
41
40
  }
42
41
  return null;
43
42
  }
44
- function _getTarget(target, document) {
43
+ function _getTarget(target) {
45
44
  let element = target;
46
45
  while (element !== null && element !== document.documentElement) {
47
46
  if (hasOpenreplayAttribute(element, 'masked')) {
@@ -65,7 +64,8 @@ function _getTarget(target, document) {
65
64
  if (tag === 'INPUT') {
66
65
  return element;
67
66
  }
68
- if (isClickable(element) || getLabelAttribute(element) !== null) {
67
+ if (isClickable(element) ||
68
+ getLabelAttribute(element) !== null) {
69
69
  return element;
70
70
  }
71
71
  element = element.parentElement;
@@ -78,7 +78,7 @@ export default function (app) {
78
78
  if (dl !== null) {
79
79
  return dl;
80
80
  }
81
- if (hasTag(target, 'INPUT')) {
81
+ if (hasTag(target, "INPUT")) {
82
82
  return getInputLabel(target);
83
83
  }
84
84
  if (isClickable(target)) {
@@ -104,46 +104,39 @@ export default function (app) {
104
104
  });
105
105
  const sendMouseMove = () => {
106
106
  if (mousePositionChanged) {
107
- app.send(MouseMove(mousePositionX, mousePositionY));
107
+ app.send(new MouseMove(mousePositionX, mousePositionY));
108
108
  mousePositionChanged = false;
109
109
  }
110
110
  };
111
- const patchDocument = (document) => {
112
- const selectorMap = {};
113
- function getSelector(id, target) {
114
- return (selectorMap[id] = selectorMap[id] || _getSelector(target, document));
111
+ const selectorMap = {};
112
+ function getSelector(id, target) {
113
+ return selectorMap[id] = selectorMap[id] || _getSelector(target);
114
+ }
115
+ app.attachEventListener(document.documentElement, 'mouseover', (e) => {
116
+ const target = getTarget(e.target);
117
+ if (target !== mouseTarget) {
118
+ mouseTarget = target;
119
+ mouseTargetTime = performance.now();
115
120
  }
116
- app.attachEventListener(document.documentElement, 'mouseover', (e) => {
117
- const target = getTarget(e.target, document);
118
- if (target !== mouseTarget) {
119
- mouseTarget = target;
120
- mouseTargetTime = performance.now();
121
- }
122
- });
123
- app.attachEventListener(document, 'mousemove', (e) => {
124
- const { top, left } = app.observer.getDocumentOffset(document);
125
- mousePositionX = e.clientX + left;
126
- mousePositionY = e.clientY + top;
127
- mousePositionChanged = true;
128
- }, false);
129
- app.attachEventListener(document, 'click', (e) => {
130
- const target = getTarget(e.target, document);
131
- if ((!e.clientX && !e.clientY) || target === null) {
132
- return;
133
- }
134
- const id = app.nodes.getID(target);
135
- if (id !== undefined) {
136
- sendMouseMove();
137
- app.send(MouseClick(id, mouseTarget === target ? Math.round(performance.now() - mouseTargetTime) : 0, getTargetLabel(target), getSelector(id, target)), true);
138
- }
139
- mouseTarget = null;
140
- });
141
- };
142
- app.nodes.attachNodeCallback((node) => {
143
- if (isDocument(node)) {
144
- patchDocument(node);
121
+ });
122
+ app.attachEventListener(document, 'mousemove', (e) => {
123
+ mousePositionX = e.clientX;
124
+ mousePositionY = e.clientY;
125
+ mousePositionChanged = true;
126
+ }, false);
127
+ app.attachEventListener(document, 'click', (e) => {
128
+ const target = getTarget(e.target);
129
+ if ((!e.clientX && !e.clientY) || target === null) {
130
+ return;
145
131
  }
132
+ const id = app.nodes.getID(target);
133
+ if (id !== undefined) {
134
+ sendMouseMove();
135
+ app.send(new MouseClick(id, mouseTarget === target
136
+ ? Math.round(performance.now() - mouseTargetTime)
137
+ : 0, getTargetLabel(target), getSelector(id, target)), true);
138
+ }
139
+ mouseTarget = null;
146
140
  });
147
- patchDocument(document);
148
141
  app.ticker.attach(sendMouseMove, 10);
149
142
  }
@@ -1,4 +1,4 @@
1
- import type App from '../app/index.js';
1
+ import type App from "../app/index.js";
2
2
  export declare const deviceMemory: number;
3
3
  export declare const jsHeapSizeLimit: number;
4
4
  export interface Options {
@@ -1,5 +1,5 @@
1
- import { IN_BROWSER } from '../utils.js';
2
- import { PerformanceTrack } from '../app/messages.gen.js';
1
+ import { IN_BROWSER } from "../utils.js";
2
+ import { PerformanceTrack } from "../common/messages.js";
3
3
  const perf = IN_BROWSER && 'performance' in window && 'memory' in performance // works in Chrome only
4
4
  ? performance
5
5
  : { memory: {} };
@@ -31,7 +31,7 @@ export default function (app, opts) {
31
31
  if (frames === undefined || ticks === undefined) {
32
32
  return;
33
33
  }
34
- app.send(PerformanceTrack(frames, ticks, perf.memory.totalJSHeapSize || 0, perf.memory.usedJSHeapSize || 0));
34
+ app.send(new PerformanceTrack(frames, ticks, perf.memory.totalJSHeapSize || 0, perf.memory.usedJSHeapSize || 0));
35
35
  ticks = frames = document.hidden ? -1 : 0;
36
36
  };
37
37
  app.attachStartCallback(() => {
@@ -1,2 +1,2 @@
1
- import type App from '../app/index.js';
1
+ import type App from "../app/index.js";
2
2
  export default function (app: App): void;
@@ -1,14 +1,9 @@
1
- import { SetViewportScroll, SetNodeScroll } from '../app/messages.gen.js';
2
- import { isElementNode, isRootNode } from '../app/guards.js';
1
+ import { SetViewportScroll, SetNodeScroll } from "../common/messages.js";
2
+ import { isElementNode } from "../app/guards.js";
3
3
  export default function (app) {
4
4
  let documentScroll = false;
5
5
  const nodeScroll = new Map();
6
- function setNodeScroll(target) {
7
- if (target instanceof Element) {
8
- nodeScroll.set(target, [target.scrollLeft, target.scrollTop]);
9
- }
10
- }
11
- const sendSetViewportScroll = app.safe(() => app.send(SetViewportScroll(window.pageXOffset ||
6
+ const sendSetViewportScroll = app.safe(() => app.send(new SetViewportScroll(window.pageXOffset ||
12
7
  (document.documentElement && document.documentElement.scrollLeft) ||
13
8
  (document.body && document.body.scrollLeft) ||
14
9
  0, window.pageYOffset ||
@@ -18,7 +13,7 @@ export default function (app) {
18
13
  const sendSetNodeScroll = app.safe((s, node) => {
19
14
  const id = app.nodes.getID(node);
20
15
  if (id !== undefined) {
21
- app.send(SetNodeScroll(id, s[0], s[1]));
16
+ app.send(new SetNodeScroll(id, s[0], s[1]));
22
17
  }
23
18
  });
24
19
  app.attachStartCallback(sendSetViewportScroll);
@@ -30,20 +25,16 @@ export default function (app) {
30
25
  if (isStart && isElementNode(node) && node.scrollLeft + node.scrollTop > 0) {
31
26
  nodeScroll.set(node, [node.scrollLeft, node.scrollTop]);
32
27
  }
33
- else if (isRootNode(node)) {
34
- // scroll is not-composed event (https://javascript.info/shadow-dom-events)
35
- app.attachEventListener(node, 'scroll', (e) => {
36
- setNodeScroll(e.target);
37
- });
38
- }
39
28
  });
40
- app.attachEventListener(document, 'scroll', (e) => {
29
+ app.attachEventListener(window, 'scroll', (e) => {
41
30
  const target = e.target;
42
31
  if (target === document) {
43
32
  documentScroll = true;
44
33
  return;
45
34
  }
46
- setNodeScroll(target);
35
+ if (target instanceof Element) {
36
+ nodeScroll.set(target, [target.scrollLeft, target.scrollTop]);
37
+ }
47
38
  });
48
39
  app.ticker.attach(() => {
49
40
  if (documentScroll) {
@@ -1,4 +1,4 @@
1
- import type App from '../app/index.js';
1
+ import type App from "../app/index.js";
2
2
  export interface Options {
3
3
  captureResourceTimings: boolean;
4
4
  capturePageLoadTimings: boolean;