Spec-Zone.ru › Mocha

mocha

Установка

Установите глобально с помощью npm:

$ npm install --global mocha

или в качестве зависимости разработки для вашего проекта:

$ npm install --save-dev mocha

Начиная с версии 9.0.0, Mocha требует Node.js версии 12.0.0 или новее.

Начало работы

$ npm install mocha
$ mkdir test
$ $EDITOR test/test.js # or open with your favorite editor

В вашем редакторе:

var assert = require('assert');
describe('Array', function() {
  describe('#indexOf()', function() {
    it('should return -1 when the value is not present', function() {
      assert.equal([1, 2, 3].indexOf(4), -1);
    });
  });
});

Вернувшись в терминал:

$ ./node_modules/mocha/bin/mocha

  Array
    #indexOf()
      ✓ should return -1 when the value is not present


  1 passing (9ms)

Настройте скрипт тестов в package.json:

"scripts": {
  "test": "mocha"
}

Затем запустите тесты с помощью:

$ npm test

Обзор цикла выполнения

Обновлено для версии 8.0.0.

Ниже приведён среднеуровневый обзор «потока выполнения» Mocha при запуске в Node.js; «менее важные» детали опущены.

В браузере файлы тестов загружаются тегами <script>, и вызов mocha.run() начинается на шаге 9 ниже.

Последовательный режим

  1. Пользователь (то есть вы) выполняет mocha
  2. Загружает опции из конфигурационных файлов, если они присутствуют
  3. Mocha обрабатывает любые командно-строковые опции (подробности см. в разделе слияния конфигураций)
  4. Если обнаружены известные флаги для исполняемого файла node:
    1. Mocha запустит node в дочернем процессе, выполнив себя с этими флагами
    2. В противном случае Mocha не запускает дочерний процесс
  5. Mocha загружает модули, указанные в --require
    1. Если загруженный таким образом файл содержит известные экспорты, специфичные для Mocha (например, плагины для корневых хуков), Mocha «регистрирует» их
    2. В противном случае Mocha игнорирует любые экспорты модуля --require
  6. Mocha проверяет все пользовательские репортеры или интерфейсы, которые были загружены через --require или иным образом
  7. Mocha обнаруживает файлы тестов; при отсутствии файлов или каталогов он находит файлы с расширениями .js, .mjs или .cjs в каталоге test (но не в его подкаталогах), относительно текущей рабочей директории
  8. Интерфейс (по умолчанию) bdd загружает файлы тестов в произвольном порядке, которые получают контекст, специфичный для интерфейса global (например, describe() становится глобальным в файле теста)
  9. Когда файл теста загружается, Mocha выполняет все его наборы и находит, но не выполняет, любые хуки и тесты в них.
  10. В верхней части хуки, тесты и наборы добавляются в «невидимый» корневой набор; для всего процесса существует только один корневой набор
  11. Mocha выполняет глобальные фикстуры настройки, если таковые имеются
  12. Начиная с «корневого» набора, Mocha выполняет:
  13. Любые хуки «перед всем» (для корневого набора это происходит только один раз; см. плагины для корневых хуков)
  14. Для каждого теста Mocha выполняет:
    1. Любые хуки «перед каждым»
    2. Тест (и сообщает о результате)
    3. Любые хуки «после каждого»
  15. Если у текущего набора есть дочерний набор, повторите шаги 10 для каждого дочернего набора; каждый дочерний набор унаследует любые хуки «перед каждым» и «после каждого», определённые в родительском наборе
  16. Любые хуки «после всего» (для корневого набора это происходит только один раз; см. плагины для корневых хуков)
  17. Mocha печатает итоговое резюме/эпилог, если применимо
  18. Mocha выполняет глобальные фикстуры завершения, если таковые имеются

Параллельный режим

  1. Повторите шаги 1–6 из раздела Последовательный режим выше, пропустив проверку репортера
  2. Все найденные файлы тестов помещаются в очередь (их не загружает основной процесс)
  3. Mocha выполняет глобальные фикстуры настройки, если таковые имеются
  4. Mocha создаёт пул дочерних процессов («рабочие процессы»)
  5. Непосредственно перед тем, как рабочий процесс выполнит первый полученный тест, он «инициализирует себя» следующим образом:
    1. Загружает все --require модули
    2. Регистрирует любые плагины для корневых хуков
    3. Игнорирует глобальные фикстуры и пользовательские репортеры
    4. Проверяет корректность встроенного или пользовательского интерфейса
  6. Когда рабочий процесс получает файл теста для выполнения, он создаёт новый экземпляр Mocha для одного файла теста и:
  7. Рабочий процесс повторяет шаг 8 из раздела выше
  8. Рабочий процесс повторяет шаг 10 из раздела выше с оговоркой, что рабочий процесс не сообщает результаты тестов напрямую; он хранит их в буфере памяти
  9. По завершении файла теста результаты из буфера возвращаются в основной процесс, который затем передаёт их указанному пользователем репортеру (по умолчанию spec)
  10. Рабочий процесс становится доступным для пула; пул предоставляет рабочему процессу другой файл теста для выполнения, если таковые остаются
  11. Mocha печатает итоговое резюме/эпилог, если применимо
  12. Mocha выполняет глобальные фикстуры завершения, если таковые имеются

Обнаружение нескольких вызовов done()

Если вы используете асинхронные тесты на основе обратного вызова, Mocha выдаст ошибку, если done() вызывается несколько раз. Это полезно для обнаружения случайных двойных обратных вызовов.

it('double done', function(done) {
  // Calling `done()` twice is an error
  setImmediate(done);
  setImmediate(done);
});

Выполнение вышеприведённого теста выдаст сообщение об ошибке:

$ ./node_modules/.bin/mocha mocha.test.js


  ✓ double done
  1) double done

  1 passing (6ms)
  1 failing

  1) double done:
     Error: done() called multiple times
      at Object.<anonymous> (mocha.test.js:1:63)
      at require (internal/module.js:11:18)
      at Array.forEach (<anonymous>)
      at startup (bootstrap_node.js:187:16)
      at bootstrap_node.js:608:3

Утверждения

Mocha позволяет использовать любую библиотеку утверждений, которую вы пожелаете. В приведённом выше примере мы используем встроенный модуль утверждений Node.js assert — но в целом, если он вызывает Error, он будет работать! Это означает, что вы можете использовать библиотеки такие как:

  • should.js - стиль BDD, показанный в этих документах
  • expect.js - утверждения в стиле expect()
  • chai - утверждения в стиле expect(), assert() и should
  • better-assert - утверждения в стиле C с самодокументированием assert()
  • unexpected - «расширяемый инструмент утверждений BDD»

Асинхронный код

Добавив аргумент (обычно с именем done) в обратный вызов it() теста, Mocha поймёт, что должен подождать, пока эта функция не будет вызвана для завершения теста. Этот обратный вызов принимает экземпляр Error (или подкласс) или ложное значение; всё остальное является неверным использованием и вызывает ошибку (обычно приводящую к неудачному тесту).

describe('User', function() {
  describe('#save()', function() {
    it('should save without error', function(done) {
      var user = new User('Luna');
      user.save(function(err) {
        if (err) done(err);
        else done();
      });
    });
  });
});

В качестве альтернативы, используйте обратный вызов done() напрямую (который будет обрабатывать аргумент ошибки, если он существует):

describe('User', function() {
  describe('#save()', function() {
    it('should save without error', function(done) {
      var user = new User('Luna');
      user.save(done);
    });
  });
});

Работа с промисами

В качестве альтернативы использованию обратного вызова done() вы можете вернуть Promise. Это полезно, если API, которые вы тестируете, возвращают промисы вместо обратных вызовов:

beforeEach(function() {
  return db.clear().then(function() {
    return db.save([tobi, loki, jane]);
  });
});

describe('#find()', function() {
  it('respond with matching records', function() {
    return db.find({type: 'User'}).should.eventually.have.length(3);
  });
});

В последнем примере используется Chai as Promised для удобного утверждения промисов.

В Mocha v3.0.0 и новее, возврат Promise и вызов done() приведут к исключению, так как это обычно ошибка:

const assert = require('assert');

// antipattern
it('should complete this test', function(done) {
  return new Promise(function(resolve) {
    assert.ok(true);
    resolve();
  }).then(done);
});

Вышеприведённый тест завершится с ошибкой Error: Resolution method is overspecified. Specify a callback *or* return a Promise; not both.. В версиях, более старых чем v3.0.0, вызов done() фактически игнорируется.

Использование async / await

Если ваша среда JS поддерживает async / await, вы также можете писать асинхронные тесты так:

beforeEach(async function() {
  await db.clear();
  await db.save([tobi, loki, jane]);
});

describe('#find()', function() {
  it('responds with matching records', async function() {
    const users = await db.find({type: 'User'});
    users.should.have.length(3);
  });
});

Синхронный код

При тестировании синхронного кода опустите обратный вызов, и Mocha автоматически перейдёт к следующему тесту.

describe('Array', function() {
  describe('#indexOf()', function() {
    it('should return -1 when the value is not present', function() {
      [1, 2, 3].indexOf(5).should.equal(-1);
      [1, 2, 3].indexOf(0).should.equal(-1);
    });
  });
});

Стрелочные функции

Использование стрелочных функций (также «лямбда-функций») в Mocha не рекомендуется. Лямбды лексически привязываются к this и не могут получить доступ к контексту Mocha. Например, следующий код завершится ошибкой:

describe('my suite', () => {
  it('my test', () => {
    // should set the timeout of this test to 1000 ms; instead will fail
    this.timeout(1000);
    assert.ok(true);
  });
});

Если вам не нужно использовать контекст Mocha, лямбды должны работать. Помните, что использование лямбд будет сложнее при необходимости рефакторинга!

Хуки

В своём стандартном интерфейсе «BDD» Mocha предоставляет хуки before(), after(), beforeEach() и afterEach(). Их следует использовать для подготовки предварительных условий и очистки после тестов.

describe('hooks', function() {
  before(function() {
    // runs once before the first test in this block
  });

  after(function() {
    // runs once after the last test in this block
  });

  beforeEach(function() {
    // runs before each test in this block
  });

  afterEach(function() {
    // runs after each test in this block
  });

  // test cases
});

Тесты могут появляться перед, после или между вашими хуками. Хуки будут выполняться в порядке их определения, соответственно; все хуки before() выполняются (один раз), затем любые хуки beforeEach(), тесты, любые хуки afterEach() и, наконец, хуки after() (один раз).

Описание хуков

