@amplitude/plugin-autocapture-browser 1.2.9 → 1.3.0
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/lib/cjs/autocapture/track-action-click.d.ts.map +1 -1
- package/lib/cjs/autocapture/track-action-click.js.map +1 -1
- package/lib/cjs/autocapture/track-change.d.ts +3 -1
- package/lib/cjs/autocapture/track-change.d.ts.map +1 -1
- package/lib/cjs/autocapture/track-change.js +2 -2
- package/lib/cjs/autocapture/track-change.js.map +1 -1
- package/lib/cjs/autocapture/track-click.d.ts +3 -1
- package/lib/cjs/autocapture/track-click.d.ts.map +1 -1
- package/lib/cjs/autocapture/track-click.js +2 -2
- package/lib/cjs/autocapture/track-click.js.map +1 -1
- package/lib/cjs/autocapture-plugin.d.ts +1 -14
- package/lib/cjs/autocapture-plugin.d.ts.map +1 -1
- package/lib/cjs/autocapture-plugin.js +65 -77
- package/lib/cjs/autocapture-plugin.js.map +1 -1
- package/lib/cjs/helpers.d.ts +20 -1
- package/lib/cjs/helpers.d.ts.map +1 -1
- package/lib/cjs/helpers.js +59 -1
- package/lib/cjs/helpers.js.map +1 -1
- package/lib/cjs/observables.d.ts +10 -0
- package/lib/cjs/observables.d.ts.map +1 -0
- package/lib/cjs/observables.js +30 -0
- package/lib/cjs/observables.js.map +1 -0
- package/lib/cjs/pageActions/actions.d.ts +12 -0
- package/lib/cjs/pageActions/actions.d.ts.map +1 -0
- package/lib/cjs/pageActions/actions.js +65 -0
- package/lib/cjs/pageActions/actions.js.map +1 -0
- package/lib/cjs/pageActions/matchEventToFilter.d.ts +10 -0
- package/lib/cjs/pageActions/matchEventToFilter.d.ts.map +1 -0
- package/lib/cjs/pageActions/matchEventToFilter.js +30 -0
- package/lib/cjs/pageActions/matchEventToFilter.js.map +1 -0
- package/lib/cjs/pageActions/triggers.d.ts +20 -0
- package/lib/cjs/pageActions/triggers.d.ts.map +1 -0
- package/lib/cjs/pageActions/triggers.js +133 -0
- package/lib/cjs/pageActions/triggers.js.map +1 -0
- package/lib/cjs/version.d.ts +1 -1
- package/lib/cjs/version.js +1 -1
- package/lib/cjs/version.js.map +1 -1
- package/lib/esm/autocapture/track-action-click.d.ts.map +1 -1
- package/lib/esm/autocapture/track-action-click.js +1 -1
- package/lib/esm/autocapture/track-action-click.js.map +1 -1
- package/lib/esm/autocapture/track-change.d.ts +3 -1
- package/lib/esm/autocapture/track-change.d.ts.map +1 -1
- package/lib/esm/autocapture/track-change.js +3 -3
- package/lib/esm/autocapture/track-change.js.map +1 -1
- package/lib/esm/autocapture/track-click.d.ts +3 -1
- package/lib/esm/autocapture/track-click.d.ts.map +1 -1
- package/lib/esm/autocapture/track-click.js +2 -2
- package/lib/esm/autocapture/track-click.js.map +1 -1
- package/lib/esm/autocapture-plugin.d.ts +1 -14
- package/lib/esm/autocapture-plugin.d.ts.map +1 -1
- package/lib/esm/autocapture-plugin.js +67 -78
- package/lib/esm/autocapture-plugin.js.map +1 -1
- package/lib/esm/helpers.d.ts +20 -1
- package/lib/esm/helpers.d.ts.map +1 -1
- package/lib/esm/helpers.js +55 -0
- package/lib/esm/helpers.js.map +1 -1
- package/lib/esm/observables.d.ts +10 -0
- package/lib/esm/observables.d.ts.map +1 -0
- package/lib/esm/observables.js +25 -0
- package/lib/esm/observables.js.map +1 -0
- package/lib/esm/pageActions/actions.d.ts +12 -0
- package/lib/esm/pageActions/actions.d.ts.map +1 -0
- package/lib/esm/pageActions/actions.js +59 -0
- package/lib/esm/pageActions/actions.js.map +1 -0
- package/lib/esm/pageActions/matchEventToFilter.d.ts +10 -0
- package/lib/esm/pageActions/matchEventToFilter.d.ts.map +1 -0
- package/lib/esm/pageActions/matchEventToFilter.js +26 -0
- package/lib/esm/pageActions/matchEventToFilter.js.map +1 -0
- package/lib/esm/pageActions/triggers.d.ts +20 -0
- package/lib/esm/pageActions/triggers.d.ts.map +1 -0
- package/lib/esm/pageActions/triggers.js +126 -0
- package/lib/esm/pageActions/triggers.js.map +1 -0
- package/lib/esm/version.d.ts +1 -1
- package/lib/esm/version.js +1 -1
- package/lib/esm/version.js.map +1 -1
- package/lib/scripts/amplitude-min.js +1 -1
- package/lib/scripts/amplitude-min.js.gz +0 -0
- package/lib/scripts/amplitude-min.js.map +1 -1
- package/lib/scripts/amplitude-min.umd.js +1 -1
- package/lib/scripts/amplitude-min.umd.js.gz +0 -0
- package/lib/scripts/autocapture/track-action-click.d.ts.map +1 -1
- package/lib/scripts/autocapture/track-change.d.ts +3 -1
- package/lib/scripts/autocapture/track-change.d.ts.map +1 -1
- package/lib/scripts/autocapture/track-click.d.ts +3 -1
- package/lib/scripts/autocapture/track-click.d.ts.map +1 -1
- package/lib/scripts/autocapture-plugin.d.ts +1 -14
- package/lib/scripts/autocapture-plugin.d.ts.map +1 -1
- package/lib/scripts/helpers.d.ts +20 -1
- package/lib/scripts/helpers.d.ts.map +1 -1
- package/lib/scripts/observables.d.ts +10 -0
- package/lib/scripts/observables.d.ts.map +1 -0
- package/lib/scripts/pageActions/actions.d.ts +12 -0
- package/lib/scripts/pageActions/actions.d.ts.map +1 -0
- package/lib/scripts/pageActions/matchEventToFilter.d.ts +10 -0
- package/lib/scripts/pageActions/matchEventToFilter.d.ts.map +1 -0
- package/lib/scripts/pageActions/triggers.d.ts +20 -0
- package/lib/scripts/pageActions/triggers.d.ts.map +1 -0
- package/lib/scripts/version.d.ts +1 -1
- package/package.json +4 -3
package/lib/cjs/helpers.js
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.filterOutNonTrackableEvents = exports.generateUniqueId = exports.asyncLoadScript = exports.getEventTagProps = exports.getClosestElement = exports.querySelectUniqueElements = exports.getNearestLabel = exports.removeEmptyProperties = exports.isEmpty = exports.getAttributesWithPrefix = exports.isPageUrlAllowed = exports.getText = exports.isNonSensitiveElement = exports.isTextNode = exports.isNonSensitiveString = exports.createShouldTrackEvent = void 0;
|
|
3
|
+
exports.isElementBasedEvent = exports.addAdditionalEventProperties = exports.getEventProperties = exports.filterOutNonTrackableEvents = exports.generateUniqueId = exports.asyncLoadScript = exports.getEventTagProps = exports.getClosestElement = exports.querySelectUniqueElements = exports.getNearestLabel = exports.removeEmptyProperties = exports.isEmpty = exports.getAttributesWithPrefix = exports.isPageUrlAllowed = exports.getText = exports.isNonSensitiveElement = exports.isTextNode = exports.isNonSensitiveString = exports.createShouldTrackEvent = void 0;
|
|
4
4
|
var tslib_1 = require("tslib");
|
|
5
5
|
/* eslint-disable no-restricted-globals */
|
|
6
6
|
var constants = tslib_1.__importStar(require("./constants"));
|
|
7
|
+
var hierarchy_1 = require("./hierarchy");
|
|
7
8
|
var SENSITIVE_TAGS = ['input', 'select', 'textarea'];
|
|
8
9
|
var createShouldTrackEvent = function (autocaptureOptions, allowlist) {
|
|
9
10
|
return function (actionType, element) {
|
|
@@ -260,4 +261,61 @@ var filterOutNonTrackableEvents = function (event) {
|
|
|
260
261
|
return true;
|
|
261
262
|
};
|
|
262
263
|
exports.filterOutNonTrackableEvents = filterOutNonTrackableEvents;
|
|
264
|
+
// Returns the Amplitude event properties for the given element.
|
|
265
|
+
var getEventProperties = function (actionType, element, dataAttributePrefix) {
|
|
266
|
+
var _a;
|
|
267
|
+
var _b, _c;
|
|
268
|
+
/* istanbul ignore next */
|
|
269
|
+
var tag = (_c = (_b = element === null || element === void 0 ? void 0 : element.tagName) === null || _b === void 0 ? void 0 : _b.toLowerCase) === null || _c === void 0 ? void 0 : _c.call(_b);
|
|
270
|
+
/* istanbul ignore next */
|
|
271
|
+
var rect = typeof element.getBoundingClientRect === 'function' ? element.getBoundingClientRect() : { left: null, top: null };
|
|
272
|
+
var ariaLabel = element.getAttribute('aria-label');
|
|
273
|
+
var attributes = (0, exports.getAttributesWithPrefix)(element, dataAttributePrefix);
|
|
274
|
+
var nearestLabel = (0, exports.getNearestLabel)(element);
|
|
275
|
+
/* istanbul ignore next */
|
|
276
|
+
var properties = (_a = {},
|
|
277
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_ID] = element.getAttribute('id') || '',
|
|
278
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_CLASS] = element.getAttribute('class'),
|
|
279
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_HIERARCHY] = (0, hierarchy_1.getHierarchy)(element),
|
|
280
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_TAG] = tag,
|
|
281
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_TEXT] = (0, exports.getText)(element),
|
|
282
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_POSITION_LEFT] = rect.left == null ? null : Math.round(rect.left),
|
|
283
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_POSITION_TOP] = rect.top == null ? null : Math.round(rect.top),
|
|
284
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_ARIA_LABEL] = ariaLabel,
|
|
285
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_ATTRIBUTES] = attributes,
|
|
286
|
+
_a[constants.AMPLITUDE_EVENT_PROP_ELEMENT_PARENT_LABEL] = nearestLabel,
|
|
287
|
+
_a[constants.AMPLITUDE_EVENT_PROP_PAGE_URL] = window.location.href.split('?')[0],
|
|
288
|
+
_a[constants.AMPLITUDE_EVENT_PROP_PAGE_TITLE] = (typeof document !== 'undefined' && document.title) || '',
|
|
289
|
+
_a[constants.AMPLITUDE_EVENT_PROP_VIEWPORT_HEIGHT] = window.innerHeight,
|
|
290
|
+
_a[constants.AMPLITUDE_EVENT_PROP_VIEWPORT_WIDTH] = window.innerWidth,
|
|
291
|
+
_a);
|
|
292
|
+
if (tag === 'a' && actionType === 'click' && element instanceof HTMLAnchorElement) {
|
|
293
|
+
properties[constants.AMPLITUDE_EVENT_PROP_ELEMENT_HREF] = element.href;
|
|
294
|
+
}
|
|
295
|
+
return (0, exports.removeEmptyProperties)(properties);
|
|
296
|
+
};
|
|
297
|
+
exports.getEventProperties = getEventProperties;
|
|
298
|
+
var addAdditionalEventProperties = function (event, type, selectorAllowlist, dataAttributePrefix) {
|
|
299
|
+
var baseEvent = {
|
|
300
|
+
event: event,
|
|
301
|
+
timestamp: Date.now(),
|
|
302
|
+
type: type,
|
|
303
|
+
};
|
|
304
|
+
if (isElementBasedEvent(baseEvent) && baseEvent.event.target !== null) {
|
|
305
|
+
// Retrieve additional event properties from the target element
|
|
306
|
+
var closestTrackedAncestor = (0, exports.getClosestElement)(baseEvent.event.target, selectorAllowlist);
|
|
307
|
+
if (closestTrackedAncestor) {
|
|
308
|
+
baseEvent.closestTrackedAncestor = closestTrackedAncestor;
|
|
309
|
+
baseEvent.targetElementProperties = (0, exports.getEventProperties)(baseEvent.type, closestTrackedAncestor, dataAttributePrefix);
|
|
310
|
+
}
|
|
311
|
+
return baseEvent;
|
|
312
|
+
}
|
|
313
|
+
return baseEvent;
|
|
314
|
+
};
|
|
315
|
+
exports.addAdditionalEventProperties = addAdditionalEventProperties;
|
|
316
|
+
// Type predicate
|
|
317
|
+
function isElementBasedEvent(event) {
|
|
318
|
+
return event.type === 'click' || event.type === 'change';
|
|
319
|
+
}
|
|
320
|
+
exports.isElementBasedEvent = isElementBasedEvent;
|
|
263
321
|
//# sourceMappingURL=helpers.js.map
|
package/lib/cjs/helpers.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"helpers.js","sourceRoot":"","sources":["../../src/helpers.ts"],"names":[],"mappings":"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","sourcesContent":["/* eslint-disable no-restricted-globals */\nimport * as constants from './constants';\nimport { ElementInteractionsOptions, ActionType } from '@amplitude/analytics-core';\nimport { ElementBasedEvent, ElementBasedTimestampedEvent } from './autocapture-plugin';\n\nexport type JSONValue = string | number | boolean | null | { [x: string]: JSONValue } | Array<JSONValue>;\n\nconst SENSITIVE_TAGS = ['input', 'select', 'textarea'];\n\nexport type shouldTrackEvent = (actionType: ActionType, element: Element) => boolean;\n\nexport const createShouldTrackEvent = (\n autocaptureOptions: ElementInteractionsOptions,\n allowlist: string[], // this can be any type of css selector allow list\n): shouldTrackEvent => {\n return (actionType: ActionType, element: Element) => {\n const { pageUrlAllowlist, shouldTrackEventResolver } = autocaptureOptions;\n\n /* istanbul ignore next */\n const tag = element?.tagName?.toLowerCase?.();\n // window, document, and Text nodes have no tag\n if (!tag) {\n return false;\n }\n\n if (shouldTrackEventResolver) {\n return shouldTrackEventResolver(actionType, element);\n }\n\n if (!isPageUrlAllowed(window.location.href, pageUrlAllowlist)) {\n return false;\n }\n\n /* istanbul ignore next */\n const elementType = String(element?.getAttribute('type')) || '';\n if (typeof elementType === 'string') {\n switch (elementType.toLowerCase()) {\n case 'hidden':\n return false;\n case 'password':\n return false;\n }\n }\n\n /* istanbul ignore if */\n if (allowlist) {\n const hasMatchAnyAllowedSelector = allowlist.some((selector) => !!element?.matches?.(selector));\n if (!hasMatchAnyAllowedSelector) {\n return false;\n }\n }\n\n switch (tag) {\n case 'input':\n case 'select':\n case 'textarea':\n return actionType === 'change' || actionType === 'click';\n default: {\n /* istanbul ignore next */\n const computedStyle = window?.getComputedStyle?.(element);\n /* istanbul ignore next */\n if (computedStyle && computedStyle.getPropertyValue('cursor') === 'pointer' && actionType === 'click') {\n return true;\n }\n return actionType === 'click';\n }\n }\n };\n};\n\nexport const isNonSensitiveString = (text: string | null) => {\n if (text == null) {\n return false;\n }\n if (typeof text === 'string') {\n const ccRegex =\n /^(?:(4[0-9]{12}(?:[0-9]{3})?)|(5[1-5][0-9]{14})|(6(?:011|5[0-9]{2})[0-9]{12})|(3[47][0-9]{13})|(3(?:0[0-5]|[68][0-9])[0-9]{11})|((?:2131|1800|35[0-9]{3})[0-9]{11}))$/;\n if (ccRegex.test((text || '').replace(/[- ]/g, ''))) {\n return false;\n }\n const ssnRegex = /(^\\d{3}-?\\d{2}-?\\d{4}$)/;\n if (ssnRegex.test(text)) {\n return false;\n }\n }\n return true;\n};\n\nexport const isTextNode = (node: Node) => {\n return !!node && node.nodeType === 3;\n};\n\nexport const isNonSensitiveElement = (element: Element) => {\n /* istanbul ignore next */\n const tag = element?.tagName?.toLowerCase?.();\n const isContentEditable =\n element instanceof HTMLElement ? element.getAttribute('contenteditable')?.toLowerCase() === 'true' : false;\n\n return !SENSITIVE_TAGS.includes(tag) && !isContentEditable;\n};\n\n// Maybe this can be simplified with element.innerText, keep and manual concatenating for now, more research needed.\nexport const getText = (element: Element): string => {\n let text = '';\n if (isNonSensitiveElement(element) && element.childNodes && element.childNodes.length) {\n element.childNodes.forEach((child) => {\n let childText = '';\n if (isTextNode(child)) {\n if (child.textContent) {\n childText = child.textContent;\n }\n } else {\n childText = getText(child as Element);\n }\n text += childText\n .split(/(\\s+)/)\n .filter(isNonSensitiveString)\n .join('')\n .replace(/[\\r\\n]/g, ' ')\n .replace(/[ ]+/g, ' ')\n .substring(0, 255);\n });\n }\n return text;\n};\n\nexport const isPageUrlAllowed = (url: string, pageUrlAllowlist: (string | RegExp)[] | undefined) => {\n if (!pageUrlAllowlist || !pageUrlAllowlist.length) {\n return true;\n }\n return pageUrlAllowlist.some((allowedUrl) => {\n if (typeof allowedUrl === 'string') {\n return url === allowedUrl;\n }\n return url.match(allowedUrl);\n });\n};\n\nexport const getAttributesWithPrefix = (element: Element, prefix: string): { [key: string]: string } => {\n return element.getAttributeNames().reduce((attributes: { [key: string]: string }, attributeName) => {\n if (attributeName.startsWith(prefix)) {\n const attributeKey = attributeName.replace(prefix, '');\n const attributeValue = element.getAttribute(attributeName);\n if (attributeKey) {\n attributes[attributeKey] = attributeValue || '';\n }\n }\n return attributes;\n }, {});\n};\n\nexport const isEmpty = (value: unknown) => {\n return (\n value === undefined ||\n value === null ||\n (typeof value === 'object' && Object.keys(value).length === 0) ||\n (typeof value === 'string' && value.trim().length === 0)\n );\n};\n\nexport const removeEmptyProperties = (properties: { [key: string]: unknown }) => {\n return Object.keys(properties).reduce((filteredProperties: { [key: string]: unknown }, key) => {\n const value = properties[key];\n if (!isEmpty(value)) {\n filteredProperties[key] = value;\n }\n return filteredProperties;\n }, {});\n};\n\nexport const getNearestLabel = (element: Element): string => {\n const parent = element.parentElement;\n if (!parent) {\n return '';\n }\n let labelElement;\n try {\n labelElement = parent.querySelector(':scope>span,h1,h2,h3,h4,h5,h6');\n } catch (error) {\n /* istanbul ignore next */\n labelElement = null;\n }\n if (labelElement) {\n /* istanbul ignore next */\n const labelText = labelElement.textContent || '';\n return isNonSensitiveString(labelText) ? labelText : '';\n }\n return getNearestLabel(parent);\n};\n\nexport const querySelectUniqueElements = (root: Element | Document, selectors: string[]): Element[] => {\n if (root && 'querySelectorAll' in root && typeof root.querySelectorAll === 'function') {\n const elementSet = selectors.reduce((elements: Set<Element>, selector) => {\n if (selector) {\n const selectedElements = Array.from(root.querySelectorAll(selector));\n selectedElements.forEach((element) => {\n elements.add(element);\n });\n }\n return elements;\n }, new Set<Element>());\n return Array.from(elementSet);\n }\n return [];\n};\n\n// Similar as element.closest, but works with multiple selectors\nexport const getClosestElement = (element: Element | null, selectors: string[]): Element | null => {\n if (!element) {\n return null;\n }\n /* istanbul ignore next */\n if (selectors.some((selector) => element?.matches?.(selector))) {\n return element;\n }\n /* istanbul ignore next */\n return getClosestElement(element?.parentElement, selectors);\n};\n\n// Returns the element properties for the given element in Visual Labeling.\nexport const getEventTagProps = (element: Element) => {\n if (!element) {\n return {};\n }\n /* istanbul ignore next */\n const tag = element?.tagName?.toLowerCase?.();\n\n const properties: Record<string, JSONValue> = {\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_TAG]: tag,\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_TEXT]: getText(element),\n [constants.AMPLITUDE_EVENT_PROP_PAGE_URL]: window.location.href.split('?')[0],\n };\n return removeEmptyProperties(properties);\n};\n\nexport const asyncLoadScript = (url: string) => {\n return new Promise((resolve, reject) => {\n try {\n const scriptElement = document.createElement('script');\n scriptElement.type = 'text/javascript';\n scriptElement.async = true;\n scriptElement.src = url;\n scriptElement.addEventListener(\n 'load',\n () => {\n resolve({ status: true });\n },\n { once: true },\n );\n scriptElement.addEventListener('error', () => {\n reject({\n status: false,\n message: `Failed to load the script ${url}`,\n });\n });\n /* istanbul ignore next */\n document.head?.appendChild(scriptElement);\n } catch (error) {\n /* istanbul ignore next */\n reject(error);\n }\n });\n};\n\nexport function generateUniqueId(): string {\n return `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;\n}\n\nexport const filterOutNonTrackableEvents = (event: ElementBasedTimestampedEvent<ElementBasedEvent>): boolean => {\n // Filter out changeEvent events with no target\n // This could happen when change events are triggered programmatically\n if (event.event.target === null || !event.closestTrackedAncestor) {\n return false;\n }\n\n return true;\n};\n"]}
|
|
1
|
+
{"version":3,"file":"helpers.js","sourceRoot":"","sources":["../../src/helpers.ts"],"names":[],"mappings":"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","sourcesContent":["/* eslint-disable no-restricted-globals */\nimport * as constants from './constants';\nimport { ElementInteractionsOptions, ActionType } from '@amplitude/analytics-core';\nimport { getHierarchy } from './hierarchy';\n\nexport type JSONValue = string | number | boolean | null | { [x: string]: JSONValue } | Array<JSONValue>;\n\nconst SENSITIVE_TAGS = ['input', 'select', 'textarea'];\n\nexport type shouldTrackEvent = (actionType: ActionType, element: Element) => boolean;\n\nexport const createShouldTrackEvent = (\n autocaptureOptions: ElementInteractionsOptions,\n allowlist: string[], // this can be any type of css selector allow list\n): shouldTrackEvent => {\n return (actionType: ActionType, element: Element) => {\n const { pageUrlAllowlist, shouldTrackEventResolver } = autocaptureOptions;\n\n /* istanbul ignore next */\n const tag = element?.tagName?.toLowerCase?.();\n // window, document, and Text nodes have no tag\n if (!tag) {\n return false;\n }\n\n if (shouldTrackEventResolver) {\n return shouldTrackEventResolver(actionType, element);\n }\n\n if (!isPageUrlAllowed(window.location.href, pageUrlAllowlist)) {\n return false;\n }\n\n /* istanbul ignore next */\n const elementType = String(element?.getAttribute('type')) || '';\n if (typeof elementType === 'string') {\n switch (elementType.toLowerCase()) {\n case 'hidden':\n return false;\n case 'password':\n return false;\n }\n }\n\n /* istanbul ignore if */\n if (allowlist) {\n const hasMatchAnyAllowedSelector = allowlist.some((selector) => !!element?.matches?.(selector));\n if (!hasMatchAnyAllowedSelector) {\n return false;\n }\n }\n\n switch (tag) {\n case 'input':\n case 'select':\n case 'textarea':\n return actionType === 'change' || actionType === 'click';\n default: {\n /* istanbul ignore next */\n const computedStyle = window?.getComputedStyle?.(element);\n /* istanbul ignore next */\n if (computedStyle && computedStyle.getPropertyValue('cursor') === 'pointer' && actionType === 'click') {\n return true;\n }\n return actionType === 'click';\n }\n }\n };\n};\n\nexport const isNonSensitiveString = (text: string | null) => {\n if (text == null) {\n return false;\n }\n if (typeof text === 'string') {\n const ccRegex =\n /^(?:(4[0-9]{12}(?:[0-9]{3})?)|(5[1-5][0-9]{14})|(6(?:011|5[0-9]{2})[0-9]{12})|(3[47][0-9]{13})|(3(?:0[0-5]|[68][0-9])[0-9]{11})|((?:2131|1800|35[0-9]{3})[0-9]{11}))$/;\n if (ccRegex.test((text || '').replace(/[- ]/g, ''))) {\n return false;\n }\n const ssnRegex = /(^\\d{3}-?\\d{2}-?\\d{4}$)/;\n if (ssnRegex.test(text)) {\n return false;\n }\n }\n return true;\n};\n\nexport const isTextNode = (node: Node) => {\n return !!node && node.nodeType === 3;\n};\n\nexport const isNonSensitiveElement = (element: Element) => {\n /* istanbul ignore next */\n const tag = element?.tagName?.toLowerCase?.();\n const isContentEditable =\n element instanceof HTMLElement ? element.getAttribute('contenteditable')?.toLowerCase() === 'true' : false;\n\n return !SENSITIVE_TAGS.includes(tag) && !isContentEditable;\n};\n\n// Maybe this can be simplified with element.innerText, keep and manual concatenating for now, more research needed.\nexport const getText = (element: Element): string => {\n let text = '';\n if (isNonSensitiveElement(element) && element.childNodes && element.childNodes.length) {\n element.childNodes.forEach((child) => {\n let childText = '';\n if (isTextNode(child)) {\n if (child.textContent) {\n childText = child.textContent;\n }\n } else {\n childText = getText(child as Element);\n }\n text += childText\n .split(/(\\s+)/)\n .filter(isNonSensitiveString)\n .join('')\n .replace(/[\\r\\n]/g, ' ')\n .replace(/[ ]+/g, ' ')\n .substring(0, 255);\n });\n }\n return text;\n};\n\nexport const isPageUrlAllowed = (url: string, pageUrlAllowlist: (string | RegExp)[] | undefined) => {\n if (!pageUrlAllowlist || !pageUrlAllowlist.length) {\n return true;\n }\n return pageUrlAllowlist.some((allowedUrl) => {\n if (typeof allowedUrl === 'string') {\n return url === allowedUrl;\n }\n return url.match(allowedUrl);\n });\n};\n\nexport const getAttributesWithPrefix = (element: Element, prefix: string): { [key: string]: string } => {\n return element.getAttributeNames().reduce((attributes: { [key: string]: string }, attributeName) => {\n if (attributeName.startsWith(prefix)) {\n const attributeKey = attributeName.replace(prefix, '');\n const attributeValue = element.getAttribute(attributeName);\n if (attributeKey) {\n attributes[attributeKey] = attributeValue || '';\n }\n }\n return attributes;\n }, {});\n};\n\nexport const isEmpty = (value: unknown) => {\n return (\n value === undefined ||\n value === null ||\n (typeof value === 'object' && Object.keys(value).length === 0) ||\n (typeof value === 'string' && value.trim().length === 0)\n );\n};\n\nexport const removeEmptyProperties = (properties: { [key: string]: unknown }) => {\n return Object.keys(properties).reduce((filteredProperties: { [key: string]: unknown }, key) => {\n const value = properties[key];\n if (!isEmpty(value)) {\n filteredProperties[key] = value;\n }\n return filteredProperties;\n }, {});\n};\n\nexport const getNearestLabel = (element: Element): string => {\n const parent = element.parentElement;\n if (!parent) {\n return '';\n }\n let labelElement;\n try {\n labelElement = parent.querySelector(':scope>span,h1,h2,h3,h4,h5,h6');\n } catch (error) {\n /* istanbul ignore next */\n labelElement = null;\n }\n if (labelElement) {\n /* istanbul ignore next */\n const labelText = labelElement.textContent || '';\n return isNonSensitiveString(labelText) ? labelText : '';\n }\n return getNearestLabel(parent);\n};\n\nexport const querySelectUniqueElements = (root: Element | Document, selectors: string[]): Element[] => {\n if (root && 'querySelectorAll' in root && typeof root.querySelectorAll === 'function') {\n const elementSet = selectors.reduce((elements: Set<Element>, selector) => {\n if (selector) {\n const selectedElements = Array.from(root.querySelectorAll(selector));\n selectedElements.forEach((element) => {\n elements.add(element);\n });\n }\n return elements;\n }, new Set<Element>());\n return Array.from(elementSet);\n }\n return [];\n};\n\n// Similar as element.closest, but works with multiple selectors\nexport const getClosestElement = (element: Element | null, selectors: string[]): Element | null => {\n if (!element) {\n return null;\n }\n /* istanbul ignore next */\n if (selectors.some((selector) => element?.matches?.(selector))) {\n return element;\n }\n /* istanbul ignore next */\n return getClosestElement(element?.parentElement, selectors);\n};\n\n// Returns the element properties for the given element in Visual Labeling.\nexport const getEventTagProps = (element: Element) => {\n if (!element) {\n return {};\n }\n /* istanbul ignore next */\n const tag = element?.tagName?.toLowerCase?.();\n\n const properties: Record<string, JSONValue> = {\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_TAG]: tag,\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_TEXT]: getText(element),\n [constants.AMPLITUDE_EVENT_PROP_PAGE_URL]: window.location.href.split('?')[0],\n };\n return removeEmptyProperties(properties);\n};\n\nexport const asyncLoadScript = (url: string) => {\n return new Promise((resolve, reject) => {\n try {\n const scriptElement = document.createElement('script');\n scriptElement.type = 'text/javascript';\n scriptElement.async = true;\n scriptElement.src = url;\n scriptElement.addEventListener(\n 'load',\n () => {\n resolve({ status: true });\n },\n { once: true },\n );\n scriptElement.addEventListener('error', () => {\n reject({\n status: false,\n message: `Failed to load the script ${url}`,\n });\n });\n /* istanbul ignore next */\n document.head?.appendChild(scriptElement);\n } catch (error) {\n /* istanbul ignore next */\n reject(error);\n }\n });\n};\n\nexport function generateUniqueId(): string {\n return `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;\n}\n\nexport const filterOutNonTrackableEvents = (event: ElementBasedTimestampedEvent<ElementBasedEvent>): boolean => {\n // Filter out changeEvent events with no target\n // This could happen when change events are triggered programmatically\n if (event.event.target === null || !event.closestTrackedAncestor) {\n return false;\n }\n\n return true;\n};\n\n// Returns the Amplitude event properties for the given element.\nexport const getEventProperties = (actionType: ActionType, element: Element, dataAttributePrefix: string) => {\n /* istanbul ignore next */\n const tag = element?.tagName?.toLowerCase?.();\n /* istanbul ignore next */\n const rect =\n typeof element.getBoundingClientRect === 'function' ? element.getBoundingClientRect() : { left: null, top: null };\n const ariaLabel = element.getAttribute('aria-label');\n const attributes = getAttributesWithPrefix(element, dataAttributePrefix);\n const nearestLabel = getNearestLabel(element);\n /* istanbul ignore next */\n const properties: Record<string, any> = {\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_ID]: element.getAttribute('id') || '',\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_CLASS]: element.getAttribute('class'),\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_HIERARCHY]: getHierarchy(element),\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_TAG]: tag,\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_TEXT]: getText(element),\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_POSITION_LEFT]: rect.left == null ? null : Math.round(rect.left),\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_POSITION_TOP]: rect.top == null ? null : Math.round(rect.top),\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_ARIA_LABEL]: ariaLabel,\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_ATTRIBUTES]: attributes,\n [constants.AMPLITUDE_EVENT_PROP_ELEMENT_PARENT_LABEL]: nearestLabel,\n [constants.AMPLITUDE_EVENT_PROP_PAGE_URL]: window.location.href.split('?')[0],\n [constants.AMPLITUDE_EVENT_PROP_PAGE_TITLE]: (typeof document !== 'undefined' && document.title) || '',\n [constants.AMPLITUDE_EVENT_PROP_VIEWPORT_HEIGHT]: window.innerHeight,\n [constants.AMPLITUDE_EVENT_PROP_VIEWPORT_WIDTH]: window.innerWidth,\n };\n if (tag === 'a' && actionType === 'click' && element instanceof HTMLAnchorElement) {\n properties[constants.AMPLITUDE_EVENT_PROP_ELEMENT_HREF] = element.href;\n }\n return removeEmptyProperties(properties);\n};\n\nexport type AutoCaptureOptionsWithDefaults = Required<\n Pick<ElementInteractionsOptions, 'debounceTime' | 'cssSelectorAllowlist' | 'actionClickAllowlist'>\n> &\n ElementInteractionsOptions;\n\nexport const addAdditionalEventProperties = <T>(\n event: T,\n type: TimestampedEvent<T>['type'],\n selectorAllowlist: string[],\n dataAttributePrefix: string,\n): TimestampedEvent<T> | ElementBasedTimestampedEvent<T> => {\n const baseEvent: BaseTimestampedEvent<T> | ElementBasedTimestampedEvent<T> = {\n event,\n timestamp: Date.now(),\n type,\n };\n\n if (isElementBasedEvent(baseEvent) && baseEvent.event.target !== null) {\n // Retrieve additional event properties from the target element\n const closestTrackedAncestor = getClosestElement(baseEvent.event.target as HTMLElement, selectorAllowlist);\n if (closestTrackedAncestor) {\n baseEvent.closestTrackedAncestor = closestTrackedAncestor;\n baseEvent.targetElementProperties = getEventProperties(\n baseEvent.type,\n closestTrackedAncestor,\n dataAttributePrefix,\n );\n }\n return baseEvent;\n }\n\n return baseEvent;\n};\n\n// Base TimestampedEvent type\nexport type BaseTimestampedEvent<T> = {\n event: T;\n timestamp: number;\n type: 'rage' | 'click' | 'change' | 'error' | 'navigate' | 'mutation';\n};\n\n// Specific types for events with targetElementProperties\nexport type ElementBasedEvent = MouseEvent | Event;\nexport type ElementBasedTimestampedEvent<T> = BaseTimestampedEvent<T> & {\n event: MouseEvent | Event;\n type: 'click' | 'change';\n closestTrackedAncestor: Element;\n targetElementProperties: Record<string, any>;\n};\n\nexport type evaluateTriggersFn = <T extends ElementBasedEvent>(\n event: ElementBasedTimestampedEvent<T>,\n) => ElementBasedTimestampedEvent<T>;\n\n// Union type for all possible TimestampedEvents\nexport type TimestampedEvent<T> = BaseTimestampedEvent<T> | ElementBasedTimestampedEvent<T>;\n\n// Type predicate\nexport function isElementBasedEvent<T>(event: BaseTimestampedEvent<T>): event is ElementBasedTimestampedEvent<T> {\n return event.type === 'click' || event.type === 'change';\n}\n"]}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { Observable } from 'rxjs';
|
|
2
|
+
/**
|
|
3
|
+
* Creates an observable that tracks DOM mutations on the document body.
|
|
4
|
+
*/
|
|
5
|
+
export declare const createMutationObservable: () => Observable<MutationRecord[]>;
|
|
6
|
+
/**
|
|
7
|
+
* Creates an observable that tracks click events on the document.
|
|
8
|
+
*/
|
|
9
|
+
export declare const createClickObservable: () => Observable<MouseEvent>;
|
|
10
|
+
//# sourceMappingURL=observables.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"observables.d.ts","sourceRoot":"","sources":["../../src/observables.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAa,MAAM,MAAM,CAAC;AAE7C;;GAEG;AACH,eAAO,MAAM,wBAAwB,QAAO,WAAW,cAAc,EAAE,CAatE,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,qBAAqB,QAAO,WAAW,UAAU,CAE7D,CAAC"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.createClickObservable = exports.createMutationObservable = void 0;
|
|
4
|
+
var rxjs_1 = require("rxjs");
|
|
5
|
+
/**
|
|
6
|
+
* Creates an observable that tracks DOM mutations on the document body.
|
|
7
|
+
*/
|
|
8
|
+
var createMutationObservable = function () {
|
|
9
|
+
return new rxjs_1.Observable(function (observer) {
|
|
10
|
+
var mutationObserver = new MutationObserver(function (mutations) {
|
|
11
|
+
observer.next(mutations);
|
|
12
|
+
});
|
|
13
|
+
mutationObserver.observe(document.body, {
|
|
14
|
+
childList: true,
|
|
15
|
+
attributes: true,
|
|
16
|
+
characterData: true,
|
|
17
|
+
subtree: true,
|
|
18
|
+
});
|
|
19
|
+
return function () { return mutationObserver.disconnect(); };
|
|
20
|
+
});
|
|
21
|
+
};
|
|
22
|
+
exports.createMutationObservable = createMutationObservable;
|
|
23
|
+
/**
|
|
24
|
+
* Creates an observable that tracks click events on the document.
|
|
25
|
+
*/
|
|
26
|
+
var createClickObservable = function () {
|
|
27
|
+
return (0, rxjs_1.fromEvent)(document, 'click', { capture: true });
|
|
28
|
+
};
|
|
29
|
+
exports.createClickObservable = createClickObservable;
|
|
30
|
+
//# sourceMappingURL=observables.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"observables.js","sourceRoot":"","sources":["../../src/observables.ts"],"names":[],"mappings":";;;AAAA,6BAA6C;AAE7C;;GAEG;AACI,IAAM,wBAAwB,GAAG;IACtC,OAAO,IAAI,iBAAU,CAAmB,UAAC,QAAQ;QAC/C,IAAM,gBAAgB,GAAG,IAAI,gBAAgB,CAAC,UAAC,SAAS;YACtD,QAAQ,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;QAC3B,CAAC,CAAC,CAAC;QACH,gBAAgB,CAAC,OAAO,CAAC,QAAQ,CAAC,IAAI,EAAE;YACtC,SAAS,EAAE,IAAI;YACf,UAAU,EAAE,IAAI;YAChB,aAAa,EAAE,IAAI;YACnB,OAAO,EAAE,IAAI;SACd,CAAC,CAAC;QACH,OAAO,cAAM,OAAA,gBAAgB,CAAC,UAAU,EAAE,EAA7B,CAA6B,CAAC;IAC7C,CAAC,CAAC,CAAC;AACL,CAAC,CAAC;AAbW,QAAA,wBAAwB,4BAanC;AAEF;;GAEG;AACI,IAAM,qBAAqB,GAAG;IACnC,OAAO,IAAA,gBAAS,EAAa,QAAQ,EAAE,OAAO,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC,CAAC;AACrE,CAAC,CAAC;AAFW,QAAA,qBAAqB,yBAEhC","sourcesContent":["import { Observable, fromEvent } from 'rxjs';\n\n/**\n * Creates an observable that tracks DOM mutations on the document body.\n */\nexport const createMutationObservable = (): Observable<MutationRecord[]> => {\n return new Observable<MutationRecord[]>((observer) => {\n const mutationObserver = new MutationObserver((mutations) => {\n observer.next(mutations);\n });\n mutationObserver.observe(document.body, {\n childList: true,\n attributes: true,\n characterData: true,\n subtree: true,\n });\n return () => mutationObserver.disconnect();\n });\n};\n\n/**\n * Creates an observable that tracks click events on the document.\n */\nexport const createClickObservable = (): Observable<MouseEvent> => {\n return fromEvent<MouseEvent>(document, 'click', { capture: true });\n};\n"]}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { DataSource, PageAction } from '@amplitude/analytics-core/lib/esm/types/element-interactions';
|
|
2
|
+
import { ElementBasedTimestampedEvent, ElementBasedEvent } from 'src/helpers';
|
|
3
|
+
/**
|
|
4
|
+
* Gets the DOM element specified by the data source configuration
|
|
5
|
+
* @param dataSource - Configuration for finding the target element
|
|
6
|
+
* @param contextElement - The element to start searching from
|
|
7
|
+
* @returns The matching DOM element or undefined if not found
|
|
8
|
+
*/
|
|
9
|
+
export declare const getDataSource: (dataSource: DataSource, contextElement: HTMLElement) => Element | null | undefined;
|
|
10
|
+
export declare const extractDataFromDataSource: (dataSource: DataSource, contextElement: HTMLElement) => string | null | undefined;
|
|
11
|
+
export declare const executeActions: (actions: (string | PageAction)[], ev: ElementBasedTimestampedEvent<ElementBasedEvent>) => void;
|
|
12
|
+
//# sourceMappingURL=actions.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"actions.d.ts","sourceRoot":"","sources":["../../../src/pageActions/actions.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,UAAU,EAAE,MAAM,8DAA8D,CAAC;AAC3G,OAAO,EAAE,4BAA4B,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAG9E;;;;;GAKG;AACH,eAAO,MAAM,aAAa,eAAgB,UAAU,kBAAkB,WAAW,+BAoBhF,CAAC;AAGF,eAAO,MAAM,yBAAyB,eAAgB,UAAU,kBAAkB,WAAW,8BAkB5F,CAAC;AAGF,eAAO,MAAM,cAAc,YAChB,CAAC,MAAM,GAAG,UAAU,CAAC,EAAE,MAC5B,6BAA6B,iBAAiB,CAAC,SAepD,CAAC"}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.executeActions = exports.extractDataFromDataSource = exports.getDataSource = void 0;
|
|
4
|
+
// Get DataSource
|
|
5
|
+
/**
|
|
6
|
+
* Gets the DOM element specified by the data source configuration
|
|
7
|
+
* @param dataSource - Configuration for finding the target element
|
|
8
|
+
* @param contextElement - The element to start searching from
|
|
9
|
+
* @returns The matching DOM element or undefined if not found
|
|
10
|
+
*/
|
|
11
|
+
var getDataSource = function (dataSource, contextElement) {
|
|
12
|
+
// Only process DOM_ELEMENT type data sources
|
|
13
|
+
if (dataSource.sourceType === 'DOM_ELEMENT') {
|
|
14
|
+
// If scope is specified, find the closest ancestor matching the scope rather than using documentElement (html) as the scope
|
|
15
|
+
var scopingElement = document.documentElement;
|
|
16
|
+
if (dataSource.scope && contextElement) {
|
|
17
|
+
scopingElement = contextElement.closest(dataSource.scope);
|
|
18
|
+
}
|
|
19
|
+
// If we have both a scope and selector, find the matching element
|
|
20
|
+
if (scopingElement && dataSource.selector) {
|
|
21
|
+
return scopingElement.querySelector(dataSource.selector);
|
|
22
|
+
}
|
|
23
|
+
// Return scopingElement if no selector was specified
|
|
24
|
+
return scopingElement;
|
|
25
|
+
}
|
|
26
|
+
// Return undefined for non-DOM_ELEMENT data sources
|
|
27
|
+
return undefined;
|
|
28
|
+
};
|
|
29
|
+
exports.getDataSource = getDataSource;
|
|
30
|
+
// extract DataSource
|
|
31
|
+
var extractDataFromDataSource = function (dataSource, contextElement) {
|
|
32
|
+
// Extract from DOM Element
|
|
33
|
+
if (dataSource.sourceType === 'DOM_ELEMENT') {
|
|
34
|
+
var sourceElement = (0, exports.getDataSource)(dataSource, contextElement);
|
|
35
|
+
if (!sourceElement) {
|
|
36
|
+
return undefined;
|
|
37
|
+
}
|
|
38
|
+
if (dataSource.elementExtractType === 'TEXT') {
|
|
39
|
+
return sourceElement.textContent;
|
|
40
|
+
}
|
|
41
|
+
else if (dataSource.elementExtractType === 'ATTRIBUTE' && dataSource.attribute) {
|
|
42
|
+
return sourceElement.getAttribute(dataSource.attribute);
|
|
43
|
+
}
|
|
44
|
+
return undefined;
|
|
45
|
+
}
|
|
46
|
+
// TODO: Extract from other source types
|
|
47
|
+
return undefined;
|
|
48
|
+
};
|
|
49
|
+
exports.extractDataFromDataSource = extractDataFromDataSource;
|
|
50
|
+
// Execute actions for a condition and attach event properties to the event if needed
|
|
51
|
+
var executeActions = function (actions, ev) {
|
|
52
|
+
actions.forEach(function (action) {
|
|
53
|
+
// Skip if actions is string until action set is implemented
|
|
54
|
+
if (typeof action === 'string') {
|
|
55
|
+
return;
|
|
56
|
+
}
|
|
57
|
+
if (action.actionType === 'ATTACH_EVENT_PROPERTY') {
|
|
58
|
+
var data = (0, exports.extractDataFromDataSource)(action.dataSource, ev.closestTrackedAncestor);
|
|
59
|
+
// Attach data to event
|
|
60
|
+
ev.targetElementProperties[action.destinationKey] = data;
|
|
61
|
+
}
|
|
62
|
+
});
|
|
63
|
+
};
|
|
64
|
+
exports.executeActions = executeActions;
|
|
65
|
+
//# sourceMappingURL=actions.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"actions.js","sourceRoot":"","sources":["../../../src/pageActions/actions.ts"],"names":[],"mappings":";;;AAGA,iBAAiB;AACjB;;;;;GAKG;AACI,IAAM,aAAa,GAAG,UAAC,UAAsB,EAAE,cAA2B;IAC/E,6CAA6C;IAC7C,IAAI,UAAU,CAAC,UAAU,KAAK,aAAa,EAAE;QAC3C,4HAA4H;QAC5H,IAAI,cAAc,GAAuB,QAAQ,CAAC,eAAe,CAAC;QAClE,IAAI,UAAU,CAAC,KAAK,IAAI,cAAc,EAAE;YACtC,cAAc,GAAG,cAAc,CAAC,OAAO,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC;SAC3D;QAED,kEAAkE;QAClE,IAAI,cAAc,IAAI,UAAU,CAAC,QAAQ,EAAE;YACzC,OAAO,cAAc,CAAC,aAAa,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC;SAC1D;QAED,qDAAqD;QACrD,OAAO,cAAc,CAAC;KACvB;IAED,oDAAoD;IACpD,OAAO,SAAS,CAAC;AACnB,CAAC,CAAC;AApBW,QAAA,aAAa,iBAoBxB;AAEF,qBAAqB;AACd,IAAM,yBAAyB,GAAG,UAAC,UAAsB,EAAE,cAA2B;IAC3F,2BAA2B;IAC3B,IAAI,UAAU,CAAC,UAAU,KAAK,aAAa,EAAE;QAC3C,IAAM,aAAa,GAAG,IAAA,qBAAa,EAAC,UAAU,EAAE,cAAc,CAAC,CAAC;QAChE,IAAI,CAAC,aAAa,EAAE;YAClB,OAAO,SAAS,CAAC;SAClB;QAED,IAAI,UAAU,CAAC,kBAAkB,KAAK,MAAM,EAAE;YAC5C,OAAO,aAAa,CAAC,WAAW,CAAC;SAClC;aAAM,IAAI,UAAU,CAAC,kBAAkB,KAAK,WAAW,IAAI,UAAU,CAAC,SAAS,EAAE;YAChF,OAAO,aAAa,CAAC,YAAY,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC;SACzD;QACD,OAAO,SAAS,CAAC;KAClB;IAED,wCAAwC;IACxC,OAAO,SAAS,CAAC;AACnB,CAAC,CAAC;AAlBW,QAAA,yBAAyB,6BAkBpC;AAEF,qFAAqF;AAC9E,IAAM,cAAc,GAAG,UAC5B,OAAgC,EAChC,EAAmD;IAEnD,OAAO,CAAC,OAAO,CAAC,UAAC,MAAM;QACrB,4DAA4D;QAC5D,IAAI,OAAO,MAAM,KAAK,QAAQ,EAAE;YAC9B,OAAO;SACR;QAED,IAAI,MAAM,CAAC,UAAU,KAAK,uBAAuB,EAAE;YACjD,IAAM,IAAI,GAAG,IAAA,iCAAyB,EAAC,MAAM,CAAC,UAAU,EAAE,EAAE,CAAC,sBAAqC,CAAC,CAAC;YAEpG,uBAAuB;YACvB,EAAE,CAAC,uBAAuB,CAAC,MAAM,CAAC,cAAc,CAAC,GAAG,IAAI,CAAC;SAC1D;IACH,CAAC,CAAC,CAAC;AACL,CAAC,CAAC;AAjBW,QAAA,cAAc,kBAiBzB","sourcesContent":["import type { DataSource, PageAction } from '@amplitude/analytics-core/lib/esm/types/element-interactions';\nimport { ElementBasedTimestampedEvent, ElementBasedEvent } from 'src/helpers';\n\n// Get DataSource\n/**\n * Gets the DOM element specified by the data source configuration\n * @param dataSource - Configuration for finding the target element\n * @param contextElement - The element to start searching from\n * @returns The matching DOM element or undefined if not found\n */\nexport const getDataSource = (dataSource: DataSource, contextElement: HTMLElement) => {\n // Only process DOM_ELEMENT type data sources\n if (dataSource.sourceType === 'DOM_ELEMENT') {\n // If scope is specified, find the closest ancestor matching the scope rather than using documentElement (html) as the scope\n let scopingElement: HTMLElement | null = document.documentElement;\n if (dataSource.scope && contextElement) {\n scopingElement = contextElement.closest(dataSource.scope);\n }\n\n // If we have both a scope and selector, find the matching element\n if (scopingElement && dataSource.selector) {\n return scopingElement.querySelector(dataSource.selector);\n }\n\n // Return scopingElement if no selector was specified\n return scopingElement;\n }\n\n // Return undefined for non-DOM_ELEMENT data sources\n return undefined;\n};\n\n// extract DataSource\nexport const extractDataFromDataSource = (dataSource: DataSource, contextElement: HTMLElement) => {\n // Extract from DOM Element\n if (dataSource.sourceType === 'DOM_ELEMENT') {\n const sourceElement = getDataSource(dataSource, contextElement);\n if (!sourceElement) {\n return undefined;\n }\n\n if (dataSource.elementExtractType === 'TEXT') {\n return sourceElement.textContent;\n } else if (dataSource.elementExtractType === 'ATTRIBUTE' && dataSource.attribute) {\n return sourceElement.getAttribute(dataSource.attribute);\n }\n return undefined;\n }\n\n // TODO: Extract from other source types\n return undefined;\n};\n\n// Execute actions for a condition and attach event properties to the event if needed\nexport const executeActions = (\n actions: (string | PageAction)[],\n ev: ElementBasedTimestampedEvent<ElementBasedEvent>,\n) => {\n actions.forEach((action) => {\n // Skip if actions is string until action set is implemented\n if (typeof action === 'string') {\n return;\n }\n\n if (action.actionType === 'ATTACH_EVENT_PROPERTY') {\n const data = extractDataFromDataSource(action.dataSource, ev.closestTrackedAncestor as HTMLElement);\n\n // Attach data to event\n ev.targetElementProperties[action.destinationKey] = data;\n }\n });\n};\n"]}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import type { Filter } from '@amplitude/analytics-core/lib/esm/types/element-interactions';
|
|
2
|
+
import { ElementBasedTimestampedEvent, ElementBasedEvent } from 'src/helpers';
|
|
3
|
+
/**
|
|
4
|
+
* Matches an event to a single filter
|
|
5
|
+
* @param event - The event to match
|
|
6
|
+
* @param filter - The filter to match against
|
|
7
|
+
* @returns boolean indicating if the event matches the filter
|
|
8
|
+
*/
|
|
9
|
+
export declare const matchEventToFilter: (event: ElementBasedTimestampedEvent<ElementBasedEvent>, filter: Filter) => boolean;
|
|
10
|
+
//# sourceMappingURL=matchEventToFilter.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"matchEventToFilter.d.ts","sourceRoot":"","sources":["../../../src/pageActions/matchEventToFilter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,8DAA8D,CAAC;AAC3F,OAAO,EAAE,4BAA4B,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAE9E;;;;;GAKG;AACH,eAAO,MAAM,kBAAkB,UAAW,6BAA6B,iBAAiB,CAAC,UAAU,MAAM,YAoBxG,CAAC"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.matchEventToFilter = void 0;
|
|
4
|
+
/**
|
|
5
|
+
* Matches an event to a single filter
|
|
6
|
+
* @param event - The event to match
|
|
7
|
+
* @param filter - The filter to match against
|
|
8
|
+
* @returns boolean indicating if the event matches the filter
|
|
9
|
+
*/
|
|
10
|
+
var matchEventToFilter = function (event, filter) {
|
|
11
|
+
try {
|
|
12
|
+
if (filter.subprop_key === '[Amplitude] Element Text') {
|
|
13
|
+
// TODO: add support for the other operators
|
|
14
|
+
return (filter.subprop_op === 'exact' &&
|
|
15
|
+
filter.subprop_value.includes(event.targetElementProperties['[Amplitude] Element Text']));
|
|
16
|
+
}
|
|
17
|
+
else if (filter.subprop_key === '[Amplitude] Element Hierarchy') {
|
|
18
|
+
// Check if the element ancestory matches the CSS selector, always check this last since it is the most expensive
|
|
19
|
+
return (filter.subprop_op === 'autotrack css match' &&
|
|
20
|
+
!!event.closestTrackedAncestor.closest(filter.subprop_value.toString()));
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
catch (error) {
|
|
24
|
+
console.error('Error matching event to filter', error);
|
|
25
|
+
return false;
|
|
26
|
+
}
|
|
27
|
+
return false;
|
|
28
|
+
};
|
|
29
|
+
exports.matchEventToFilter = matchEventToFilter;
|
|
30
|
+
//# sourceMappingURL=matchEventToFilter.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"matchEventToFilter.js","sourceRoot":"","sources":["../../../src/pageActions/matchEventToFilter.ts"],"names":[],"mappings":";;;AAGA;;;;;GAKG;AACI,IAAM,kBAAkB,GAAG,UAAC,KAAsD,EAAE,MAAc;IACvG,IAAI;QACF,IAAI,MAAM,CAAC,WAAW,KAAK,0BAA0B,EAAE;YACrD,4CAA4C;YAC5C,OAAO,CACL,MAAM,CAAC,UAAU,KAAK,OAAO;gBAC7B,MAAM,CAAC,aAAa,CAAC,QAAQ,CAAC,KAAK,CAAC,uBAAuB,CAAC,0BAA0B,CAAW,CAAC,CACnG,CAAC;SACH;aAAM,IAAI,MAAM,CAAC,WAAW,KAAK,+BAA+B,EAAE;YACjE,iHAAiH;YACjH,OAAO,CACL,MAAM,CAAC,UAAU,KAAK,qBAAqB;gBAC3C,CAAC,CAAC,KAAK,CAAC,sBAAsB,CAAC,OAAO,CAAC,MAAM,CAAC,aAAa,CAAC,QAAQ,EAAE,CAAC,CACxE,CAAC;SACH;KACF;IAAC,OAAO,KAAK,EAAE;QACd,OAAO,CAAC,KAAK,CAAC,gCAAgC,EAAE,KAAK,CAAC,CAAC;QACvD,OAAO,KAAK,CAAC;KACd;IACD,OAAO,KAAK,CAAC;AACf,CAAC,CAAC;AApBW,QAAA,kBAAkB,sBAoB7B","sourcesContent":["import type { Filter } from '@amplitude/analytics-core/lib/esm/types/element-interactions';\nimport { ElementBasedTimestampedEvent, ElementBasedEvent } from 'src/helpers';\n\n/**\n * Matches an event to a single filter\n * @param event - The event to match\n * @param filter - The filter to match against\n * @returns boolean indicating if the event matches the filter\n */\nexport const matchEventToFilter = (event: ElementBasedTimestampedEvent<ElementBasedEvent>, filter: Filter) => {\n try {\n if (filter.subprop_key === '[Amplitude] Element Text') {\n // TODO: add support for the other operators\n return (\n filter.subprop_op === 'exact' &&\n filter.subprop_value.includes(event.targetElementProperties['[Amplitude] Element Text'] as string)\n );\n } else if (filter.subprop_key === '[Amplitude] Element Hierarchy') {\n // Check if the element ancestory matches the CSS selector, always check this last since it is the most expensive\n return (\n filter.subprop_op === 'autotrack css match' &&\n !!event.closestTrackedAncestor.closest(filter.subprop_value.toString())\n );\n }\n } catch (error) {\n console.error('Error matching event to filter', error);\n return false;\n }\n return false;\n};\n"]}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { Trigger } from '@amplitude/analytics-core/lib/esm/types/element-interactions';
|
|
2
|
+
import type { LabeledEvent } from '@amplitude/analytics-core/lib/esm/types/element-interactions';
|
|
3
|
+
import { ElementBasedTimestampedEvent, ElementBasedEvent } from 'src/helpers';
|
|
4
|
+
export declare const groupLabeledEventIdsByEventType: (labeledEvents?: LabeledEvent[] | null) => {
|
|
5
|
+
click: Set<string>;
|
|
6
|
+
change: Set<string>;
|
|
7
|
+
};
|
|
8
|
+
export declare const createLabeledEventToTriggerMap: (triggers: Trigger[]) => Map<string, Trigger[]>;
|
|
9
|
+
/**
|
|
10
|
+
* Matches an event to labeled events based on the event's properties.
|
|
11
|
+
* The logic matches exactly what is supported by the query backend.
|
|
12
|
+
* TODO: later pre-filter the labeled events based on URL first
|
|
13
|
+
*
|
|
14
|
+
* @param event - The event to match against labeled events
|
|
15
|
+
* @param labeledEvents - Array of labeled events to match against
|
|
16
|
+
* @returns Array of matching labeled events
|
|
17
|
+
*/
|
|
18
|
+
export declare const matchEventToLabeledEvents: (event: ElementBasedTimestampedEvent<ElementBasedEvent>, labeledEvents: LabeledEvent[]) => LabeledEvent[];
|
|
19
|
+
export declare const matchLabeledEventsToTriggers: (labeledEvents: LabeledEvent[], leToTriggerMap: Map<string, Trigger[]>) => Trigger[];
|
|
20
|
+
//# sourceMappingURL=triggers.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"triggers.d.ts","sourceRoot":"","sources":["../../../src/pageActions/triggers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,8DAA8D,CAAC;AAEvF,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,8DAA8D,CAAC;AACjG,OAAO,EAAE,4BAA4B,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAK9E,eAAO,MAAM,+BAA+B,mBAAoB,YAAY,EAAE,GAAG,IAAI;;;CAoBpF,CAAC;AAGF,eAAO,MAAM,8BAA8B,aAAc,OAAO,EAAE,2BAkBjE,CAAC;AAEF;;;;;;;;GAQG;AACH,eAAO,MAAM,yBAAyB,UAC7B,6BAA6B,iBAAiB,CAAC,iBACvC,YAAY,EAAE,mBAO9B,CAAC;AAEF,eAAO,MAAM,4BAA4B,kBAAmB,YAAY,EAAE,kBAAkB,IAAI,MAAM,EAAE,OAAO,EAAE,CAAC,cASjH,CAAC"}
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.matchLabeledEventsToTriggers = exports.matchEventToLabeledEvents = exports.createLabeledEventToTriggerMap = exports.groupLabeledEventIdsByEventType = void 0;
|
|
4
|
+
var tslib_1 = require("tslib");
|
|
5
|
+
var matchEventToFilter_1 = require("./matchEventToFilter");
|
|
6
|
+
// groups labeled events by event type
|
|
7
|
+
// skips any labeled events with malformed definitions or unexpected event_type
|
|
8
|
+
var groupLabeledEventIdsByEventType = function (labeledEvents) {
|
|
9
|
+
var e_1, _a, e_2, _b;
|
|
10
|
+
var _c;
|
|
11
|
+
var groupedLabeledEvents = {
|
|
12
|
+
click: new Set(),
|
|
13
|
+
change: new Set(),
|
|
14
|
+
};
|
|
15
|
+
if (!labeledEvents) {
|
|
16
|
+
return groupedLabeledEvents;
|
|
17
|
+
}
|
|
18
|
+
try {
|
|
19
|
+
for (var labeledEvents_1 = tslib_1.__values(labeledEvents), labeledEvents_1_1 = labeledEvents_1.next(); !labeledEvents_1_1.done; labeledEvents_1_1 = labeledEvents_1.next()) {
|
|
20
|
+
var le = labeledEvents_1_1.value;
|
|
21
|
+
try {
|
|
22
|
+
try {
|
|
23
|
+
for (var _d = (e_2 = void 0, tslib_1.__values(le.definition)), _e = _d.next(); !_e.done; _e = _d.next()) {
|
|
24
|
+
var def = _e.value;
|
|
25
|
+
(_c = groupedLabeledEvents[def.event_type]) === null || _c === void 0 ? void 0 : _c.add(le.id);
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
catch (e_2_1) { e_2 = { error: e_2_1 }; }
|
|
29
|
+
finally {
|
|
30
|
+
try {
|
|
31
|
+
if (_e && !_e.done && (_b = _d.return)) _b.call(_d);
|
|
32
|
+
}
|
|
33
|
+
finally { if (e_2) throw e_2.error; }
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
catch (e) {
|
|
37
|
+
// Skip this labeled event if there is an error
|
|
38
|
+
console.warn('Skipping Labeled Event due to malformed definition', le === null || le === void 0 ? void 0 : le.id, e);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
catch (e_1_1) { e_1 = { error: e_1_1 }; }
|
|
43
|
+
finally {
|
|
44
|
+
try {
|
|
45
|
+
if (labeledEvents_1_1 && !labeledEvents_1_1.done && (_a = labeledEvents_1.return)) _a.call(labeledEvents_1);
|
|
46
|
+
}
|
|
47
|
+
finally { if (e_1) throw e_1.error; }
|
|
48
|
+
}
|
|
49
|
+
return groupedLabeledEvents;
|
|
50
|
+
};
|
|
51
|
+
exports.groupLabeledEventIdsByEventType = groupLabeledEventIdsByEventType;
|
|
52
|
+
// TODO: add tests
|
|
53
|
+
var createLabeledEventToTriggerMap = function (triggers) {
|
|
54
|
+
var e_3, _a, e_4, _b;
|
|
55
|
+
var labeledEventToTriggerMap = new Map();
|
|
56
|
+
try {
|
|
57
|
+
for (var triggers_1 = tslib_1.__values(triggers), triggers_1_1 = triggers_1.next(); !triggers_1_1.done; triggers_1_1 = triggers_1.next()) {
|
|
58
|
+
var trigger = triggers_1_1.value;
|
|
59
|
+
try {
|
|
60
|
+
for (var _c = (e_4 = void 0, tslib_1.__values(trigger.conditions)), _d = _c.next(); !_d.done; _d = _c.next()) {
|
|
61
|
+
var condition = _d.value;
|
|
62
|
+
if (condition.type === 'LABELED_EVENT') {
|
|
63
|
+
var eventId = condition.match.eventId;
|
|
64
|
+
// Get existing triggers for this event ID or initialize empty array
|
|
65
|
+
var existingTriggers = labeledEventToTriggerMap.get(eventId);
|
|
66
|
+
if (!existingTriggers) {
|
|
67
|
+
existingTriggers = [];
|
|
68
|
+
labeledEventToTriggerMap.set(eventId, existingTriggers);
|
|
69
|
+
}
|
|
70
|
+
// Add current trigger to the list of triggers for this event ID
|
|
71
|
+
existingTriggers.push(trigger);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
catch (e_4_1) { e_4 = { error: e_4_1 }; }
|
|
76
|
+
finally {
|
|
77
|
+
try {
|
|
78
|
+
if (_d && !_d.done && (_b = _c.return)) _b.call(_c);
|
|
79
|
+
}
|
|
80
|
+
finally { if (e_4) throw e_4.error; }
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
catch (e_3_1) { e_3 = { error: e_3_1 }; }
|
|
85
|
+
finally {
|
|
86
|
+
try {
|
|
87
|
+
if (triggers_1_1 && !triggers_1_1.done && (_a = triggers_1.return)) _a.call(triggers_1);
|
|
88
|
+
}
|
|
89
|
+
finally { if (e_3) throw e_3.error; }
|
|
90
|
+
}
|
|
91
|
+
return labeledEventToTriggerMap;
|
|
92
|
+
};
|
|
93
|
+
exports.createLabeledEventToTriggerMap = createLabeledEventToTriggerMap;
|
|
94
|
+
/**
|
|
95
|
+
* Matches an event to labeled events based on the event's properties.
|
|
96
|
+
* The logic matches exactly what is supported by the query backend.
|
|
97
|
+
* TODO: later pre-filter the labeled events based on URL first
|
|
98
|
+
*
|
|
99
|
+
* @param event - The event to match against labeled events
|
|
100
|
+
* @param labeledEvents - Array of labeled events to match against
|
|
101
|
+
* @returns Array of matching labeled events
|
|
102
|
+
*/
|
|
103
|
+
var matchEventToLabeledEvents = function (event, labeledEvents) {
|
|
104
|
+
return labeledEvents.filter(function (le) {
|
|
105
|
+
return le.definition.some(function (def) {
|
|
106
|
+
return def.event_type === event.type && def.filters.every(function (filter) { return (0, matchEventToFilter_1.matchEventToFilter)(event, filter); });
|
|
107
|
+
});
|
|
108
|
+
});
|
|
109
|
+
};
|
|
110
|
+
exports.matchEventToLabeledEvents = matchEventToLabeledEvents;
|
|
111
|
+
var matchLabeledEventsToTriggers = function (labeledEvents, leToTriggerMap) {
|
|
112
|
+
var e_5, _a;
|
|
113
|
+
var matchingTriggers = new Set();
|
|
114
|
+
try {
|
|
115
|
+
for (var labeledEvents_2 = tslib_1.__values(labeledEvents), labeledEvents_2_1 = labeledEvents_2.next(); !labeledEvents_2_1.done; labeledEvents_2_1 = labeledEvents_2.next()) {
|
|
116
|
+
var le = labeledEvents_2_1.value;
|
|
117
|
+
var triggers = leToTriggerMap.get(le.id);
|
|
118
|
+
if (triggers) {
|
|
119
|
+
triggers.forEach(function (trigger) { return matchingTriggers.add(trigger); });
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
catch (e_5_1) { e_5 = { error: e_5_1 }; }
|
|
124
|
+
finally {
|
|
125
|
+
try {
|
|
126
|
+
if (labeledEvents_2_1 && !labeledEvents_2_1.done && (_a = labeledEvents_2.return)) _a.call(labeledEvents_2);
|
|
127
|
+
}
|
|
128
|
+
finally { if (e_5) throw e_5.error; }
|
|
129
|
+
}
|
|
130
|
+
return Array.from(matchingTriggers);
|
|
131
|
+
};
|
|
132
|
+
exports.matchLabeledEventsToTriggers = matchLabeledEventsToTriggers;
|
|
133
|
+
//# sourceMappingURL=triggers.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"triggers.js","sourceRoot":"","sources":["../../../src/pageActions/triggers.ts"],"names":[],"mappings":"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","sourcesContent":["import { Trigger } from '@amplitude/analytics-core/lib/esm/types/element-interactions';\n// Return which labeled events, if any, the element matches\nimport type { LabeledEvent } from '@amplitude/analytics-core/lib/esm/types/element-interactions';\nimport { ElementBasedTimestampedEvent, ElementBasedEvent } from 'src/helpers';\nimport { matchEventToFilter } from './matchEventToFilter';\n\n// groups labeled events by event type\n// skips any labeled events with malformed definitions or unexpected event_type\nexport const groupLabeledEventIdsByEventType = (labeledEvents?: LabeledEvent[] | null) => {\n const groupedLabeledEvents = {\n click: new Set<string>(),\n change: new Set<string>(),\n };\n if (!labeledEvents) {\n return groupedLabeledEvents;\n }\n\n for (const le of labeledEvents) {\n try {\n for (const def of le.definition) {\n groupedLabeledEvents[def.event_type]?.add(le.id);\n }\n } catch (e) {\n // Skip this labeled event if there is an error\n console.warn('Skipping Labeled Event due to malformed definition', le?.id, e);\n }\n }\n return groupedLabeledEvents;\n};\n\n// TODO: add tests\nexport const createLabeledEventToTriggerMap = (triggers: Trigger[]) => {\n const labeledEventToTriggerMap = new Map<string, Trigger[]>();\n for (const trigger of triggers) {\n for (const condition of trigger.conditions) {\n if (condition.type === 'LABELED_EVENT') {\n const eventId = condition.match.eventId;\n // Get existing triggers for this event ID or initialize empty array\n let existingTriggers = labeledEventToTriggerMap.get(eventId);\n if (!existingTriggers) {\n existingTriggers = [];\n labeledEventToTriggerMap.set(eventId, existingTriggers);\n }\n // Add current trigger to the list of triggers for this event ID\n existingTriggers.push(trigger);\n }\n }\n }\n return labeledEventToTriggerMap;\n};\n\n/**\n * Matches an event to labeled events based on the event's properties.\n * The logic matches exactly what is supported by the query backend.\n * TODO: later pre-filter the labeled events based on URL first\n *\n * @param event - The event to match against labeled events\n * @param labeledEvents - Array of labeled events to match against\n * @returns Array of matching labeled events\n */\nexport const matchEventToLabeledEvents = (\n event: ElementBasedTimestampedEvent<ElementBasedEvent>,\n labeledEvents: LabeledEvent[],\n) => {\n return labeledEvents.filter((le) => {\n return le.definition.some((def) => {\n return def.event_type === event.type && def.filters.every((filter) => matchEventToFilter(event, filter));\n });\n });\n};\n\nexport const matchLabeledEventsToTriggers = (labeledEvents: LabeledEvent[], leToTriggerMap: Map<string, Trigger[]>) => {\n const matchingTriggers = new Set<Trigger>();\n for (const le of labeledEvents) {\n const triggers = leToTriggerMap.get(le.id);\n if (triggers) {\n triggers.forEach((trigger) => matchingTriggers.add(trigger));\n }\n }\n return Array.from(matchingTriggers);\n};\n"]}
|
package/lib/cjs/version.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export declare const VERSION = "1.
|
|
1
|
+
export declare const VERSION = "1.3.0";
|
|
2
2
|
//# sourceMappingURL=version.d.ts.map
|
package/lib/cjs/version.js
CHANGED
package/lib/cjs/version.js.map
CHANGED
|
@@ -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.
|
|
1
|
+
{"version":3,"file":"version.js","sourceRoot":"","sources":["../../src/version.ts"],"names":[],"mappings":";;;AAAa,QAAA,OAAO,GAAG,OAAO,CAAC","sourcesContent":["export const VERSION = '1.3.0';\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"track-action-click.d.ts","sourceRoot":"","sources":["../../../src/autocapture/track-action-click.ts"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"track-action-click.d.ts","sourceRoot":"","sources":["../../../src/autocapture/track-action-click.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,oBAAoB,EAAE,8BAA8B,EAAmB,MAAM,wBAAwB,CAAC;AAE/G,OAAO,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAC;AACtE,OAAO,EAIL,gBAAgB,EACjB,MAAM,YAAY,CAAC;AAGpB,wBAAgB,gBAAgB,CAAC,EAC/B,SAAS,EACT,cAAc,EACd,OAAO,EACP,kBAAkB,EAClB,gBAAgB,EAChB,sBAAsB,GACvB,EAAE;IACD,SAAS,EAAE,aAAa,CAAC;IACzB,cAAc,EAAE,oBAAoB,CAAC;IACrC,OAAO,EAAE,8BAA8B,CAAC;IACxC,kBAAkB,EAAE,CAAC,UAAU,EAAE,UAAU,EAAE,OAAO,EAAE,OAAO,KAAK,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IACtF,sBAAsB,EAAE,gBAAgB,CAAC;IACzC,gBAAgB,EAAE,gBAAgB,CAAC;CACpC,+BAsDA"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { __read, __spreadArray } from "tslib";
|
|
2
2
|
import { filter, map, merge, switchMap, take, timeout, EMPTY } from 'rxjs';
|
|
3
|
-
import { filterOutNonTrackableEvents, getClosestElement } from '../helpers';
|
|
3
|
+
import { filterOutNonTrackableEvents, getClosestElement, } from '../helpers';
|
|
4
4
|
import { AMPLITUDE_ELEMENT_CLICKED_EVENT } from '../constants';
|
|
5
5
|
export function trackActionClick(_a) {
|
|
6
6
|
var amplitude = _a.amplitude, allObservables = _a.allObservables, options = _a.options, getEventProperties = _a.getEventProperties, shouldTrackEvent = _a.shouldTrackEvent, shouldTrackActionClick = _a.shouldTrackActionClick;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"track-action-click.js","sourceRoot":"","sources":["../../../src/autocapture/track-action-click.ts"],"names":[],"mappings":";
|
|
1
|
+
{"version":3,"file":"track-action-click.js","sourceRoot":"","sources":["../../../src/autocapture/track-action-click.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,KAAK,EAAE,SAAS,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,MAAM,CAAC;AAE3E,OAAO,EAEL,2BAA2B,EAC3B,iBAAiB,GAElB,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,+BAA+B,EAAE,MAAM,cAAc,CAAC;AAE/D,MAAM,UAAU,gBAAgB,CAAC,EAchC;QAbC,SAAS,eAAA,EACT,cAAc,oBAAA,EACd,OAAO,aAAA,EACP,kBAAkB,wBAAA,EAClB,gBAAgB,sBAAA,EAChB,sBAAsB,4BAAA;IASd,IAAA,eAAe,GAA6C,cAAc,gBAA3D,EAAE,kBAAkB,GAAyB,cAAc,mBAAvC,EAAE,kBAAkB,GAAK,cAAc,mBAAnB,CAAoB;IAEnF,IAAM,uBAAuB,GAAG,eAAe,CAAC,IAAI,CAClD,MAAM,CAAC,UAAC,KAAK;QACX,oFAAoF;QACpF,OAAO,CAAC,gBAAgB,CAAC,OAAO,EAAE,KAAK,CAAC,sBAAsB,CAAC,CAAC;IAClE,CAAC,CAAC,EACF,GAAG,CAAC,UAAC,KAAK;QACR,oGAAoG;QACpG,IAAM,oBAAoB,GAAG,iBAAiB,CAAC,KAAK,CAAC,KAAK,CAAC,MAAiB,EAAE,OAAO,CAAC,oBAAoB,CAAC,CAAC;QAC5G,KAAK,CAAC,sBAAsB,GAAG,oBAA+B,CAAC;QAE/D,wFAAwF;QACxF,IAAI,KAAK,CAAC,sBAAsB,KAAK,IAAI,EAAE;YACzC,KAAK,CAAC,uBAAuB,GAAG,kBAAkB,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,sBAAsB,CAAC,CAAC;SAC9F;QACD,OAAO,KAAK,CAAC;IACf,CAAC,CAAC,EACF,MAAM,CAAC,2BAA2B,CAAC,EACnC,MAAM,CAAC,UAAC,UAAU;QAChB,uDAAuD;QACvD,OAAO,sBAAsB,CAAC,OAAO,EAAE,UAAU,CAAC,sBAAsB,CAAC,CAAC;IAC5E,CAAC,CAAC,CACH,CAAC;IAEF,IAAM,iBAAiB,GAEnB,CAAC,kBAAkB,CAAC,CAAC;IACzB,0BAA0B;IAC1B,IAAI,kBAAkB,EAAE;QACtB,iBAAiB,CAAC,IAAI,CAAC,kBAAkB,CAAC,CAAC;KAC5C;IACD,IAAM,kBAAkB,GAAG,KAAK,wCAAI,iBAAiB,UAAC,CAAC;IAEvD,IAAM,YAAY,GAAG,uBAAuB,CAAC,IAAI;IAC/C,+HAA+H;IAC/H,oEAAoE;IACpE,SAAS,CAAC,UAAC,KAAK;QACd,OAAA,kBAAkB,CAAC,IAAI,CACrB,IAAI,CAAC,CAAC,CAAC,EACP,OAAO,CAAC,EAAE,KAAK,EAAE,GAAG,EAAE,IAAI,EAAE,cAAM,OAAA,KAAK,EAAL,CAAK,EAAE,CAAC,EAAE,2EAA2E;QACvH,GAAG,CAAC,cAAM,OAAA,KAAK,EAAL,CAAK,CAAC,CACjB;IAJD,CAIC,CACF,CACF,CAAC;IAEF,OAAO,YAAY,CAAC,SAAS,CAAC,UAAC,WAAW;QACxC,0BAA0B;QAC1B,SAAS,aAAT,SAAS,uBAAT,SAAS,CAAE,KAAK,CACd,+BAA+B,EAC/B,kBAAkB,CAAC,OAAO,EAAG,WAAwD,CAAC,sBAAsB,CAAC,CAC9G,CAAC;IACJ,CAAC,CAAC,CAAC;AACL,CAAC","sourcesContent":["import { AllWindowObservables, AutoCaptureOptionsWithDefaults, ObservablesEnum } from 'src/autocapture-plugin';\nimport { filter, map, merge, switchMap, take, timeout, EMPTY } from 'rxjs';\nimport { BrowserClient, ActionType } from '@amplitude/analytics-core';\nimport {\n ElementBasedTimestampedEvent,\n filterOutNonTrackableEvents,\n getClosestElement,\n shouldTrackEvent,\n} from '../helpers';\nimport { AMPLITUDE_ELEMENT_CLICKED_EVENT } from '../constants';\n\nexport function trackActionClick({\n amplitude,\n allObservables,\n options,\n getEventProperties,\n shouldTrackEvent,\n shouldTrackActionClick,\n}: {\n amplitude: BrowserClient;\n allObservables: AllWindowObservables;\n options: AutoCaptureOptionsWithDefaults;\n getEventProperties: (actionType: ActionType, element: Element) => Record<string, any>;\n shouldTrackActionClick: shouldTrackEvent;\n shouldTrackEvent: shouldTrackEvent;\n}) {\n const { clickObservable, mutationObservable, navigateObservable } = allObservables;\n\n const filteredClickObservable = clickObservable.pipe(\n filter((click) => {\n // Filter out regularly tracked click events that are already handled in trackClicks\n return !shouldTrackEvent('click', click.closestTrackedAncestor);\n }),\n map((click) => {\n // overwrite the closestTrackedAncestor with the closest element that is on the actionClickAllowlist\n const closestActionClickEl = getClosestElement(click.event.target as Element, options.actionClickAllowlist);\n click.closestTrackedAncestor = closestActionClickEl as Element;\n\n // overwrite the targetElementProperties with the properties of the closestActionClickEl\n if (click.closestTrackedAncestor !== null) {\n click.targetElementProperties = getEventProperties(click.type, click.closestTrackedAncestor);\n }\n return click;\n }),\n filter(filterOutNonTrackableEvents),\n filter((clickEvent) => {\n // Only track change on elements that should be tracked\n return shouldTrackActionClick('click', clickEvent.closestTrackedAncestor);\n }),\n );\n\n const changeObservables: Array<\n AllWindowObservables[ObservablesEnum.MutationObservable] | AllWindowObservables[ObservablesEnum.NavigateObservable]\n > = [mutationObservable];\n /* istanbul ignore next */\n if (navigateObservable) {\n changeObservables.push(navigateObservable);\n }\n const mutationOrNavigate = merge(...changeObservables);\n\n const actionClicks = filteredClickObservable.pipe(\n // If a mutation occurs within 0.5 seconds of a click event (timeout({ first: 500 })), it emits the original first click event.\n // take 1 to only limit the action events in case there are multiple\n switchMap((click) =>\n mutationOrNavigate.pipe(\n take(1),\n timeout({ first: 500, with: () => EMPTY }), // in case of timeout, map to empty to prevent any click from being emitted\n map(() => click),\n ),\n ),\n );\n\n return actionClicks.subscribe((actionClick) => {\n /* istanbul ignore next */\n amplitude?.track(\n AMPLITUDE_ELEMENT_CLICKED_EVENT,\n getEventProperties('click', (actionClick as ElementBasedTimestampedEvent<MouseEvent>).closestTrackedAncestor),\n );\n });\n}\n"]}
|