'use strict';
const utils = require('../utils'); const Context = require('../context'); const Mocha = require('../mocha'); const collectFiles = require('./collect-files');
/**
* Exports the `watchRun` function that runs mocha in "watch" mode. * @see module:lib/cli/run-helpers * @module * @private */
/**
* Run Mocha in "watch" mode * @param {Mocha} mocha - Mocha instance * @param {Object} opts - Options * @param {string} opts.ui - User interface * @param {Object} fileCollectParams - Parameters that control test * file collection. See `lib/cli/collect-files.js`. * @param {string[]} fileCollectParams.extension - List of extensions to watch * @private */
module.exports = (mocha, {ui}, fileCollectParams) => {
let runner; const files = collectFiles(fileCollectParams); console.log(); hideCursor(); process.on('SIGINT', () => { showCursor(); console.log('\n'); // By UNIX/Posix convention this indicates that the process was // killed by SIGINT which has portable number 2. process.exit(128 + 2); }); const watchFiles = utils.files(process.cwd(), fileCollectParams.extension); let runAgain = false; const loadAndRun = () => { try { mocha.files = files; runAgain = false; runner = mocha.run(() => { runner = null; if (runAgain) { rerun(); } }); } catch (e) { console.log(e.stack); } }; const purge = () => { watchFiles.forEach(Mocha.unloadFile); }; loadAndRun(); const rerun = () => { purge(); eraseLine(); mocha.suite = mocha.suite.clone(); mocha.suite.ctx = new Context(); mocha.ui(ui); loadAndRun(); }; utils.watch(watchFiles, () => { runAgain = true; if (runner) { runner.abort(); } else { rerun(); } });
};
/**
* Hide the cursor. * @ignore * @private */
const hideCursor = () => {
process.stdout.write('\u001b[?25l');
};
/**
* Show the cursor. * @ignore * @private */
const showCursor = () => {
process.stdout.write('\u001b[?25h');
};
/**
* Erases the line on stdout * @private */
const eraseLine = () => {
process.stdout.write('\u001b[2K');
};