Любой хук можно вызвать с необязательным описанием, что упрощает поиск ошибок в ваших тестах. Если хуку задаётся именованная функция, это имя будет использоваться, если описание не предоставлено.

beforeEach(function() {
  // beforeEach hook
});

beforeEach(function namedFun() {
  // beforeEach:namedFun
});

beforeEach('some description', function() {
  // beforeEach:some description
});

Асинхронные хуки

Все хуки (before(), after(), beforeEach(), afterEach()) могут быть синхронными или асинхронными, ведя себя как обычный тест. Например, вы можете захотеть заполнить базу данных тестовыми данными перед каждым тестом:

describe('Connection', function() {
  var db = new Connection(),
    tobi = new User('tobi'),
    loki = new User('loki'),
    jane = new User('jane');

  beforeEach(function(done) {
    db.clear(function(err) {
      if (err) return done(err);
      db.save([tobi, loki, jane], done);
    });
  });

  describe('#find()', function() {
    it('respond with matching records', function(done) {
      db.find({type: 'User'}, function(err, res) {
        if (err) return done(err);
        res.should.have.length(3);
        done();
      });
    });
  });
});

Хуки верхнего уровня

Хуки, определённые в верхнем уровне файла теста (вне набора), являются корневыми хуками.

Начиная с версии 8.0.0, Плагины для корневых хуков являются предпочтительным механизмом для установки корневых хуков.

Отложенный корневой набор

ПРЕДУПРЕЖДЕНИЕ: Отложенные корневые наборы несовместимы с режимом параллельных тестов.

Если вам нужно выполнить асинхронные операции перед запуском любого из ваших наборов, вы можете отложить корневой набор. Запустите mocha с флагом --delay. Это добавит специальную функцию обратного вызова run() к глобальному контексту:

setTimeout(function() {
  // do some setup

  describe('my suite', function() {
    // ...
  });

  run();
}, 5000);

Отложенные тесты

«Отложенные» — то есть «кто-то должен написать эти тестовые случаи в будущем» — тестовые случаи без обратного вызова:

describe('Array', function() {
  describe('#indexOf()', function() {
    // pending test below
    it('should return -1 when the value is not present');
  });
});

Отложенные тесты будут включены в результаты тестов и помечены как отложенные. Отложенный тест не считается проваленным тестом.

Прочитайте раздел включённых тестов для примера условного назначения тесту статуса «отложен» через this.skip().

Исключительные тесты

ПРЕДУПРЕЖДЕНИЕ: Эксклюзивные тесты несовместимы с режимом параллельных тестов.

Функция эксклюзивности позволяет запускать только указанный набор или тестовый случай, добавив .only() к функции. Вот пример запуска только определённого набора:

describe('Array', function() {
  describe.only('#indexOf()', function() {
    // ...
  });
});

Примечание: Все вложенные наборы по-прежнему будут выполняться.

Вот пример запуска отдельного тестового случая:

describe('Array', function() {
  describe('#indexOf()', function() {
    it.only('should return -1 unless present', function() {
      // ...
    });

    it('should return the index when present', function() {
      // ...
    });
  });
});

До версии v3.0.0, .only() использовал сопоставление строк, чтобы определить, какие тесты нужно выполнить; теперь это не так. В версии v3.0.0 или более поздней, .only() может быть использован несколько раз для определения подмножества тестов для выполнения:

describe('Array', function() {
  describe('#indexOf()', function() {
    it.only('should return -1 unless present', function() {
      // this test will be run
    });

    it.only('should return the index when present', function() {
      // this test will also be run
    });

    it('should return -1 if called with a non-Array context', function() {
      // this test will not be run
    });
  });
});

Вы также можете выбрать несколько наборов:

describe('Array', function() {
  describe.only('#indexOf()', function() {
    it('should return -1 unless present', function() {
      // this test will be run
    });

    it('should return the index when present', function() {
      // this test will also be run
    });
  });

  describe.only('#concat()', function() {
    it('should return a new Array', function() {
      // this test will also be run
    });
  });

  describe('#slice()', function() {
    it('should return a new Array', function() {
      // this test will not be run
    });
  });
});

Но тесты имеют приоритет:

describe('Array', function() {
  describe.only('#indexOf()', function() {
    it.only('should return -1 unless present', function() {
      // this test will be run
    });

    it('should return the index when present', function() {
      // this test will not be run
    });
  });
});

Примечание: Хуки, если они присутствуют, всё равно будут выполнены.

Будьте внимательны, не добавляйте использование .only() в систему контроля версий, если вы этого не хотите! Для этого можно запустить mocha с опцией --forbid-only в команде непрерывной интеграции или в хуке git precommit.

Включительно тесты

Эта функция является обратной .only(). Добавив .skip(), вы можете указать Mocha игнорировать тестовый(ые) случай(ы). Любое пропущенное будет помечено как ожидающее и будет отображено как таковое. Вот пример пропуска отдельного теста:

describe('Array', function() {
  describe('#indexOf()', function() {
    it.skip('should return -1 unless present', function() {
      // this test will not be run
    });

    it('should return the index when present', function() {
      // this test will be run
    });
  });
});

Вы также можете поставить .skip() на весь набор. Это эквивалентно добавлению .skip() ко всем тестам в наборе. Хуки в наборе также пропускаются.

describe('Array', function() {
  describe.skip('#indexOf()', function() {
    it('should return -1 unless present', function() {
      // this test will not be run
    });
  });
});

Примечание: Код во пропускаемых наборах, который находится вне хуков или тестов, всё равно будет выполнен, так как mocha всё равно вызовет функцию набора для построения структуры набора для визуализации.

Лучшая практика: Используйте .skip() вместо того, чтобы выключать тесты комментариями.

Вы также можете пропустить во время выполнения с помощью this.skip(). Если тесту необходима среда или конфигурация, которые нельзя определить заранее, подходит пропуск во время выполнения. Например:

it('should only test in the correct environment', function() {
  if (/* check test environment */) {
    // make assertions
  } else {
    this.skip();
  }
});

Вышеуказанный тест будет отображаться как ожидающий. Также важно отметить, что вызов this.skip() фактически прервёт тест.

Лучшая практика: Чтобы избежать путаницы, не выполняйте дальнейшие инструкции в тесте или хуке после вызова this.skip().

Сравните вышеуказанный тест со следующим кодом:

it('should only test in the correct environment', function() {
  if (/* check test environment */) {
    // make assertions
  } else {
    // do nothing
  }
});

Поскольку этот тест ничего не делает, он будет отображаться как пройденный.

Лучшая практика: Не делайте ничего! Тест должен делать утверждение или использовать this.skip().

Чтобы пропустить несколько тестов таким образом, используйте this.skip() в хуке «перед всеми»:

before(function() {
  if (/* check test environment */) {
    // setup code
  } else {
    this.skip();
  }
});

Это пропустит все блоки it, beforeEach/afterEach и describe в наборе. before/after хуки пропускаются, если они не определены на том же уровне, что и хук, содержащий this.skip().

describe('outer', function() {
  before(function() {
    this.skip();
  });

  after(function() {
    // will be executed
  });

  describe('inner', function() {
    before(function() {
      // will be skipped
    });

    after(function() {
      // will be skipped
    });
  });
});

Обновлено в v7.0.0: Пропуск теста внутри хука «после всех» запрещён и вызовет исключение. Используйте оператор return или другие средства для прерывания выполнения хука.

Перед Mocha v3.0.0, this.skip() не поддерживался в асинхронных тестах и хуках.

Повтор тестов

Вы можете выбрать повтор не удачных тестов до определённого числа раз. Эта функция предназначена для обработки end-to-end тестов (функциональные тесты/Selenium…), где ресурсы трудно смоделировать/заглушить. Не рекомендуется использовать эту функцию для юнит-тестов.

Эта функция повторно выполняет неудачный тест и соответствующие ему beforeEach/afterEach хуки, но не before/after хуки. this.retries() не влияет на неудачные хуки.

ПРИМЕЧАНИЕ: Пример ниже был написан с использованием Selenium webdriver (который перезаписывает глобальные хуки Mocha для Promise цепи).

describe('retries', function() {
  // Retry all tests in this suite up to 4 times
  this.retries(4);

  beforeEach(function() {
    browser.get('http://www.yahoo.com');
  });

  it('should succeed on the 3rd try', function() {
    // Specify this test to only retry up to 2 times
    this.retries(2);
    expect($('.foo').isDisplayed()).to.eventually.be.true;
  });
});

Динамическое создание тестов

Учитывая использование Mocha выражений функций для определения наборов и тестовых случаев, легко генерировать тесты динамически. Специальный синтаксис не требуется — обычный JavaScript может быть использован для достижения функциональности, подобной «параметризованным» тестам, которые вы можете видеть в других фреймворках.

Рассмотрим следующий пример:

const assert = require('assert');

function add(args) {
  return args.reduce((prev, curr) => prev + curr, 0);
}

describe('add()', function() {
  const tests = [
    {args: [1, 2], expected: 3},
    {args: [1, 2, 3], expected: 6},
    {args: [1, 2, 3, 4], expected: 10}
  ];

  tests.forEach(({args, expected}) => {
    it(`correctly adds ${args.length} args`, function() {
      const res = add(args);
      assert.strictEqual(res, expected);
    });
  });
});

Вышеуказанный код создаст набор с тремя спецификациями:

$ mocha

  add()
    ✓ correctly adds 2 args
    ✓ correctly adds 3 args
    ✓ correctly adds 4 args

Тесты, добавленные внутри обработчика .forEach, часто не работают с плагинами редактора, особенно с функциями «запуск правой кнопкой мыши». Другой способ параметризовать тесты — генерировать их с помощью замыкания. Следующий пример эквивалентен предыдущему:

describe('add()', function() {
  const testAdd = ({args, expected}) =>
    function() {
      const res = add(args);
      assert.strictEqual(res, expected);
    };

  it('correctly adds 2 args', testAdd({args: [1, 2], expected: 3}));
  it('correctly adds 3 args', testAdd({args: [1, 2, 3], expected: 6}));
  it('correctly adds 4 args', testAdd({args: [1, 2, 3, 4], expected: 10}));
});

С помощью top-level await вы можете собирать данные о тестах динамически и асинхронно во время загрузки файла теста:

// testfile.mjs
import assert from 'assert';

// top-level await: Node >= v14.8.0 with ESM test file
const tests = await new Promise(resolve => {
  setTimeout(() => {
    resolve([
      {args: [1, 2], expected: 3},
      {args: [1, 2, 3], expected: 6},
      {args: [1, 2, 3, 4], expected: 10}
    ]);
  }, 5000);
});

