@amplitude/plugin-autocapture-browser 1.6.0 → 1.6.1

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.
@@ -1,7 +1,6 @@
1
1
  import { AllWindowObservables } from 'src/autocapture-plugin';
2
2
  import { BrowserClient } from '@amplitude/analytics-core';
3
3
  import { shouldTrackEvent } from '../helpers';
4
- export declare function _overrideRageClickConfig(rageClickThreshold: number, rageClickWindowMs: number): void;
5
4
  export declare function trackRageClicks({ amplitude, allObservables, shouldTrackRageClick, }: {
6
5
  amplitude: BrowserClient;
7
6
  allObservables: AllWindowObservables;
@@ -1 +1 @@
1
- {"version":3,"file":"track-rage-click.d.ts","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAE9D,OAAO,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAC1D,OAAO,EAA+B,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAQ3E,wBAAgB,wBAAwB,CAAC,kBAAkB,EAAE,MAAM,EAAE,iBAAiB,EAAE,MAAM,QAG7F;AAgBD,wBAAgB,eAAe,CAAC,EAC9B,SAAS,EACT,cAAc,EACd,oBAAoB,GACrB,EAAE;IACD,SAAS,EAAE,aAAa,CAAC;IACzB,cAAc,EAAE,oBAAoB,CAAC;IACrC,oBAAoB,EAAE,gBAAgB,CAAC;CACxC,+BAmDA"}
1
+ {"version":3,"file":"track-rage-click.d.ts","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAE9D,OAAO,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAC1D,OAAO,EAA+B,gBAAgB,EAAE,MAAM,YAAY,CAAC;AA4B3E,wBAAgB,eAAe,CAAC,EAC9B,SAAS,EACT,cAAc,EACd,oBAAoB,GACrB,EAAE;IACD,SAAS,EAAE,aAAa,CAAC;IACzB,cAAc,EAAE,oBAAoB,CAAC;IACrC,oBAAoB,EAAE,gBAAgB,CAAC;CACxC,+BAyEA"}
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.trackRageClicks = exports._overrideRageClickConfig = void 0;
3
+ exports.trackRageClicks = void 0;
4
4
  var tslib_1 = require("tslib");
5
5
  var rxjs_1 = require("rxjs");
6
6
  var helpers_1 = require("../helpers");
@@ -8,47 +8,55 @@ var constants_1 = require("../constants");
8
8
  var analytics_core_1 = require("@amplitude/analytics-core");
9
9
  var RAGE_CLICK_THRESHOLD = analytics_core_1.DEFAULT_RAGE_CLICK_THRESHOLD;
10
10
  var RAGE_CLICK_WINDOW_MS = analytics_core_1.DEFAULT_RAGE_CLICK_WINDOW_MS;
11
- // allow override of rage click config for testing only
12
- function _overrideRageClickConfig(rageClickThreshold, rageClickWindowMs) {
13
- RAGE_CLICK_THRESHOLD = rageClickThreshold;
14
- RAGE_CLICK_WINDOW_MS = rageClickWindowMs;
15
- }
16
- exports._overrideRageClickConfig = _overrideRageClickConfig;
17
11
  function trackRageClicks(_a) {
18
12
  var amplitude = _a.amplitude, allObservables = _a.allObservables, shouldTrackRageClick = _a.shouldTrackRageClick;
19
13
  var clickObservable = allObservables.clickObservable;
20
- // Buffer clicks within a RAGE_CLICK_WINDOW_MS window and filter for rage clicks
21
- var rageClickObservable = clickObservable.pipe((0, rxjs_1.filter)(helpers_1.filterOutNonTrackableEvents), (0, rxjs_1.filter)(function (click) {
14
+ // Keep track of all clicks within the sliding window
15
+ var clickWindow = [];
16
+ return clickObservable
17
+ .pipe((0, rxjs_1.filter)(helpers_1.filterOutNonTrackableEvents), (0, rxjs_1.filter)(function (click) {
22
18
  return shouldTrackRageClick('click', click.closestTrackedAncestor);
23
- }), (0, rxjs_1.bufferTime)(RAGE_CLICK_WINDOW_MS), (0, rxjs_1.filter)(function (clicks) {
24
- // filter if not enough clicks to be a rage click
25
- if (clicks.length < RAGE_CLICK_THRESHOLD) {
26
- return false;
19
+ }), (0, rxjs_1.map)(function (click) {
20
+ var now = click.timestamp;
21
+ // if the current click isn't on the same element as the most recent click,
22
+ // clear the sliding window and start over
23
+ if (clickWindow.length > 0 &&
24
+ clickWindow[clickWindow.length - 1].closestTrackedAncestor !== click.closestTrackedAncestor) {
25
+ clickWindow.splice(0, clickWindow.length);
27
26
  }
28
- // filter if the last RAGE_CLICK_THRESHOLD clicks were not all on the same element
29
- var trailingIndex = clicks.length - 1;
30
- var lastClickTarget = clicks[trailingIndex].event.target;
31
- while (--trailingIndex >= clicks.length - RAGE_CLICK_THRESHOLD) {
32
- if (clicks[trailingIndex].event.target !== lastClickTarget) {
33
- return false;
27
+ // remove past clicks that are outside the sliding window
28
+ var clickPtr = 0;
29
+ for (; clickPtr < clickWindow.length; clickPtr++) {
30
+ if (now - clickWindow[clickPtr].timestamp < RAGE_CLICK_WINDOW_MS) {
31
+ break;
34
32
  }
35
33
  }
36
- // if we reach here that means the last RAGE_CLICK_THRESHOLD clicks were all on the same element
37
- // and thus we have a rage click
38
- return true;
39
- }), (0, rxjs_1.map)(function (clicks) {
40
- var firstClick = clicks[0];
41
- var lastClick = clicks[clicks.length - 1];
42
- var rageClickEvent = tslib_1.__assign({ '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(), '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(), '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp, '[Amplitude] Clicks': clicks.map(function (click) { return ({
34
+ clickWindow.splice(0, clickPtr);
35
+ // add the current click to the window
36
+ clickWindow.push(click);
37
+ // if there's not enough clicks to be a rage click, return null
38
+ if (clickWindow.length < RAGE_CLICK_THRESHOLD) {
39
+ return null;
40
+ }
41
+ // if we've made it here, we have enough trailing clicks on the same element
42
+ // for it to be a rage click
43
+ var firstClick = clickWindow[0];
44
+ var lastClick = clickWindow[clickWindow.length - 1];
45
+ var rageClickEvent = tslib_1.__assign({ '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(), '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(), '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp, '[Amplitude] Clicks': clickWindow.map(function (click) { return ({
43
46
  X: click.event.clientX,
44
47
  Y: click.event.clientY,
45
48
  Time: click.timestamp,
46
- }); }), '[Amplitude] Click Count': clicks.length }, firstClick.targetElementProperties);
49
+ }); }), '[Amplitude] Click Count': clickWindow.length }, firstClick.targetElementProperties);
50
+ // restart the sliding window
51
+ clickWindow.splice(0, clickWindow.length);
47
52
  return { rageClickEvent: rageClickEvent, time: firstClick.timestamp };
48
- }));
49
- return rageClickObservable.subscribe(function (_a) {
50
- var rageClickEvent = _a.rageClickEvent, time = _a.time;
51
- amplitude.track(constants_1.AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, rageClickEvent, { time: time });
53
+ }), (0, rxjs_1.filter)(function (result) { return result !== null; }))
54
+ .subscribe(function (data) {
55
+ /* istanbul ignore if */
56
+ if (data === null) {
57
+ return;
58
+ }
59
+ amplitude.track(constants_1.AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, data.rageClickEvent, { time: data.time });
52
60
  });
