From 77c17bc1dd044a8fe32d902376d9dd97ee390d8a Mon Sep 17 00:00:00 2001 From: Simen Bekkhus Date: Mon, 11 Nov 2019 09:39:05 +0100 Subject: [PATCH] feat: allow reporters to be default exports (#9161) --- CHANGELOG.md | 1 + docs/Configuration.md | 1 + .../customReporters.test.ts.snap | 7 ++++ e2e/__tests__/customReporters.test.ts | 15 ++++++++ .../reporters/DefaultExportReporter.js | 34 +++++++++++++++++++ packages/jest-config/src/normalize.ts | 2 +- packages/jest-core/src/TestScheduler.ts | 14 ++++---- 7 files changed, 67 insertions(+), 7 deletions(-) create mode 100644 e2e/custom-reporters/reporters/DefaultExportReporter.js diff --git a/CHANGELOG.md b/CHANGELOG.md index 0a516030235a..ebf99b7e814e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ - `[jest-config]` Throw the full error message and stack when a Jest preset is missing a dependency ([#8924](https://github.com/facebook/jest/pull/8924)) - `[jest-config]` [**BREAKING**] Set default display name color based on runner ([#8689](https://github.com/facebook/jest/pull/8689)) - `[jest-config]` Merge preset globals with project globals ([#9027](https://github.com/facebook/jest/pull/9027)) +- `[jest-core]` Support reporters as default exports ([#9161](https://github.com/facebook/jest/pull/9161)) - `[jest-diff]` Add options for colors and symbols ([#8841](https://github.com/facebook/jest/pull/8841)) - `[jest-diff]` [**BREAKING**] Export as ECMAScript module ([#8873](https://github.com/facebook/jest/pull/8873)) - `[jest-diff]` Add `includeChangeCounts` and rename `Indicator` options ([#8881](https://github.com/facebook/jest/pull/8881)) diff --git a/docs/Configuration.md b/docs/Configuration.md index 23af2d858c76..f789e1c15dd6 100644 --- a/docs/Configuration.md +++ b/docs/Configuration.md @@ -627,6 +627,7 @@ class MyCustomReporter { } module.exports = MyCustomReporter; +// or export default MyCustomReporter; ``` Custom reporters can also force Jest to exit with non-0 code by returning an Error from `getLastError()` methods diff --git a/e2e/__tests__/__snapshots__/customReporters.test.ts.snap b/e2e/__tests__/__snapshots__/customReporters.test.ts.snap index 0e5662c84102..86db90781b48 100644 --- a/e2e/__tests__/__snapshots__/customReporters.test.ts.snap +++ b/e2e/__tests__/__snapshots__/customReporters.test.ts.snap @@ -119,6 +119,13 @@ exports[`Custom Reporters Integration invalid format for adding reporters 1`] = `; +exports[`Custom Reporters Integration reporters can be default exports 1`] = ` +run start +test start +test complete +run complete +`; + exports[`Custom Reporters Integration valid array format for adding reporters 1`] = ` { "onRunComplete": { diff --git a/e2e/__tests__/customReporters.test.ts b/e2e/__tests__/customReporters.test.ts index 55aafea3c67f..41b405c2b017 100644 --- a/e2e/__tests__/customReporters.test.ts +++ b/e2e/__tests__/customReporters.test.ts @@ -121,6 +121,21 @@ describe('Custom Reporters Integration', () => { expect(wrap(stdout)).toMatchSnapshot(); }); + test('reporters can be default exports', () => { + const {stderr, stdout, exitCode} = runJest('custom-reporters', [ + '--no-cache', + '--config', + JSON.stringify({ + reporters: ['/reporters/DefaultExportReporter.js'], + }), + 'add.test.js', + ]); + + expect(stderr).toBe(''); + expect(exitCode).toBe(0); + expect(wrap(stdout)).toMatchSnapshot(); + }); + test('prints reporter errors', () => { writeFiles(DIR, { '__tests__/test.test.js': `test('test', () => {});`, diff --git a/e2e/custom-reporters/reporters/DefaultExportReporter.js b/e2e/custom-reporters/reporters/DefaultExportReporter.js new file mode 100644 index 000000000000..e094f344e5e6 --- /dev/null +++ b/e2e/custom-reporters/reporters/DefaultExportReporter.js @@ -0,0 +1,34 @@ +/** + * Copyright (c) Facebook, Inc. and its affiliates. All Rights Reserved. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + */ + +// TODO: use babel to transpile actual import/export in Jest 26 +Object.defineProperty(exports, '__esModule', { + value: true, +}); +exports.default = void 0; + +const _reporters = require('@jest/reporters'); + +class TestReporter extends _reporters.BaseReporter { + onTestStart() { + console.log('test start'); + } + + onTestResult() { + console.log('test complete'); + } + + onRunStart() { + console.log('run start'); + } + + onRunComplete() { + console.log('run complete'); + } +} + +exports.default = TestReporter; diff --git a/packages/jest-config/src/normalize.ts b/packages/jest-config/src/normalize.ts index b1e2afb4602a..4a1f9c681e64 100644 --- a/packages/jest-config/src/normalize.ts +++ b/packages/jest-config/src/normalize.ts @@ -393,7 +393,7 @@ const normalizeReporters = (options: Config.InitialOptionsWithRootDir) => { basedir: options.rootDir, }); if (!reporter) { - throw new Error( + throw new Resolver.ModuleNotFoundError( `Could not resolve a module for a custom reporter.\n` + ` Module name: ${reporterPath}`, ); diff --git a/packages/jest-core/src/TestScheduler.ts b/packages/jest-core/src/TestScheduler.ts index ed6d73528982..58a141136ea4 100644 --- a/packages/jest-core/src/TestScheduler.ts +++ b/packages/jest-core/src/TestScheduler.ts @@ -28,6 +28,7 @@ import { buildFailureTestResult, makeEmptyAggregatedTestResult, } from '@jest/test-result'; +import {interopRequireDefault} from 'jest-util'; import ReporterDispatcher from './ReporterDispatcher'; import TestWatcher from './TestWatcher'; import {shouldRunInBand} from './testSchedulerHelper'; @@ -315,15 +316,16 @@ export default class TestScheduler { if (path === 'default') return; try { - const Reporter = require(path); + // TODO: Use `requireAndTranspileModule` for Jest 26 + const Reporter = interopRequireDefault(require(path)).default; this.addReporter(new Reporter(this._globalConfig, options)); } catch (error) { - throw new Error( + error.message = 'An error occurred while adding the reporter at path "' + - path + - '".' + - error.message, - ); + chalk.bold(path) + + '".' + + error.message; + throw error; } }); }