// in suites ASYNCHRONOUS callbacks are NOT supported
describe('add()', function() {
  tests.forEach(({args, expected}) => {
    it(`correctly adds ${args.length} args`, function() {
      const res = args.reduce((sum, curr) => sum + curr, 0);
      assert.strictEqual(res, expected);
    });
  });
});

Продолжительность теста

Многие репортеры будут отображать продолжительность теста и помечать медленные тесты (по умолчанию: 75мс), как показано здесь с репортером SPEC:

test duration

Существует три уровня продолжительности теста (изображённые на следующей картинке):

  1. БЫСТРО: Тесты, выполняемые в течение половины порога «медленного», покажут продолжительность в зелёном цвете (если вообще).
  2. НОРМАЛЬНО: Тесты, выполняемые с превышением половины порога (но всё ещё в пределах), покажут продолжительность в жёлтом цвете.
  3. МЕДЛЕННО: Тесты, выполняемые с превышением порога, покажут продолжительность в красном цвете.

test duration range

Чтобы изменить то, что считается «медленным», вы можете использовать метод slow():

describe('something slow', function() {
  this.slow(300000); // five minutes

  it('should take long enough for me to go make a sandwich', function() {
    // ...
  });
});

Таймауты

Уровень набора

Таймауты уровня набора могут быть применены к целым тестовым «наборам» или отключены с помощью this.timeout(0). Это будет унаследовано всеми вложенными наборами и тестовыми случаями, которые не переопределяют значение.

describe('a suite of tests', function() {
  this.timeout(500);

  it('should take less than 500ms', function(done) {
    setTimeout(done, 300);
  });

  it('should take less than 500ms as well', function(done) {
    setTimeout(done, 250);
  });
});

Уровень теста

Также могут быть применены таймауты для каждого теста, или использование this.timeout(0) для отключения таймаутов в целом:

it('should take less than 500ms', function(done) {
  this.timeout(500);
  setTimeout(done, 300);
});

Уровень хука

Также могут быть применены таймауты уровня хука:

describe('a suite of tests', function() {
  beforeEach(function(done) {
    this.timeout(3000); // A very long environment setup.
    setTimeout(done, 2500);
  });
});

Опять же, используйте this.timeout(0) для отключения таймаута для хука.

В версии v3.0.0 или более поздней, параметр, переданный в this.timeout(), больший, чем максимальное значение задержки, приведёт к отключению таймаута. В версии v8.0.0 или более поздней, this.enableTimeouts() был удалён. Предупреждение: С асинхронными тестами, если вы отключите таймауты через this.timeout(0) и затем не вызовете done(), ваш тест завершится без уведомлений.

Различия

Mocha поддерживает свойства err.expected и err.actual любых брошенных AssertionError исключений из библиотеки утверждений. Mocha попытается отобразить разницу между ожидаемым и тем, что утверждение фактически увидело. Вот пример «строкового» различия с помощью --inline-diffs:

string diffs

Использование командной строки

mocha [spec..]

Run tests with Mocha

Commands
  mocha inspect [spec..]  Run tests with Mocha                         [default]
  mocha init <path>       create a client-side Mocha setup at <path>

Rules & Behavior
      --allow-uncaught       Allow uncaught errors to propagate        [boolean]
  -A, --async-only           Require all tests to use a callback (async) or
                             return a Promise                          [boolean]
  -b, --bail                 Abort ("bail") after first test failure   [boolean]
      --check-leaks          Check for global variable leaks           [boolean]
      --delay                Delay initial execution of root suite     [boolean]
      --dry-run              Report tests without executing them       [boolean]
      --exit                 Force Mocha to quit after tests complete  [boolean]
      --forbid-only          Fail if exclusive test(s) encountered     [boolean]
      --forbid-pending       Fail if pending test(s) encountered       [boolean]
      --global, --globals    List of allowed global variables            [array]
  -j, --jobs                 Number of concurrent jobs for --parallel; use 1 to
                             run in serial
                                   [number] [default: (number of CPU cores - 1)]
  -p, --parallel             Run tests in parallel                     [boolean]
      --retries              Retry failed tests this many times         [number]
  -s, --slow                 Specify "slow" test threshold (in milliseconds)
                                                          [string] [default: 75]
  -t, --timeout, --timeouts  Specify test timeout threshold (in milliseconds)
                                                        [string] [default: 2000]
  -u, --ui                   Specify user interface    [string] [default: "bdd"]

Reporting & Output
  -c, --color, --colors                     Force-enable color output  [boolean]
      --diff                                Show diff on failure
                                                       [boolean] [default: true]
      --full-trace                          Display full stack traces  [boolean]
  -G, --growl                               Enable Growl notifications [boolean]
      --inline-diffs                        Display actual/expected differences
                                            inline within each string  [boolean]
  -R, --reporter                            Specify reporter to use
                                                      [string] [default: "spec"]
  -O, --reporter-option,                    Reporter-specific options
  --reporter-options                        (<k=v,[k1=v1,..]>)           [array]

Configuration
      --config   Path to config file       [string] [default: (nearest rc file)]
      --package  Path to package.json for config                        [string]

File Handling
      --extension          File extension(s) to load
                                           [array] [default: ["js","cjs","mjs"]]
      --file               Specify file(s) to be loaded prior to root suite
                           execution                   [array] [default: (none)]
      --ignore, --exclude  Ignore file(s) or glob pattern(s)
                                                       [array] [default: (none)]
      --recursive          Look for tests in subdirectories            [boolean]
  -r, --require            Require module              [array] [default: (none)]
  -S, --sort               Sort test files                             [boolean]
  -w, --watch              Watch files in the current working directory for
                           changes                                     [boolean]
      --watch-files        List of paths or globs to watch               [array]
      --watch-ignore       List of paths or globs to exclude from watching
                                      [array] [default: ["node_modules",".git"]]

Test Filters
  -f, --fgrep   Only run tests containing this string                   [string]
  -g, --grep    Only run tests matching this string or regexp           [string]
  -i, --invert  Inverts --grep and --fgrep matches                     [boolean]

Positional Arguments
  spec  One or more files, directories, or globs to test
                                                     [array] [default: ["test"]]

Other Options
  -h, --help             Show usage information & exit                 [boolean]
  -V, --version          Show version number & exit                    [boolean]
      --list-interfaces  List built-in user interfaces & exit          [boolean]
      --list-reporters   List built-in reporters & exit                [boolean]

Mocha Resources
    Chat: https://gitter.im/mochajs/mocha
  GitHub: https://github.com/mochajs/mocha.git
    Docs: https://mochajs.org/

--allow-uncaught

По умолчанию Mocha попытается перехватить необработанные исключения, брошенные при запуске тестов, и отобразить их как сбои тестов. Используйте --allow-uncaught для отключения этого поведения и позволяйте необработанным исключениям распространяться. Обычно это приведёт к аварийному завершению процесса.

Этот флаг полезен при отладке особенно трудно отслеживаемых исключений.

--async-only, -A

Выполнить правило, что тесты должны быть написаны в стиле «асинхронного», что означает, что каждый тест предоставляет done обратный вызов или возвращает Promise. Несоответствующие тесты будут помечены как ошибки.

--bail, -b

Принуждает Mocha остановить выполнение тестов после первой обнаруженной ошибки теста. Соответствующие хуки «после каждого» и «после всех» выполняются для потенциальной очистки.

--bail не подразумевает --exit.

--check-leaks

Используйте эту опцию, чтобы Mocha проверял утечки глобальных переменных во время выполнения тестов. Укажите приемлемые глобальные переменные с помощью опции --global (например: --check-leaks --global jQuery --global MyLib).

--compilers

--compilers был удалён в v6.0.0. См. дальнейшее объяснение и обходные пути.

--dry-run

Новое в v9.0.0.

Отчёт о тестах без их выполнения, ни тестов, ни хуков.

--exit

Обновлено в v4.0.0.

Кратко: Если ваши тесты зависают после обновления до Mocha v4.0.0 или более поздней версии, используйте --exit для быстрого (хотя и не обязательно рекомендуемого) исправления.

До версии v4.0.0, по умолчанию, Mocha принуждал свой собственный процесс к завершению после завершения выполнения всех тестов. Это поведение позволяет возникать ряду потенциальных проблем; это указывает на тесты (или фикстуры, средства, код, подлежащий тестированию и т.д.), которые не очищают за собой должным образом. В конечном счёте, «грязные» тесты могут (но не всегда) привести к ложноположительным или ложноотрицательным результатам.

«Зависание» чаще всего проявляется, если сервер всё ещё прослушивает порт или сокет всё ещё открыт и т.д. Это также может быть что-то вроде неуправляемого setInterval() или даже некорректного Promise, который никогда не выполнил свою задачу.

Поведение по умолчанию в версии v4.0.0 (и более поздних) — --no-exit, в то время как ранее это было --exit.

Самый простой способ «исправить» проблему — передать --exit процессу Mocha. Это может занять много времени для отладки — потому что не всегда очевидно, где проблема — но это рекомендуется сделать.

Чтобы убедиться, что ваши тесты не оставляют беспорядка, вот несколько идей для начала:

  • См. руководство Node.js по отладке
  • Используйте новый async_hooks API (пример)
  • Попробуйте что-то вроде wtfnode
  • Используйте .only, пока вы не найдёте тест, из-за которого Mocha зависает

--forbid-only

Выполнить правило, что тесты не могут быть эксклюзивными (использование, например, describe.only() или it.only() запрещено).

--forbid-only приводит к сбою Mocha при обнаружении эксклюзивного («только») теста или набора тестов, и дальнейшее выполнение тестов будет прервано.

--forbid-pending

Выполнить правило, чтобы тесты не пропускались (использование, например, describe.skip(), it.skip() или this.skip() в любом месте запрещено).

--forbid-pending приводит к сбою Mocha при обнаружении пропущенного («ожидаемого») теста или набора тестов, и дальнейшее выполнение тестов будет прервано.

--global <variable-name>

Обновлено в версии 6.0.0; параметр --global и --globals теперь являются псевдонимами.

Определите имя глобальной переменной. Например, предположим, что ваше приложение намеренно экспонирует глобальную переменную с именем app и YUI, вы можете добавить --global app --global YUI.

--global принимает шаблоны. Вы можете использовать --global '*bar', и это будет соответствовать foobar, barbar и т. д. Вы также можете передать '*', чтобы игнорировать все глобальные переменные.