53
61
  }
54
62
  exports.trackRageClicks = trackRageClicks;
@@ -1 +1 @@
1
- {"version":3,"file":"track-rage-click.js","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":";;;;AACA,6BAA+C;AAE/C,sCAA2E;AAC3E,0CAAoE;AACpE,4DAAuG;AAEvG,IAAI,oBAAoB,GAAG,6CAA4B,CAAC;AACxD,IAAI,oBAAoB,GAAG,6CAA4B,CAAC;AAExD,uDAAuD;AACvD,SAAgB,wBAAwB,CAAC,kBAA0B,EAAE,iBAAyB;IAC5F,oBAAoB,GAAG,kBAAkB,CAAC;IAC1C,oBAAoB,GAAG,iBAAiB,CAAC;AAC3C,CAAC;AAHD,4DAGC;AAgBD,SAAgB,eAAe,CAAC,EAQ/B;QAPC,SAAS,eAAA,EACT,cAAc,oBAAA,EACd,oBAAoB,0BAAA;IAMZ,IAAA,eAAe,GAAK,cAAc,gBAAnB,CAAoB;IAE3C,gFAAgF;IAChF,IAAM,mBAAmB,GAAG,eAAe,CAAC,IAAI,CAC9C,IAAA,aAAM,EAAC,qCAA2B,CAAC,EACnC,IAAA,aAAM,EAAC,UAAC,KAAK;QACX,OAAO,oBAAoB,CAAC,OAAO,EAAE,KAAK,CAAC,sBAAsB,CAAC,CAAC;IACrE,CAAC,CAAC,EACF,IAAA,iBAAU,EAAC,oBAAoB,CAAC,EAChC,IAAA,aAAM,EAAC,UAAC,MAAM;QACZ,iDAAiD;QACjD,IAAI,MAAM,CAAC,MAAM,GAAG,oBAAoB,EAAE;YACxC,OAAO,KAAK,CAAC;SACd;QAED,kFAAkF;QAClF,IAAI,aAAa,GAAG,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC;QACtC,IAAM,eAAe,GAAG,MAAM,CAAC,aAAa,CAAC,CAAC,KAAK,CAAC,MAAM,CAAC;QAC3D,OAAO,EAAE,aAAa,IAAI,MAAM,CAAC,MAAM,GAAG,oBAAoB,EAAE;YAC9D,IAAI,MAAM,CAAC,aAAa,CAAC,CAAC,KAAK,CAAC,MAAM,KAAK,eAAe,EAAE;gBAC1D,OAAO,KAAK,CAAC;aACd;SACF;QAED,gGAAgG;QAChG,gCAAgC;QAChC,OAAO,IAAI,CAAC;IACd,CAAC,CAAC,EACF,IAAA,UAAG,EAAC,UAAC,MAAM;QACT,IAAM,UAAU,GAAG,MAAM,CAAC,CAAC,CAAC,CAAC;QAC7B,IAAM,SAAS,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;QAC5C,IAAM,cAAc,sBAClB,wBAAwB,EAAE,IAAI,IAAI,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC,WAAW,EAAE,EACtE,sBAAsB,EAAE,IAAI,IAAI,CAAC,SAAS,CAAC,SAAS,CAAC,CAAC,WAAW,EAAE,EACnE,sBAAsB,EAAE,SAAS,CAAC,SAAS,GAAG,UAAU,CAAC,SAAS,EAClE,oBAAoB,EAAE,MAAM,CAAC,GAAG,CAAC,UAAC,KAAK,IAAK,OAAA,CAAC;gBAC3C,CAAC,EAAG,KAAK,CAAC,KAAoB,CAAC,OAAO;gBACtC,CAAC,EAAG,KAAK,CAAC,KAAoB,CAAC,OAAO;gBACtC,IAAI,EAAE,KAAK,CAAC,SAAS;aACtB,CAAC,EAJ0C,CAI1C,CAAC,EACH,yBAAyB,EAAE,MAAM,CAAC,MAAM,IACrC,UAAU,CAAC,uBAAuB,CACtC,CAAC;QACF,OAAO,EAAE,cAAc,gBAAA,EAAE,IAAI,EAAE,UAAU,CAAC,SAAS,EAAE,CAAC;IACxD,CAAC,CAAC,CACH,CAAC;IAEF,OAAO,mBAAmB,CAAC,SAAS,CAAC,UAAC,EAAwB;YAAtB,cAAc,oBAAA,EAAE,IAAI,UAAA;QAC1D,SAAS,CAAC,KAAK,CAAC,gDAAoC,EAAE,cAAc,EAAE,EAAE,IAAI,MAAA,EAAE,CAAC,CAAC;IAClF,CAAC,CAAC,CAAC;AACL,CAAC;AA3DD,0CA2DC","sourcesContent":["import { AllWindowObservables } from 'src/autocapture-plugin';\nimport { filter, map, bufferTime } from 'rxjs';\nimport { BrowserClient } from '@amplitude/analytics-core';\nimport { filterOutNonTrackableEvents, shouldTrackEvent } from '../helpers';\nimport { AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT } from '../constants';\nimport { DEFAULT_RAGE_CLICK_THRESHOLD, DEFAULT_RAGE_CLICK_WINDOW_MS } from '@amplitude/analytics-core';\n\nlet RAGE_CLICK_THRESHOLD = DEFAULT_RAGE_CLICK_THRESHOLD;\nlet RAGE_CLICK_WINDOW_MS = DEFAULT_RAGE_CLICK_WINDOW_MS;\n\n// allow override of rage click config for testing only\nexport function _overrideRageClickConfig(rageClickThreshold: number, rageClickWindowMs: number) {\n RAGE_CLICK_THRESHOLD = rageClickThreshold;\n RAGE_CLICK_WINDOW_MS = rageClickWindowMs;\n}\n\ntype Click = {\n X: number;\n Y: number;\n Time: number;\n};\n\ntype EventRageClick = {\n '[Amplitude] Begin Time': string; // ISO-8601\n '[Amplitude] End Time': string; // ISO-8601\n '[Amplitude] Duration': number;\n '[Amplitude] Clicks': Array<Click>;\n '[Amplitude] Click Count': number;\n};\n\nexport function trackRageClicks({\n amplitude,\n allObservables,\n shouldTrackRageClick,\n}: {\n amplitude: BrowserClient;\n allObservables: AllWindowObservables;\n shouldTrackRageClick: shouldTrackEvent;\n}) {\n const { clickObservable } = allObservables;\n\n // Buffer clicks within a RAGE_CLICK_WINDOW_MS window and filter for rage clicks\n const rageClickObservable = clickObservable.pipe(\n filter(filterOutNonTrackableEvents),\n filter((click) => {\n return shouldTrackRageClick('click', click.closestTrackedAncestor);\n }),\n bufferTime(RAGE_CLICK_WINDOW_MS),\n filter((clicks) => {\n // filter if not enough clicks to be a rage click\n if (clicks.length < RAGE_CLICK_THRESHOLD) {\n return false;\n }\n\n // filter if the last RAGE_CLICK_THRESHOLD clicks were not all on the same element\n let trailingIndex = clicks.length - 1;\n const lastClickTarget = clicks[trailingIndex].event.target;\n while (--trailingIndex >= clicks.length - RAGE_CLICK_THRESHOLD) {\n if (clicks[trailingIndex].event.target !== lastClickTarget) {\n return false;\n }\n }\n\n // if we reach here that means the last RAGE_CLICK_THRESHOLD clicks were all on the same element\n // and thus we have a rage click\n return true;\n }),\n map((clicks) => {\n const firstClick = clicks[0];\n const lastClick = clicks[clicks.length - 1];\n const rageClickEvent: EventRageClick = {\n '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(),\n '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(),\n '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp,\n '[Amplitude] Clicks': clicks.map((click) => ({\n X: (click.event as MouseEvent).clientX,\n Y: (click.event as MouseEvent).clientY,\n Time: click.timestamp,\n })),\n '[Amplitude] Click Count': clicks.length,\n ...firstClick.targetElementProperties,\n };\n return { rageClickEvent, time: firstClick.timestamp };\n }),\n );\n\n return rageClickObservable.subscribe(({ rageClickEvent, time }) => {\n amplitude.track(AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, rageClickEvent, { time });\n });\n}\n"]}
1
+ {"version":3,"file":"track-rage-click.js","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":"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","sourcesContent":["import { AllWindowObservables } from 'src/autocapture-plugin';\nimport { filter, map } from 'rxjs';\nimport { BrowserClient } from '@amplitude/analytics-core';\nimport { filterOutNonTrackableEvents, shouldTrackEvent } from '../helpers';\nimport { AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT } from '../constants';\nimport { DEFAULT_RAGE_CLICK_THRESHOLD, DEFAULT_RAGE_CLICK_WINDOW_MS } from '@amplitude/analytics-core';\n\nconst RAGE_CLICK_THRESHOLD = DEFAULT_RAGE_CLICK_THRESHOLD;\nconst RAGE_CLICK_WINDOW_MS = DEFAULT_RAGE_CLICK_WINDOW_MS;\n\ntype Click = {\n X: number;\n Y: number;\n Time: number;\n};\n\ntype EventRageClick = {\n '[Amplitude] Begin Time': string; // ISO-8601\n '[Amplitude] End Time': string; // ISO-8601\n '[Amplitude] Duration': number;\n '[Amplitude] Clicks': Array<Click>;\n '[Amplitude] Click Count': number;\n};\n\ntype ClickEvent = {\n event: MouseEvent | Event;\n timestamp: number;\n targetElementProperties: Record<string, any>;\n closestTrackedAncestor: Element | null;\n};\n\nexport function trackRageClicks({\n amplitude,\n allObservables,\n shouldTrackRageClick,\n}: {\n amplitude: BrowserClient;\n allObservables: AllWindowObservables;\n shouldTrackRageClick: shouldTrackEvent;\n}) {\n const { clickObservable } = allObservables;\n\n // Keep track of all clicks within the sliding window\n const clickWindow: ClickEvent[] = [];\n\n return clickObservable\n .pipe(\n filter(filterOutNonTrackableEvents),\n filter((click) => {\n return shouldTrackRageClick('click', click.closestTrackedAncestor);\n }),\n map((click) => {\n const now = click.timestamp;\n\n // if the current click isn't on the same element as the most recent click,\n // clear the sliding window and start over\n if (\n clickWindow.length > 0 &&\n clickWindow[clickWindow.length - 1].closestTrackedAncestor !== click.closestTrackedAncestor\n ) {\n clickWindow.splice(0, clickWindow.length);\n }\n\n // remove past clicks that are outside the sliding window\n let clickPtr = 0;\n for (; clickPtr < clickWindow.length; clickPtr++) {\n if (now - clickWindow[clickPtr].timestamp < RAGE_CLICK_WINDOW_MS) {\n break;\n }\n }\n clickWindow.splice(0, clickPtr);\n\n // add the current click to the window\n clickWindow.push(click);\n\n // if there's not enough clicks to be a rage click, return null\n if (clickWindow.length < RAGE_CLICK_THRESHOLD) {\n return null;\n }\n\n // if we've made it here, we have enough trailing clicks on the same element\n // for it to be a rage click\n const firstClick = clickWindow[0];\n const lastClick = clickWindow[clickWindow.length - 1];\n\n const rageClickEvent: EventRageClick = {\n '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(),\n '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(),\n '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp,\n '[Amplitude] Clicks': clickWindow.map((click) => ({\n X: (click.event as MouseEvent).clientX,\n Y: (click.event as MouseEvent).clientY,\n Time: click.timestamp,\n })),\n '[Amplitude] Click Count': clickWindow.length,\n ...firstClick.targetElementProperties,\n };\n\n // restart the sliding window\n clickWindow.splice(0, clickWindow.length);\n\n return { rageClickEvent, time: firstClick.timestamp };\n }),\n filter((result) => result !== null),\n )\n .subscribe((data: { rageClickEvent: EventRageClick; time: number } | null) => {\n /* istanbul ignore if */\n if (data === null) {\n return;\n }\n amplitude.track(AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, data.rageClickEvent, { time: data.time });\n });\n}\n"]}
@@ -1,2 +1,2 @@
1
- export declare const VERSION = "1.6.0";
1
+ export declare const VERSION = "1.6.1";
2
2
  //# sourceMappingURL=version.d.ts.map
