@opentelemetry/browser-instrumentation 0.6.0 → 0.7.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/README.md
CHANGED
|
@@ -194,10 +194,24 @@ By default the instrumentation captures `click` events. You can configure which
|
|
|
194
194
|
|
|
195
195
|
```typescript
|
|
196
196
|
new UserActionInstrumentation({
|
|
197
|
-
|
|
197
|
+
// Array of actions to automatically capture. Default: ['click'].
|
|
198
|
+
autoCapturedActions: [],
|
|
199
|
+
|
|
200
|
+
// Mutate the log record before it is emitted (e.g. attach custom attributes).
|
|
201
|
+
applyCustomLogRecordData: (logRecord) => {
|
|
202
|
+
logRecord.attributes = {
|
|
203
|
+
...logRecord.attributes,
|
|
204
|
+
'app.user.role': 'admin',
|
|
205
|
+
};
|
|
206
|
+
},
|
|
198
207
|
});
|
|
199
208
|
```
|
|
200
209
|
|
|
210
|
+
| Option | Type | Default | Description |
|
|
211
|
+
|--------|------|---------|-------------|
|
|
212
|
+
| `autoCapturedActions` | `AutoCapturedUserAction[]` | `['click']` | Array of actions to automatically capture. |
|
|
213
|
+
| `applyCustomLogRecordData` | `(logRecord: LogRecord) => void` | — | Hook to modify log records before they are emitted. Errors thrown from this hook are caught and logged via the instrumentation diag logger. |
|
|
214
|
+
|
|
201
215
|
#### Additional Attributes
|
|
202
216
|
|
|
203
217
|
Data attributes with the prefix `data-otel-` on the target element will be added as additional attributes to the generated log record. For example:
|
package/dist/package.js
CHANGED
|
@@ -2,7 +2,7 @@ import { version } from "../package.js";
|
|
|
2
2
|
import { getElementCSSSelector } from "../utils/getElementCSSSelector.js";
|
|
3
3
|
import { ATTR_CSS_SELECTOR, ATTR_MOUSE_EVENT_BUTTON, ATTR_PAGE_X, ATTR_PAGE_Y, ATTR_TAGS, ATTR_TAG_NAME, CLICK_EVENT_NAME } from "./semconv.js";
|
|
4
4
|
import { SeverityNumber } from "@opentelemetry/api-logs";
|
|
5
|
-
import { InstrumentationBase } from "@opentelemetry/instrumentation";
|
|
5
|
+
import { InstrumentationBase, safeExecuteInTheMiddle } from "@opentelemetry/instrumentation";
|
|
6
6
|
//#region src/user-action/instrumentation.ts
|
|
7
7
|
const DEFAULT_AUTO_CAPTURED_ACTIONS = ["click"];
|
|
8
8
|
const OTEL_ELEMENT_ATTRIBUTE_PREFIX = "data-otel-";
|
|
@@ -34,7 +34,7 @@ var UserActionInstrumentation = class extends InstrumentationBase {
|
|
|
34
34
|
});
|
|
35
35
|
const otelPrefixedAttributes = {};
|
|
36
36
|
for (const attr of element.attributes) if (attr.name.startsWith(OTEL_ELEMENT_ATTRIBUTE_PREFIX)) otelPrefixedAttributes[attr.name.slice(10)] = attr.value;
|
|
37
|
-
|
|
37
|
+
const logRecord = {
|
|
38
38
|
severityNumber: SeverityNumber.INFO,
|
|
39
39
|
eventName: CLICK_EVENT_NAME,
|
|
40
40
|
attributes: {
|
|
@@ -45,7 +45,15 @@ var UserActionInstrumentation = class extends InstrumentationBase {
|
|
|
45
45
|
[ATTR_MOUSE_EVENT_BUTTON]: this._getMouseButtonFromMouseEvent(event),
|
|
46
46
|
[ATTR_CSS_SELECTOR]: cssSelector
|
|
47
47
|
}
|
|
48
|
-
}
|
|
48
|
+
};
|
|
49
|
+
this._applyCustomLogRecordData(logRecord);
|
|
50
|
+
this.logger.emit(logRecord);
|
|
51
|
+
}
|
|
52
|
+
_applyCustomLogRecordData(logRecord) {
|
|
53
|
+
const applyCustomLogRecordData = this.getConfig().applyCustomLogRecordData;
|
|
54
|
+
if (applyCustomLogRecordData) safeExecuteInTheMiddle(() => applyCustomLogRecordData(logRecord), (error) => {
|
|
55
|
+
if (error) this._diag.error("applyCustomLogRecordData hook failed", error);
|
|
56
|
+
}, true);
|
|
49
57
|
}
|
|
50
58
|
enable() {
|
|
51
59
|
const autoCapturedActions = this._config.autoCapturedActions ?? DEFAULT_AUTO_CAPTURED_ACTIONS;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"instrumentation.js","names":[],"sources":["../../src/user-action/instrumentation.ts"],"sourcesContent":["/*\n * Copyright The OpenTelemetry Authors\n * SPDX-License-Identifier: Apache-2.0\n */\
|
|
1
|
+
{"version":3,"file":"instrumentation.js","names":[],"sources":["../../src/user-action/instrumentation.ts"],"sourcesContent":["/*\n * Copyright The OpenTelemetry Authors\n * SPDX-License-Identifier: Apache-2.0\n */\nimport type { LogRecord } from '@opentelemetry/api-logs';\nimport { SeverityNumber } from '@opentelemetry/api-logs';\nimport {\n InstrumentationBase,\n safeExecuteInTheMiddle,\n} from '@opentelemetry/instrumentation';\nimport { getElementCSSSelector } from '#utils';\nimport { version } from '../../package.json' with { type: 'json' };\nimport {\n ATTR_CSS_SELECTOR,\n ATTR_MOUSE_EVENT_BUTTON,\n ATTR_PAGE_X,\n ATTR_PAGE_Y,\n ATTR_TAG_NAME,\n ATTR_TAGS,\n CLICK_EVENT_NAME,\n} from './semconv.ts';\nimport type {\n AutoCapturedUserAction,\n MouseButton,\n UserActionInstrumentationConfig,\n} from './types.ts';\n\nconst DEFAULT_AUTO_CAPTURED_ACTIONS: AutoCapturedUserAction[] = ['click'];\nconst OTEL_ELEMENT_ATTRIBUTE_PREFIX = 'data-otel-';\n\n/**\n * This class automatically instruments different User Actions within the browser.\n */\nexport class UserActionInstrumentation extends InstrumentationBase<UserActionInstrumentationConfig> {\n private declare _onClickHandler?: (event: MouseEvent) => void;\n\n constructor(config: UserActionInstrumentationConfig = {}) {\n super(\n '@opentelemetry/browser-instrumentation/user-action',\n version,\n config,\n );\n }\n\n protected override init() {\n return [];\n }\n\n private _getMouseButtonFromMouseEvent(event: MouseEvent): MouseButton {\n switch (event.button) {\n case 0:\n return 'left';\n case 1:\n return 'middle';\n case 2:\n return 'right';\n default:\n return 'left';\n }\n }\n\n private onClick(event: MouseEvent) {\n const element = event.target;\n\n if (!(element instanceof HTMLElement)) {\n return;\n }\n\n if (element.hasAttribute('disabled')) {\n return;\n }\n\n const cssSelector = getElementCSSSelector(element, {\n useIdForTargetElement: true,\n useIdForAncestors: true,\n });\n const otelPrefixedAttributes: Record<string, string> = {};\n\n // Grab all the attributes in the element that start with data-otel-*\n for (const attr of element.attributes) {\n if (attr.name.startsWith(OTEL_ELEMENT_ATTRIBUTE_PREFIX)) {\n otelPrefixedAttributes[\n attr.name.slice(OTEL_ELEMENT_ATTRIBUTE_PREFIX.length)\n ] = attr.value;\n }\n }\n\n const logRecord: LogRecord = {\n severityNumber: SeverityNumber.INFO,\n eventName: CLICK_EVENT_NAME,\n attributes: {\n [ATTR_PAGE_X]: event.pageX,\n [ATTR_PAGE_Y]: event.pageY,\n [ATTR_TAG_NAME]: element.tagName,\n [ATTR_TAGS]: otelPrefixedAttributes,\n [ATTR_MOUSE_EVENT_BUTTON]: this._getMouseButtonFromMouseEvent(event),\n [ATTR_CSS_SELECTOR]: cssSelector,\n },\n };\n\n this._applyCustomLogRecordData(logRecord);\n\n this.logger.emit(logRecord);\n }\n\n private _applyCustomLogRecordData(logRecord: LogRecord) {\n const applyCustomLogRecordData = this.getConfig().applyCustomLogRecordData;\n if (applyCustomLogRecordData) {\n safeExecuteInTheMiddle(\n () => applyCustomLogRecordData(logRecord),\n (error) => {\n if (error) {\n this._diag.error('applyCustomLogRecordData hook failed', error);\n }\n },\n true,\n );\n }\n }\n\n override enable(): void {\n const autoCapturedActions =\n this._config.autoCapturedActions ?? DEFAULT_AUTO_CAPTURED_ACTIONS;\n if (!this._onClickHandler) {\n this._onClickHandler = this.onClick.bind(this);\n }\n\n if (autoCapturedActions.includes('click')) {\n document.addEventListener('click', this._onClickHandler, true);\n }\n }\n\n override disable(): void {\n if (this._onClickHandler) {\n document.removeEventListener('click', this._onClickHandler, true);\n }\n }\n}\n"],"mappings":";;;;;;AA2BA,MAAM,gCAA0D,CAAC,OAAO;AACxE,MAAM,gCAAgC;;;;AAKtC,IAAa,4BAAb,cAA+C,oBAAqD;CAGlG,YAAY,SAA0C,CAAC,GAAG;EACxD,MACE,sDACA,SACA,MACF;CACF;CAEA,OAA0B;EACxB,OAAO,CAAC;CACV;CAEA,8BAAsC,OAAgC;EACpE,QAAQ,MAAM,QAAd;GACE,KAAK,GACH,OAAO;GACT,KAAK,GACH,OAAO;GACT,KAAK,GACH,OAAO;GACT,SACE,OAAO;EACX;CACF;CAEA,QAAgB,OAAmB;EACjC,MAAM,UAAU,MAAM;EAEtB,IAAI,EAAE,mBAAmB,cACvB;EAGF,IAAI,QAAQ,aAAa,UAAU,GACjC;EAGF,MAAM,cAAc,sBAAsB,SAAS;GACjD,uBAAuB;GACvB,mBAAmB;EACrB,CAAC;EACD,MAAM,yBAAiD,CAAC;EAGxD,KAAK,MAAM,QAAQ,QAAQ,YACzB,IAAI,KAAK,KAAK,WAAW,6BAA6B,GACpD,uBACE,KAAK,KAAK,MAAM,EAAoC,KAClD,KAAK;EAIb,MAAM,YAAuB;GAC3B,gBAAgB,eAAe;GAC/B,WAAW;GACX,YAAY;KACT,cAAc,MAAM;KACpB,cAAc,MAAM;KACpB,gBAAgB,QAAQ;KACxB,YAAY;KACZ,0BAA0B,KAAK,8BAA8B,KAAK;KAClE,oBAAoB;GACvB;EACF;EAEA,KAAK,0BAA0B,SAAS;EAExC,KAAK,OAAO,KAAK,SAAS;CAC5B;CAEA,0BAAkC,WAAsB;EACtD,MAAM,2BAA2B,KAAK,UAAU,CAAC,CAAC;EAClD,IAAI,0BACF,6BACQ,yBAAyB,SAAS,IACvC,UAAU;GACT,IAAI,OACF,KAAK,MAAM,MAAM,wCAAwC,KAAK;EAElE,GACA,IACF;CAEJ;CAEA,SAAwB;EACtB,MAAM,sBACJ,KAAK,QAAQ,uBAAuB;EACtC,IAAI,CAAC,KAAK,iBACR,KAAK,kBAAkB,KAAK,QAAQ,KAAK,IAAI;EAG/C,IAAI,oBAAoB,SAAS,OAAO,GACtC,SAAS,iBAAiB,SAAS,KAAK,iBAAiB,IAAI;CAEjE;CAEA,UAAyB;EACvB,IAAI,KAAK,iBACP,SAAS,oBAAoB,SAAS,KAAK,iBAAiB,IAAI;CAEpE;AACF"}
|
|
@@ -1,12 +1,16 @@
|
|
|
1
|
+
import { LogRecord } from "@opentelemetry/api-logs";
|
|
1
2
|
import { InstrumentationConfig } from "@opentelemetry/instrumentation";
|
|
2
3
|
//#region src/user-action/types.d.ts
|
|
3
4
|
type AutoCapturedUserAction = 'click';
|
|
5
|
+
type ApplyCustomLogRecordDataFunction = (logRecord: LogRecord) => void;
|
|
4
6
|
/**
|
|
5
7
|
* UserActionInstrumentation Configuration
|
|
6
8
|
*/
|
|
7
9
|
interface UserActionInstrumentationConfig extends InstrumentationConfig {
|
|
8
10
|
autoCapturedActions?: AutoCapturedUserAction[];
|
|
11
|
+
/** Hook to modify log records before they are emitted. */
|
|
12
|
+
applyCustomLogRecordData?: ApplyCustomLogRecordDataFunction;
|
|
9
13
|
}
|
|
10
14
|
//#endregion
|
|
11
|
-
export { AutoCapturedUserAction, UserActionInstrumentationConfig };
|
|
15
|
+
export { ApplyCustomLogRecordDataFunction, AutoCapturedUserAction, UserActionInstrumentationConfig };
|
|
12
16
|
//# sourceMappingURL=types.d.ts.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@opentelemetry/browser-instrumentation",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.7.0",
|
|
4
4
|
"description": "OpenTelemetry browser instrumentations.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"opentelemetry",
|
|
@@ -51,9 +51,9 @@
|
|
|
51
51
|
"test:coverage": "vitest --coverage"
|
|
52
52
|
},
|
|
53
53
|
"dependencies": {
|
|
54
|
-
"@opentelemetry/api-logs": "^0.
|
|
55
|
-
"@opentelemetry/core": "^2.
|
|
56
|
-
"@opentelemetry/instrumentation": "^0.
|
|
54
|
+
"@opentelemetry/api-logs": "^0.221.0",
|
|
55
|
+
"@opentelemetry/core": "^2.10.0",
|
|
56
|
+
"@opentelemetry/instrumentation": "^0.221.0",
|
|
57
57
|
"@opentelemetry/semantic-conventions": "^1.43.0",
|
|
58
58
|
"web-vitals": "^5.3.0"
|
|
59
59
|
},
|
|
@@ -61,7 +61,7 @@
|
|
|
61
61
|
"@opentelemetry/api": "^1.9.1"
|
|
62
62
|
},
|
|
63
63
|
"devDependencies": {
|
|
64
|
-
"@opentelemetry/sdk-logs": "0.
|
|
64
|
+
"@opentelemetry/sdk-logs": "0.221.0"
|
|
65
65
|
},
|
|
66
66
|
"publishConfig": {
|
|
67
67
|
"access": "public"
|