--global может принимать список, разделенный запятыми; --global app,YUI эквивалентно --global app --global YUI.

Используя этот параметр в сочетании с --check-leaks, вы можете указать белый список известных глобальных переменных, которые, как вы ожидаете, будут утечкой в глобальную область видимости.

--retries <n>

Повторно выполнить не пройденные тесты n раз.

Mocha по умолчанию не повторно выполняет не пройденные тесты.

--slow <ms>, -s <ms>

Укажите порог «медленного» теста в миллисекундах. Mocha использует его для выделения тестовых случаев, которые занимают слишком много времени. «Медленные» тесты не считаются ошибочными.

Примечание: тест, который выполняется половину времени «медленного» теста, будет выделен жёлтым цветом с репортером по умолчанию spec; тест, который выполняется в течение всего времени «медленного» теста, будет выделен красным цветом.

--timeout <ms>, -t <ms>

Обновление в v6.0.0: --no-timeout подразумевается при вызове Mocha с флагами инспекции. Он эквивалентен --timeout 0. --timeout 99999999 больше не нужен.

Указывает таймаут тестового случая, по умолчанию равный двум (2) секундам (2000 миллисекунд). Тесты, которые занимают больше этого времени, будут помечены как не пройденные.

Для переопределения вы можете передать таймаут в миллисекундах или значение с суффиксом s, например, --timeout 2s и --timeout 2000 эквивалентны.

Для отключения таймаутов используйте --no-timeout.

Примечание: синхронные (блокирующие) тесты также ограничены таймаутом, но они не завершатся до тех пор, пока код не перестанет блокироваться. Бесконечные циклы всё ещё будут бесконечными циклами!

--ui <name>, -u <name>

Параметр --ui позволяет указать интерфейс, используемый по умолчанию, bdd.

--color, -c, --colors

Обновлено в v6.0.0. --colors теперь является псевдонимом для --color.

«Принудительно» включить цветной вывод или, иначе, принудительно отключить его с помощью --no-color. По умолчанию Mocha использует модуль supports-color для принятия решения.

В некоторых случаях цветной вывод будет явно подавлен определёнными репортерами, выводом в машиночитаемом формате.

--diff

Если это возможно, отобразить различие между ожидаемым и фактическим значениями при возникновении ошибки проверки.

Этот флаг необычен тем, что по умолчанию равен true; используйте --no-diff для подавления собственного вывода diff Mocha.

Некоторые библиотеки проверки предоставят свои собственные разницы, в этом случае разницы Mocha не будут использоваться независимо от значения по умолчанию.

Собственный вывод diff Mocha не соответствует известным стандартам и предназначен для удобного чтения человеком.

--full-trace

Включить полные трассировки стека. По умолчанию Mocha пытается преобразовать трассировки стека в менее шумный (хотя и всё ещё полезный) вывод.

Этот флаг полезен при отладке предполагаемой проблемы в Mocha или самом Node.js.

--growl, -G

Включить Growl (или уведомления на уровне ОС, где это возможно).

Требуется дополнительное программное обеспечение; для получения дополнительной информации см. документацию модуля growl.

--inline-diffs

Включить «встроенные» различия, альтернативный вывод для сравнения строк.

Полезно при работе с большими строками.

Ничего не делает, если библиотека проверки предоставляет свой собственный вывод сравнения.

--reporter <name>, -R <name>

Укажите репортер, который будет использоваться, по умолчанию это spec.

Позволяет использовать репортеры сторонних разработчиков. Например, mocha-lcov-reporter можно использовать с --reporter mocha-lcov-reporter после его установки.

--reporter-option <option>, -O <option>, --reporter-options <option>

Обновлено в v6.0.0. Может быть указано несколько раз. --reporter-options теперь является псевдонимом для --reporter-option.

Предоставьте параметры, специфичные для репортера в формате <key>=<value>, например, --reporter tap --reporter-option tapVersion=13.

Не все репортеры принимают параметры.

Может быть указано как список, разделенный запятыми.

--config <path>

Новое в v6.0.0.

Укажите явный путь к файлу настройки.

По умолчанию Mocha будет искать файл конфигурации, если --config не указан; используйте --no-config, чтобы подавить это поведение.

--opts <path>

Удалено в v8.0.0. Пожалуйста, используйте файл конфигурации вместо этого.

--package <path>

Новое в v6.0.0.

Укажите явный путь к package.json файлу (по-видимому содержащему конфигурацию в свойстве mocha).

По умолчанию Mocha ищет package.json в текущей рабочей директории или ближайшем предке и будет использовать первый найденный файл (независимо от того, содержит ли он свойство mocha); чтобы подавить поиск package.json, используйте --no-package.

--extension <ext>

Файлы с этим расширением будут считаться тестовыми файлами. По умолчанию это js.

Указание --extension удалит .js как расширение тестовых файлов; используйте --extension js, чтобы добавить его обратно. Например, для загрузки тестовых файлов .mjs и .js необходимо указать --extension mjs --extension js.

Параметр может быть указан несколько раз. Параметр принимает список, разделенный запятыми: --extension a,b эквивалентно --extension a --extension b.

Новое в v8.2.0.

--extension теперь поддерживает многокомпонентные расширения (например, spec.js), точки перед расширением (.js) и их комбинации (.spec.js);

--file <file|directory|glob>

ПРЕДУПРЕЖДЕНИЕ: --file несовместим с параллельным режимом.

Явно включить тестовый файл для загрузки перед другими тестовыми файлами. Допускается несколько применений --file, и они будут загружаться в заданном порядке.

Полезно, если вы хотите объявить, например, хуки, которые будут выполняться перед каждым тестом во всех других тестовых файлах.

Файлы, указанные таким образом, не зависят от --sort или --recursive.

Файлы, указанные таким образом, должны содержать один или несколько наборов тестов или хуков. Если это не так, рассмотрите --require.

--ignore <file|directory|glob>, --exclude <file|directory|glob>,

Явно проигнорировать (исключить) один или несколько тестовых файлов, каталогов или шаблонов (например, some/**/files*), которые в противном случае были бы загружены.

Файлы, указанные с помощью --file, не затрагиваются этим параметром.

Может быть указано несколько раз.

--recursive

При поиске тестовых файлов рекурсивно входить в подкаталоги.

См. --extension для определения файлов, которые считаются тестовыми файлами.

--require <module>, -r <module>

Загрузить модуль перед загрузкой пользовательского интерфейса или тестовых файлов. Это полезно для:

  • Тестовых средств
  • Библиотек проверки, которые дополняют встроенные функции или глобальную область видимости (таких как should.js)
  • Компиляторы, такие как Babel через @babel/register или TypeScript через ts-node (используя --require ts-node/register). См. примеры работы с Babel в Babel или TypeScript в TypeScript.

Модули, требуемые таким образом, ожидают синхронной работы; Mocha не будет ждать завершения асинхронных задач в требуемом модуле.

Вы не можете использовать --require для установки хуков. Если вы хотите установить хуки для выполнения, например, перед каждым тестом, используйте Root Hook Plugin.

Начиная с v8.0.0, Mocha поддерживает --require для NodeJS native ESM. Отдельного флага --import нет.

--sort, -S

ПРЕДУПРЕЖДЕНИЕ: --sort несовместим с параллельным режимом.

Сортировать тестовые файлы (по абсолютному пути) с помощью Array.prototype.sort.

--watch, -w

Повторно запускать тесты при изменениях файлов.

Параметры --watch-files и --watch-ignore могут использоваться для управления файлами, которые отслеживаются на изменения.

Тесты можно повторно запустить вручную, набрав ⓡ ⓢ ⏎ (такой же ярлык, как и nodemon).

--watch-files <file|directory|glob>

Новое в v7.0.0

Список путей или шаблонов для отслеживания, когда --watch задан. Если файл, соответствующий заданному шаблону, изменяется или добавляется или удаляется, mocha перезапустит все тесты.

Если путь является каталогом, будут отслеживаться все файлы и подкаталоги.

По умолчанию отслеживаются все файлы в текущей директории с одним из расширений, предоставленных --extension, и не содержащиеся в папках node_modules или .git.

Опцию можно указывать несколько раз. Опция принимает список, разделенный запятыми: --watch-files a,b эквивалентно --watch-files a --watch-files b

--watch-ignore <file|directory|glob>

Новое в версии 7.0.0

Список путей или шаблонов, которые нужно исключить из наблюдения. По умолчанию установлено значение node_modules и .git.

Для исключения всех файлов в каталоге предпочтительнее использовать foo/bar вместо foo/bar/**/*. Последнее всё ещё будет отслеживать каталог foo/bar, но игнорировать все изменения содержимого этого каталога.

Опцию можно указывать несколько раз. Опция принимает список, разделенный запятыми: --watch-ignore a,b эквивалентно --watch-ignore a --watch-ignore b

--fgrep <string>, -f <string>

ИЗМЕНЕНИЕ ВЕРСИИ в v6.0.0; теперь взаимоисключающее с --grep.

Принудительно запустить Mocha только для тестов, заголовки которых содержат указанный string.

Взаимоисключающее с --grep.

--grep <regexp>, -g <regexp>

ИЗМЕНЕНИЕ ВЕРСИИ в v6.0.0; теперь взаимоисключающее с --fgrep.

Принудительно запустить Mocha только для тестов, соответствующих заданному regexp, которое интерпретируется как RegExp.

Например, если у вас есть тесты, связанные с «api», а также с «app», как показано в приведенном ниже фрагменте; можно использовать --grep api или --grep app, чтобы запустить один из них. То же самое относится к любой другой части заголовка набора или тестового случая, --grep users также будет допустимым, или даже --grep GET.

describe('api', function() {
  describe('GET /api/users', function() {
    it('respond with an array of users', function() {
      // ...
    });
  });
});

describe('app', function() {
  describe('GET /users', function() {
    it('respond with an array of users', function() {
      // ...
    });
  });
});

Взаимоисключающее с --fgrep.

--invert

Использовать обратное соответствие, указанное в --grep или fgrep.

Требуется либо --grep, либо --fgrep (но не оба).

--inspect, --inspect-brk, inspect

ИЗМЕНЕНИЕ ВЕРСИИ в v7.0.0; --debug / --debug-brk удалены, а debug устарело.

Включает инспектор Node.js.

Используйте --inspect / --inspect-brk для запуска инспектора V8 для использования с Chrome Dev Tools.

Используйте inspect для запуска внутреннего отладчика Node.js.

Все эти опции взаимоисключающие.

