@wdio/cli 7.20.6 → 7.20.8-alpha.504
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bin/wdio.js +7 -1
- package/build/commands/config.d.ts +3 -3
- package/build/commands/config.d.ts.map +1 -1
- package/build/commands/config.js +58 -69
- package/build/commands/index.d.ts +2 -0
- package/build/commands/index.d.ts.map +1 -0
- package/build/commands/index.js +5 -0
- package/build/commands/install.d.ts +3 -3
- package/build/commands/install.d.ts.map +1 -1
- package/build/commands/install.js +28 -35
- package/build/commands/repl.d.ts +5 -5
- package/build/commands/repl.d.ts.map +1 -1
- package/build/commands/repl.js +15 -29
- package/build/commands/run.d.ts +7 -5
- package/build/commands/run.d.ts.map +1 -1
- package/build/commands/run.js +54 -33
- package/build/constants.d.ts +16 -2
- package/build/constants.d.ts.map +1 -1
- package/build/constants.js +53 -48
- package/build/index.d.ts +4 -3
- package/build/index.d.ts.map +1 -1
- package/build/index.js +24 -41
- package/build/interface.d.ts +3 -3
- package/build/interface.d.ts.map +1 -1
- package/build/interface.js +57 -52
- package/build/launcher.d.ts +4 -4
- package/build/launcher.d.ts.map +1 -1
- package/build/launcher.js +81 -61
- package/build/types.d.ts +2 -2
- package/build/types.d.ts.map +1 -1
- package/build/types.js +1 -2
- package/build/utils.d.ts +8 -1
- package/build/utils.d.ts.map +1 -1
- package/build/utils.js +102 -92
- package/build/watcher.d.ts +1 -1
- package/build/watcher.d.ts.map +1 -1
- package/build/watcher.js +25 -24
- package/package.json +32 -27
package/build/interface.js
CHANGED
|
@@ -1,39 +1,41 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
};
|
|
5
|
-
|
|
6
|
-
const
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
1
|
+
import { EventEmitter } from 'node:events';
|
|
2
|
+
import chalk, { supportsColor } from 'chalk';
|
|
3
|
+
import logger from '@wdio/logger';
|
|
4
|
+
import { getRunnerName } from './utils.js';
|
|
5
|
+
const log = logger('@wdio/cli');
|
|
6
|
+
const EVENT_FILTER = ['sessionStarted', 'sessionEnded', 'finisedCommand'];
|
|
7
|
+
export default class WDIOCLInterface extends EventEmitter {
|
|
8
|
+
_config;
|
|
9
|
+
totalWorkerCnt;
|
|
10
|
+
_isWatchMode;
|
|
11
|
+
hasAnsiSupport;
|
|
12
|
+
result = {
|
|
13
|
+
finished: 0,
|
|
14
|
+
passed: 0,
|
|
15
|
+
retries: 0,
|
|
16
|
+
failed: 0
|
|
17
|
+
};
|
|
18
|
+
_jobs = new Map();
|
|
19
|
+
_specFileRetries;
|
|
20
|
+
_specFileRetriesDelay;
|
|
21
|
+
_skippedSpecs = 0;
|
|
22
|
+
_inDebugMode = false;
|
|
23
|
+
_start = new Date();
|
|
24
|
+
_messages = {
|
|
25
|
+
reporter: {},
|
|
26
|
+
debugger: {}
|
|
27
|
+
};
|
|
12
28
|
constructor(_config, totalWorkerCnt, _isWatchMode = false) {
|
|
13
29
|
super();
|
|
14
30
|
this._config = _config;
|
|
15
31
|
this.totalWorkerCnt = totalWorkerCnt;
|
|
16
32
|
this._isWatchMode = _isWatchMode;
|
|
17
|
-
this.result = {
|
|
18
|
-
finished: 0,
|
|
19
|
-
passed: 0,
|
|
20
|
-
retries: 0,
|
|
21
|
-
failed: 0
|
|
22
|
-
};
|
|
23
|
-
this._jobs = new Map();
|
|
24
|
-
this._skippedSpecs = 0;
|
|
25
|
-
this._inDebugMode = false;
|
|
26
|
-
this._start = new Date();
|
|
27
|
-
this._messages = {
|
|
28
|
-
reporter: {},
|
|
29
|
-
debugger: {}
|
|
30
|
-
};
|
|
31
33
|
/**
|
|
32
34
|
* Colors can be forcibly enabled/disabled with env variable `FORCE_COLOR`
|
|
33
35
|
* `FORCE_COLOR=1` - forcibly enable colors
|
|
34
36
|
* `FORCE_COLOR=0` - forcibly disable colors
|
|
35
37
|
*/
|
|
36
|
-
this.hasAnsiSupport =
|
|
38
|
+
this.hasAnsiSupport = supportsColor && supportsColor.hasBasic;
|
|
37
39
|
this.totalWorkerCnt = totalWorkerCnt;
|
|
38
40
|
this._isWatchMode = _isWatchMode;
|
|
39
41
|
this._specFileRetries = _config.specFileRetries || 0;
|
|
@@ -62,27 +64,27 @@ class WDIOCLInterface extends events_1.EventEmitter {
|
|
|
62
64
|
};
|
|
63
65
|
}
|
|
64
66
|
onStart() {
|
|
65
|
-
this.log(
|
|
67
|
+
this.log(chalk.bold(`\nExecution of ${chalk.blue(this.totalWorkerCnt)} workers started at`), this._start.toISOString());
|
|
66
68
|
if (this._inDebugMode) {
|
|
67
|
-
this.log(
|
|
69
|
+
this.log(chalk.bgYellow.black('DEBUG mode enabled!'));
|
|
68
70
|
}
|
|
69
71
|
if (this._isWatchMode) {
|
|
70
|
-
this.log(
|
|
72
|
+
this.log(chalk.bgYellow.black('WATCH mode enabled!'));
|
|
71
73
|
}
|
|
72
74
|
this.log('');
|
|
73
75
|
}
|
|
74
76
|
onSpecRunning(rid) {
|
|
75
|
-
this.onJobComplete(rid, this._jobs.get(rid), 0,
|
|
77
|
+
this.onJobComplete(rid, this._jobs.get(rid), 0, chalk.bold.cyan('RUNNING'));
|
|
76
78
|
}
|
|
77
79
|
onSpecRetry(rid, job, retries = 0) {
|
|
78
80
|
const delayMsg = this._specFileRetriesDelay > 0 ? ` after ${this._specFileRetriesDelay}s` : '';
|
|
79
|
-
this.onJobComplete(rid, job, retries,
|
|
81
|
+
this.onJobComplete(rid, job, retries, chalk.bold(chalk.yellow('RETRYING') + delayMsg));
|
|
80
82
|
}
|
|
81
83
|
onSpecPass(rid, job, retries = 0) {
|
|
82
|
-
this.onJobComplete(rid, job, retries,
|
|
84
|
+
this.onJobComplete(rid, job, retries, chalk.bold.green('PASSED'));
|
|
83
85
|
}
|
|
84
86
|
onSpecFailure(rid, job, retries = 0) {
|
|
85
|
-
this.onJobComplete(rid, job, retries,
|
|
87
|
+
this.onJobComplete(rid, job, retries, chalk.bold.red('FAILED'));
|
|
86
88
|
}
|
|
87
89
|
onSpecSkip(rid, job) {
|
|
88
90
|
this.onJobComplete(rid, job, 0, 'SKIPPED', log.info);
|
|
@@ -90,7 +92,7 @@ class WDIOCLInterface extends events_1.EventEmitter {
|
|
|
90
92
|
onJobComplete(cid, job, retries = 0, message = '', _logger = this.log) {
|
|
91
93
|
const details = [`[${cid}]`, message];
|
|
92
94
|
if (job) {
|
|
93
|
-
details.push('in',
|
|
95
|
+
details.push('in', getRunnerName(job.caps), this.getFilenames(job.specs));
|
|
94
96
|
}
|
|
95
97
|
if (retries > 0) {
|
|
96
98
|
details.push(`(${retries} retries)`);
|
|
@@ -98,13 +100,12 @@ class WDIOCLInterface extends events_1.EventEmitter {
|
|
|
98
100
|
return _logger(...details);
|
|
99
101
|
}
|
|
100
102
|
onTestError(payload) {
|
|
101
|
-
var _a, _b, _c;
|
|
102
103
|
const error = {
|
|
103
|
-
type:
|
|
104
|
-
message:
|
|
105
|
-
stack:
|
|
104
|
+
type: payload.error?.type || 'Error',
|
|
105
|
+
message: payload.error?.message || (typeof payload.error === 'string' ? payload.error : 'Unknown error.'),
|
|
106
|
+
stack: payload.error?.stack
|
|
106
107
|
};
|
|
107
|
-
return this.log(`[${payload.cid}]`, `${
|
|
108
|
+
return this.log(`[${payload.cid}]`, `${chalk.red(error.type)} in "${payload.fullTitle}"\n${chalk.red(error.stack || error.message)}`);
|
|
108
109
|
}
|
|
109
110
|
getFilenames(specs = []) {
|
|
110
111
|
if (specs.length > 0) {
|
|
@@ -161,18 +162,20 @@ class WDIOCLInterface extends events_1.EventEmitter {
|
|
|
161
162
|
return args;
|
|
162
163
|
}
|
|
163
164
|
logHookError(error) {
|
|
164
|
-
return this.log(`${
|
|
165
|
+
return this.log(`${chalk.red(error.name)} in "${error.origin}"\n${chalk.red(error.stack || error.message)}`);
|
|
165
166
|
}
|
|
166
167
|
/**
|
|
167
168
|
* event handler that is triggered when runner sends up events
|
|
168
169
|
*/
|
|
169
170
|
onMessage(event) {
|
|
171
|
+
// let a = true
|
|
172
|
+
// if (a) return
|
|
170
173
|
if (event.name === 'reporterRealTime') {
|
|
171
174
|
this.log(event.content);
|
|
172
175
|
return;
|
|
173
176
|
}
|
|
174
177
|
if (event.origin === 'debugger' && event.name === 'start') {
|
|
175
|
-
this.log(
|
|
178
|
+
this.log(chalk.yellow(event.params.introMessage));
|
|
176
179
|
this._inDebugMode = true;
|
|
177
180
|
return this._inDebugMode;
|
|
178
181
|
}
|
|
@@ -183,13 +186,16 @@ class WDIOCLInterface extends events_1.EventEmitter {
|
|
|
183
186
|
if (event.name === 'testFrameworkInit') {
|
|
184
187
|
return this.emit('job:start', event.content);
|
|
185
188
|
}
|
|
186
|
-
if (
|
|
187
|
-
return log.
|
|
188
|
-
}
|
|
189
|
-
if (event.origin === 'worker' && event.name === 'error') {
|
|
190
|
-
return this.log(`[${event.cid}]`, chalk_1.default.white.bgRed.bold(' Error: '), event.content.message || event.content.stack || event.content);
|
|
189
|
+
if (event.name === 'error') {
|
|
190
|
+
return this.log(`[${event.cid}]`, chalk.white.bgRed.bold(' Error: '), event.content ? (event.content.message || event.content.stack || event.content) : '');
|
|
191
191
|
}
|
|
192
192
|
if (event.origin !== 'reporter' && event.origin !== 'debugger') {
|
|
193
|
+
/**
|
|
194
|
+
* filter certain events though
|
|
195
|
+
*/
|
|
196
|
+
if (EVENT_FILTER.includes(event.name)) {
|
|
197
|
+
return;
|
|
198
|
+
}
|
|
193
199
|
return this.log(event.cid, event.origin, event.name, event.content);
|
|
194
200
|
}
|
|
195
201
|
if (event.name === 'printFailureMessage') {
|
|
@@ -224,18 +230,18 @@ class WDIOCLInterface extends events_1.EventEmitter {
|
|
|
224
230
|
const reporter = this._messages.reporter;
|
|
225
231
|
this._messages.reporter = {};
|
|
226
232
|
for (const [reporterName, messages] of Object.entries(reporter)) {
|
|
227
|
-
this.log('\n',
|
|
233
|
+
this.log('\n', chalk.bold.magenta(`"${reporterName}" Reporter:`));
|
|
228
234
|
this.log(messages.join(''));
|
|
229
235
|
}
|
|
230
236
|
}
|
|
231
237
|
printSummary() {
|
|
232
238
|
const totalJobs = this.totalWorkerCnt - this.result.retries;
|
|
233
239
|
const elapsed = (new Date(Date.now() - this._start.getTime())).toUTCString().match(/(\d\d:\d\d:\d\d)/)[0];
|
|
234
|
-
const retries = this.result.retries ?
|
|
235
|
-
const failed = this.result.failed ?
|
|
236
|
-
const skipped = this._skippedSpecs > 0 ?
|
|
240
|
+
const retries = this.result.retries ? chalk.yellow(this.result.retries, 'retries') + ', ' : '';
|
|
241
|
+
const failed = this.result.failed ? chalk.red(this.result.failed, 'failed') + ', ' : '';
|
|
242
|
+
const skipped = this._skippedSpecs > 0 ? chalk.gray(this._skippedSpecs, 'skipped') + ', ' : '';
|
|
237
243
|
const percentCompleted = totalJobs ? Math.round(this.result.finished / totalJobs * 100) : 0;
|
|
238
|
-
return this.log('\nSpec Files:\t',
|
|
244
|
+
return this.log('\nSpec Files:\t', chalk.green(this.result.passed, 'passed') + ', ' + retries + failed + skipped + totalJobs, 'total', `(${percentCompleted}% completed)`, 'in', elapsed, '\n');
|
|
239
245
|
}
|
|
240
246
|
finalise() {
|
|
241
247
|
if (this._isWatchMode) {
|
|
@@ -245,4 +251,3 @@ class WDIOCLInterface extends events_1.EventEmitter {
|
|
|
245
251
|
this.printSummary();
|
|
246
252
|
}
|
|
247
253
|
}
|
|
248
|
-
exports.default = WDIOCLInterface;
|
package/build/launcher.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { ConfigParser } from '@wdio/config';
|
|
2
2
|
import type { Options, Capabilities, Services } from '@wdio/types';
|
|
3
|
-
import CLInterface from './interface';
|
|
4
|
-
import { RunCommandArguments } from './types';
|
|
3
|
+
import CLInterface from './interface.js';
|
|
4
|
+
import type { RunCommandArguments } from './types';
|
|
5
5
|
interface EndMessage {
|
|
6
6
|
cid: string;
|
|
7
7
|
exitCode: number;
|
|
@@ -14,8 +14,8 @@ declare class Launcher {
|
|
|
14
14
|
private _isWatchMode;
|
|
15
15
|
configParser: ConfigParser;
|
|
16
16
|
isMultiremote: boolean;
|
|
17
|
-
runner
|
|
18
|
-
interface
|
|
17
|
+
runner?: Services.RunnerInstance;
|
|
18
|
+
interface?: CLInterface;
|
|
19
19
|
private _exitCode;
|
|
20
20
|
private _hasTriggeredExitRoutine;
|
|
21
21
|
private _schedule;
|
package/build/launcher.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"launcher.d.ts","sourceRoot":"","sources":["../src/launcher.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,YAAY,EAAE,MAAM,cAAc,CAAA;AAE3C,OAAO,KAAK,EAAE,OAAO,EAAE,YAAY,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AAElE,OAAO,WAAW,MAAM,
|
|
1
|
+
{"version":3,"file":"launcher.d.ts","sourceRoot":"","sources":["../src/launcher.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,YAAY,EAAE,MAAM,cAAc,CAAA;AAE3C,OAAO,KAAK,EAAE,OAAO,EAAE,YAAY,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AAElE,OAAO,WAAW,MAAM,gBAAgB,CAAA;AAExC,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,SAAS,CAAA;AAkBlD,UAAU,UAAU;IAChB,GAAG,EAAE,MAAM,CAAC;IACZ,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB,OAAO,EAAE,MAAM,CAAA;CAClB;AAED,cAAM,QAAQ;IAiBN,OAAO,CAAC,eAAe;IACvB,OAAO,CAAC,KAAK;IACb,OAAO,CAAC,YAAY;IAlBjB,YAAY,eAAqB;IACjC,aAAa,UAAQ;IACrB,MAAM,CAAC,EAAE,QAAQ,CAAC,cAAc,CAAA;IAChC,SAAS,CAAC,EAAE,WAAW,CAAA;IAE9B,OAAO,CAAC,SAAS,CAAI;IACrB,OAAO,CAAC,wBAAwB,CAAQ;IACxC,OAAO,CAAC,SAAS,CAAiB;IAClC,OAAO,CAAC,IAAI,CAAe;IAC3B,OAAO,CAAC,cAAc,CAAI;IAC1B,OAAO,CAAC,aAAa,CAAI;IAEzB,OAAO,CAAC,SAAS,CAAC,CAA4B;IAC9C,OAAO,CAAC,QAAQ,CAAC,CAAU;gBAGf,eAAe,EAAE,MAAM,EACvB,KAAK,GAAE,OAAO,CAAC,mBAAmB,CAAM,EACxC,YAAY,UAAQ;IAUhC;;;OAGG;IACG,GAAG;IAgGT;;OAEG;IACH,OAAO,CAAE,MAAM,EAAE,QAAQ,CAAC,OAAO,CAAC,UAAU,CAAC,EAAE,IAAI,EAAE,YAAY,CAAC,kBAAkB,GAAG,OAAO,CAAC,MAAM,CAAC;IAyEtG;;OAEG;IACH,WAAW,CAAC,YAAY,EAAE,CAAC,YAAY,CAAC,mBAAmB,GAAG,YAAY,CAAC,eAAe,GAAG,YAAY,CAAC,kBAAkB,CAAC,EAAE,eAAe,EAAE,MAAM;;;;IAetJ;;;OAGG;IACH,QAAQ;IAmER;;;OAGG;IACH,2BAA2B;IAI3B;;;OAGG;IACH,oBAAoB;IAIpB;;;;;;OAMG;IACG,aAAa,CACf,KAAK,EAAE,MAAM,EAAE,EACf,IAAI,EAAE,YAAY,CAAC,mBAAmB,GAAG,YAAY,CAAC,eAAe,GAAG,YAAY,CAAC,uBAAuB,EAC5G,GAAG,EAAE,MAAM,EACX,GAAG,EAAE,MAAM,GAAG,SAAS,EACvB,OAAO,EAAE,MAAM;IAyFnB,OAAO,CAAC,gBAAgB;IAWxB;;;;OAIG;IACH,WAAW,CAAE,GAAG,EAAE,MAAM;IAOxB;;;;;;OAMG;IACG,UAAU,CAAC,EAAE,GAAG,EAAE,GAAG,EAAE,QAAQ,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE,UAAU;IAkDnE;;;;;OAKG;IACH,WAAW,CAAE,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,IAAI,KAAK,IAAI;IAc7C;;;OAGG;IACH,OAAO,CAAC,kBAAkB;CAG7B;AAED,eAAe,QAAQ,CAAA"}
|
package/build/launcher.js
CHANGED
|
@@ -1,38 +1,47 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
const
|
|
10
|
-
const config_1 = require("@wdio/config");
|
|
11
|
-
const utils_1 = require("@wdio/utils");
|
|
12
|
-
const interface_1 = __importDefault(require("./interface"));
|
|
13
|
-
const utils_2 = require("./utils");
|
|
14
|
-
const log = (0, logger_1.default)('@wdio/cli:launcher');
|
|
1
|
+
import fs from 'node:fs/promises';
|
|
2
|
+
import path from 'node:path';
|
|
3
|
+
import exitHook from 'async-exit-hook';
|
|
4
|
+
import logger from '@wdio/logger';
|
|
5
|
+
import { ConfigParser } from '@wdio/config';
|
|
6
|
+
import { initialisePlugin, initialiseLauncherService, sleep } from '@wdio/utils';
|
|
7
|
+
import CLInterface from './interface.js';
|
|
8
|
+
import { runLauncherHook, runOnCompleteHook, runServiceHook } from './utils.js';
|
|
9
|
+
const log = logger('@wdio/cli:launcher');
|
|
15
10
|
class Launcher {
|
|
11
|
+
_configFilePath;
|
|
12
|
+
_args;
|
|
13
|
+
_isWatchMode;
|
|
14
|
+
configParser = new ConfigParser();
|
|
15
|
+
isMultiremote = false;
|
|
16
|
+
runner;
|
|
17
|
+
interface;
|
|
18
|
+
_exitCode = 0;
|
|
19
|
+
_hasTriggeredExitRoutine = false;
|
|
20
|
+
_schedule = [];
|
|
21
|
+
_rid = [];
|
|
22
|
+
_runnerStarted = 0;
|
|
23
|
+
_runnerFailed = 0;
|
|
24
|
+
_launcher;
|
|
25
|
+
_resolve;
|
|
16
26
|
constructor(_configFilePath, _args = {}, _isWatchMode = false) {
|
|
17
27
|
this._configFilePath = _configFilePath;
|
|
18
28
|
this._args = _args;
|
|
19
29
|
this._isWatchMode = _isWatchMode;
|
|
20
|
-
this._exitCode = 0;
|
|
21
|
-
this._hasTriggeredExitRoutine = false;
|
|
22
|
-
this._schedule = [];
|
|
23
|
-
this._rid = [];
|
|
24
|
-
this._runnerStarted = 0;
|
|
25
|
-
this._runnerFailed = 0;
|
|
26
|
-
this.configParser = new config_1.ConfigParser();
|
|
27
30
|
/**
|
|
28
31
|
* merge auto compile opts to understand how to parse the config
|
|
29
32
|
*/
|
|
30
33
|
if (_args.autoCompileOpts) {
|
|
31
34
|
this.configParser.merge({ autoCompileOpts: _args.autoCompileOpts });
|
|
32
35
|
}
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* run sequence
|
|
39
|
+
* @return {Promise} that only gets resolves with either an exitCode or an error
|
|
40
|
+
*/
|
|
41
|
+
async run() {
|
|
42
|
+
await this.configParser.autoCompile();
|
|
43
|
+
await this.configParser.addConfigFile(this._configFilePath);
|
|
44
|
+
this.configParser.merge(this._args);
|
|
36
45
|
const config = this.configParser.getConfig();
|
|
37
46
|
/**
|
|
38
47
|
* assign parsed autocompile options into args so it can be used within the worker
|
|
@@ -42,35 +51,29 @@ class Launcher {
|
|
|
42
51
|
const capabilities = this.configParser.getCapabilities();
|
|
43
52
|
this.isMultiremote = !Array.isArray(capabilities);
|
|
44
53
|
if (config.outputDir) {
|
|
45
|
-
|
|
46
|
-
process.env.WDIO_LOG_PATH =
|
|
54
|
+
await fs.mkdir(path.join(config.outputDir), { recursive: true });
|
|
55
|
+
process.env.WDIO_LOG_PATH = path.join(config.outputDir, 'wdio.log');
|
|
47
56
|
}
|
|
48
|
-
|
|
57
|
+
logger.setLogLevelsConfig(config.logLevels, config.logLevel);
|
|
49
58
|
const totalWorkerCnt = Array.isArray(capabilities)
|
|
50
59
|
? capabilities
|
|
51
60
|
.map((c) => this.configParser.getSpecs(c.specs, c.exclude).length)
|
|
52
61
|
.reduce((a, b) => a + b, 0)
|
|
53
62
|
: 1;
|
|
54
|
-
|
|
55
|
-
this.runner = new Runner(_configFilePath, config);
|
|
56
|
-
this.interface = new interface_1.default(config, totalWorkerCnt, this._isWatchMode);
|
|
63
|
+
this.interface = new CLInterface(config, totalWorkerCnt, this._isWatchMode);
|
|
57
64
|
config.runnerEnv.FORCE_COLOR = Number(this.interface.hasAnsiSupport);
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
* @return {Promise} that only gets resolves with either an exitCode or an error
|
|
62
|
-
*/
|
|
63
|
-
async run() {
|
|
65
|
+
const [runnerName, runnerOptions] = Array.isArray(config.runner) ? config.runner : [config.runner, {}];
|
|
66
|
+
const Runner = (await initialisePlugin(runnerName, 'runner')).default;
|
|
67
|
+
this.runner = new Runner(runnerOptions, config);
|
|
64
68
|
/**
|
|
65
69
|
* catches ctrl+c event
|
|
66
70
|
*/
|
|
67
|
-
(
|
|
71
|
+
exitHook(this.exitHandler.bind(this));
|
|
68
72
|
let exitCode = 0;
|
|
69
73
|
let error = undefined;
|
|
70
74
|
try {
|
|
71
|
-
const config = this.configParser.getConfig();
|
|
72
75
|
const caps = this.configParser.getCapabilities();
|
|
73
|
-
const { ignoredWorkerServices, launcherServices } =
|
|
76
|
+
const { ignoredWorkerServices, launcherServices } = await initialiseLauncherService(config, caps);
|
|
74
77
|
this._launcher = launcherServices;
|
|
75
78
|
this._args.ignoredWorkerServices = ignoredWorkerServices;
|
|
76
79
|
/**
|
|
@@ -82,8 +85,8 @@ class Launcher {
|
|
|
82
85
|
* run onPrepare hook
|
|
83
86
|
*/
|
|
84
87
|
log.info('Run onPrepare hook');
|
|
85
|
-
await
|
|
86
|
-
await
|
|
88
|
+
await runLauncherHook(config.onPrepare, config, caps);
|
|
89
|
+
await runServiceHook(this._launcher, 'onPrepare', config, caps);
|
|
87
90
|
exitCode = await this.runMode(config, caps);
|
|
88
91
|
/**
|
|
89
92
|
* run onComplete hook
|
|
@@ -93,11 +96,11 @@ class Launcher {
|
|
|
93
96
|
* available running hooks in this order
|
|
94
97
|
*/
|
|
95
98
|
log.info('Run onComplete hook');
|
|
96
|
-
const onCompleteResults = await
|
|
97
|
-
await
|
|
99
|
+
const onCompleteResults = await runOnCompleteHook(config.onComplete, config, caps, exitCode, this.interface.result);
|
|
100
|
+
await runServiceHook(this._launcher, 'onComplete', exitCode, config, caps);
|
|
98
101
|
// if any of the onComplete hooks failed, update the exit code
|
|
99
102
|
exitCode = onCompleteResults.includes(1) ? 1 : exitCode;
|
|
100
|
-
await
|
|
103
|
+
await logger.waitForBuffer();
|
|
101
104
|
this.interface.finalise();
|
|
102
105
|
}
|
|
103
106
|
catch (err) {
|
|
@@ -153,11 +156,17 @@ class Launcher {
|
|
|
153
156
|
* Regular mode
|
|
154
157
|
*/
|
|
155
158
|
for (let capabilities of caps) {
|
|
159
|
+
/**
|
|
160
|
+
* when using browser runner we only allow one session per browser
|
|
161
|
+
*/
|
|
162
|
+
const availableInstances = config.runner === 'browser'
|
|
163
|
+
? 1
|
|
164
|
+
: capabilities.maxInstances || config.maxInstancesPerCapability;
|
|
156
165
|
this._schedule.push({
|
|
157
166
|
cid: cid++,
|
|
158
167
|
caps: capabilities,
|
|
159
168
|
specs: this.formatSpecs(capabilities, specFileRetries),
|
|
160
|
-
availableInstances
|
|
169
|
+
availableInstances,
|
|
161
170
|
runningInstances: 0
|
|
162
171
|
});
|
|
163
172
|
}
|
|
@@ -183,8 +192,7 @@ class Launcher {
|
|
|
183
192
|
* Format the specs into an array of objects with files and retries
|
|
184
193
|
*/
|
|
185
194
|
formatSpecs(capabilities, specFileRetries) {
|
|
186
|
-
|
|
187
|
-
files = this.configParser.getSpecs(capabilities.specs, capabilities.exclude);
|
|
195
|
+
const files = this.configParser.getSpecs(capabilities.specs, capabilities.exclude);
|
|
188
196
|
return files.map(file => {
|
|
189
197
|
if (typeof file === 'string') {
|
|
190
198
|
return { files: [file], retries: specFileRetries };
|
|
@@ -276,10 +284,13 @@ class Launcher {
|
|
|
276
284
|
* @param {Number} retries Number of retries remaining
|
|
277
285
|
*/
|
|
278
286
|
async startInstance(specs, caps, cid, rid, retries) {
|
|
287
|
+
if (!this.runner || !this.interface) {
|
|
288
|
+
throw new Error('Internal Error: no runner initialised, call run() first');
|
|
289
|
+
}
|
|
279
290
|
let config = this.configParser.getConfig();
|
|
280
291
|
// wait before retrying the spec file
|
|
281
292
|
if (typeof config.specFileRetriesDelay === 'number' && config.specFileRetries > 0 && config.specFileRetries !== retries) {
|
|
282
|
-
await
|
|
293
|
+
await sleep(config.specFileRetriesDelay * 1000);
|
|
283
294
|
}
|
|
284
295
|
// Retried tests receive the cid of the failing test as rid
|
|
285
296
|
// so they can run with the same cid of the failing test.
|
|
@@ -313,25 +324,31 @@ class Launcher {
|
|
|
313
324
|
let defaultArgs = (capExecArgs.length) ? process.execArgv : [];
|
|
314
325
|
// If an arg appears multiple times the last occurrence is used
|
|
315
326
|
let execArgv = [...defaultArgs, ...debugArgs, ...capExecArgs];
|
|
316
|
-
// set '--no-wasm-code-gc' deliberatively as it causes problems with
|
|
317
|
-
// @wdio/sync and recent TypeScript compiles
|
|
318
|
-
if (!execArgv.includes('--no-wasm-code-gc')) {
|
|
319
|
-
execArgv.push('--no-wasm-code-gc');
|
|
320
|
-
}
|
|
321
327
|
// bump up worker count
|
|
322
328
|
this._runnerStarted++;
|
|
323
329
|
// run worker hook to allow modify runtime and capabilities of a specific worker
|
|
324
330
|
log.info('Run onWorkerStart hook');
|
|
325
|
-
await
|
|
331
|
+
await runLauncherHook(config.onWorkerStart, runnerId, caps, specs, this._args, execArgv)
|
|
326
332
|
.catch((error) => this._workerHookError(error));
|
|
327
|
-
await
|
|
333
|
+
await runServiceHook(this._launcher, 'onWorkerStart', runnerId, caps, specs, this._args, execArgv)
|
|
328
334
|
.catch((error) => this._workerHookError(error));
|
|
329
335
|
// prefer launcher settings in capabilities over general launcher
|
|
330
336
|
const worker = this.runner.run({
|
|
331
337
|
cid: runnerId,
|
|
332
338
|
command: 'run',
|
|
333
339
|
configFile: this._configFilePath,
|
|
334
|
-
args: {
|
|
340
|
+
args: {
|
|
341
|
+
...this._args,
|
|
342
|
+
...(config?.autoCompileOpts
|
|
343
|
+
? { autoCompileOpts: config.autoCompileOpts }
|
|
344
|
+
: {}),
|
|
345
|
+
/**
|
|
346
|
+
* Pass on user and key values to ensure they are available in the worker process when using
|
|
347
|
+
* environment variables that were locally exported but not part of the environment.
|
|
348
|
+
*/
|
|
349
|
+
user: config.user,
|
|
350
|
+
key: config.key
|
|
351
|
+
},
|
|
335
352
|
caps,
|
|
336
353
|
specs,
|
|
337
354
|
execArgv,
|
|
@@ -342,6 +359,9 @@ class Launcher {
|
|
|
342
359
|
worker.on('exit', this.endHandler.bind(this));
|
|
343
360
|
}
|
|
344
361
|
_workerHookError(error) {
|
|
362
|
+
if (!this.interface) {
|
|
363
|
+
throw new Error('Internal Error: no interface initialised, call run() first');
|
|
364
|
+
}
|
|
345
365
|
this.interface.logHookError(error);
|
|
346
366
|
if (this._resolve) {
|
|
347
367
|
this._resolve(1);
|
|
@@ -379,7 +399,7 @@ class Launcher {
|
|
|
379
399
|
/**
|
|
380
400
|
* avoid emitting job:end if watch mode has been stopped by user
|
|
381
401
|
*/
|
|
382
|
-
if (!this._isWatchModeHalted()) {
|
|
402
|
+
if (!this._isWatchModeHalted() && this.interface) {
|
|
383
403
|
this.interface.emit('job:end', { cid: rid, passed, retries });
|
|
384
404
|
}
|
|
385
405
|
/**
|
|
@@ -391,9 +411,9 @@ class Launcher {
|
|
|
391
411
|
this._schedule[cid].runningInstances--;
|
|
392
412
|
log.info('Run onWorkerEnd hook');
|
|
393
413
|
const config = this.configParser.getConfig();
|
|
394
|
-
await
|
|
414
|
+
await runLauncherHook(config.onWorkerEnd, rid, exitCode, specs, retries)
|
|
395
415
|
.catch((error) => this._workerHookError(error));
|
|
396
|
-
await
|
|
416
|
+
await runServiceHook(this._launcher, 'onWorkerEnd', rid, exitCode, specs, retries)
|
|
397
417
|
.catch((error) => this._workerHookError(error));
|
|
398
418
|
/**
|
|
399
419
|
* do nothing if
|
|
@@ -415,7 +435,7 @@ class Launcher {
|
|
|
415
435
|
* session first before killing
|
|
416
436
|
*/
|
|
417
437
|
exitHandler(callback) {
|
|
418
|
-
if (!callback) {
|
|
438
|
+
if (!callback || !this.runner || !this.interface) {
|
|
419
439
|
return;
|
|
420
440
|
}
|
|
421
441
|
if (this._hasTriggeredExitRoutine) {
|
|
@@ -433,4 +453,4 @@ class Launcher {
|
|
|
433
453
|
return this._isWatchMode && this._hasTriggeredExitRoutine;
|
|
434
454
|
}
|
|
435
455
|
}
|
|
436
|
-
|
|
456
|
+
export default Launcher;
|
package/build/types.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { Options, Reporters } from '@wdio/types';
|
|
2
|
-
import { BACKEND_CHOICES, REGION_OPTION, COMPILER_OPTION_ANSWERS } from './constants';
|
|
1
|
+
import type { Options, Reporters } from '@wdio/types';
|
|
2
|
+
import type { BACKEND_CHOICES, REGION_OPTION, COMPILER_OPTION_ANSWERS } from './constants';
|
|
3
3
|
declare type ValueOf<T> = T[keyof T];
|
|
4
4
|
export interface Questionnair {
|
|
5
5
|
runner: 'local';
|
package/build/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAA;
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
|
package/build/types.js
CHANGED
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
1
|
+
export {};
|
package/build/utils.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { SevereServiceError } from 'webdriverio';
|
|
2
2
|
import type { Options, Capabilities, Services } from '@wdio/types';
|
|
3
|
-
import { ReplCommandArguments, Questionnair, SupportedPackage, OnCompleteResult, ParsedAnswers } from './types';
|
|
3
|
+
import type { ReplCommandArguments, Questionnair, SupportedPackage, OnCompleteResult, ParsedAnswers } from './types';
|
|
4
4
|
export declare class HookError extends SevereServiceError {
|
|
5
5
|
origin: string;
|
|
6
6
|
constructor(message: string, origin: string);
|
|
@@ -90,4 +90,11 @@ export declare function getPathForFileGeneration(answers: Questionnair): {
|
|
|
90
90
|
relativePath: string;
|
|
91
91
|
};
|
|
92
92
|
export declare function getDefaultFiles(answers: Partial<Questionnair>, filePath: string): string;
|
|
93
|
+
/**
|
|
94
|
+
* Ensure core WebdriverIO packages have the same version as cli so that if someone
|
|
95
|
+
* installs `@wdio/cli@next` and runs the wizard, all related packages have the same version.
|
|
96
|
+
* running `matchAll` to a version like "8.0.0-alpha.249+4bc237701", results in:
|
|
97
|
+
* ['8.0.0-alpha.249+4bc237701', '8', '0', '0', 'alpha', '249', '4bc237701']
|
|
98
|
+
*/
|
|
99
|
+
export declare function specifyVersionIfNeeded(packagesToInstall: string[], version: string): string[];
|
|
93
100
|
//# sourceMappingURL=utils.d.ts.map
|
package/build/utils.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../src/utils.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../src/utils.ts"],"names":[],"mappings":"AAcA,OAAO,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAA;AAGhD,OAAO,KAAK,EAAE,OAAO,EAAE,YAAY,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AAGlE,OAAO,KAAK,EAAE,oBAAoB,EAAE,YAAY,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,aAAa,EAAE,MAAM,SAAS,CAAA;AAUpH,qBAAa,SAAU,SAAQ,kBAAkB;IACtC,MAAM,EAAE,MAAM,CAAA;gBACT,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM;CAI9C;AAED;;GAEG;AACH,wBAAsB,cAAc,CAChC,QAAQ,EAAE,QAAQ,CAAC,eAAe,EAAE,EACpC,QAAQ,EAAE,MAAM,QAAQ,CAAC,aAAa,EACtC,GAAG,IAAI,EAAE,GAAG,EAAE,sBA2BjB;AAED;;;;;GAKG;AACH,wBAAsB,eAAe,CAAC,IAAI,EAAE,QAAQ,GAAG,QAAQ,EAAE,EAAE,GAAG,IAAI,EAAE,GAAG,EAAE,yBAmBhF;AAED;;;;;;;GAOG;AACH,wBAAsB,iBAAiB,CACnC,cAAc,EAAE,QAAQ,GAAG,QAAQ,EAAE,EACrC,MAAM,EAAE,OAAO,CAAC,UAAU,EAC1B,YAAY,EAAE,YAAY,CAAC,kBAAkB,EAC7C,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,gBAAgB,sBAkB5B;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAE,IAAI,GAAE,YAAY,CAAC,mBAAwB,UAkBzE;AAoBD,wBAAgB,YAAY,CAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,2BASzD;AAED,wBAAgB,aAAa,CAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,sBAYxE;AAED,wBAAgB,cAAc,CAAC,KAAK,EAAE,gBAAgB,EAAE,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,MAAM,UAAQ,QAmC3F;AAED;;GAEG;AACH,wBAAgB,0BAA0B,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,SAAS,GAAG,gBAAgB,CAMvF;AAED,wBAAsB,uBAAuB,CAAE,OAAO,EAAE,aAAa,iBAWpE;AAED,eAAO,MAAM,sBAAsB,YAAa,MAAM,EAAE,KAAG,OAAO,GAAG,MAgBpE,CAAA;AAED,wBAAgB,eAAe,CAAC,GAAG,EAAE,oBAAoB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAgDxD;AAED;;;GAGG;AACH,wBAAgB,OAAO,CAAE,QAAQ,EAAE,MAAM,WAOxC;AAED;;;GAGG;AACH,wBAAgB,UAAU,CAAE,GAAG,EAAE,MAAM,WActC;AAED;;GAEG;AACH,wBAAsB,iBAAiB,CAAE,OAAO,EAAE,aAAa,iBA6B9D;AAED,wBAAsB,UAAU,CAAC,GAAG,EAAE,OAAO,GAAG,OAAO,CAAC,YAAY,CAAC,CA2BpE;AAED,wBAAgB,wBAAwB,CAAE,OAAO,EAAE,YAAY;;;;;EA+B9D;AAED,wBAAgB,eAAe,CAAE,OAAO,EAAE,OAAO,CAAC,YAAY,CAAC,EAAE,QAAQ,EAAE,MAAM,UAIhF;AAED;;;;;GAKG;AACH,wBAAgB,sBAAsB,CAAE,iBAAiB,EAAE,MAAM,EAAE,EAAE,OAAO,EAAE,MAAM,YAgBnF"}
|