Tutorial: Create a Custom Reporter

Create a Custom Reporter

Mocha allows you to define and use custom reporters install via npm.

For example, if mocha-foo-reporter was published to the npm registry, you could install it via npm install mocha-foo-reporter --save-dev, then use it via mocha --reporter mocha-foo-reporter.

Example Custom Reporter

If you're looking to get started quickly, here's an example of a custom reporter:

// my-reporter.js

'use strict';

const Mocha = require('mocha');
const {
  EVENT_RUN_BEGIN,
  EVENT_RUN_END,
  EVENT_TEST_FAIL,
  EVENT_TEST_PASS,
  EVENT_SUITE_BEGIN,
  EVENT_SUITE_END
} = Mocha.Runner.constants;

// this reporter outputs test results, indenting two spaces per suite
class MyReporter {
  constructor(runner) {
    this._indents = 0;
    const stats = runner.stats;

    runner
      .once(EVENT_RUN_BEGIN, () => {
        console.log('start');
      })
      .on(EVENT_SUITE_BEGIN, () => {
        this.increaseIndent();
      })
      .on(EVENT_SUITE_END, () => {
        this.decreaseIndent();
      })
      .on(EVENT_TEST_PASS, test => {
        // Test#fullTitle() returns the suite name(s)
        // prepended to the test title
        console.log(`${this.indent()}pass: ${test.fullTitle()}`);
      })
      .on(EVENT_TEST_FAIL, (test, err) => {
        console.log(
          `${this.indent()}fail: ${test.fullTitle()} - error: ${err.message}`
        );
      })
      .once(EVENT_RUN_END, () => {
        console.log(`end: ${stats.passes}/${stats.passes + stats.failures} ok`);
      });
  }

  indent() {
    return Array(this._indents).join('  ');
  }

  increaseIndent() {
    this._indents++;
  }

  decreaseIndent() {
    this._indents--;
  }
}

module.exports = MyReporter;

To use this reporter, execute mocha --reporter /path/to/my-reporter.js.

For further examples, the built-in reporter implementations are the best place to look. The integration tests may also be helpful.

The Base Reporter Class

Base is an "abstract" class. It contains console-specific settings and utilities, commonly used by built-in reporters. Browsing the built-in reporter implementations, you may often see static properties of Base referenced.

It's often useful--but not necessary--for a custom reporter to extend Base.

Statistics

Mocha adds a stats property of type StatsCollector to the reporter's Runner instance (passed as first argument to constructor).

Events

A reporter should listen for events emitted from the runner (a singleton instance of Runner).

The event names are exported from the constants property of Mocha.Runner:

ConstantEvent NameEvent ArgumentsDescription
EVENT_RUN_BEGINstart(n/a)Execution will begin.
EVENT_RUN_ENDend(n/a)All Suites, Tests and Hooks have completed execution.
EVENT_DELAY_BEGINwaiting(n/a)Waiting for global.run() to be called; only emitted when delay option is true.
EVENT_DELAY_ENDready(n/a)User called global.run() and the root suite is ready to execute.
EVENT_SUITE_BEGINsuiteSuiteThe Hooks and Tests within a Suite will be executed, including any nested Suites.
EVENT_SUITE_ENDsuite endSuiteThe Hooks, Tests, and nested Suites within a Suite have completed execution.
EVENT_HOOK_BEGINhookHookA Hook will be executed.
EVENT_HOOK_ENDhook endHookA Hook has completed execution.
EVENT_TEST_BEGINtestTestA Test will be executed.
EVENT_TEST_ENDtest endTestA Test has completed execution.
EVENT_TEST_FAILfailTest, ErrorA Test has failed or thrown an exception.
EVENT_TEST_PASSpassTestA Test has passed.
EVENT_TEST_PENDINGpendingTestA Test was skipped.
EVENT_TEST_RETRYretryTest, ErrorA Test failed, but is about to be retried; only emitted if the retry option is nonzero.

Please use these constants instead of the event names in your own reporter! This will ensure compatibility with future versions of Mocha.

It's important to understand that all Suite callbacks will be run before the Runner emits EVENT_RUN_BEGIN. Hooks and tests won't run until after the Runner emits EVENT_RUN_BEGIN.