Подразумевает --no-timeout.

--parallel, -p

Новое в версии v.8.0.0.

Используйте флаг --parallel для запуска тестов в пуле рабочих потоков.

Каждый тестовый файл будет помещен в очередь и выполнен, как только освободится рабочий поток.

ПРИМЕЧАНИЕ: --parallel имеет определенные последствия для поведения Mocha, о которых вы должны знать. Узнайте больше о запуске тестов параллельно.

--jobs <count>, -j <count>

Новое в версии v.8.0.0.

Используйте --jobs <count> для указания максимального числа процессов в пуле рабочих потоков.

Значение по умолчанию — количество ядер процессора минус 1.

Подсказка: используйте --jobs 0 или --jobs 1 для временного отключения --parallel.

Не оказывает никакого влияния, если не используется с --parallel.

О типах опций

Обновлено в v6.0.0.

Каждый флаг с аннотацией типа [boolean] в выводе Mocha --help можно отменить, добавив --no- перед именем флага. Например, --no-color отключит вывод цвета Mocha, который по умолчанию включен.

Если не указано иное, все флаги булевого типа по умолчанию установлены в false.

Об флагах node

Исполняемый файл mocha поддерживает все применимые флаги, которые поддерживает исполняемый файл node.

Эти флаги различаются в зависимости от версии Node.js.

Флаги node можно определить в конфигурации Mocha конфигурации.

--enable-source-maps

Новое в Node.js v12.12.0

Если флаг --enable-source-maps передаётся в mocha, будут собраны карты исходного кода и использованы для предоставления точных трассировок стека для транскрипции исходного кода:

Error: cool
    at Object.<anonymous> (/Users/fake-user/bigco/nodejs-tasks/build/src/index.js:27:7)
        -> /Users/fake-user/bigco/nodejs-tasks/src/index.ts:24:7

Об флагах V8

Добавьте --v8- к любому флагу, указанному в выводе node --v8-options (исключая сам --v8-options), чтобы использовать его.

Флаги V8 можно определить в конфигурации Mocha.

Параллельные тесты

Новое в версии v.8.0.0.

В зависимости от количества и характера ваших тестов, вы можете получить значительное улучшение производительности при запуске тестов параллельно (используя флаг --parallel).

Параллельные тесты должны работать «из коробки» для многих случаев использования. Однако вы должны быть осведомлены о некоторых важных последствиях поведения.

Примечание: Авторы сторонних библиотек, созданных на основе Mocha, должны прочитать это!

Ограничения репортеров

Из-за особенностей следующих репортеров они не могут работать при запуске тестов параллельно:

  • markdown
  • progress
  • json-stream

Эти репортеры ожидают, что Mocha узнает количество тестов, которые он планирует запустить, перед выполнением. Эта информация недоступна в режиме параллельного выполнения, так как тестовые файлы загружаются только тогда, когда они должны быть запущены.

В последовательном режиме результаты тестов «потоком» появляются по мере их выполнения. В параллельном режиме вывод репортера буферизуется; отчёт будет происходить после завершения каждого файла. На практике вывод репортера будет появляться «блоками» (но в остальном будет идентичен). Если тестовый файл работает особенно медленно, может быть значительная пауза во время его выполнения.

Запрещены эксклюзивные тесты

Вы не можете использовать it.only, describe.only, this.only() и т. д. в режиме параллельного выполнения. Это по той же причине, что и несовместимые репортеры, указанные выше: в режиме параллельного выполнения Mocha не загружает все файлы и наборы в память перед запуском тестов.

Предлагаемые решения:

  1. Используйте --grep или --fgrep вместо этого; это не особенно эффективно, но оно сработает.
  2. Не используйте режим параллельного выполнения. Вероятно, вы не будете запускать очень много эксклюзивных тестов, поэтому вы не получите большой выгоды от режима параллельного выполнения.

СОВЕТ: Если режим параллельного выполнения определён в вашем конфигурационном файле, вы можете временно отключить его в командной строке, используя либо флаг --no-parallel, либо уменьшив счётчик задач, например, --jobs=0.

Порядок файлов не определён

В режиме параллельного выполнения Mocha не гарантирует порядок запуска тестовых файлов, а также то, какой рабочий процесс их выполнит.

Из-за этого следующие опции, зависящие от порядка, не могут быть использованы в режиме параллельного выполнения:

  • --file
  • --sort
  • --delay

Изменчивость длительности тестов

Запуск тестов в параллельном режиме естественным образом использует больше системных ресурсов. Операционная система может тратить дополнительное время на планирование и завершение некоторых операций в зависимости от нагрузки на систему. По этой причине время ожидания отдельных тестов может потребоваться увеличить либо глобально, либо иначе.

«Отказ» — «лучшие усилия»

При использовании --bail (или this.bail()) для выхода после первой ошибки, скорее всего, другие тесты будут выполняться одновременно. Mocha должен закрыть свои рабочие процессы перед выходом.

Аналогично, подпроцессы могут вызывать необработанные исключения. При использовании --allow-uncaught Mocha «поднимет» это исключение в основной процесс, но всё равно должен закрыть свои процессы.

В любом случае Mocha прервёт запуск теста «очень скоро».

Корневые хуки не являются глобальными

ПРИМЕЧАНИЕ: Это относится только к запуску в параллельном режиме.

Корневой хук — это хук в тестовом файле, который не определён в рамках набора. Пример использования интерфейса bdd:

// test/setup.js

// root hook to run before every test (even in other files)
beforeEach(function() {
  doMySetup();
});

// root hook to run after every test (even in other files)
afterEach(function() {
  doMyTeardown();
});

При запуске (в стандартном «последовательном» режиме) с помощью этой команды:

mocha --file "./test/setup.js" "./test/**/*.spec.js"

setup.js будет выполнен сначала и установит два хука, показанные выше, для каждого теста, найденного в ./test/**/*.spec.js.

Приведенный выше пример не работает в параллельном режиме.

Когда Mocha запускается в параллельном режиме, тестовые файлы не используют один и тот же процесс, ни один из них не использует один и тот же экземпляр Mocha. Следовательно, гипотетический корневой хук, определённый в тестовом файле A, не будет присутствовать в тестовом файле B.

Вот несколько предложенных решений:

  1. require('./setup.js') или import './setup.js' в начале каждого тестового файла. Лучше избегать этого для тех, кто не хочет лишнего кода.
  2. Рекомендовано: Определите корневые хуки в «требуемом» файле, используя новую (также начиная с версии 8.0.0) систему плагинов корневых хуков.

Если вам нужно выполнить какой-то код один раз и только один раз, используйте глобальную фикстуру вместо этого.

Поддержка браузеров отсутствует

Режим параллельного выполнения доступен только в Node.js на данный момент.

Ограниченный API репортеров для сторонних репортеров

Сторонние репортеры могут столкнуться с проблемами при попытке получить доступ к несуществующим свойствам в объектах Test, Suite и Hook. Если сторонний репортер не работает в режиме параллельного выполнения (но работает в последовательном режиме), пожалуйста, создайте вопрос.

Устранение неполадок режима параллельного выполнения

Если вы обнаружите, что ваши тесты не работают должным образом при запуске с --parallel, либо смиритесь и двигайтесь дальше, либо воспользуйтесь этим полезным списком проверок, чтобы заставить всё работать:

END_OF_DOCUMENT_MARKER
  • ✅ Убедитесь, что вы используете поддерживаемый репортер.
  • ✅ Убедитесь, что вы не используете другие неподдерживаемые флаги.
  • ✅ Дважды проверьте свой конфигурационный файл; параметры, заданные в конфигурационных файлах, будут объединены с любыми параметрами командной строки.
  • ✅ Поищите корневые хуки (они выглядят как этот) в своих тестах. Переместите их во плагин корневого хука.
  • ✅ Используемые вами библиотеки утверждений, моков или другие библиотеки тестов используют корневые хуки? Возможно, их необходимо переработать для совместимости с параллельным режимом.
  • ✅ Если тесты неожиданно выходят за пределы времени ожидания, возможно, вам нужно увеличить значение по умолчанию для времени ожидания теста (через --timeout)
  • ✅ Убедитесь, что ваши тесты не зависят от выполнения в определённом порядке.
  • ✅ Убедитесь, что ваши тесты очищают за собой; удаляйте временные файлы, дескрипторы, сокеты и т. д. Не пытайтесь совместно использовать состояние или ресурсы между файлами тестов.

Ограничения параллельного тестирования

Некоторые типы тестов не подходят для параллельного выполнения. Например, тесты, крайне чувствительные к времени, или тесты, которые выполняют запросы ввода-вывода к ограниченному пулу ресурсов (таким как открытие портов или автоматизация окон браузера, обращение к тестовой базе данных или удалённому серверу и т. д.).

Услуги CI облачных сервисов с бесплатным тарифом могут не предоставлять подходящий контейнер или виртуальную машину с несколькими ядрами для своих агентов сборки. Что касается ожидаемого прироста производительности в CI: ваши результаты могут отличаться. Может помочь использование условного оператора в .mocharc.js для проверки process.env.CI и соответствующей корректировки количества задач.

Маловероятно (но не исключено), что вы увидите прирост производительности от количества задач большего, чем количество доступных ядер процессора. Тем не менее, экспериментируйте с количеством задач — универсального решения нет, и уникальные характеристики ваших тестов определят оптимальное количество задач; может быть даже, что меньше — быстрее!

Плагины корневых хуков

Новое в версии v8.0.0.

В некоторых случаях вам может потребоваться хук перед (или после) каждым тестом в каждом файле. Эти хуки называются корневыми хуками. До версии v8.0.0 это достигалось с помощью --file в сочетании с корневыми хуками (см. пример выше). Это всё ещё работает в версии v8.0.0, но не при запуске тестов в параллельном режиме! По этой причине запуск корневых хуков таким способом крайне не рекомендуется и в будущем может быть устаревшим.

Плагин корневого хука — это файл JavaScript, загружаемый через --require, который «регистрирует» один или несколько корневых хуков для использования во всех файлах тестов.

Определение плагина корневого хука

Файл плагина корневого хука — это скрипт, который экспортирует (через module.exports) свойство mochaHooks. Он загружается через --require <file>.

Вот простой пример, определяющий корневой хук, написанный с использованием синтаксиса CJS и ESM.

# С CommonJS

// test/hooks.js

exports.mochaHooks = {
  beforeEach(done) {
    // do something before every test
    done();
  }
};

# С ES Модулями

В этих примерах используется расширение .mjs.

