@dynatrace/rum-javascript-sdk 1.331.18 → 1.333.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -390
- package/dist/testing/index.d.ts +4 -0
- package/dist/testing/index.js +3 -0
- package/dist/testing/snapshot.d.ts +129 -0
- package/dist/testing/snapshot.js +385 -0
- package/dist/testing/test.d.ts +9 -0
- package/dist/testing/test.js +237 -160
- package/dist/types/index-typedoc.d.ts +3 -0
- package/dist/types/index-typedoc.js +4 -1
- package/dist/types/rum-events/rum-event-keys.d.ts +9 -0
- package/dist/types/rum-events/rum-event-keys.js +11 -1
- package/dist/types/rum-events/rum-internal-selfmonitoring-event.d.ts +5 -1
- package/dist/types/rum-events/rum-internal-selfmonitoring-event.js +5 -1
- package/dist/types/rum-events/rum-web-request-event.d.ts +2 -1
- package/dist/types/rum-events/rum-web-request-event.js +2 -1
- package/dist/types/rum-events/shared-namespaces-and-fields/general-rum-event-fields.d.ts +1 -0
- package/dist/types/rum-events/shared-namespaces-and-fields/general-rum-event-fields.js +1 -1
- package/docs/1-overview.md +405 -0
- package/docs/2-testing.md +424 -0
- package/docs/{types.md → 3-types.md} +8 -2
- package/docs/{USERACTIONS.md → 4-useractions.md} +10 -8
- package/package.json +46 -9
- package/docs/testing.md +0 -215
|
@@ -0,0 +1,424 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: Testing with Playwright
|
|
3
|
+
---
|
|
4
|
+
# Dynatrace RUM JavaScript Testing Framework for Playwright
|
|
5
|
+
|
|
6
|
+
This framework provides a Playwright fixture for testing observability by interacting with the Dynatrace Real User Monitoring (RUM) API.
|
|
7
|
+
|
|
8
|
+
## Setup Instructions
|
|
9
|
+
|
|
10
|
+
Follow these steps to configure and use the framework:
|
|
11
|
+
|
|
12
|
+
### 1. Create an Access Token
|
|
13
|
+
1. Navigate to the **Access Tokens** app in Dynatrace.
|
|
14
|
+
2. Create a new token with the following permission:
|
|
15
|
+
- **Permission**: `Read RUM manual insertion tags`
|
|
16
|
+
- **Scope**: `API V2`
|
|
17
|
+
3. Copy the generated token for use in the next steps.
|
|
18
|
+
|
|
19
|
+
### 2. Provide Required Parameters
|
|
20
|
+
To use the framework, you need to provide the following details:
|
|
21
|
+
- **Environment URL**: The URL of the Dynatrace API endpoint to connect to, see
|
|
22
|
+
[RUM manual insertion tags API](https://docs.dynatrace.com/docs/discover-dynatrace/references/dynatrace-api/environment-api/rum/rum-manual-insertion-tags)
|
|
23
|
+
for details. Example: _https://{your-environment-id}.live.dynatrace.com_ or
|
|
24
|
+
_https://{your-activegate-domain}/e/{your-environment-id}_
|
|
25
|
+
- **Application ID**: The application ID to identify the correct RUM JavaScript to fetch. You can find
|
|
26
|
+
this in the URL if you open the Experience Vitals app and select the frontend you
|
|
27
|
+
want to test. Example: APPLICATION-ABCDEF0123456789
|
|
28
|
+
- **Token**: The API token created in Step 1.
|
|
29
|
+
|
|
30
|
+
Populate your playwright config file with these fields or call `test.use` to provide them to a test suite, like so:
|
|
31
|
+
```ts
|
|
32
|
+
import { test } from "@dynatrace/rum-javascript-sdk/test";
|
|
33
|
+
|
|
34
|
+
test.describe("my suite", () => {
|
|
35
|
+
test.use({
|
|
36
|
+
dynatraceConfig: {
|
|
37
|
+
appId: process.env.DT_APP_ID!,
|
|
38
|
+
token: process.env.DT_TOKEN!,
|
|
39
|
+
endpointUrl: process.env.DT_ENDPOINT_URL!
|
|
40
|
+
}
|
|
41
|
+
});
|
|
42
|
+
});
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
### 3. Assert on events
|
|
46
|
+
|
|
47
|
+
Use the provided `expect` functions to assert on events the RUM JavaScript should have sent:
|
|
48
|
+
```ts
|
|
49
|
+
test("expect specific event", async ({ page, dynatraceTesting }) => {
|
|
50
|
+
await page.goto("http://127.0.0.1:3000/ui");
|
|
51
|
+
await page.getByText("Explore data").first().click();
|
|
52
|
+
await dynatraceTesting.expectToHaveSentEvent(expect.objectContaining({
|
|
53
|
+
"event_properties.component_rendered": "Data"
|
|
54
|
+
}));
|
|
55
|
+
});
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
## Important: Fixture Destructuring Order
|
|
59
|
+
|
|
60
|
+
⚠️ **The order of fixture destructuring matters!**
|
|
61
|
+
|
|
62
|
+
The `dynatraceTesting` fixture must be destructured **before** any custom fixtures that navigate the page. This ensures the RUM JavaScript is injected before navigation occurs.
|
|
63
|
+
|
|
64
|
+
### ✅ Correct Order
|
|
65
|
+
```typescript
|
|
66
|
+
test("my test", async ({ dynatraceTesting, myCustomFixture, page }) => {
|
|
67
|
+
// dynatraceTesting is initialized first
|
|
68
|
+
// RUM script is injected via page.addInitScript
|
|
69
|
+
// Then myCustomFixture can safely navigate
|
|
70
|
+
await page.goto("https://example.com");
|
|
71
|
+
});
|
|
72
|
+
```
|
|
73
|
+
|
|
74
|
+
### ❌ Incorrect Order
|
|
75
|
+
```typescript
|
|
76
|
+
test("my test", async ({ myCustomFixture, dynatraceTesting, page }) => {
|
|
77
|
+
// If myCustomFixture navigates the page, it happens BEFORE
|
|
78
|
+
// dynatraceTesting is initialized, so RUM script is not injected
|
|
79
|
+
// This will cause the test to fail with "no events received"
|
|
80
|
+
});
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
### Why This Happens
|
|
84
|
+
|
|
85
|
+
Playwright initializes fixtures in the order they appear in the destructuring pattern. The `dynatraceTesting` fixture uses `page.addInitScript()` to inject the RUM JavaScript, which only affects subsequent page navigations.
|
|
86
|
+
|
|
87
|
+
### Custom Fixtures That Navigate
|
|
88
|
+
|
|
89
|
+
If you have custom fixtures that call `page.goto()`, always destructure `dynatraceTesting` first:
|
|
90
|
+
|
|
91
|
+
```typescript
|
|
92
|
+
// Define custom fixture
|
|
93
|
+
const test = base.extend<{ myApp: MyApp }>({
|
|
94
|
+
myApp: async ({ page }, use) => {
|
|
95
|
+
await page.goto("https://myapp.com"); // Navigation happens here
|
|
96
|
+
await use(new MyApp(page));
|
|
97
|
+
}
|
|
98
|
+
});
|
|
99
|
+
|
|
100
|
+
// Use fixtures in correct order
|
|
101
|
+
test("test", async ({ dynatraceTesting, myApp }) => {
|
|
102
|
+
// ✅ Correct: dynatraceTesting initialized before myApp
|
|
103
|
+
});
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
## Troubleshooting
|
|
107
|
+
|
|
108
|
+
The test fixture works by intercepting network requests to the RUM ingestion endpoint and capturing
|
|
109
|
+
the events sent by the RUM JavaScript.
|
|
110
|
+
Note that this has an impact on your capturing environment, since these beacons report real data.
|
|
111
|
+
|
|
112
|
+
### Missing Configuration Error
|
|
113
|
+
|
|
114
|
+
If you see an error like:
|
|
115
|
+
```
|
|
116
|
+
[Dynatrace Testing] Missing required configuration fields: endpointUrl, appId, token
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
This means the required configuration was not provided. Make sure to configure the fixture using `test.use()`:
|
|
120
|
+
|
|
121
|
+
```typescript
|
|
122
|
+
test.use({
|
|
123
|
+
dynatraceConfig: {
|
|
124
|
+
endpointUrl: process.env.DT_ENDPOINT_URL!,
|
|
125
|
+
appId: process.env.DT_APP_ID!,
|
|
126
|
+
token: process.env.DT_TOKEN!
|
|
127
|
+
}
|
|
128
|
+
});
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
### No Events Received
|
|
132
|
+
|
|
133
|
+
If your tests fail with "Dynatrace didn't send any events":
|
|
134
|
+
|
|
135
|
+
1. **Check fixture ordering** - Ensure `dynatraceTesting` is destructured before any fixtures that navigate the page
|
|
136
|
+
2. **Check the page URL** - If you see a warning about the page already being navigated, fix the fixture order
|
|
137
|
+
|
|
138
|
+
### Event Dumping
|
|
139
|
+
|
|
140
|
+
When `dumpEventsOnFail` is enabled, the framework will output detailed information about received events when assertions fail:
|
|
141
|
+
|
|
142
|
+
```
|
|
143
|
+
[Dynatrace Testing] Event Dump (expectToHaveSentEvent - no match)
|
|
144
|
+
Total events received: 3
|
|
145
|
+
Total beacons received: 2
|
|
146
|
+
|
|
147
|
+
Received events:
|
|
148
|
+
|
|
149
|
+
Event 1: { "event_properties.custom_val": "load", ... }
|
|
150
|
+
Event 2: { "event_properties.custom_val": "user-action", ... }
|
|
151
|
+
Event 3: { "event_properties.custom_val": "custom", ... }
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
This helps identify why expected events weren't matched.
|
|
155
|
+
|
|
156
|
+
## Testing API
|
|
157
|
+
The `DynatraceTesting` interface provides utility methods for validating observability-related events and beacon
|
|
158
|
+
requests during tests.
|
|
159
|
+
|
|
160
|
+
---
|
|
161
|
+
|
|
162
|
+
## Methods
|
|
163
|
+
|
|
164
|
+
### `waitForBeacons(options?: { minCount?: number; timeout?: number }): Promise<BeaconRequest[]>`
|
|
165
|
+
|
|
166
|
+
Waits for a specified number of beacon requests or until a timeout occurs.
|
|
167
|
+
|
|
168
|
+
#### Parameters:
|
|
169
|
+
- `options` *(Optional)*:
|
|
170
|
+
- `minCount`: The minimum number of beacon requests to wait for.
|
|
171
|
+
- `timeout`: The maximum time to wait for beacon requests, in milliseconds. *(Default: 30,000)*
|
|
172
|
+
|
|
173
|
+
#### Returns:
|
|
174
|
+
A promise that resolves with an array of beacon requests.
|
|
175
|
+
|
|
176
|
+
---
|
|
177
|
+
|
|
178
|
+
### `expectToHaveSentEvent(event: Record<string, unknown>, options?: { timeout?: number }): Promise<void>`
|
|
179
|
+
|
|
180
|
+
Verifies that a specific event has been sent, optionally within a timeout period.
|
|
181
|
+
|
|
182
|
+
#### Parameters:
|
|
183
|
+
- `event`: The event to check, represented as a key-value pair object. This uses Playwright's `expect(event).toMatchObject`.
|
|
184
|
+
- `options` *(Optional)*:
|
|
185
|
+
- `timeout`: The maximum time to wait for the event to be sent, in milliseconds. *(Default: 30,000)*
|
|
186
|
+
|
|
187
|
+
#### Returns:
|
|
188
|
+
A promise that resolves when the event is confirmed to have been sent.
|
|
189
|
+
|
|
190
|
+
---
|
|
191
|
+
|
|
192
|
+
### `expectToHaveSentEventTimes(event: Record<string, unknown>, times: number, options?: { timeout?: number }): Promise<void>`
|
|
193
|
+
|
|
194
|
+
Verifies that a specific event has been sent a specified number of times, optionally within a timeout period.
|
|
195
|
+
|
|
196
|
+
#### Parameters:
|
|
197
|
+
- `event`: The event to check, represented as a key-value pair object. This uses Playwright's `expect(event).toMatchObject`.
|
|
198
|
+
- `times`: The exact number of times the event is expected to have been sent.
|
|
199
|
+
- `options` *(Optional)*:
|
|
200
|
+
- `timeout`: The maximum time to wait for the event to be sent, in milliseconds. *(Default: 30,000)*
|
|
201
|
+
|
|
202
|
+
#### Returns:
|
|
203
|
+
A promise that resolves when the event is confirmed to have been sent the specified number of times.
|
|
204
|
+
|
|
205
|
+
---
|
|
206
|
+
|
|
207
|
+
### `clearEvents(): void`
|
|
208
|
+
|
|
209
|
+
Clears all events and beacons, allowing subsequent expectations to ignore events that have been sent in the past.
|
|
210
|
+
|
|
211
|
+
#### Example:
|
|
212
|
+
```typescript
|
|
213
|
+
sendFooEvent();
|
|
214
|
+
await dynatraceTesting.expectToHaveSentEventTimes({ foo: "bar" }, 1);
|
|
215
|
+
|
|
216
|
+
dynatraceTesting.clearEvents();
|
|
217
|
+
|
|
218
|
+
await dynatraceTesting.expectToHaveSentEventTimes({ foo: "bar" }, 1);
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
---
|
|
222
|
+
|
|
223
|
+
### `toMatchEventSnapshot(options?: SnapshotOptions): Promise<void>`
|
|
224
|
+
|
|
225
|
+
Compares captured events against a stored snapshot file. On first run, creates the snapshot. On subsequent runs, compares and fails if different. Volatile fields (timestamps, IDs, etc.) are processed by default to prevent flaky tests.
|
|
226
|
+
|
|
227
|
+
#### Parameters:
|
|
228
|
+
- `options` *(Optional)*:
|
|
229
|
+
- `ignoredFields`: Array of field names or patterns whose values are replaced with `[IGNORED]` placeholder before comparison:
|
|
230
|
+
- **Exact field names** (e.g., `"start_time"`): Value replaced with `[IGNORED]`
|
|
231
|
+
- **Wildcard patterns** (e.g., `"dt.rum.*"`): All matching fields have values replaced with `[IGNORED]`
|
|
232
|
+
|
|
233
|
+
Default: `DEFAULT_IGNORED_FIELDS` - includes timestamps, session IDs, trace IDs, etc.
|
|
234
|
+
- `removedFields`: Array of field names or patterns to remove entirely before comparison:
|
|
235
|
+
- **Exact field names** (e.g., `"performance.time_origin"`): Field is removed
|
|
236
|
+
- **Wildcard patterns** (e.g., `"inp.*"`): All matching fields are removed
|
|
237
|
+
|
|
238
|
+
Default: `DEFAULT_REMOVED_FIELDS` - includes web vitals, performance metrics, viewport dimensions.
|
|
239
|
+
- `ignoreEvents`: Array of event patterns to filter out completely. Events matching any pattern are excluded from the snapshot. Default: `DEFAULT_IGNORED_EVENTS` (filters long tasks and self-monitoring events).
|
|
240
|
+
- `name`: Custom snapshot name. If not provided, defaults to `"events"`.
|
|
241
|
+
|
|
242
|
+
#### Returns:
|
|
243
|
+
A promise that resolves when the snapshot comparison succeeds.
|
|
244
|
+
|
|
245
|
+
#### Example - Basic Usage:
|
|
246
|
+
```typescript
|
|
247
|
+
test("captures user action events", async ({ page, dynatraceTesting }) => {
|
|
248
|
+
await page.goto("http://127.0.0.1:3000/ui");
|
|
249
|
+
await page.getByText("Submit").click();
|
|
250
|
+
|
|
251
|
+
// Wait for events to be captured
|
|
252
|
+
await dynatraceTesting.waitForBeacons({ minCount: 1 });
|
|
253
|
+
|
|
254
|
+
// Compare against snapshot
|
|
255
|
+
await dynatraceTesting.toMatchEventSnapshot();
|
|
256
|
+
});
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
#### Example - Custom Ignored and Removed Properties:
|
|
260
|
+
```typescript
|
|
261
|
+
import { DEFAULT_IGNORED_FIELDS, DEFAULT_REMOVED_FIELDS } from "@dynatrace/rum-javascript-sdk/test";
|
|
262
|
+
|
|
263
|
+
test("captures events with custom property handling", async ({ page, dynatraceTesting }) => {
|
|
264
|
+
await page.goto("http://127.0.0.1:3000/ui");
|
|
265
|
+
await page.getByText("Submit").click();
|
|
266
|
+
|
|
267
|
+
await dynatraceTesting.waitForBeacons({ minCount: 1 });
|
|
268
|
+
|
|
269
|
+
// Extend defaults with additional patterns
|
|
270
|
+
await dynatraceTesting.toMatchEventSnapshot({
|
|
271
|
+
ignoredFields: [
|
|
272
|
+
...DEFAULT_IGNORED_FIELDS,
|
|
273
|
+
"event_properties.request_id" // Value replaced with [IGNORED]
|
|
274
|
+
],
|
|
275
|
+
removedFields: [
|
|
276
|
+
...DEFAULT_REMOVED_FIELDS,
|
|
277
|
+
"user_action.resources.*" // All matching fields removed entirely
|
|
278
|
+
]
|
|
279
|
+
});
|
|
280
|
+
});
|
|
281
|
+
```
|
|
282
|
+
|
|
283
|
+
#### Example - Custom Event Filtering:
|
|
284
|
+
```typescript
|
|
285
|
+
import { DEFAULT_IGNORED_EVENTS } from "@dynatrace/rum-javascript-sdk/test";
|
|
286
|
+
|
|
287
|
+
test("captures events excluding specific patterns", async ({ page, dynatraceTesting }) => {
|
|
288
|
+
await page.goto("http://127.0.0.1:3000/ui");
|
|
289
|
+
await page.getByText("Submit").click();
|
|
290
|
+
|
|
291
|
+
await dynatraceTesting.waitForBeacons({ minCount: 1 });
|
|
292
|
+
|
|
293
|
+
// Filter out specific event types
|
|
294
|
+
await dynatraceTesting.toMatchEventSnapshot({
|
|
295
|
+
ignoreEvents: [
|
|
296
|
+
...DEFAULT_IGNORED_EVENTS,
|
|
297
|
+
{ "characteristics.has_navigation": true }, // Exclude navigation events
|
|
298
|
+
{ "url.full": "http://example.com/favicon.ico" } // Exclude specific URL
|
|
299
|
+
]
|
|
300
|
+
});
|
|
301
|
+
});
|
|
302
|
+
```
|
|
303
|
+
|
|
304
|
+
#### Example - Named Snapshots:
|
|
305
|
+
```typescript
|
|
306
|
+
test("captures multiple event sequences", async ({ page, dynatraceTesting }) => {
|
|
307
|
+
await page.goto("http://127.0.0.1:3000/ui");
|
|
308
|
+
|
|
309
|
+
// First interaction
|
|
310
|
+
await page.getByText("Login").click();
|
|
311
|
+
await dynatraceTesting.waitForBeacons({ minCount: 1 });
|
|
312
|
+
await dynatraceTesting.toMatchEventSnapshot({ name: "login-events" });
|
|
313
|
+
|
|
314
|
+
dynatraceTesting.clearEvents();
|
|
315
|
+
|
|
316
|
+
// Second interaction
|
|
317
|
+
await page.getByText("Submit").click();
|
|
318
|
+
await dynatraceTesting.waitForBeacons({ minCount: 1 });
|
|
319
|
+
await dynatraceTesting.toMatchEventSnapshot({ name: "submit-events" });
|
|
320
|
+
});
|
|
321
|
+
```
|
|
322
|
+
|
|
323
|
+
#### Example - Browser-Specific Snapshots:
|
|
324
|
+
|
|
325
|
+
Event snapshots may differ between browsers due to variations in timing, event ordering, or browser-specific behavior. To handle this, include the `browserName` fixture in your snapshot name to create separate snapshots per browser:
|
|
326
|
+
|
|
327
|
+
```typescript
|
|
328
|
+
test("captures events per browser", async ({ page, dynatraceTesting, browserName }) => {
|
|
329
|
+
await page.goto("http://127.0.0.1:3000/ui");
|
|
330
|
+
await page.getByText("Submit").click();
|
|
331
|
+
|
|
332
|
+
await dynatraceTesting.waitForBeacons({ minCount: 1 });
|
|
333
|
+
|
|
334
|
+
// Creates separate snapshots: basic-events-chromium, basic-events-firefox, basic-events-webkit
|
|
335
|
+
await dynatraceTesting.toMatchEventSnapshot({
|
|
336
|
+
name: `basic-events-${browserName}`
|
|
337
|
+
});
|
|
338
|
+
});
|
|
339
|
+
```
|
|
340
|
+
|
|
341
|
+
This creates separate snapshot files for each browser:
|
|
342
|
+
```
|
|
343
|
+
e2e/
|
|
344
|
+
├── my-test.spec.ts
|
|
345
|
+
└── my-test.spec.ts-snapshots/
|
|
346
|
+
├── basic-events-chromium.events.snap
|
|
347
|
+
├── basic-events-firefox.events.snap
|
|
348
|
+
└── basic-events-webkit.events.snap
|
|
349
|
+
```
|
|
350
|
+
|
|
351
|
+
#### Snapshot Files
|
|
352
|
+
|
|
353
|
+
Snapshots are stored alongside your test files in a directory named `<test-file>-snapshots/`. For example:
|
|
354
|
+
```
|
|
355
|
+
e2e/
|
|
356
|
+
├── my-test.spec.ts
|
|
357
|
+
└── my-test.spec.ts-snapshots/
|
|
358
|
+
└── events.events.snap
|
|
359
|
+
```
|
|
360
|
+
|
|
361
|
+
The snapshot files contain JSON-formatted event data with ignored fields replaced by `[IGNORED]` and removed fields omitted:
|
|
362
|
+
```json
|
|
363
|
+
[
|
|
364
|
+
{
|
|
365
|
+
"duration": "[IGNORED]",
|
|
366
|
+
"name": "click on Submit",
|
|
367
|
+
"start_time": "[IGNORED]",
|
|
368
|
+
"type": "user_action"
|
|
369
|
+
}
|
|
370
|
+
]
|
|
371
|
+
```
|
|
372
|
+
|
|
373
|
+
#### Updating Snapshots
|
|
374
|
+
|
|
375
|
+
To update snapshots when event structures change intentionally, run Playwright with the `--update-snapshots` flag:
|
|
376
|
+
|
|
377
|
+
```bash
|
|
378
|
+
npx playwright test --update-snapshots
|
|
379
|
+
```
|
|
380
|
+
|
|
381
|
+
#### Default Ignored Fields
|
|
382
|
+
|
|
383
|
+
The following fields have their values replaced with `[IGNORED]` by default:
|
|
384
|
+
|
|
385
|
+
| Category | Fields |
|
|
386
|
+
|----------|--------|
|
|
387
|
+
| **Timing** | `start_time`, `duration`, `timestamp` |
|
|
388
|
+
| **Session/Instance IDs** | `dt.rum.sid`, `dt.rum.browser.sid`, `dt.rum.instance.id`, `user_session.id`, `user.anonymous_id`, `view.instance_id`, `page.instance_id`, `user_action.instance_id`, etc. |
|
|
389
|
+
| **Distributed Tracing** | `trace.id`, `span.id` |
|
|
390
|
+
| **Self-monitoring** | `dt.rum.sfm_events`, `dt.support.last_user_input` |
|
|
391
|
+
|
|
392
|
+
#### Default Removed Fields
|
|
393
|
+
|
|
394
|
+
The following fields are removed entirely by default (they vary in count or presence between runs):
|
|
395
|
+
|
|
396
|
+
| Category | Fields |
|
|
397
|
+
|----------|--------|
|
|
398
|
+
| **Performance** | `performance.*` |
|
|
399
|
+
| **Web Vitals** | `fcp.*`, `fp.*`, `ttfb.*`, `lcp.*`, `fid.*`, `inp.*`, `cls.*` |
|
|
400
|
+
| **Long Tasks** | `long_task.*` |
|
|
401
|
+
| **Viewport/Screen** | `browser.window.*`, `device.screen.*` |
|
|
402
|
+
|
|
403
|
+
#### Default Ignored Events
|
|
404
|
+
|
|
405
|
+
The following event patterns are filtered out by default:
|
|
406
|
+
|
|
407
|
+
| Pattern | Description |
|
|
408
|
+
|---------|-------------|
|
|
409
|
+
| `{ "characteristics.has_long_task": true }` | Long task events (timing varies) |
|
|
410
|
+
| `{ "characteristics.is_self_monitoring": true }` | Self-monitoring events |
|
|
411
|
+
|
|
412
|
+
#### Troubleshooting Snapshot Failures
|
|
413
|
+
|
|
414
|
+
When a snapshot comparison fails, the error message includes:
|
|
415
|
+
1. The path to the snapshot file
|
|
416
|
+
2. A line-by-line diff showing expected vs actual values
|
|
417
|
+
3. Instructions for updating the snapshot
|
|
418
|
+
|
|
419
|
+
Common causes of snapshot failures:
|
|
420
|
+
- **New fields added to events**: Update the snapshot with `--update-snapshots`
|
|
421
|
+
- **Volatile field values**: Add the field to `ignoredFields` to replace values with `[IGNORED]`
|
|
422
|
+
- **Varying field presence**: Add the field to `removedFields` (use `fieldname.*` wildcard to remove all fields with that prefix)
|
|
423
|
+
- **Unwanted events**: Add an event pattern to `ignoreEvents` to filter them out
|
|
424
|
+
- **Intentional changes**: Review the diff and update the snapshot if correct
|
|
@@ -1,10 +1,16 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: Dynatrace Api Types
|
|
3
|
+
---
|
|
1
4
|
# Dynatrace Api Types
|
|
2
5
|
This package contains the Typescript type information for the `dynatrace` API of the RUM JavaScript.
|
|
3
6
|
|
|
4
7
|
Keep in mind that when the RUM JavaScript is updated, this type package also has to be updated to provide accurate types.
|
|
5
8
|
|
|
6
9
|
## Installation
|
|
7
|
-
|
|
10
|
+
|
|
11
|
+
```bash
|
|
12
|
+
npm install --save-dev @dynatrace/rum-javascript-sdk
|
|
13
|
+
````
|
|
8
14
|
|
|
9
15
|
## Configuration
|
|
10
16
|
Make sure to add these paths to `"typeRoots"` in tsconfig.json under `"compilerOptions"`
|
|
@@ -41,4 +47,4 @@ if (window.dynatrace) {
|
|
|
41
47
|
}
|
|
42
48
|
```
|
|
43
49
|
|
|
44
|
-
Refer to the [
|
|
50
|
+
Refer to the [User Actions API](./4-useractions.md) for details about `dynatrace.userActions`.
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: User Actions API
|
|
3
|
+
---
|
|
1
4
|
# User Actions API
|
|
2
5
|
|
|
3
6
|
**Experimental Feature** • This guide explains how to use the User Actions API to manually control user action creation, monitoring, and lifecycle management in your web application.
|
|
@@ -64,7 +67,7 @@ User actions can complete for various reasons, indicated by the `user_action.com
|
|
|
64
67
|
|
|
65
68
|
## API approaches
|
|
66
69
|
|
|
67
|
-
You can use the User Actions API directly, or via its synchronous or asynchronous SDK functions, matching the pattern established in the [
|
|
70
|
+
You can use the User Actions API directly, or via its synchronous or asynchronous SDK functions, matching the pattern established in the [RUM JavaScript SDK Overview](./1-overview.md):
|
|
68
71
|
|
|
69
72
|
### Direct API (via `dynatrace.userActions`)
|
|
70
73
|
|
|
@@ -234,8 +237,8 @@ dynatrace.addEventModifier(evt => {
|
|
|
234
237
|
```
|
|
235
238
|
|
|
236
239
|
:::note
|
|
237
|
-
Using `event_properties` requires you to configure them
|
|
238
|
-
|
|
240
|
+
Using `event_properties` requires you to configure them on the server side.
|
|
241
|
+
See [Event and session properties](https://www.dynatrace.com/support/doc/experience-vitals/experience-vitals-settings/event-and-session-properties) for more details.
|
|
239
242
|
:::
|
|
240
243
|
|
|
241
244
|
### Check user action state
|
|
@@ -588,7 +591,7 @@ class CheckoutTracker {
|
|
|
588
591
|
...this.checkoutAction.event_properties,
|
|
589
592
|
'event_properties.checkout_step': step,
|
|
590
593
|
...Object.entries(additionalData).reduce((acc, [key, value]) => {
|
|
591
|
-
// Remember to configure the properties
|
|
594
|
+
// Remember to configure the properties on the server side!
|
|
592
595
|
acc[`event_properties.${key}`] = value;
|
|
593
596
|
return acc;
|
|
594
597
|
}, {} as Record<string, any>)
|
|
@@ -979,12 +982,11 @@ All async functions follow the same pattern, accepting an optional `timeout` par
|
|
|
979
982
|
|
|
980
983
|
## Additional resources
|
|
981
984
|
|
|
982
|
-
- [RUM JavaScript SDK Overview](
|
|
983
|
-
-
|
|
984
|
-
- [RUM JavaScript Typedoc](https://www.dynatrace.com/support/doc/javascriptapi/doc-latest/)
|
|
985
|
+
- [RUM JavaScript SDK Overview](./1-overview.md)
|
|
986
|
+
- {@link dynatrace.addEventModifier | Event Modification API} - For modifying user action events
|
|
985
987
|
|
|
986
988
|
---
|
|
987
989
|
|
|
988
990
|
:::note
|
|
989
|
-
This API is experimental and subject to change. Always check for updates when upgrading to new versions of the RUM JavaScript
|
|
991
|
+
This API is experimental and subject to change. Always check for updates when upgrading to new versions of the RUM JavaScript.
|
|
990
992
|
:::
|
package/package.json
CHANGED
|
@@ -1,10 +1,47 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@dynatrace/rum-javascript-sdk",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.333.2",
|
|
4
4
|
"description": "JavaScript API for Real User Monitoring (RUM)",
|
|
5
5
|
"sideEffects": false,
|
|
6
6
|
"type": "module",
|
|
7
7
|
"types": "./dist/types/index.d.ts",
|
|
8
|
+
"typesVersions": {
|
|
9
|
+
"*": {
|
|
10
|
+
"api": [
|
|
11
|
+
"./dist/api/index.d.ts"
|
|
12
|
+
],
|
|
13
|
+
"api/user-actions": [
|
|
14
|
+
"./dist/api/user-actions.d.ts"
|
|
15
|
+
],
|
|
16
|
+
"api/promises": [
|
|
17
|
+
"./dist/api/promises/index.d.ts"
|
|
18
|
+
],
|
|
19
|
+
"api/promises/user-actions": [
|
|
20
|
+
"./dist/api/promises/user-actions.d.ts"
|
|
21
|
+
],
|
|
22
|
+
"test": [
|
|
23
|
+
"./dist/testing/index.d.ts"
|
|
24
|
+
],
|
|
25
|
+
"types": [
|
|
26
|
+
"./dist/types/index.d.ts"
|
|
27
|
+
],
|
|
28
|
+
"types/user-actions": [
|
|
29
|
+
"./dist/types/user-actions/index.d.ts"
|
|
30
|
+
],
|
|
31
|
+
"types/api": [
|
|
32
|
+
"./dist/types/api/index.d.ts"
|
|
33
|
+
],
|
|
34
|
+
"types/rum-events": [
|
|
35
|
+
"./dist/types/rum-events/index.d.ts"
|
|
36
|
+
],
|
|
37
|
+
"types/rum-events/event-context": [
|
|
38
|
+
"./dist/types/rum-events/event-context/index.d.ts"
|
|
39
|
+
],
|
|
40
|
+
"types/rum-events/shared-namespaces-and-fields": [
|
|
41
|
+
"./dist/types/rum-events/shared-namespaces-and-fields/index.d.ts"
|
|
42
|
+
]
|
|
43
|
+
}
|
|
44
|
+
},
|
|
8
45
|
"files": [
|
|
9
46
|
"dist/api/**/*.js",
|
|
10
47
|
"dist/api/**/*.d.ts",
|
|
@@ -42,9 +79,9 @@
|
|
|
42
79
|
"default": "./dist/types/internal/index.js"
|
|
43
80
|
},
|
|
44
81
|
"./test": {
|
|
45
|
-
"types": "./dist/testing/
|
|
46
|
-
"import": "./dist/testing/
|
|
47
|
-
"default": "./dist/testing/
|
|
82
|
+
"types": "./dist/testing/index.d.ts",
|
|
83
|
+
"import": "./dist/testing/index.js",
|
|
84
|
+
"default": "./dist/testing/index.js"
|
|
48
85
|
},
|
|
49
86
|
"./types": {
|
|
50
87
|
"types": "./dist/types/index.d.ts",
|
|
@@ -94,15 +131,15 @@
|
|
|
94
131
|
"license": "ISC",
|
|
95
132
|
"devDependencies": {
|
|
96
133
|
"@types/node": "25.0.3",
|
|
97
|
-
"@vitest/coverage-v8": "
|
|
98
|
-
"@vitest/ui": "
|
|
134
|
+
"@vitest/coverage-v8": "4.1.0-beta.1",
|
|
135
|
+
"@vitest/ui": "4.1.0-beta.1",
|
|
99
136
|
"eslint": "9.38.0",
|
|
100
137
|
"jsdom": "27.0.1",
|
|
101
138
|
"knip": "5.27.0",
|
|
102
139
|
"typedoc": "0.28.10",
|
|
103
140
|
"typedoc-plugin-mdn-links": "5.0.3",
|
|
104
141
|
"typescript": "5.8.2",
|
|
105
|
-
"vitest": "
|
|
142
|
+
"vitest": "4.1.0-beta.1"
|
|
106
143
|
},
|
|
107
144
|
"scripts": {
|
|
108
145
|
"build:lib": "tsc -b tsconfig.build.json",
|
|
@@ -110,8 +147,8 @@
|
|
|
110
147
|
"lint": "eslint \"source/**/*.ts\" \"./*.{ts,js,mjs}\"",
|
|
111
148
|
"lint:fix": "eslint \"source/**/*.ts\" \"./*.{ts,js,mjs}\" --fix && echo No Lint-Problems found",
|
|
112
149
|
"//": "Note: these 2 scripts below are only for local builds. The CI build in build.groovy needs to be updated as well if there are any changes",
|
|
113
|
-
"doc:api-gen3-internal": "typedoc --treatWarningsAsErrors --options ./typedoc-gen3-internal.api.json --tsconfig ./tsconfig-gen3.apidoc.json
|
|
114
|
-
"doc:api-gen3-public": "typedoc --treatWarningsAsErrors --options ./typedoc-gen3-public.api.json --tsconfig ./tsconfig-gen3.apidoc.json
|
|
150
|
+
"doc:api-gen3-internal": "typedoc --treatWarningsAsErrors --options ./typedoc-gen3-internal.api.json --tsconfig ./tsconfig-gen3.apidoc.json",
|
|
151
|
+
"doc:api-gen3-public": "typedoc --treatWarningsAsErrors --options ./typedoc-gen3-public.api.json --tsconfig ./tsconfig-gen3.apidoc.json",
|
|
115
152
|
"find-deadcode": "knip"
|
|
116
153
|
}
|
|
117
154
|
}
|