Skip to content

Commit 7d53aa5

Browse files
✅ [RUM-10146] mock global performance buffer when mocking PerformanceObserver (#3752)
1 parent ed91cb5 commit 7d53aa5

File tree

4 files changed

+40
-47
lines changed

4 files changed

+40
-47
lines changed

packages/rum-core/src/browser/performanceObservable.spec.ts

Lines changed: 3 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,7 @@
11
import type { Duration, Subscription } from '@datadog/browser-core'
22
import type { Clock } from '@datadog/browser-core/test'
33
import { mockClock } from '@datadog/browser-core/test'
4-
import type { GlobalPerformanceBufferMock } from '../../test'
5-
import {
6-
createPerformanceEntry,
7-
mockGlobalPerformanceBuffer,
8-
mockPerformanceObserver,
9-
mockRumConfiguration,
10-
} from '../../test'
4+
import { createPerformanceEntry, mockPerformanceObserver, mockRumConfiguration } from '../../test'
115
import { RumPerformanceEntryType, createPerformanceObservable } from './performanceObservable'
126

137
describe('performanceObservable', () => {
@@ -66,7 +60,6 @@ describe('performanceObservable', () => {
6660

6761
it('should notify buffered performance resources asynchronously', () => {
6862
const { notifyPerformanceEntries } = mockPerformanceObserver()
69-
// add the performance entry to the buffer
7063
notifyPerformanceEntries([createPerformanceEntry(RumPerformanceEntryType.RESOURCE, { name: allowedUrl })])
7164

7265
const performanceResourceObservable = createPerformanceObservable(configuration, {
@@ -81,12 +74,6 @@ describe('performanceObservable', () => {
8174
})
8275

8376
describe('fallback strategy when type not supported', () => {
84-
let globalPerformanceBufferMock: GlobalPerformanceBufferMock
85-
86-
beforeEach(() => {
87-
globalPerformanceBufferMock = mockGlobalPerformanceBuffer()
88-
})
89-
9077
it('should notify performance resources when type not supported', () => {
9178
const { notifyPerformanceEntries } = mockPerformanceObserver({ typeSupported: false })
9279
const performanceResourceObservable = createPerformanceObservable(configuration, {
@@ -99,11 +86,9 @@ describe('performanceObservable', () => {
9986
})
10087

10188
it('should notify buffered performance resources when type not supported', () => {
102-
mockPerformanceObserver({ typeSupported: false })
89+
const { notifyPerformanceEntries } = mockPerformanceObserver({ typeSupported: false })
10390
// add the performance entry to the buffer
104-
globalPerformanceBufferMock.addPerformanceEntry(
105-
createPerformanceEntry(RumPerformanceEntryType.RESOURCE, { name: allowedUrl })
106-
)
91+
notifyPerformanceEntries([createPerformanceEntry(RumPerformanceEntryType.RESOURCE, { name: allowedUrl })])
10792

10893
const performanceResourceObservable = createPerformanceObservable(configuration, {
10994
type: RumPerformanceEntryType.RESOURCE,

packages/rum-core/src/domain/contexts/pageStateHistory.spec.ts

Lines changed: 20 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import type { ServerDuration, Duration, RelativeTime } from '@datadog/browser-co
22
import { HookNames } from '@datadog/browser-core'
33
import type { Clock } from '../../../../core/test'
44
import { mockClock, registerCleanupTask } from '../../../../core/test'
5-
import { mockRumConfiguration, mockPerformanceObserver } from '../../../test'
5+
import { createPerformanceEntry, mockPerformanceObserver, mockRumConfiguration } from '../../../test'
66
import { RumEventType } from '../../rawRumEvent.types'
77
import * as performanceObservable from '../../browser/performanceObservable'
88
import type { Hooks } from '../hooks'
@@ -14,18 +14,17 @@ describe('pageStateHistory', () => {
1414
let clock: Clock
1515
let hooks: Hooks
1616
const configuration = mockRumConfiguration()
17-
let getEntriesByTypeSpy: jasmine.Spy<Performance['getEntriesByType']>
1817

1918
beforeEach(() => {
2019
clock = mockClock()
2120
hooks = createHooks()
22-
getEntriesByTypeSpy = spyOn(performance, 'getEntriesByType').and.returnValue([])
2321
})
2422

2523
describe('wasInPageStateDuringPeriod', () => {
2624
let pageStateHistory: PageStateHistory
2725

2826
beforeEach(() => {
27+
mockPerformanceObserver()
2928
pageStateHistory = startPageStateHistory(hooks, configuration)
3029
registerCleanupTask(pageStateHistory.stop)
3130
})
@@ -70,6 +69,7 @@ describe('pageStateHistory', () => {
7069
let pageStateHistory: PageStateHistory
7170

7271
beforeEach(() => {
72+
mockPerformanceObserver()
7373
pageStateHistory = startPageStateHistory(hooks, configuration)
7474
registerCleanupTask(pageStateHistory.stop)
7575
})
@@ -180,6 +180,7 @@ describe('pageStateHistory', () => {
180180
let pageStateHistory: PageStateHistory
181181

182182
beforeEach(() => {
183+
mockPerformanceObserver()
183184
pageStateHistory = startPageStateHistory(hooks, configuration)
184185
registerCleanupTask(pageStateHistory.stop)
185186
})
@@ -226,22 +227,20 @@ describe('pageStateHistory', () => {
226227
})
227228

228229
it('should backfill history if visibility-state is supported and entries exist', () => {
229-
mockPerformanceObserver({
230-
supportedEntryTypes: [
231-
...Object.values(performanceObservable.RumPerformanceEntryType).filter(
232-
(type) => type !== performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE
233-
),
234-
performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE,
235-
],
230+
const { notifyPerformanceEntries } = mockPerformanceObserver({
231+
supportedEntryTypes: [performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE],
236232
})
237233

238-
const mockEntries = [
239-
{ entryType: 'visibility-state', name: 'visible', startTime: 5 },
240-
{ entryType: 'visibility-state', name: 'hidden', startTime: 15 },
241-
] as PerformanceEntry[]
242-
getEntriesByTypeSpy
243-
.withArgs(performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE)
244-
.and.returnValue(mockEntries)
234+
notifyPerformanceEntries([
235+
createPerformanceEntry(performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE, {
236+
name: 'visible',
237+
startTime: 5 as RelativeTime,
238+
}),
239+
createPerformanceEntry(performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE, {
240+
name: 'hidden',
241+
startTime: 15 as RelativeTime,
242+
}),
243+
])
245244

246245
pageStateHistory = startPageStateHistory(hooks, configuration)
247246
registerCleanupTask(pageStateHistory.stop)
@@ -254,19 +253,15 @@ describe('pageStateHistory', () => {
254253

255254
it('should not backfill if visibility-state is not supported', () => {
256255
mockPerformanceObserver({
257-
supportedEntryTypes: Object.values(performanceObservable.RumPerformanceEntryType).filter(
258-
(type) => type !== performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE
259-
),
256+
supportedEntryTypes: [],
260257
})
261258

262-
getEntriesByTypeSpy.calls.reset()
263-
264259
pageStateHistory = startPageStateHistory(hooks, configuration)
265260
registerCleanupTask(pageStateHistory.stop)
266261

267-
expect(getEntriesByTypeSpy).not.toHaveBeenCalledWith(
268-
performanceObservable.RumPerformanceEntryType.VISIBILITY_STATE
269-
)
262+
expect(
263+
pageStateHistory.wasInPageStateDuringPeriod(PageState.ACTIVE, 5 as RelativeTime, 5 as Duration)
264+
).toBeFalse()
270265
})
271266
})
272267
})

packages/rum-core/test/emulate/mockPerformanceObserver.ts

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import { registerCleanupTask } from '@datadog/browser-core/test'
22
import { objectValues } from '@datadog/browser-core'
33
import { RumPerformanceEntryType, type RumPerformanceEntry } from '../../src/browser/performanceObservable'
4+
import { mockGlobalPerformanceBuffer } from './mockGlobalPerformanceBuffer'
45

56
export function mockPerformanceObserver({
67
typeSupported = true,
@@ -9,7 +10,8 @@ export function mockPerformanceObserver({
910
} = {}) {
1011
const originalPerformanceObserver = window.PerformanceObserver
1112
const instances = new Set<MockPerformanceObserver>()
12-
let bufferedEntries: RumPerformanceEntry[] = []
13+
14+
const { addPerformanceEntry } = mockGlobalPerformanceBuffer([])
1315

1416
class MockPerformanceObserver {
1517
static supportedEntryTypes = supportedEntryTypes
@@ -32,7 +34,9 @@ export function mockPerformanceObserver({
3234
this.entryTypes = entryTypes || (type ? [type] : [])
3335
instances.add(this)
3436
if (buffered) {
35-
notify(this, bufferedEntries)
37+
for (const entryType of this.entryTypes) {
38+
notify(this, performance.getEntriesByType(entryType) as RumPerformanceEntry[])
39+
}
3640
}
3741
}
3842

@@ -46,7 +50,6 @@ export function mockPerformanceObserver({
4650
registerCleanupTask(() => {
4751
window.PerformanceObserver = originalPerformanceObserver
4852
instances.clear()
49-
bufferedEntries = []
5053
})
5154

5255
function notify(observer: MockPerformanceObserver, entries: RumPerformanceEntry[]) {
@@ -66,7 +69,9 @@ export function mockPerformanceObserver({
6669

6770
return {
6871
notifyPerformanceEntries: (entries: RumPerformanceEntry[]) => {
69-
bufferedEntries.push(...entries)
72+
for (const entry of entries) {
73+
addPerformanceEntry(entry as PerformanceEntry)
74+
}
7075
instances.forEach((instance) => notify(instance, entries))
7176
},
7277
}

packages/rum-core/test/fixtures.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -267,6 +267,14 @@ export function createPerformanceEntry<T extends RumPerformanceEntryType>(
267267
}
268268
break
269269

270+
case RumPerformanceEntryType.VISIBILITY_STATE:
271+
entry = {
272+
entryType: RumPerformanceEntryType.VISIBILITY_STATE,
273+
name: 'visible',
274+
startTime: 0 as RelativeTime,
275+
}
276+
break
277+
270278
default:
271279
throw new Error(`Unsupported entryType fixture: ${entryType}`)
272280
}

0 commit comments

Comments
 (0)