@@ -1,5 +1,5 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.VERSION = void 0;
4
- exports.VERSION = '1.6.0';
4
+ exports.VERSION = '1.6.1';
5
5
  //# sourceMappingURL=version.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"version.js","sourceRoot":"","sources":["../../src/version.ts"],"names":[],"mappings":";;;AAAa,QAAA,OAAO,GAAG,OAAO,CAAC","sourcesContent":["export const VERSION = '1.6.0';\n"]}
1
+ {"version":3,"file":"version.js","sourceRoot":"","sources":["../../src/version.ts"],"names":[],"mappings":";;;AAAa,QAAA,OAAO,GAAG,OAAO,CAAC","sourcesContent":["export const VERSION = '1.6.1';\n"]}
@@ -1,7 +1,6 @@
1
1
  import { AllWindowObservables } from 'src/autocapture-plugin';
2
2
  import { BrowserClient } from '@amplitude/analytics-core';
3
3
  import { shouldTrackEvent } from '../helpers';
4
- export declare function _overrideRageClickConfig(rageClickThreshold: number, rageClickWindowMs: number): void;
5
4
  export declare function trackRageClicks({ amplitude, allObservables, shouldTrackRageClick, }: {
6
5
  amplitude: BrowserClient;
7
6
  allObservables: AllWindowObservables;
@@ -1 +1 @@
1
- {"version":3,"file":"track-rage-click.d.ts","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAE9D,OAAO,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAC1D,OAAO,EAA+B,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAQ3E,wBAAgB,wBAAwB,CAAC,kBAAkB,EAAE,MAAM,EAAE,iBAAiB,EAAE,MAAM,QAG7F;AAgBD,wBAAgB,eAAe,CAAC,EAC9B,SAAS,EACT,cAAc,EACd,oBAAoB,GACrB,EAAE;IACD,SAAS,EAAE,aAAa,CAAC;IACzB,cAAc,EAAE,oBAAoB,CAAC;IACrC,oBAAoB,EAAE,gBAAgB,CAAC;CACxC,+BAmDA"}
1
+ {"version":3,"file":"track-rage-click.d.ts","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAE9D,OAAO,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAC1D,OAAO,EAA+B,gBAAgB,EAAE,MAAM,YAAY,CAAC;AA4B3E,wBAAgB,eAAe,CAAC,EAC9B,SAAS,EACT,cAAc,EACd,oBAAoB,GACrB,EAAE;IACD,SAAS,EAAE,aAAa,CAAC;IACzB,cAAc,EAAE,oBAAoB,CAAC;IACrC,oBAAoB,EAAE,gBAAgB,CAAC;CACxC,+BAyEA"}
@@ -1,50 +1,59 @@
1
1
  import { __assign } from "tslib";
2
- import { filter, map, bufferTime } from 'rxjs';
2
+ import { filter, map } from 'rxjs';
3
3
  import { filterOutNonTrackableEvents } from '../helpers';
4
4
  import { AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT } from '../constants';
5
5
  import { DEFAULT_RAGE_CLICK_THRESHOLD, DEFAULT_RAGE_CLICK_WINDOW_MS } from '@amplitude/analytics-core';
6
6
  var RAGE_CLICK_THRESHOLD = DEFAULT_RAGE_CLICK_THRESHOLD;
7
7
  var RAGE_CLICK_WINDOW_MS = DEFAULT_RAGE_CLICK_WINDOW_MS;
8
- // allow override of rage click config for testing only
9
- export function _overrideRageClickConfig(rageClickThreshold, rageClickWindowMs) {
10
- RAGE_CLICK_THRESHOLD = rageClickThreshold;
11
- RAGE_CLICK_WINDOW_MS = rageClickWindowMs;
12
- }
13
8
  export function trackRageClicks(_a) {
14
9
  var amplitude = _a.amplitude, allObservables = _a.allObservables, shouldTrackRageClick = _a.shouldTrackRageClick;
15
10
  var clickObservable = allObservables.clickObservable;
16
- // Buffer clicks within a RAGE_CLICK_WINDOW_MS window and filter for rage clicks
17
- var rageClickObservable = clickObservable.pipe(filter(filterOutNonTrackableEvents), filter(function (click) {
11
+ // Keep track of all clicks within the sliding window
12
+ var clickWindow = [];
13
+ return clickObservable
14
+ .pipe(filter(filterOutNonTrackableEvents), filter(function (click) {
18
15
  return shouldTrackRageClick('click', click.closestTrackedAncestor);
19
- }), bufferTime(RAGE_CLICK_WINDOW_MS), filter(function (clicks) {
20
- // filter if not enough clicks to be a rage click
21
- if (clicks.length < RAGE_CLICK_THRESHOLD) {
22
- return false;
16
+ }), map(function (click) {
17
+ var now = click.timestamp;
18
+ // if the current click isn't on the same element as the most recent click,
19
+ // clear the sliding window and start over
20
+ if (clickWindow.length > 0 &&
21
+ clickWindow[clickWindow.length - 1].closestTrackedAncestor !== click.closestTrackedAncestor) {
22
+ clickWindow.splice(0, clickWindow.length);
23
23
  }
24
- // filter if the last RAGE_CLICK_THRESHOLD clicks were not all on the same element
25
- var trailingIndex = clicks.length - 1;
26
- var lastClickTarget = clicks[trailingIndex].event.target;
27
- while (--trailingIndex >= clicks.length - RAGE_CLICK_THRESHOLD) {
28
- if (clicks[trailingIndex].event.target !== lastClickTarget) {
29
- return false;
24
+ // remove past clicks that are outside the sliding window
25
+ var clickPtr = 0;
26
+ for (; clickPtr < clickWindow.length; clickPtr++) {
27
+ if (now - clickWindow[clickPtr].timestamp < RAGE_CLICK_WINDOW_MS) {
28
+ break;
30
29
  }
31
30
  }
32
- // if we reach here that means the last RAGE_CLICK_THRESHOLD clicks were all on the same element
33
- // and thus we have a rage click
34
- return true;
35
- }), map(function (clicks) {
36
- var firstClick = clicks[0];
37
- var lastClick = clicks[clicks.length - 1];
38
- var rageClickEvent = __assign({ '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(), '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(), '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp, '[Amplitude] Clicks': clicks.map(function (click) { return ({
31
+ clickWindow.splice(0, clickPtr);
32
+ // add the current click to the window
33
+ clickWindow.push(click);
34
+ // if there's not enough clicks to be a rage click, return null
35
+ if (clickWindow.length < RAGE_CLICK_THRESHOLD) {
36
+ return null;
37
+ }
38
+ // if we've made it here, we have enough trailing clicks on the same element
39
+ // for it to be a rage click
40
+ var firstClick = clickWindow[0];
41
+ var lastClick = clickWindow[clickWindow.length - 1];
42
+ var rageClickEvent = __assign({ '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(), '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(), '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp, '[Amplitude] Clicks': clickWindow.map(function (click) { return ({
39
43
  X: click.event.clientX,
40
44
  Y: click.event.clientY,
41
45
  Time: click.timestamp,
42
- }); }), '[Amplitude] Click Count': clicks.length }, firstClick.targetElementProperties);
46
+ }); }), '[Amplitude] Click Count': clickWindow.length }, firstClick.targetElementProperties);
47
+ // restart the sliding window
48
+ clickWindow.splice(0, clickWindow.length);
43
49
  return { rageClickEvent: rageClickEvent, time: firstClick.timestamp };
44
- }));
45
- return rageClickObservable.subscribe(function (_a) {
46
- var rageClickEvent = _a.rageClickEvent, time = _a.time;
47
- amplitude.track(AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, rageClickEvent, { time: time });
50
+ }), filter(function (result) { return result !== null; }))
51
+ .subscribe(function (data) {
52
+ /* istanbul ignore if */
53
+ if (data === null) {
54
+ return;
55
+ }
56
+ amplitude.track(AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, data.rageClickEvent, { time: data.time });
48
57
  });
