From 7c8b864f65fa606e2732fdfbbf13de537166f31f Mon Sep 17 00:00:00 2001 From: lukedgr Date: Tue, 2 Jun 2015 21:56:14 -0700 Subject: [PATCH 1/5] Make mocha options configurable Makes the mocha UI, Reporter, Timeout, etc configurable using a mocha.json to specify the values. --- .../Nodejs/TestFrameworks/mocha/mocha.js | 67 +++++++++++++++---- 1 file changed, 53 insertions(+), 14 deletions(-) diff --git a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js index 87ae90e09..1ae62eee1 100644 --- a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js +++ b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js @@ -1,5 +1,10 @@ var fs = require('fs'); +// Choose 'tap' rather than 'min' or 'xunit'. The reason is that +// 'min' produces undisplayable text to stdout and stderr under piped/redirect, +// and 'xunit' does not print the stack trace from the test. +var defaultMochaOptions = { ui: 'tdd', reporter: 'tap', timeout: 600000 }; + var find_tests = function (testFileList, discoverResultFile, projectFolder) { var Mocha = detectMocha(projectFolder); if (!Mocha) { @@ -11,7 +16,7 @@ var find_tests = function (testFileList, discoverResultFile, projectFolder) { if (suite.tests && suite.tests.length !== 0) { suite.tests.forEach(function (t, i, testArray) { testList.push({ - test: t.fullTitle(), + test: t.title, suite: suite.fullTitle(), file: testFile, line: 0, @@ -29,15 +34,14 @@ var find_tests = function (testFileList, discoverResultFile, projectFolder) { } var testList = []; testFileList.split(';').forEach(function (testFile) { - var mocha = new Mocha(); + var mocha = initializeMocha(Mocha, projectFolder); try { - mocha.ui('tdd'); mocha.addFile(testFile); mocha.loadFiles(); getTestList(mocha.suite, testFile); } catch (e) { //we would like continue discover other files, so swallow, log and continue; - console.error('catch discover error:' + e); + logError('An error occurred during mocha discovery:' + e); } }); @@ -53,33 +57,68 @@ var run_tests = function (testName, testFile, workingFolder, projectFolder) { return; } - var mocha = new Mocha(); - mocha.ui('tdd'); - //set timeout to 10 minutes, because the default of 2 sec might be too short (TODO: make it configurable) - mocha.suite.timeout(600000); + var mocha = initializeMocha(Mocha, projectFolder); + if (testName) { mocha.grep(testName); } mocha.addFile(testFile); - // Choose 'tap' rather than 'min' or 'xunit'. The reason is that - // 'min' produces undisplayable text to stdout and stderr under piped/redirect, - // and 'xunit' does not print the stack trace from the test. - mocha.reporter('tap'); - mocha.run(function (code) { process.exit(code); }); }; +function logError(errorMessage) { + console.log("NTVS_ERROR: " + errorMessage); +} + function detectMocha(projectFolder) { try { var Mocha = new require(projectFolder + '\\node_modules\\mocha'); return Mocha; } catch (ex) { - console.log("NTVS_ERROR:Failed to find Mocha package. Mocha must be installed in the project locally. Mocha can be installed locally with the npm manager via solution explorer or with \".npm install mocha\" via the Node.js interactive window."); + logError("Failed to find Mocha package. Mocha must be installed in the project locally. Mocha can be installed locally with the npm manager via solution explorer or with \".npm install mocha\" via the Node.js interactive window."); return null; } } +function initializeMocha(Mocha, projectFolder) { + var mocha = new Mocha(); + applyMochaOptions(mocha, getMochaOptions(projectFolder)); + return mocha; +} + +function applyMochaOptions(mocha, options) { + if (options) { + for (var opt in options) { + var mochaOpt = mocha[opt]; + var optValue = options[opt]; + + if (typeof mochaOpt == 'function') { + try { + mochaOpt.call(mocha, optValue); + } catch (e) { + error("Could not set mocha option '" + opt + "' with value '" + optValue + "' due to error: " + e); + } + } + } + } +} + +function getMochaOptions(projectFolder) { + var mochaOptions = defaultMochaOptions; + try { + var options = require(projectFolder + '\\test\\mocha.json'); + options = options || {}; + for (var opt in options) { + mochaOptions[opt] = options[opt]; + } + } catch (ex) { + console.log("NTVS: mocha.json options file not found. Using default values."); + } + + return mochaOptions; +} + module.exports.run_tests = run_tests; From ab67cb97941d61161c05faa61f2145dc95696ecf Mon Sep 17 00:00:00 2001 From: lukedgr Date: Wed, 3 Jun 2015 08:31:32 -0700 Subject: [PATCH 2/5] Fixed reporting if failure occurs applying options. --- Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js index 1ae62eee1..889eb99dc 100644 --- a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js +++ b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js @@ -99,7 +99,7 @@ function applyMochaOptions(mocha, options) { try { mochaOpt.call(mocha, optValue); } catch (e) { - error("Could not set mocha option '" + opt + "' with value '" + optValue + "' due to error: " + e); + logError("Could not set mocha option '" + opt + "' with value '" + optValue + "' due to error: " + e); } } } From a254430250cbd4d3f25f1687cd8724a6dbccf833 Mon Sep 17 00:00:00 2001 From: lukedgr Date: Thu, 18 Jun 2015 16:12:30 -0700 Subject: [PATCH 3/5] Cleaned up code based on comments on PR Use path instead of manual path setting and updated error reporting. --- .../Nodejs/TestFrameworks/mocha/mocha.js | 21 ++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js index 889eb99dc..d2c4dcaf8 100644 --- a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js +++ b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js @@ -1,4 +1,5 @@ var fs = require('fs'); +var path = require('path'); // Choose 'tap' rather than 'min' or 'xunit'. The reason is that // 'min' produces undisplayable text to stdout and stderr under piped/redirect, @@ -41,7 +42,7 @@ var find_tests = function (testFileList, discoverResultFile, projectFolder) { getTestList(mocha.suite, testFile); } catch (e) { //we would like continue discover other files, so swallow, log and continue; - logError('An error occurred during mocha discovery:' + e); + logError('NTVS_ERROR: An error occurred during mocha test discovery in file: ' + testFile, e); } }); @@ -69,13 +70,18 @@ var run_tests = function (testName, testFile, workingFolder, projectFolder) { }); }; -function logError(errorMessage) { - console.log("NTVS_ERROR: " + errorMessage); +function logError(errorMessage, error) { + if (typeof error === 'undefined') { + console.error("NTVS_ERROR: " + errorMessage); + } else { + console.error("NTVS_ERROR: " + errorMessage, error); + } } function detectMocha(projectFolder) { try { - var Mocha = new require(projectFolder + '\\node_modules\\mocha'); + var mochaPath = path.join(projectFolder, 'node_modules', 'mocha'); + var Mocha = new require(mochaPath); return Mocha; } catch (ex) { logError("Failed to find Mocha package. Mocha must be installed in the project locally. Mocha can be installed locally with the npm manager via solution explorer or with \".npm install mocha\" via the Node.js interactive window."); @@ -95,11 +101,11 @@ function applyMochaOptions(mocha, options) { var mochaOpt = mocha[opt]; var optValue = options[opt]; - if (typeof mochaOpt == 'function') { + if (typeof mochaOpt === 'function') { try { mochaOpt.call(mocha, optValue); } catch (e) { - logError("Could not set mocha option '" + opt + "' with value '" + optValue + "' due to error: " + e); + logError("Could not set mocha option '" + opt + "' with value '" + optValue + "' due to error: ", e); } } } @@ -109,7 +115,8 @@ function applyMochaOptions(mocha, options) { function getMochaOptions(projectFolder) { var mochaOptions = defaultMochaOptions; try { - var options = require(projectFolder + '\\test\\mocha.json'); + var optionsPath = path.join(projectFolder, 'test', 'mocha.json'); + var options = require(optionsPath); options = options || {}; for (var opt in options) { mochaOptions[opt] = options[opt]; From 620f956d4e80ea6aab786c265ae30298083d2ade Mon Sep 17 00:00:00 2001 From: lukedgr Date: Fri, 19 Jun 2015 13:39:54 -0700 Subject: [PATCH 4/5] Make log error more flexible, and clean up error messages --- .../Product/Nodejs/TestFrameworks/mocha/mocha.js | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js index d2c4dcaf8..22f8d08fb 100644 --- a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js +++ b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js @@ -42,7 +42,7 @@ var find_tests = function (testFileList, discoverResultFile, projectFolder) { getTestList(mocha.suite, testFile); } catch (e) { //we would like continue discover other files, so swallow, log and continue; - logError('NTVS_ERROR: An error occurred during mocha test discovery in file: ' + testFile, e); + logError('An error occurred during mocha test discovery in file: ' + testFile, e); } }); @@ -70,12 +70,10 @@ var run_tests = function (testName, testFile, workingFolder, projectFolder) { }); }; -function logError(errorMessage, error) { - if (typeof error === 'undefined') { - console.error("NTVS_ERROR: " + errorMessage); - } else { - console.error("NTVS_ERROR: " + errorMessage, error); - } +function logError() { + var errorArgs = Array.prototype.slice.call(arguments); + errorArgs.unshift("NTVS_ERROR:"); + console.error.apply(console, errorArgs); } function detectMocha(projectFolder) { @@ -105,7 +103,7 @@ function applyMochaOptions(mocha, options) { try { mochaOpt.call(mocha, optValue); } catch (e) { - logError("Could not set mocha option '" + opt + "' with value '" + optValue + "' due to error: ", e); + logError("Could not set mocha option '" + opt + "' with value '" + optValue + "' due to error:", e); } } } From 831ef2c4da8a147f1f9106c40061f2297020acaa Mon Sep 17 00:00:00 2001 From: lukedgr Date: Fri, 19 Jun 2015 17:07:55 -0700 Subject: [PATCH 5/5] Change console.log to logError if options file not found. --- Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js index 22f8d08fb..55447702f 100644 --- a/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js +++ b/Nodejs/Product/Nodejs/TestFrameworks/mocha/mocha.js @@ -120,7 +120,7 @@ function getMochaOptions(projectFolder) { mochaOptions[opt] = options[opt]; } } catch (ex) { - console.log("NTVS: mocha.json options file not found. Using default values."); + logError("mocha.json options file not found. Using default values."); } return mochaOptions;