Подсказка: Если у вас возникают проблемы с работой ES модулей, обратитесь к документации Node.js.

// test/hooks.mjs

export const mochaHooks = {
  beforeEach(done) {
    // do something before every test
    done();
  }
};

Примечание: дальнейшие примеры будут использовать синтаксис ESM.

Доступные корневые хуки

Корневые хуки работают с любым интерфейсом, но имена свойств не меняются. Другими словами, если вы используете интерфейс tdd, то suiteSetup соответствует beforeAll, а setup соответствует beforeEach.

Доступные корневые хуки и их поведение:

  • beforeAll:
    • В режиме последовательного выполнения (по умолчанию в Mocha), перед началом всех тестов, один раз
    • В режиме параллельного выполнения, выполняется перед началом всех тестов, для каждого файла
  • beforeEach:
    • В обоих режимах, выполняется перед каждым тестом
  • afterAll:
    • В режиме последовательного выполнения, выполняется после окончания всех тестов, один раз
    • В режиме параллельного выполнения, выполняется после окончания всех тестов, для каждого файла
  • afterEach:
    • В обоих режимах, выполняется после каждого теста

Подсказка: Если вам нужно гарантировать, что код выполняется один раз и только один раз в любом режиме, используйте глобальные фикстуры.

Как и в случае с другими хуками, this ссылается на текущий объект контекста:

// test/hooks.mjs

export const mochaHooks = {
  beforeAll() {
    // skip all tests for bob
    if (require('os').userInfo().username === 'bob') {
      return this.skip();
    }
  }
};

Несколько корневых хуков в одном плагине

Для целей организации можно определить несколько корневых хуков в одном плагине. Например:

// test/hooks.mjs

export const mochaHooks = {
  beforeEach: [
    function(done) {
      // do something before every test,
      // then run the next hook in this array
    },
    async function() {
      // async or Promise-returning functions allowed
    }
  ]
};

Плагины корневых хуков могут экспортировать функцию

Если вам нужно выполнить некоторую логику, например, выбрать корневой хук условно на основе среды, то mochaHooks может быть функцией, которая возвращает ожидаемый объект.

// test/hooks.mjs

export const mochaHooks = () => {
  if (process.env.CI) {
    // root hooks object
    return {
      beforeEach: [
        function() {
          // CI-specific beforeEach
        },
        function() {
          // some other CI-specific beforeEach
        }
      ]
    };
  }
  // root hooks object
  return {
    beforeEach() {
      // regular beforeEach
    }
  };
};

Если вам нужно выполнить асинхронную операцию, то mochaHooks может возвращать Promise:

// test/hooks.mjs

export const mochaHooks = async () => {
  const result = await checkSomething();
  // only use a root hook if `result` is truthy
  if (result) {
    // root hooks object
    return {
      beforeEach() {
        // something
      }
    };
  }
};

Несколько плагинов корневых хуков

Несколько плагинов корневых хуков можно зарегистрировать, используя --require несколько раз. Например, чтобы зарегистрировать корневые хуки в hooks-a.js и hooks-b.js, используйте --require hooks-a.js --require hooks-b.js. Они будут зарегистрированы (и выполнены) в порядке.

Миграция тестов для использования плагинов корневых хуков

Чтобы перенести ваши тесты, использующие корневые хуки, в плагин корневого хука:

  1. Найдите ваши корневые хуки (хуки, определённые вне набора — обычно describe() обратный вызов).
  2. Создайте новый файл, например, test/hooks.js.
  3. Переместите ваши корневые хуки в test/hooks.js.
  4. В test/hooks.js сделайте ваши хуки членом экспортируемого свойства mochaHooks.
  5. Используйте --require test/hooks.js (ещё лучше: используйте конфигурационный файл с {"require": "test/hooks.js"}) при запуске тестов.

Например, предположим, что следующий файл, test/test.spec.js, содержит корневые хуки:

// test/test.spec.js

beforeEach(function() {
  // global setup for all tests
});

after(function() {
  // one-time final cleanup
});

describe('my test suite', function() {
  it('should have run my global setup', function() {
    // make assertion
  });
});

Ваш test/hooks.js (в этом примере, CJS модуль) должен содержать:

// test/hooks.js

exports.mochaHooks = {
  beforeEach: function() {
    // global setup for all tests
  },
  afterAll: function() {
    // one-time final cleanup
  }
};

ВАЖНО! after превращается в afterAll, а before превращается в beforeAll.

Ваш исходный test/test.spec.js теперь должен содержать:

// test/test.spec.js

describe('my test suite', function() {
  it('should have run my global setup', function() {
    // make assertion
  });
});

Запуск mocha --require test/hooks.js test/test.spec.js будет выполняться как прежде (и теперь готов к использованию с --parallel).

Миграция библиотеки для использования плагинов корневых хуков

Если вы — разработчик библиотеки, и ваша библиотека использует корневые хуки, вы можете выполнить миграцию, переработав точку входа:

  • Ваша библиотека всегда должна экспортировать mochaHooks объект.
  • Чтобы сохранить обратную совместимость, запустите ваши корневые хуки только в том случае, если существует global.beforeEach (или другой соответствующий хук).
  • Инструктируйте пользователей о том, что --require <your-package> при запуске mocha.

Глобальные фикстуры

Новое в версии v8.2.0

На первый взгляд, глобальные фикстуры похожи на корневые хуки. Однако, в отличие от корневых хуков, глобальные фикстуры:

  1. Гарантированно выполняются один раз и только один раз
  2. Ведут себя одинаково в режиме параллельного выполнения, режиме отслеживания изменений и режиме последовательного выполнения
  3. Не делят контекст с тестами, наборами или другими хуками

Существует два типа глобальных фикстур: фикстуры глобальной настройки и фикстуры глобальной завершающей обработки.

Фикстуры глобальной настройки

Чтобы создать фикстуру глобальной настройки, экспортируйте mochaGlobalSetup из скрипта, например:

// fixtures.cjs

// can be async or not
exports.mochaGlobalSetup = async function() {
  this.server = await startSomeServer({port: process.env.TEST_PORT});
  console.log(`server running on port ${this.server.port}`);
};

…или ES модуль:

// fixtures.mjs

// can be async or not
export async function mochaGlobalSetup() {
  this.server = await startSomeServer({port: process.env.TEST_PORT});
  console.log(`server running on port ${this.server.port}`);
}

Для использования загрузите этот файл при запуске Mocha через mocha --require fixtures.cjs (или как вы назвали файл).

Помните: вы можете определять «требования» в файле конфигурации.

Теперь, перед тем как Mocha загрузит и запустит ваши тесты, он выполнит вышеуказанную фикстуру глобальной настройки, запустив сервер для тестирования. Однако этот сервер не будет остановлен по завершении Mocha! Для этого используйте фикстуру глобальной завершающей обработки.

Фикстуры глобальной завершающей обработки

Так же, как и фикстура глобальной настройки, фикстура глобальной завершающей обработки может быть создана путём экспорта из «требуемого» скрипта (мы можем разместить оба типа фикстур в одном файле):

// fixtures.cjs, cont'd

// can be async or not
exports.mochaGlobalTeardown = async function() {
  await this.server.stop();
  console.log('server stopped!');
};

…или ES модуль:

// fixtures.mjs, cont'd

// can be async or not
export async function mochaGlobalTeardown() {
  await this.server.stop();
  console.log('server stopped!');
}

Обратите внимание, что мы использовали this в примерах фикстур. Фикстуры глобальной настройки и глобальной завершающей обработки делят контекст, что означает, что мы можем добавлять свойства к объекту контекста (this) в фикстуре настройки и ссылаться на них позже в фикстуре завершающей обработки. Это более полезно, когда фикстуры находятся в отдельных файлах, так как вы можете просто использовать правила области видимости переменных JavaScript (пример ниже).

Как было объяснено выше — и ниже — файлы тестов не имеют доступа к этому объекту контекста.

Когда использовать глобальные фикстуры

Глобальные фикстуры хорошо подходят для запуска сервера, открытия сокета или создания других ресурсов, к которым ваши тесты будут неоднократно обращаться через ввод-вывод.

Когда не использовать глобальные фикстуры

Если вам нужно получить доступ к значению в памяти (например, дескриптору файла или подключению к базе данных), не используйте глобальные фикстуры для этого, потому что ваши тесты не смогут получить доступ к значению.

Вы могли бы проявить сообразительность и попытаться обойти это ограничение, присвоив что-то объекту global, но это не сработает в параллельном режиме. Наверное, лучше придерживаться правил!

Вместо этого используйте глобальную фикстуру для запуска базы данных и используйте плагины корневых хуков или обычные хуки для создания подключения.

Вот пример использования глобальных фикстур и хуков «перед всеми» для выполнения задачи. Обратите внимание, что мы нигде в наших тестах не ссылаемся на объект server!

Сначала используйте глобальную фикстуру для запуска и остановки тестового сервера:

// fixtures.mjs

let server;

export const mochaGlobalSetup = async () => {
  server = await startSomeServer({port: process.env.TEST_PORT});
  console.log(`server running on port ${server.port}`);
};

export const mochaGlobalTeardown = async () => {
  await server.stop();
  console.log('server stopped!');
};

Затем подключитесь к серверу в своих тестах:

// test.spec.mjs

import {connect} from 'my-server-connector-thingy';

describe('my API', function() {
  let connection;

  before(async function() {
    connection = await connect({port: process.env.TEST_PORT});
  });

  it('should be a nice API', function() {
    // assertions here
  });

  after(async function() {
    return connection.close();
  });
});

Наконец, используйте эту команду, чтобы объединить всё вместе: mocha --require fixtures.mjs test.spec.mjs.

Мастер выбора фикстур для деревьев решений тестов

Эта блок-схема поможет вам решить, какие из хуков, плагинов корневых хуков или глобальных фикстур следует использовать.

Мои тестытребуют настройки!Настройка ОБЯЗАТЕЛЬНО должна выполнятьсяодин раз и только один разНастройка ОБЯЗАТЕЛЬНО должнаобмениваться состоянием с тестамиДАИспользуйте Корневые Хуки иИзбегайте Параллельного РежимаИспользуйте Глобальные ФикстурыНастройка должна влиятьна тесты во ВСЕХ файлах?Используйте Корневые ХукиИспользуйте Простые ХукиДАНЕТНЕТДАНЕТ

Интерфейсы

Система «интерфейсов» Mocha позволяет разработчикам выбирать свой стиль DSL. Mocha имеет интерфейсы в стиле BDD, TDD, Exports, QUnit и Require.

