Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bind to Circus events via an optional event handler on any custom env. #8344

Merged
merged 7 commits into from Apr 19, 2019
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Expand Up @@ -2,6 +2,7 @@

### Features

- `[jest-circus]` Bind to Circus events via an optional event handler on any custom env ([#8344](https://github.com/facebook/jest/pull/8344)
- `[expect]` Improve report when matcher fails, part 15 ([#8281](https://github.com/facebook/jest/pull/8281))
- `[jest-cli]` Update `--forceExit` and "did not exit for one second" message colors ([#8329](https://github.com/facebook/jest/pull/8329))
- `[expect]` Improve report when matcher fails, part 16 ([#8306](https://github.com/facebook/jest/pull/8306))
Expand Down
8 changes: 8 additions & 0 deletions docs/Configuration.md
Expand Up @@ -861,6 +861,8 @@ test('use jsdom in this test file', () => {

You can create your own module that will be used for setting up the test environment. The module must export a class with `setup`, `teardown` and `runScript` methods. You can also pass variables from this module to your test suites by assigning them to `this.global` object – this will make them available in your test suites as global variables.

The class may optionally expose a `handleTestEvent` method to bind to events fired by [`jest-circus`](https://github.com/facebook/jest/tree/master/packages/jest-circus).

Any docblock pragmas in test files will be passed to the environment constructor and can be used for per-test configuration. If the pragma does not have a value, it will be present in the object with it's value set to an empty string. If the pragma is not present, it will not be present in the object.

_Note: TestEnvironment is sandboxed. Each test suite will trigger setup/teardown in their own TestEnvironment._
Expand Down Expand Up @@ -898,6 +900,12 @@ class CustomEnvironment extends NodeEnvironment {
runScript(script) {
return super.runScript(script);
}

handleTestEvent(event, state) {
SimenB marked this conversation as resolved.
Show resolved Hide resolved
if (event.name === 'test_start') {
// ...
}
}
}

module.exports = CustomEnvironment;
Expand Down
19 changes: 19 additions & 0 deletions packages/jest-circus/README.md
Expand Up @@ -9,6 +9,25 @@

Circus is a flux-based test runner for Jest that is fast, easy to maintain, and simple to extend.

Circus allows you to bind to events via an optional event handler on any [custom environment](https://jestjs.io/docs/en/configuration#testenvironment-string). See the [type definitions](https://github.com/facebook/jest/blob/master/packages/jest-circus/src/types.ts) for more information on the events and state data currently available.

```js
import {NodeEnvironment} from 'jest-environment-node';
import {Event, State} from 'jest-circus';

class MyCustomEnvironment extends NodeEnvironment {
//...

handleTestEvent(event: Event, state: State) {
if (event.name === 'test_start') {
// ...
}
}
}
```

Mutating event or state data is currently unsupported and may cause unexpected behavior or break in a future release without warning. New events, event data, and/or state data will not be considered a breaking change and may be added in any minor release.

## Installation

Install `jest-circus` using yarn:
Expand Down
4 changes: 3 additions & 1 deletion packages/jest-circus/src/index.ts
Expand Up @@ -195,7 +195,9 @@ const test: Global.It = (() => {

const it: Global.It = test;

export = {
export {Event, State} from './types';
export {afterAll, afterEach, beforeAll, beforeEach, describe, it, test};
export default {
afterAll,
afterEach,
beforeAll,
Expand Down
Expand Up @@ -39,6 +39,7 @@ const jestAdapter = async (

const {globals, snapshotState} = initialize({
config,
environment,
getBabelTraverse,
getPrettier,
globalConfig,
Expand Down
Expand Up @@ -6,6 +6,7 @@
*/

import {Config} from '@jest/types';
import {JestEnvironment} from '@jest/environment';
import {AssertionResult, Status, TestResult} from '@jest/test-result';
import {extractExpectedAssertionsErrors, getState, setState} from 'expect';
import {formatExecError, formatResultsErrors} from 'jest-message-util';
Expand All @@ -19,12 +20,13 @@ import {addEventHandler, dispatch, ROOT_DESCRIBE_BLOCK_NAME} from '../state';
import {getTestID} from '../utils';
import run from '../run';
import globals from '..';
import {Event, RunResult, TestEntry} from '../types';
import {Event, RunResult, TestEntry, State} from '../types';

type Process = NodeJS.Process;

export const initialize = ({
config,
environment,
getPrettier,
getBabelTraverse,
globalConfig,
Expand All @@ -33,6 +35,10 @@ export const initialize = ({
testPath,
}: {
config: Config.ProjectConfig;
environment: JestEnvironment & {
// Move this into the JestEnvironment type as an optional method when jest-circus is default.
scotthovestadt marked this conversation as resolved.
Show resolved Hide resolved
handleTestEvent?(event: Event, state: State): void;
};
getPrettier: () => null | any;
getBabelTraverse: () => Function;
globalConfig: Config.GlobalConfig;
Expand Down Expand Up @@ -83,6 +89,10 @@ export const initialize = ({

addEventHandler(eventHandler);

if (environment.handleTestEvent) {
addEventHandler(environment.handleTestEvent.bind(environment));
}

dispatch({
name: 'setup',
parentProcess,
Expand Down