Hooks allow you to run setup and teardown logic before or after your tests or test suites.
(fn: (ctx: SuiteContext) => void | Promise<void>, timeout?: number) => voidRuns once before all tests in the current suite.
import { beforeAll } from '@rstest/core';
beforeAll(async (ctx) => {
// Setup logic before all tests
// ctx.filepath gives the current test file path
});beforeAll also supports returning a function that runs after all tests for cleanup (equivalent to afterAll):
import { beforeAll } from '@rstest/core';
beforeAll(async () => {
const cleanUp = await doSomething();
// Cleanup logic after all tests
return async () => {
await cleanUp();
};
});(fn: (ctx: SuiteContext) => void | Promise<void>, timeout?: number) => voidRuns once after all tests in the current suite.
import { afterAll } from '@rstest/core';
afterAll(async (ctx) => {
// Cleanup logic after all tests
});(fn: () => void | Promise<void>, timeout?: number) => voidRuns before each test in the current suite.
import { beforeEach } from '@rstest/core';
beforeEach(async () => {
// Setup logic before each test
});beforeEach also supports returning a function that runs after each test for cleanup (equivalent to afterEach):
import { beforeEach } from '@rstest/core';
beforeEach(async () => {
const cleanUp = await doSomething();
// Cleanup logic after each test
return async () => {
await cleanUp();
};
});(fn: (ctx: { task: { result: Readonly<TestResult> } }) => void | Promise<void>, timeout?: number) => voidRuns after each test in the current suite.
import { afterEach } from '@rstest/core';
afterEach(async () => {
// Cleanup logic after each test
});(fn: (ctx: { task: { result: Readonly<TestResult> } }) => void | Promise<void>, timeout?: number) => voidCalled after the test has finished running whatever the test result is. This can be used to perform cleanup actions. This hook will be called after afterEach.
import { onTestFinished, test } from '@rstest/core';
test('test server', () => {
const server = startServer();
// Register a cleanup function to close the server after the test
onTestFinished(() => server.close());
server.listen(3000, () => {
console.log('Server is running on port 3000');
});
});It should be noted that when you use the onTestFinished hook in concurrent tests, you should get the hook from the test context. This is because Rstest cannot accurately track the specific test to which the global onTestFinished hook belongs in concurrent tests.
describe.concurrent('concurrent suite', () => {
test('test 1', async ({ onTestFinished }) => {
/* ... */
});
test('test 2', async ({ onTestFinished }) => {
/* ... */
});
});(fn: (ctx: { task: { result: Readonly<TestResult> } }) => void | Promise<void>, timeout?: number) => voidCalled after the test has failed.
import { onTestFailed, test } from '@rstest/core';
test('test server', () => {
const server = startServer();
onTestFailed(({ task }) => {
console.log(task.result.errors);
});
server.listen(3000, () => {
console.log('Server is running on port 3000');
});
});It should be noted that when you use the onTestFailed hook in concurrent tests, you should get the hook from the test context. This is because Rstest cannot accurately track the specific test to which the global onTestFailed hook belongs in concurrent tests.