BDD

Интерфейс BDD предоставляет describe(), context(), it(), specify(), before(), after(), beforeEach() и afterEach().

context() — это всего лишь псевдоним для describe() и ведет себя аналогично; он предоставляет способ сохранения тестов более простыми в чтении и структурированными. Аналогично, specify() является псевдонимом для it().

Все предыдущие примеры были написаны с использованием интерфейса BDD.

describe('Array', function() {
  before(function() {
    // ...
  });

  describe('#indexOf()', function() {
    context('when not present', function() {
      it('should not throw an error', function() {
        (function() {
          [1, 2, 3].indexOf(4);
        }.should.not.throw());
      });
      it('should return -1', function() {
        [1, 2, 3].indexOf(4).should.equal(-1);
      });
    });
    context('when present', function() {
      it('should return the index where the element first appears in the array', function() {
        [1, 2, 3].indexOf(3).should.equal(2);
      });
    });
  });
});

TDD

Интерфейс TDD предоставляет suite(), test(), suiteSetup(), suiteTeardown(), setup() и teardown():

suite('Array', function() {
  setup(function() {
    // ...
  });

  suite('#indexOf()', function() {
    test('should return -1 when not present', function() {
      assert.equal(-1, [1, 2, 3].indexOf(4));
    });
  });
});

Exports

Интерфейс Exports очень похож на предшественника Mocha — expresso. Ключи before, after, beforeEach и afterEach имеют специальное значение, значения объектов являются наборами, а значения функций — тестовыми случаями:

module.exports = {
  before: function() {
    // ...
  },

  Array: {
    '#indexOf()': {
      'should return -1 when not present': function() {
        [1, 2, 3].indexOf(4).should.equal(-1);
      }
    }
  }
};

QUnit

Интерфейс, вдохновленный QUnit, имеет «плоскую» структуру, где заголовок набора тестов определяется *до* тестовых случаев. Как и TDD, он использует suite() и test(), но, подобно BDD, также содержит before(), after(), beforeEach() и afterEach().

function ok(expr, msg) {
  if (!expr) throw new Error(msg);
}

suite('Array');

test('#length', function() {
  var arr = [1, 2, 3];
  ok(arr.length == 3);
});

test('#indexOf()', function() {
  var arr = [1, 2, 3];
  ok(arr.indexOf(1) == 0);
  ok(arr.indexOf(2) == 1);
  ok(arr.indexOf(3) == 2);
});

suite('String');

test('#length', function() {
  ok('foo'.length == 3);
});

Require

Интерфейс require позволяет вам напрямую подключать слова describe и их аналоги используя require и называть их как вам угодно. Этот интерфейс также полезен, если вы хотите избежать глобальных переменных в своих тестах.

Примечание: интерфейс require не может быть запущен с помощью исполняемого файла node и должен быть запущен с помощью mocha.

var testCase = require('mocha').describe;
var pre = require('mocha').before;
var assertions = require('mocha').it;
var assert = require('chai').assert;

testCase('Array', function() {
  pre(function() {
    // ...
  });

  testCase('#indexOf()', function() {
    assertions('should return -1 when not present', function() {
      assert.equal([1, 2, 3].indexOf(4), -1);
    });
  });
});

Отчеты

Отчеты Mocha адаптируются к окну терминала и всегда отключают цвет ANSI-escape, когда потоки stdio не связаны с TTY.

Spec

Псевдоним: Spec, spec

Это отчет по умолчанию. Отчет Spec выводит иерархическое представление, вложенное так же, как и тестовые случаи.

spec reporter spec reporter with failure

Матрица точек

Псевдоним: Dot, dot

Отчет Матрица точек представляет собой серию символов, которые отображают тестовые случаи. Ошибки выделяются красными восклицательными знаками (!), ожидающие тесты — синей запятой (,), а медленные тесты — жёлтым цветом. Хорошо подходит, если вы предпочитаете минимальный вывод.

dot matrix reporter

Nyan

Псевдоним: Nyan, nyan

Отчет Nyan — как вы могли и предположить:

js nyan cat reporter

TAP

Псевдоним: TAP, tap

Отчет TAP генерирует строки для потребителя Test-Anything-Protocol.

test anything protocol

Полоса приземления

Псевдоним: Landing, landing

Отчет Полоса приземления — это забавный отчет о тестах, имитирующий посадку самолета 😃 unicode ftw

landing strip plane reporter landing strip with failure

Список

Псевдоним: List, list

Отчет Список выводит простой список спецификаций, как тесты проходят или терпят неудачу, выводит детали ошибок внизу вывода.

list reporter

Прогресс

Псевдоним: Progress, progress

Отчет Прогресс реализует простую полосу прогресса:

progress bar

JSON

Псевдоним: JSON, json

Отчет JSON выводит один большой JSON-объект по завершении тестов (с ошибками или без).

json reporter

Потоковый JSON

Псевдоним: JSONStream, json-stream

Отчет Потоковый JSON выводит события JSON, разделенные символом новой строки, по мере их возникновения, начиная с события «начало», а затем — успешных или неудачных тестов и, наконец, события «конец».

json stream reporter

Min

Псевдоним: Min, min

Отчет Min отображает только сводку, но при этом выводит ошибки при сбоях. Этот отчет отлично подходит для использования с --watch, так как он очищает терминал, чтобы сохранить сводку тестов в верхней части.

min reporter

Документация

Псевдоним: Doc, doc

Отчет Doc выводит иерархическое представление HTML вашего набора тестов. Оберните его заголовком, подвалом и некоторым стилем, и у вас будет отличная документация!

doc reporter

Например, предположим, что у вас есть следующий JavaScript:

describe('Array', function() {
  describe('#indexOf()', function() {
    it('should return -1 when the value is not present', function() {
      [1, 2, 3].indexOf(5).should.equal(-1);
      [1, 2, 3].indexOf(0).should.equal(-1);
    });
  });
});

Команда mocha --reporter doc array даст:

<section class="suite">
  <h1>Array</h1>
  <dl>
    <section class="suite">
      <h1>#indexOf()</h1>
      <dl>
        <dt>should return -1 when the value is not present</dt>
        <dd>
          <pre><code>[1,2,3].indexOf(5).should.equal(-1);
[1,2,3].indexOf(0).should.equal(-1);</code></pre>
        </dd>
      </dl>
    </section>
  </dl>
</section>

Документация библиотеки запросов SuperAgent документация тестов была сгенерирована с помощью отчета о документации Mocha с помощью этой команды Bash:

$ mocha --reporter=doc | cat docs/head.html - docs/tail.html > docs/test.html

Обратитесь к Makefile SuperAgent для справки.

Markdown

Псевдоним: Markdown, markdown

Отчет Markdown генерирует markdown TOC и тело для вашего набора тестов. Это отлично подходит, если вы хотите использовать тесты в качестве документации на странице вики Github или в файле markdown в репозитории, который Github может отобразить. Например, вот вывод тестов Connect вывод тестов.

XUnit

Псевдоним: XUnit, xunit

Также доступен отчет XUnit. Он выводит документ XML, совместимый с XUnit, который часто используется в серверах CI.

По умолчанию он будет выведен в консоль. Чтобы записать его непосредственно в файл, используйте --reporter-option output=filename.xml.

Чтобы указать заголовок отчета, используйте --reporter-option suiteName="Custom name".

Отчеты сторонних разработчиков

Mocha позволяет определять пользовательские отчеты. Для получения дополнительной информации см. вики.

Примеры:

  • отчет TeamCity
  • наш пример работы

HTML-отчет

Псевдоним: HTML, html

HTML-отчет не предназначен для использования в командной строке.

Поддержка Node.JS native ESM

Новое в версии 7.1.0

Mocha поддерживает написание ваших тестов как модулей ES, а не только с использованием CommonJS. Например:

// test.mjs
import {add} from './add.mjs';
import assert from 'assert';

it('should add to numbers from an es module', () => {
  assert.equal(add(3, 5), 8);
});

Чтобы включить это, вам ничего специального делать не нужно. Напишите свой тестовый файл в качестве модуля ES. В Node.js это означает либо окончание файла расширением .mjs, либо, если вы хотите использовать обычное расширение .js, добавлением "type": "module" к вашему package.json. Более подробную информацию можно найти в документации Node.js.

Текущие ограничения

  • Режим наблюдения не поддерживает тестовые файлы ES Module
  • Пользовательские репортеры и пользовательские интерфейсы могут быть только файлами CommonJS
  • Файл конфигурации может быть только файлом CommonJS (.mocharc.js или .mocharc.cjs)
  • При использовании моков на уровне модулей через библиотеки, такие как proxyquire, rewiremock или rewire, воздержитесь от использования ES модулей для ваших тестовых файлов. Вы можете переключиться на использование testdouble, который поддерживает ESM.

Запуск Mocha в браузере

Mocha работает в браузере. Каждая версия Mocha будет иметь новые сборки ./mocha.js и ./mocha.css для использования в браузере.

Типичная настройка может выглядеть следующим образом, где мы вызываем mocha.setup('bdd') для использования интерфейса BDD перед загрузкой скриптов тестов, запуская их onload с mocha.run().

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <title>Mocha Tests</title>
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <link rel="stylesheet" href="https://unpkg.com/mocha/mocha.css" />
  </head>
  <body>
    <div id="mocha"></div>

    <script src="https://unpkg.com/chai/chai.js"></script>
    <script src="https://unpkg.com/mocha/mocha.js"></script>

    <script class="mocha-init">
      mocha.setup('bdd');
      mocha.checkLeaks();
    </script>
    <script src="test.array.js"></script>
    <script src="test.object.js"></script>
    <script src="test.xhr.js"></script>
    <script class="mocha-exec">
      mocha.run();
    </script>
  </body>
</html>

Grep

Браузер может использовать --grep как функциональность. Добавьте строку запроса к вашему URL: ?grep=api.

Настройка браузера

Параметры Mocha могут быть заданы через mocha.setup(). Примеры:

// Use "tdd" interface.  This is a shortcut to setting the interface;
// any other options must be passed via an object.
mocha.setup('tdd');

// This is equivalent to the above.
mocha.setup({
  ui: 'tdd'
});

// Examples of options:
mocha.setup({
  allowUncaught: true,
  asyncOnly: true,
  bail: true,
  checkLeaks: true,
  dryRun: true,
  forbidOnly: true,
  forbidPending: true,
  global: ['MyLib'],
  retries: 3,
  slow: '100',
  timeout: '2000',
  ui: 'bdd'
});

