Skip to content

Commit 142c735

Browse files
authored
fix(browser): calculate prepare time from createTesters call on the main thread (#8101)
1 parent 6246a8a commit 142c735

File tree

6 files changed

+19
-9
lines changed

6 files changed

+19
-9
lines changed

docs/guide/profiling-test-performance.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ When you run Vitest it reports multiple time metrics of your tests:
2020
- Collect: Time spent for collecting all tests in the test files. This includes the time it took to import all file dependencies.
2121
- Tests: Time spent for actually running the test cases.
2222
- Environment: Time spent for setting up the test [`environment`](/config/#environment), for example JSDOM.
23-
- Prepare: Time Vitest uses to prepare the test runner.
23+
- Prepare: Time Vitest uses to prepare the test runner. When running tests in Node, this is the time to import and execute all internal utilities inside the worker. When running tests in the browser, this also includes the time to initiate the iframe.
2424
2525
## Test runner
2626

packages/browser/src/client/channel.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ export interface IframeCleanupEvent {
4040
export interface IframePrepareEvent {
4141
event: 'prepare'
4242
iframeId: string
43+
startTime: number
4344
}
4445

4546
export type GlobalChannelIncomingEvent = GlobalChannelTestRunCanceledEvent

packages/browser/src/client/orchestrator.ts

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,7 @@ export class IframeOrchestrator {
107107

108108
if (!this.iframes.has(ID_ALL)) {
109109
debug('preparing non-isolated iframe')
110-
await this.prepareIframe(container, ID_ALL)
110+
await this.prepareIframe(container, ID_ALL, options.startTime)
111111
}
112112

113113
const config = getConfig()
@@ -140,7 +140,7 @@ export class IframeOrchestrator {
140140
this.iframes.delete(file)
141141
}
142142

143-
const iframe = await this.prepareIframe(container, file)
143+
const iframe = await this.prepareIframe(container, file, options.startTime)
144144
await setIframeViewport(iframe, width, height)
145145
// running tests after the "prepare" event
146146
await sendEventToIframe({
@@ -157,7 +157,7 @@ export class IframeOrchestrator {
157157
})
158158
}
159159

160-
private async prepareIframe(container: HTMLDivElement, iframeId: string) {
160+
private async prepareIframe(container: HTMLDivElement, iframeId: string, startTime: number) {
161161
const iframe = this.createTestIframe(iframeId)
162162
container.appendChild(iframe)
163163

@@ -167,6 +167,7 @@ export class IframeOrchestrator {
167167
sendEventToIframe({
168168
event: 'prepare',
169169
iframeId,
170+
startTime,
170171
}).then(resolve, reject)
171172
}
172173
iframe.onerror = (e) => {

packages/browser/src/client/tester/tester.ts

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ channel.addEventListener('message', async (e) => {
6363
break
6464
}
6565
case 'prepare': {
66-
await prepare().catch(err => unhandledError(err, 'Prepare Error'))
66+
await prepare(data).catch(err => unhandledError(err, 'Prepare Error'))
6767
break
6868
}
6969
case 'viewport:done':
@@ -93,7 +93,7 @@ getBrowserState().iframeId = iframeId
9393

9494
let contextSwitched = false
9595

96-
async function prepareTestEnvironment() {
96+
async function prepareTestEnvironment(options: PrepareOptions) {
9797
debug?.('trying to resolve runner', `${reloadStart}`)
9898
const config = getConfig()
9999

@@ -142,7 +142,7 @@ async function prepareTestEnvironment() {
142142
})
143143
}
144144

145-
state.durations.prepare = performance.now() - state.durations.prepare
145+
state.durations.prepare = performance.now() - options.startTime
146146

147147
return {
148148
runner,
@@ -189,8 +189,12 @@ async function executeTests(method: 'run' | 'collect', files: string[]) {
189189
}
190190
}
191191

192-
async function prepare() {
193-
preparedData = await prepareTestEnvironment()
192+
interface PrepareOptions {
193+
startTime: number
194+
}
195+
196+
async function prepare(options: PrepareOptions) {
197+
preparedData = await prepareTestEnvironment(options)
194198

195199
// page is reloading
196200
debug?.('runner resolved successfully')

packages/browser/src/node/pool.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import type {
88
} from 'vitest/node'
99
import crypto from 'node:crypto'
1010
import * as nodeos from 'node:os'
11+
import { performance } from 'node:perf_hooks'
1112
import { createDefer } from '@vitest/utils'
1213
import { stringify } from 'flatted'
1314
import { createDebugger } from 'vitest/node'
@@ -307,6 +308,7 @@ class BrowserPool {
307308
if (!this._promise) {
308309
throw new Error(`Unexpected empty queue`)
309310
}
311+
const startTime = performance.now()
310312

311313
const orchestrator = this.getOrchestrator(sessionId)
312314
debug?.('[%s] run test %s', sessionId, file)
@@ -320,6 +322,7 @@ class BrowserPool {
320322
// this will be parsed by the test iframe, not the orchestrator
321323
// so we need to stringify it first to avoid double serialization
322324
providedContext: this._providedContext || '[{}]',
325+
startTime,
323326
},
324327
)
325328
.then(() => {

packages/vitest/src/types/browser.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,4 +4,5 @@ export interface BrowserTesterOptions {
44
method: TestExecutionMethod
55
files: string[]
66
providedContext: string
7+
startTime: number
78
}

0 commit comments

Comments
 (0)