49
58
  }
50
59
  //# sourceMappingURL=track-rage-click.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"track-rage-click.js","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":"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","sourcesContent":["import { AllWindowObservables } from 'src/autocapture-plugin';\nimport { filter, map, bufferTime } from 'rxjs';\nimport { BrowserClient } from '@amplitude/analytics-core';\nimport { filterOutNonTrackableEvents, shouldTrackEvent } from '../helpers';\nimport { AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT } from '../constants';\nimport { DEFAULT_RAGE_CLICK_THRESHOLD, DEFAULT_RAGE_CLICK_WINDOW_MS } from '@amplitude/analytics-core';\n\nlet RAGE_CLICK_THRESHOLD = DEFAULT_RAGE_CLICK_THRESHOLD;\nlet RAGE_CLICK_WINDOW_MS = DEFAULT_RAGE_CLICK_WINDOW_MS;\n\n// allow override of rage click config for testing only\nexport function _overrideRageClickConfig(rageClickThreshold: number, rageClickWindowMs: number) {\n RAGE_CLICK_THRESHOLD = rageClickThreshold;\n RAGE_CLICK_WINDOW_MS = rageClickWindowMs;\n}\n\ntype Click = {\n X: number;\n Y: number;\n Time: number;\n};\n\ntype EventRageClick = {\n '[Amplitude] Begin Time': string; // ISO-8601\n '[Amplitude] End Time': string; // ISO-8601\n '[Amplitude] Duration': number;\n '[Amplitude] Clicks': Array<Click>;\n '[Amplitude] Click Count': number;\n};\n\nexport function trackRageClicks({\n amplitude,\n allObservables,\n shouldTrackRageClick,\n}: {\n amplitude: BrowserClient;\n allObservables: AllWindowObservables;\n shouldTrackRageClick: shouldTrackEvent;\n}) {\n const { clickObservable } = allObservables;\n\n // Buffer clicks within a RAGE_CLICK_WINDOW_MS window and filter for rage clicks\n const rageClickObservable = clickObservable.pipe(\n filter(filterOutNonTrackableEvents),\n filter((click) => {\n return shouldTrackRageClick('click', click.closestTrackedAncestor);\n }),\n bufferTime(RAGE_CLICK_WINDOW_MS),\n filter((clicks) => {\n // filter if not enough clicks to be a rage click\n if (clicks.length < RAGE_CLICK_THRESHOLD) {\n return false;\n }\n\n // filter if the last RAGE_CLICK_THRESHOLD clicks were not all on the same element\n let trailingIndex = clicks.length - 1;\n const lastClickTarget = clicks[trailingIndex].event.target;\n while (--trailingIndex >= clicks.length - RAGE_CLICK_THRESHOLD) {\n if (clicks[trailingIndex].event.target !== lastClickTarget) {\n return false;\n }\n }\n\n // if we reach here that means the last RAGE_CLICK_THRESHOLD clicks were all on the same element\n // and thus we have a rage click\n return true;\n }),\n map((clicks) => {\n const firstClick = clicks[0];\n const lastClick = clicks[clicks.length - 1];\n const rageClickEvent: EventRageClick = {\n '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(),\n '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(),\n '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp,\n '[Amplitude] Clicks': clicks.map((click) => ({\n X: (click.event as MouseEvent).clientX,\n Y: (click.event as MouseEvent).clientY,\n Time: click.timestamp,\n })),\n '[Amplitude] Click Count': clicks.length,\n ...firstClick.targetElementProperties,\n };\n return { rageClickEvent, time: firstClick.timestamp };\n }),\n );\n\n return rageClickObservable.subscribe(({ rageClickEvent, time }) => {\n amplitude.track(AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, rageClickEvent, { time });\n });\n}\n"]}
