Skip to content

Commit 149f8e5

Browse files
fix(reporter)!: remove deprecated APIs (#8223)
Co-authored-by: Vladimir Sheremet <sleuths.slews0s@icloud.com>
1 parent 61703c9 commit 149f8e5

35 files changed

+263
-190
lines changed

docs/advanced/api/reporters.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ Vitest has its own test run lifecycle. These are represented by reporter's metho
2525
- [`onHookEnd(afterAll)`](#onhookend)
2626
- [`onTestSuiteResult`](#ontestsuiteresult)
2727
- [`onTestModuleEnd`](#ontestmoduleend)
28+
- [`onCoverage`](#oncoverage)
2829
- [`onTestRunEnd`](#ontestrunend)
2930

3031
Tests and suites within a single module will be reported in order unless they were skipped. All skipped tests are reported at the end of suite/module.

docs/advanced/pool.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ The function is called only once (unless the server config was updated), and it'
6767

6868
Vitest calls `runTest` when new tests are scheduled to run. It will not call it if `files` is empty. The first argument is an array of [TestSpecifications](/advanced/api/test-specification). Files are sorted using [`sequencer`](/config/#sequence-sequencer) before `runTests` is called. It's possible (but unlikely) to have the same file twice, but it will always have a different project - this is implemented via [`projects`](/guide/projects) configuration.
6969

70-
Vitest will wait until `runTests` is executed before finishing a run (i.e., it will emit [`onFinished`](/advanced/reporters) only after `runTests` is resolved).
70+
Vitest will wait until `runTests` is executed before finishing a run (i.e., it will emit [`onTestRunEnd`](/advanced/reporters) only after `runTests` is resolved).
7171

7272
If you are using a custom pool, you will have to provide test files and their results yourself - you can reference [`vitest.state`](https://github.com/vitest-dev/vitest/blob/main/packages/vitest/src/node/state.ts) for that (most important are `collectFiles` and `updateTasks`). Vitest uses `startTests` function from `@vitest/runner` package to do that.
7373

docs/advanced/reporters.md

Lines changed: 6 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ And here is an example of a custom reporter:
2626
import { BaseReporter } from 'vitest/reporters'
2727

2828
export default class CustomReporter extends BaseReporter {
29-
onCollected() {
29+
onTestModuleCollected() {
3030
const files = this.ctx.state.getFiles(this.watchFilters)
3131
this.reportTestSummary(files)
3232
}
@@ -39,7 +39,7 @@ Or implement the `Reporter` interface:
3939
import type { Reporter } from 'vitest/node'
4040

4141
export default class CustomReporter implements Reporter {
42-
onCollected() {
42+
onTestModuleCollected() {
4343
// print something
4444
}
4545
}
@@ -65,22 +65,14 @@ Instead of using the tasks that reporters receive, it is recommended to use the
6565
You can get access to this API by calling `vitest.state.getReportedEntity(runnerTask)`:
6666

6767
```ts twoslash
68-
import type { Reporter, RunnerTestFile, TestModule, Vitest } from 'vitest/node'
68+
import type { Reporter, TestModule } from 'vitest/node'
6969

7070
class MyReporter implements Reporter {
71-
private vitest!: Vitest
72-
73-
onInit(vitest: Vitest) {
74-
this.vitest = vitest
75-
}
76-
77-
onFinished(files: RunnerTestFile[]) {
78-
for (const file of files) {
79-
// note that the old task implementation uses "file" instead of "module"
80-
const testModule = this.vitest.state.getReportedEntity(file) as TestModule
71+
onTestRunEnd(testModules: ReadonlyArray<TestModule>) {
72+
for (const testModule of testModules) {
8173
for (const task of testModule.children) {
8274
// ^?
83-
console.log('finished', task.type, task.fullName)
75+
console.log('test run end', task.type, task.fullName)
8476
}
8577
}
8678
}

docs/guide/migration.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -200,6 +200,7 @@ Vitest 4.0 removes some deprecated APIs, including:
200200
- `poolMatchGlobs` config option. Use [`projects`](/guide/projects) instead.
201201
- `environmentMatchGlobs` config option. Use [`projects`](/guide/projects) instead.
202202
- `workspace` config option. Use [`projects`](/guide/projects) instead.
203+
- Reporter APIs `onCollected`, `onSpecsCollected`, `onPathsCollected`, `onTaskUpdate` and `onFinished`. See [`Reporters API`](/advanced/api/reporters) for new alternatives. These APIs were introduced in Vitest `v3.0.0`.
203204
- `deps.external`, `deps.inline`, `deps.fallbackCJS` config options. Use `server.deps.external`, `server.deps.inline`, or `server.deps.fallbackCJS` instead.
204205

205206
This release also removes all deprecated types. This finally fixes an issue where Vitest accidentally pulled in `@types/node` (see [#5481](https://github.com/vitest-dev/vitest/issues/5481) and [#6141](https://github.com/vitest-dev/vitest/issues/6141)).

packages/browser/src/types.ts

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -63,11 +63,6 @@ export type Awaitable<T> = T | PromiseLike<T>
6363

6464
export interface WebSocketEvents {
6565
onCollected?: (files: RunnerTestFile[]) => Awaitable<void>
66-
onFinished?: (
67-
files: File[],
68-
errors: unknown[],
69-
coverage?: unknown
70-
) => Awaitable<void>
7166
onTaskUpdate?: (packs: TaskResultPack[]) => Awaitable<void>
7267
onUserConsoleLog?: (log: UserConsoleLog) => Awaitable<void>
7368
onPathsCollected?: (paths?: string[]) => Awaitable<void>

packages/ui/node/reporter.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ export default class HTMLReporter implements Reporter {
7171
await fs.mkdir(resolve(this.reporterDir, 'assets'), { recursive: true })
7272
}
7373

74-
async onFinished(): Promise<void> {
74+
async onTestRunEnd(): Promise<void> {
7575
const result: HTMLReportData = {
7676
paths: this.ctx.state.getPaths(),
7777
files: this.ctx.state.getFiles(),

packages/vitest/src/api/setup.ts

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,13 @@
11
import type { File, TaskEventPack, TaskResultPack, TestAnnotation } from '@vitest/runner'
2+
import type { SerializedError } from '@vitest/utils'
23
import type { IncomingMessage } from 'node:http'
34
import type { ViteDevServer } from 'vite'
45
import type { WebSocket } from 'ws'
56
import type { Vitest } from '../node/core'
6-
import type { TestCase } from '../node/reporters/reported-tasks'
7+
import type { TestCase, TestModule } from '../node/reporters/reported-tasks'
8+
import type { TestSpecification } from '../node/spec'
79
import type { Reporter } from '../node/types/reporter'
8-
import type { SerializedTestSpecification } from '../runtime/types/utils'
9-
import type { Awaitable, LabelColor, ModuleGraphData, UserConsoleLog } from '../types/general'
10+
import type { LabelColor, ModuleGraphData, UserConsoleLog } from '../types/general'
1011
import type {
1112
TransformResultWithSource,
1213
WebSocketEvents,
@@ -163,21 +164,25 @@ export class WebSocketReporter implements Reporter {
163164
public clients: Map<WebSocket, WebSocketRPC>,
164165
) {}
165166

166-
onCollected(files?: File[]): void {
167+
onTestModuleCollected(testModule: TestModule): void {
167168
if (this.clients.size === 0) {
168169
return
169170
}
171+
170172
this.clients.forEach((client) => {
171-
client.onCollected?.(files)?.catch?.(noop)
173+
client.onCollected?.([testModule.task])?.catch?.(noop)
172174
})
173175
}
174176

175-
onSpecsCollected(specs?: SerializedTestSpecification[] | undefined): Awaitable<void> {
177+
onTestRunStart(specifications: ReadonlyArray<TestSpecification>): void {
176178
if (this.clients.size === 0) {
177179
return
178180
}
181+
182+
const serializedSpecs = specifications.map(spec => spec.toJSON())
183+
179184
this.clients.forEach((client) => {
180-
client.onSpecsCollected?.(specs)?.catch?.(noop)
185+
client.onSpecsCollected?.(serializedSpecs)?.catch?.(noop)
181186
})
182187
}
183188

@@ -220,7 +225,14 @@ export class WebSocketReporter implements Reporter {
220225
})
221226
}
222227

223-
onFinished(files: File[], errors: unknown[]): void {
228+
onTestRunEnd(testModules: ReadonlyArray<TestModule>, unhandledErrors: ReadonlyArray<SerializedError>): void {
229+
if (!this.clients.size) {
230+
return
231+
}
232+
233+
const files = testModules.map(testModule => testModule.task)
234+
const errors = [...unhandledErrors]
235+
224236
this.clients.forEach((client) => {
225237
client.onFinished?.(files, errors)?.catch?.(noop)
226238
})

packages/vitest/src/node/core.ts

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -446,7 +446,6 @@ export class Vitest {
446446
this.state.blobs = { files, errors, coverages, executionTimes }
447447

448448
await this.report('onInit', this)
449-
await this.report('onPathsCollected', files.flatMap(f => f.filepath))
450449

451450
const specifications: TestSpecification[] = []
452451
for (const file of files) {
@@ -455,7 +454,6 @@ export class Vitest {
455454
specifications.push(specification)
456455
}
457456

458-
await this.report('onSpecsCollected', specifications.map(spec => spec.toJSON()))
459457
await this._testRun.start(specifications).catch(noop)
460458

461459
for (const file of files) {
@@ -698,7 +696,6 @@ export class Vitest {
698696
}
699697
}
700698
finally {
701-
// TODO: wait for coverage only if `onFinished` is defined
702699
const coverage = await this.coverageProvider?.generateCoverage({ allTestsRun })
703700

704701
const errors = this.state.getUnhandledErrors()

packages/vitest/src/node/pools/typecheck.ts

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import type { Vitest } from '../core'
44
import type { ProcessPool } from '../pool'
55
import type { TestProject } from '../project'
66
import type { TestSpecification } from '../spec'
7+
import type { TestRunEndReason } from '../types/reporter'
78
import { hasFailed } from '@vitest/runner/utils'
89
import { createDefer } from '@vitest/utils'
910
import { Typechecker } from '../../typecheck/typechecker'
@@ -42,7 +43,15 @@ export function createTypecheckPool(vitest: Vitest): ProcessPool {
4243

4344
// triggered by TSC watcher, not Vitest watcher, so we need to emulate what Vitest does in this case
4445
if (vitest.config.watch && !vitest.runningPromise) {
45-
await vitest.report('onFinished', files, [])
46+
const modules = files.map(file => vitest.state.getReportedEntity(file)).filter(e => e?.type === 'module')
47+
48+
const state: TestRunEndReason = vitest.isCancelling
49+
? 'interrupted'
50+
: modules.some(m => !m.ok())
51+
? 'failed'
52+
: 'passed'
53+
54+
await vitest.report('onTestRunEnd', modules, [], state)
4655
await vitest.report('onWatcherStart', files, [
4756
...(project.config.typecheck.ignoreSourceErrors ? [] : sourceErrors),
4857
...vitest.state.getUnhandledErrors(),

packages/vitest/src/node/reporters/base.ts

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
import type { File, Task } from '@vitest/runner'
2+
import type { SerializedError } from '@vitest/utils'
23
import type { TestError, UserConsoleLog } from '../../types/general'
34
import type { Vitest } from '../core'
4-
import type { Reporter } from '../types/reporter'
5+
import type { Reporter, TestRunEndReason } from '../types/reporter'
56
import type { TestCase, TestCollection, TestModule, TestModuleState, TestResult, TestSuite, TestSuiteState } from './reported-tasks'
67
import { performance } from 'node:perf_hooks'
78
import { getFullName, getSuites, getTestName, getTests, hasFailed } from '@vitest/runner/utils'
@@ -57,7 +58,14 @@ export abstract class BaseReporter implements Reporter {
5758
return relative(this.ctx.config.root, path)
5859
}
5960

60-
onFinished(files: File[] = this.ctx.state.getFiles(), errors: unknown[] = this.ctx.state.getUnhandledErrors()): void {
61+
onTestRunEnd(
62+
testModules: ReadonlyArray<TestModule>,
63+
unhandledErrors: ReadonlyArray<SerializedError>,
64+
_reason: TestRunEndReason,
65+
): void {
66+
const files = testModules.map(testModule => testModule.task)
67+
const errors = [...unhandledErrors]
68+
6169
this.end = performance.now()
6270
if (!files.length && !errors.length) {
6371
this.ctx.logger.printNoTestFound(this.ctx.filenamePattern)

0 commit comments

Comments
 (0)