Параметры, специфичные для браузера

Браузерный Mocha поддерживает многие, но не все параметры командной строки. Для использования параметра командной строки, содержащего «-», преобразуйте параметр в camelCase, (например, check-leaks в checkLeaks).

# Параметры, незначительно отличающиеся от параметров командной строки:

reporter {строка|конструктор} Вы можете передать имя репортера или конструктор пользовательского репортера. Вы можете найти рекомендуемые репортеры для браузера здесь. Также можно использовать встроенные репортеры. Их использование в браузерах не рекомендуется и не поддерживается, откройте консоль, чтобы увидеть результаты тестов.

# Параметры, только функционирующие в контексте браузера:

noHighlighting {логическое значение} Если установлено значение true, не пытайтесь использовать подсветку синтаксиса для кода результатов тестов.

Отчетность

HTML-репортер является стандартным репортером при запуске Mocha в браузере. Он выглядит так:

HTML test reporter

Mochawesome — отличная альтернатива стандартному HTML-репортеру.

Поддержка уведомлений рабочего стола

Уведомления рабочего стола позволяют асинхронно обмениваться данными о событиях, не заставляя вас сразу реагировать на уведомление. Их внешний вид и конкретная функциональность различаются в зависимости от платформы. Обычно они исчезают автоматически через короткое время, но их содержимое часто хранится каким-либо способом, что позволяет получить доступ к прошлым уведомлениям.

Growl был ранней реализацией системы уведомлений для OS X и Windows, отсюда и название опции Mocha --growl.

После включения, при завершении выполнения теста корневого набора, должно появиться уведомление на рабочем столе, сообщающее о том, прошли ли тесты успешно или потерпели неудачу.

Уведомления на основе Node.js

Для использования уведомлений рабочего стола с интерфейсом командной строки (CLI) необходимо предварительно установить некоторое специфичное для платформы программное обеспечение. Инструкции по этому вопросу можно найти здесь.

Включите уведомления рабочего стола Mocha следующим образом:

$ mocha --growl

Уведомления на основе браузера

Поддержка уведомлений веб-браузера становится доступной для текущих версий современных браузеров. Убедитесь, что ваша версия браузера поддерживает как promises, так и уведомления веб-браузера. Поскольку API уведомлений эволюционировал с течением времени, не ожидайте, что минимально возможная версия браузера обязательно будет работать.

Включите уведомления веб-браузера Mocha с небольшим изменением вашего HTML-кода Mocha на стороне клиента. Добавьте вызов mocha.growl() перед запуском тестов, как показано ниже:

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <title>Mocha Tests</title>
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <link rel="stylesheet" href="https://unpkg.com/mocha/mocha.css" />
  </head>
  <body>
    <div id="mocha"></div>

    <script src="https://unpkg.com/chai/chai.js"></script>
    <script src="https://unpkg.com/mocha/mocha.js"></script>

    <script class="mocha-init">
      mocha.setup('bdd');
      mocha.growl(); // <-- Enables web notifications
    </script>
    <script src="test.spec.js"></script>
    <script class="mocha-exec">
      mocha.run();
    </script>
  </body>
</html>

Настройка Mocha (Node.js)

Новинка в версии 6.0.0

Mocha поддерживает файлы конфигурации, типичные для современных инструментов командной строки, в нескольких форматах:

  • JavaScript: Создайте файл .mocharc.js (или .mocharc.cjs при использовании "type"="module" в вашем package.json) в корневом каталоге проекта и экспортируйте объект (module.exports = {/* ... */}) содержащий вашу конфигурацию.
  • YAML: Создайте файл .mocharc.yaml (или .mocharc.yml) в корневом каталоге проекта.
  • JSON: Создайте файл .mocharc.json (или .mocharc.jsonc) в корневом каталоге проекта. Комментарии, хотя и не являются допустимым JSON, разрешены в этом файле и будут проигнорированы Mocha.
  • package.json: Создайте свойство mocha в файле package.json проекта.

Пользовательские расположения

Вы можете указать пользовательское расположение файла конфигурации с помощью опции --config <path>. Mocha будет использовать расширение файла, чтобы определить, как разобрать файл, и предположит JSON, если расширение неизвестно.

Вы также можете указать пользовательское расположение package.json, используя опцию --package <path>.

Игнорирование файлов конфигурации

Чтобы пропустить поиск файлов конфигурации, используйте --no-config. Аналогично, используйте --no-package, чтобы помешать Mocha искать конфигурацию в package.json.

Приоритеты

Если не был указан пользовательский путь и если в одном каталоге существует несколько файлов конфигурации, Mocha будет искать и использовать только один. Приоритет:

  1. .mocharc.js
  2. .mocharc.yaml
  3. .mocharc.yml
  4. .mocharc.jsonc
  5. .mocharc.json

Объединение

Mocha также объединит любые параметры, найденные в package.json, в свою конфигурацию во время выполнения. В случае конфликта приоритет:

  1. Аргументы, указанные в командной строке
  2. Файл конфигурации (.mocharc.js, .mocharc.yml и т. д.)
  3. Свойство mocha объекта package.json

Параметры, которые можно безопасно повторять (например, --require), будут конкатенированы, а источники конфигурации с более высоким приоритетом будут появляться раньше в списке. Например, файл .mocharc.json, содержащий "require": "bar", совместно с выполнением mocha --require foo, заставит Mocha потребовать foo, а затем bar в указанном порядке.

Расширение конфигурации

Конфигурации могут наследовать от других модулей, используя ключевое слово extends. Подробнее см. здесь.

Формат конфигурации

  • Любой флаг «логический» (который не требует параметра, например, --bail), может быть задан с помощью булевского значения, например: "bail": true.
  • Любой параметр типа «массив» (см. mocha --help для списка) может быть строковым значением.
  • Для параметров, содержащих дефис (-), имя параметра может быть указано с использованием camelCase.
  • Псевдонимы являются допустимыми именами, например, R вместо reporter.
  • Тестовые файлы могут быть указаны с использованием spec, например, "spec": "test/**/*.spec.js".
  • Флаги для node также поддерживаются в файлах конфигурации. Будьте осторожны, так как они могут различаться в разных версиях Node.js!

Дополнительные примеры конфигурации см. в каталоге example/config на GitHub.

Каталог test/

По умолчанию, mocha ищет шаблон "./test/*.{js,cjs,mjs}", поэтому вы можете поместить свои тесты в папку test/. Если вы хотите включить подкаталоги, передайте параметр --recursive.

Чтобы настроить место, где mocha ищет тесты, вы можете передать свой собственный шаблон:

$ mocha --recursive "./spec/*.js"

Некоторые оболочки поддерживают рекурсивный поиск, используя символ подстановочного знака globstar (**). Bash >= 4.3 поддерживает это с помощью globstar параметра, который должен быть включен, чтобы получить те же результаты, что и при передаче параметра --recursive (ZSH и Fish поддерживают это по умолчанию). При включенном рекурсивном поиске следующее эквивалентно передаче параметра --recursive:

$ mocha "./spec/**/*.js"

Вы всегда должны заключать свои шаблоны в кавычки в скриптах npm. Если вы используете двойные кавычки, это оболочка UNIX, которая будет расширять шаблон. С другой стороны, если вы используете одинарные кавычки, модуль node-glob будет обрабатывать его расширение.

См. этот учебник по использованию шаблонов.

Примечание: Рекомендуется использовать двойные кавычки вокруг шаблона для обеспечения переносимости.

Коды ошибок

Новинка в версии 6.0.0

Когда сам Mocha вызывает исключение, соответствующий Error будет иметь свойство code. В применимых случаях пользователи должны проверять свойство code вместо поиска совпадений по строке со свойством message. В следующей таблице описаны эти коды ошибок:

Код Описание
ERR_MOCHA_INVALID_ARG_TYPE передан неверный тип аргумента
ERR_MOCHA_INVALID_ARG_VALUE передано неверное или неподдерживаемое значение аргумента
ERR_MOCHA_INVALID_EXCEPTION выброшено ложное или недостаточно определенное исключение
ERR_MOCHA_INVALID_INTERFACE интерфейс, указанный в параметрах, не найден
ERR_MOCHA_INVALID_REPORTER отчётчик, указанный в параметрах, не найден
ERR_MOCHA_NO_FILES_MATCH_PATTERN файл(ы) теста не найдены
ERR_MOCHA_UNSUPPORTED запрашиваемое поведение, параметр или опция не поддерживается

Плагины редактора

Доступны следующие пакеты, относящиеся к редактору:

TextMate

Пакет Mocha TextMate содержит фрагменты кода, которые ускорят и сделают написание тестов более приятным.

JetBrains

JetBrains предоставляет плагин NodeJS для своих IDE (IntelliJ IDEA, WebStorm и т. д.), который, среди прочего, содержит запуск тестов Mocha.

JetBrains Mocha Runner Plugin in Action

Плагин называется NodeJS и может быть установлен через Настройки > Плагины, при условии, что ваша лицензия это позволяет.

Wallaby.js

Wallaby.js — инструмент непрерывного тестирования, который обеспечивает отображение покрытия кода в режиме реального времени для Mocha с любой библиотекой утверждений в VS Code, Atom, IDE JetBrains (IntelliJ IDEA, WebStorm и т. д.), Sublime Text и Visual Studio для проектов как для браузера, так и для node.js.

Wallaby.js in Action

Emacs

Emacs поддерживает запуск тестов Mocha через сторонний пакет mocha.el. Пакет доступен в MELPA и может быть установлен через M-x package-install mocha.

Emacs Mocha Runner in Action

Mocha Sidebar (VS Code)

Меню Mocha Sidebar — наиболее полное расширение Mocha для VS Code.

# Функции

  • отображение всех тестов в меню боковой панели VS Code
  • запуск и отладка тестов для каждой иерархии уровней от всех тестов до одного теста (и каждой группы)
  • автоматический запуск тестов при сохранении файла
  • отображение результатов тестов непосредственно в редакторе кода

mocha side bar in Action

Примеры

Примеры реального кода:

  • Примеры Mocha
  • Express
  • Connect
  • SuperAgent
  • WebSocket.io
  • Тесты Mocha

Тестирование Mocha

Для запуска тестов Mocha вам понадобится GNU Make или совместимый аналог; Cygwin должен работать.

$ cd /path/to/mocha
$ npm install
$ npm test

© 2011–2021 JS Foundation and contributors
Licensed under the Creative Commons Attribution 4.0 International License.
https://mochajs.org/

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API