Files
elasticsearch-js/test/utils/jenkins-reporter.js
Spencer 7c1573fb07 Use standard and prettier (#10)
* switch from custom eslint config to standard + prettier

* fix new standard eslint violations

* add editorconfig file

* auto-fix all other violations

* update lint yarn script

* remove jshint comment
2019-07-09 13:24:13 -07:00

221 lines
5.1 KiB
JavaScript

/**
* ESJS reporter for running and collecting mocha test results.
*
* @param {Runner} runner
* @api public
*/
module.exports = JenkinsReporter;
var Base = require('mocha/lib/reporters/base');
var _ = require('lodash');
var chalk = require('chalk');
var makeJUnitXml = require('./make_j_unit_xml');
var fs = require('fs');
var path = require('path');
var inspect = require('util').inspect;
var log = (function() {
var locked = _.bind(process.stdout.write, process.stdout);
return function(str) {
if (typeof str !== 'string') {
str = inspect(str);
}
locked(str);
};
})();
var integration = _.find(process.argv, function(arg) {
return arg.indexOf('test/integration') > -1;
});
var unit = _.find(process.argv, function(arg) {
return arg.indexOf('test/unit') > -1;
});
var output;
if (unit) {
output = path.join(__dirname, '../junit-node-unit.xml');
} else if (integration) {
output = path.join(__dirname, '../junit-node-integration.xml');
} else {
throw new Error('unable to detect unit or integration tests');
}
function JenkinsReporter(runner) {
Base.call(this, runner);
var stats = this.stats;
var rootSuite = {
results: [],
suites: [],
};
var stack = [rootSuite];
function indt() {
return new Array(stack.length + 1).join(' ');
}
runner.on('suite', function(suite) {
if (suite.root) {
return;
}
// suite
suite = {
name: suite.fullTitle(),
results: [],
start: Date.now(),
stdout: '',
stderr: '',
};
// append to the previous stack leader
if (!stack[0].suites) {
stack[0].suites = [];
}
stack[0].suites.push(suite);
// push the suite onto the top of the stack
stack.unshift(suite);
});
runner.on('suite end', function(suite) {
if (suite.root) {
return;
}
stack[0].time = Date.now() - stack[0].start;
stack.shift();
});
runner.on('fail', function(test) {
if (test.type === 'hook') {
runner.emit('test end', test);
}
});
runner.on('test end', function(test) {
if (test.state === 'passed') {
log(chalk.green('.'));
} else if (test.pending) {
log(chalk.grey('.'));
return;
} else {
log(chalk.red('x'));
}
var errMsg = void 0;
if (test.err) {
errMsg = test.err.stack || test.err.toString();
// FF / Opera do not add the message
if (!~errMsg.indexOf(test.err.message)) {
errMsg = test.err.message + '\n' + errMsg;
}
// <=IE7 stringifies to [Object Error]. Since it can be overloaded, we
// check for the result of the stringifying.
if (errMsg === '[object Error]') {
errMsg = test.err.message;
}
// Safari doesn't give you a stack. Let's at least provide a source line.
if (
!test.err.stack &&
test.err.sourceURL &&
test.err.line !== undefined
) {
errMsg += '\n(' + test.err.sourceURL + ':' + test.err.line + ')';
}
console.error(
_.map(errMsg.split('\n'), function(line) {
return indt() + ' ' + line;
}).join('\n')
);
}
if (stack[0]) {
stack[0].results.push({
name: test.title,
time: test.duration,
pass: test.state === 'passed',
test: test,
stdout: stack[0].stdout,
stderr: stack[0].stderr,
});
stack[0].stdout = stack[0].stderr = '';
}
});
runner.on('hook end', function(hook) {
if (
hook.title.indexOf('"after each"') > -1 &&
stack[0] &&
stack[0].results.length
) {
var result = _.last(stack[0].results);
result.stdout += stack[0].stdout;
result.stderr += stack[0].stderr;
stack[0].stdout = stack[0].stderr = '';
}
});
runner.on('end', function() {
restoreStdio();
var xml = makeJUnitXml('node ' + process.version, {
stats: stats,
suites: _.map(rootSuite.suites, function removeElements(suite) {
var s = {
name: suite.name,
start: suite.start,
time: suite.time || 0,
results: suite.results,
stdout: suite.stdout,
stderr: suite.stderr,
};
if (suite.suites) {
s.suites = _.map(suite.suites, removeElements);
}
return s;
}),
});
fs.writeFileSync(output, xml, 'utf8');
console.log(
'\n' +
[
'tests complete in ' +
Math.round(stats.duration / 10) / 100 +
' seconds',
' fail: ' + chalk.red(stats.failures),
' pass: ' + chalk.green(stats.passes),
' pending: ' + chalk.grey(stats.pending),
].join('\n')
);
});
// overload the write methods on stdout and stderr
['stdout', 'stderr'].forEach(function(name) {
var obj = process[name];
var orig = obj.write;
obj.write = function(chunk) {
if (stack[0]) {
stack[0][name] = (stack[0][name] || '') + chunk;
}
// orig.apply(obj, arguments);
};
obj.__restore = function() {
this.write = orig;
};
});
function restoreStdio() {
process.stdout.__restore();
process.stderr.__restore();
}
}