1
+ {"version":3,"file":"track-rage-click.js","sourceRoot":"","sources":["../../../src/autocapture/track-rage-click.ts"],"names":[],"mappings":"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","sourcesContent":["import { AllWindowObservables } from 'src/autocapture-plugin';\nimport { filter, map } from 'rxjs';\nimport { BrowserClient } from '@amplitude/analytics-core';\nimport { filterOutNonTrackableEvents, shouldTrackEvent } from '../helpers';\nimport { AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT } from '../constants';\nimport { DEFAULT_RAGE_CLICK_THRESHOLD, DEFAULT_RAGE_CLICK_WINDOW_MS } from '@amplitude/analytics-core';\n\nconst RAGE_CLICK_THRESHOLD = DEFAULT_RAGE_CLICK_THRESHOLD;\nconst RAGE_CLICK_WINDOW_MS = DEFAULT_RAGE_CLICK_WINDOW_MS;\n\ntype Click = {\n X: number;\n Y: number;\n Time: number;\n};\n\ntype EventRageClick = {\n '[Amplitude] Begin Time': string; // ISO-8601\n '[Amplitude] End Time': string; // ISO-8601\n '[Amplitude] Duration': number;\n '[Amplitude] Clicks': Array<Click>;\n '[Amplitude] Click Count': number;\n};\n\ntype ClickEvent = {\n event: MouseEvent | Event;\n timestamp: number;\n targetElementProperties: Record<string, any>;\n closestTrackedAncestor: Element | null;\n};\n\nexport function trackRageClicks({\n amplitude,\n allObservables,\n shouldTrackRageClick,\n}: {\n amplitude: BrowserClient;\n allObservables: AllWindowObservables;\n shouldTrackRageClick: shouldTrackEvent;\n}) {\n const { clickObservable } = allObservables;\n\n // Keep track of all clicks within the sliding window\n const clickWindow: ClickEvent[] = [];\n\n return clickObservable\n .pipe(\n filter(filterOutNonTrackableEvents),\n filter((click) => {\n return shouldTrackRageClick('click', click.closestTrackedAncestor);\n }),\n map((click) => {\n const now = click.timestamp;\n\n // if the current click isn't on the same element as the most recent click,\n // clear the sliding window and start over\n if (\n clickWindow.length > 0 &&\n clickWindow[clickWindow.length - 1].closestTrackedAncestor !== click.closestTrackedAncestor\n ) {\n clickWindow.splice(0, clickWindow.length);\n }\n\n // remove past clicks that are outside the sliding window\n let clickPtr = 0;\n for (; clickPtr < clickWindow.length; clickPtr++) {\n if (now - clickWindow[clickPtr].timestamp < RAGE_CLICK_WINDOW_MS) {\n break;\n }\n }\n clickWindow.splice(0, clickPtr);\n\n // add the current click to the window\n clickWindow.push(click);\n\n // if there's not enough clicks to be a rage click, return null\n if (clickWindow.length < RAGE_CLICK_THRESHOLD) {\n return null;\n }\n\n // if we've made it here, we have enough trailing clicks on the same element\n // for it to be a rage click\n const firstClick = clickWindow[0];\n const lastClick = clickWindow[clickWindow.length - 1];\n\n const rageClickEvent: EventRageClick = {\n '[Amplitude] Begin Time': new Date(firstClick.timestamp).toISOString(),\n '[Amplitude] End Time': new Date(lastClick.timestamp).toISOString(),\n '[Amplitude] Duration': lastClick.timestamp - firstClick.timestamp,\n '[Amplitude] Clicks': clickWindow.map((click) => ({\n X: (click.event as MouseEvent).clientX,\n Y: (click.event as MouseEvent).clientY,\n Time: click.timestamp,\n })),\n '[Amplitude] Click Count': clickWindow.length,\n ...firstClick.targetElementProperties,\n };\n\n // restart the sliding window\n clickWindow.splice(0, clickWindow.length);\n\n return { rageClickEvent, time: firstClick.timestamp };\n }),\n filter((result) => result !== null),\n )\n .subscribe((data: { rageClickEvent: EventRageClick; time: number } | null) => {\n /* istanbul ignore if */\n if (data === null) {\n return;\n }\n amplitude.track(AMPLITUDE_ELEMENT_RAGE_CLICKED_EVENT, data.rageClickEvent, { time: data.time });\n });\n}\n"]}
@@ -1,2 +1,2 @@
1
- export declare const VERSION = "1.6.0";
1
+ export declare const VERSION = "1.6.1";
2
2
  //# sourceMappingURL=version.d.ts.map
@@ -1,2 +1,2 @@
1
- export var VERSION = '1.6.0';
1
+ export var VERSION = '1.6.1';
2
2
  //# sourceMappingURL=version.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"version.js","sourceRoot":"","sources":["../../src/version.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,IAAM,OAAO,GAAG,OAAO,CAAC","sourcesContent":["export const VERSION = '1.6.0';\n"]}
1
+ {"version":3,"file":"version.js","sourceRoot":"","sources":["../../src/version.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,IAAM,OAAO,GAAG,OAAO,CAAC","sourcesContent":["export const VERSION = '1.6.1';\n"]}