/
mocha
executable file
·116 lines (102 loc) · 2.92 KB
/
mocha
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
#!/usr/bin/env node
'use strict';
/**
* This wrapper executable checks for known node flags and appends them when found, before invoking the "real" _mocha(1) executable.
*
* @module bin/mocha
* @private
*/
const {deprecate} = require('../lib/utils');
const {spawn} = require('child_process');
const {loadOptions} = require('../lib/cli/options');
const {isNodeFlag, impliesNoTimeouts} = require('../lib/cli/node-flags');
const unparse = require('yargs-unparser');
const debug = require('debug')('mocha:cli');
const {aliases} = require('../lib/cli/run-option-metadata');
const mochaPath = require.resolve('./_mocha');
const childOpts = {};
const nodeOpts = {};
const opts = loadOptions(process.argv.slice(2));
debug('loaded opts', opts);
Object.keys(opts).forEach(opt => {
if (isNodeFlag(opt)) {
if (/^v8-/.test(opt)) {
opt = opt.slice(2);
}
nodeOpts[opt] = opts[opt];
if (impliesNoTimeouts(opt)) {
debug(`option "${opt}" disabled timeouts`);
childOpts.timeout = false;
}
} else {
childOpts[opt] = opts[opt];
}
});
// allow --debug to invoke --inspect on Node.js v8 or newer
if (childOpts.debug) {
nodeOpts.inspect = childOpts.debug;
childOpts.timeout = false;
delete childOpts.debug;
debug('--debug -> --inspect');
} else if (childOpts['debug-brk']) {
nodeOpts['inspect-brk'] = childOpts['debug-brk'];
childOpts.timeout = false;
delete childOpts['debug-brk'];
debug('--debug-brk -> --inspect-brk');
}
// historical
if (nodeOpts.gc) {
deprecate(
'"-gc" is deprecated and will be removed from a future version of Mocha. Use "--gc-global" instead.'
);
nodeOpts['gc-global'] = nodeOpts.gc;
delete nodeOpts.gc;
}
// Native debugger handling
// see https://nodejs.org/api/debugger.html#debugger_debugger
// look for 'debug' or 'inspect' that would launch this debugger,
// remove it from Mocha's opts and prepend it to Node's opts.
// also coerce depending on Node.js version.
if (/^(debug|inspect)$/.test(childOpts._[0])) {
childOpts.timeout = false;
childOpts._.shift();
// don't conflict with inspector
delete nodeOpts['debug'];
delete nodeOpts['inspect'];
delete nodeOpts['debug-brk'];
delete nodeOpts['inspect-brk'];
nodeOpts._ = [
parseInt(
process.version
.slice(1)
.split('.')
.shift(),
10
) >= 8
? 'inspect'
: 'debug'
];
}
const args = [].concat(
unparse(nodeOpts),
mochaPath,
unparse(childOpts, {alias: aliases})
);
debug(`exec ${process.execPath} w/ args:`, args);
const proc = spawn(process.execPath, args, {
stdio: 'inherit'
});
proc.on('exit', (code, signal) => {
process.on('exit', () => {
if (signal) {
process.kill(process.pid, signal);
} else {
process.exit(code);
}
});
});
// terminate children.
process.on('SIGINT', () => {
proc.kill('SIGINT'); // calls runner.abort()
proc.kill('SIGTERM'); // if that didn't work, we're probably in an infinite loop, so make it die.
});