codeceptjs 3.6.6 → 4.0.0-beta.1
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/codecept.js +81 -84
- package/lib/actor.js +13 -13
- package/lib/ai.js +13 -10
- package/lib/assert/empty.js +21 -20
- package/lib/assert/equal.js +39 -37
- package/lib/assert/error.js +14 -14
- package/lib/assert/include.js +47 -46
- package/lib/assert/throws.js +11 -13
- package/lib/assert/truth.js +22 -19
- package/lib/assert.js +2 -4
- package/lib/cli.js +49 -57
- package/lib/codecept.js +155 -142
- package/lib/colorUtils.js +3 -3
- package/lib/command/configMigrate.js +52 -58
- package/lib/command/definitions.js +89 -88
- package/lib/command/dryRun.js +68 -71
- package/lib/command/generate.js +188 -197
- package/lib/command/gherkin/init.js +16 -27
- package/lib/command/gherkin/snippets.js +20 -20
- package/lib/command/gherkin/steps.js +8 -8
- package/lib/command/info.js +38 -40
- package/lib/command/init.js +288 -290
- package/lib/command/interactive.js +32 -32
- package/lib/command/list.js +26 -26
- package/lib/command/run-multiple/chunk.js +5 -5
- package/lib/command/run-multiple/collection.js +3 -3
- package/lib/command/run-multiple/run.js +2 -6
- package/lib/command/run-multiple.js +93 -113
- package/lib/command/run-rerun.js +25 -20
- package/lib/command/run-workers.js +66 -64
- package/lib/command/run.js +29 -26
- package/lib/command/utils.js +65 -80
- package/lib/command/workers/runTests.js +10 -10
- package/lib/config.js +9 -10
- package/lib/container.js +48 -40
- package/lib/data/context.js +59 -60
- package/lib/data/dataScenarioConfig.js +47 -47
- package/lib/data/dataTableArgument.js +29 -29
- package/lib/data/table.js +20 -26
- package/lib/dirname.js +5 -0
- package/lib/event.js +167 -163
- package/lib/heal.js +17 -13
- package/lib/helper/AI.js +41 -130
- package/lib/helper/ApiDataFactory.js +69 -73
- package/lib/helper/Appium.js +381 -412
- package/lib/helper/Expect.js +425 -0
- package/lib/helper/ExpectHelper.js +48 -40
- package/lib/helper/FileSystem.js +79 -80
- package/lib/helper/GraphQL.js +43 -44
- package/lib/helper/GraphQLDataFactory.js +50 -50
- package/lib/helper/JSONResponse.js +62 -65
- package/lib/helper/Mochawesome.js +28 -28
- package/lib/helper/MockServer.js +14 -12
- package/lib/helper/Nightmare.js +566 -662
- package/lib/helper/Playwright.js +1216 -1361
- package/lib/helper/Protractor.js +627 -663
- package/lib/helper/Puppeteer.js +1128 -1231
- package/lib/helper/REST.js +68 -159
- package/lib/helper/SoftExpectHelper.js +2 -2
- package/lib/helper/TestCafe.js +484 -490
- package/lib/helper/WebDriver.js +1156 -1297
- package/lib/helper/clientscripts/PollyWebDriverExt.js +1 -1
- package/lib/helper/errors/ConnectionRefused.js +1 -1
- package/lib/helper/errors/ElementAssertion.js +2 -2
- package/lib/helper/errors/ElementNotFound.js +2 -2
- package/lib/helper/errors/RemoteBrowserConnectionRefused.js +1 -1
- package/lib/helper/extras/Console.js +1 -1
- package/lib/helper/extras/PlaywrightPropEngine.js +2 -2
- package/lib/helper/extras/PlaywrightReactVueLocator.js +1 -1
- package/lib/helper/extras/PlaywrightRestartOpts.js +18 -21
- package/lib/helper/extras/Popup.js +1 -1
- package/lib/helper/extras/React.js +3 -3
- package/lib/helper/network/actions.js +7 -14
- package/lib/helper/network/utils.js +2 -3
- package/lib/helper/scripts/blurElement.js +1 -1
- package/lib/helper/scripts/focusElement.js +1 -1
- package/lib/helper/scripts/highlightElement.js +1 -1
- package/lib/helper/scripts/isElementClickable.js +1 -1
- package/lib/helper/testcafe/testControllerHolder.js +1 -1
- package/lib/helper/testcafe/testcafe-utils.js +7 -6
- package/lib/helper.js +3 -1
- package/lib/history.js +5 -6
- package/lib/hooks.js +6 -6
- package/lib/html.js +7 -7
- package/lib/index.js +41 -25
- package/lib/interfaces/bdd.js +64 -47
- package/lib/interfaces/featureConfig.js +19 -19
- package/lib/interfaces/gherkin.js +118 -124
- package/lib/interfaces/scenarioConfig.js +29 -29
- package/lib/listener/artifacts.js +9 -9
- package/lib/listener/config.js +24 -24
- package/lib/listener/exit.js +12 -12
- package/lib/listener/helpers.js +42 -42
- package/lib/listener/mocha.js +11 -11
- package/lib/listener/retry.js +30 -32
- package/lib/listener/steps.js +53 -50
- package/lib/listener/timeout.js +54 -54
- package/lib/locator.js +10 -6
- package/lib/mochaFactory.js +15 -18
- package/lib/output.js +10 -6
- package/lib/parser.js +12 -15
- package/lib/pause.js +33 -40
- package/lib/plugin/allure.js +15 -15
- package/lib/plugin/autoDelay.js +37 -29
- package/lib/plugin/autoLogin.js +65 -70
- package/lib/plugin/commentStep.js +18 -18
- package/lib/plugin/coverage.js +67 -115
- package/lib/plugin/customLocator.js +20 -21
- package/lib/plugin/debugErrors.js +24 -24
- package/lib/plugin/eachElement.js +38 -38
- package/lib/plugin/fakerTransform.js +6 -6
- package/lib/plugin/heal.js +108 -67
- package/lib/plugin/pauseOnFail.js +11 -11
- package/lib/plugin/retryFailedStep.js +39 -32
- package/lib/plugin/retryTo.js +40 -46
- package/lib/plugin/screenshotOnFail.js +87 -109
- package/lib/plugin/selenoid.js +118 -131
- package/lib/plugin/standardActingHelpers.js +8 -2
- package/lib/plugin/stepByStepReport.js +91 -110
- package/lib/plugin/stepTimeout.js +23 -24
- package/lib/plugin/subtitles.js +35 -34
- package/lib/plugin/tryTo.js +30 -40
- package/lib/plugin/wdio.js +75 -78
- package/lib/recorder.js +17 -14
- package/lib/rerun.js +10 -11
- package/lib/scenario.js +23 -25
- package/lib/secret.js +2 -4
- package/lib/session.js +10 -10
- package/lib/step.js +9 -12
- package/lib/store.js +3 -2
- package/lib/transform.js +1 -1
- package/lib/translation.js +8 -7
- package/lib/ui.js +14 -12
- package/lib/utils.js +72 -70
- package/lib/within.js +10 -10
- package/lib/workerStorage.js +25 -27
- package/lib/workers.js +32 -29
- package/package.json +53 -51
- package/translations/de-DE.js +1 -1
- package/translations/fr-FR.js +1 -1
- package/translations/index.js +13 -9
- package/translations/it-IT.js +1 -1
- package/translations/ja-JP.js +1 -1
- package/translations/pl-PL.js +1 -1
- package/translations/pt-BR.js +1 -1
- package/translations/ru-RU.js +1 -1
- package/translations/zh-CN.js +1 -1
- package/translations/zh-TW.js +1 -1
- package/typings/index.d.ts +65 -415
- package/typings/promiseBasedTypes.d.ts +32 -0
- package/typings/types.d.ts +32 -0
|
@@ -1,55 +1,55 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
1
|
+
import { getConfig, getTestRoot } from './utils.js';
|
|
2
|
+
import recorder from '../recorder.js';
|
|
3
|
+
import Codecept from '../codecept.js';
|
|
4
|
+
import Container from '../container.js';
|
|
5
|
+
import * as event from '../event.js';
|
|
6
|
+
import * as output from '../output.js';
|
|
7
|
+
import webHelpers from '../plugin/standardActingHelpers.js';
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
export default async function (path, options) {
|
|
10
10
|
// Backward compatibility for --profile
|
|
11
|
-
process.profile = options.profile
|
|
12
|
-
process.env.profile = options.profile
|
|
13
|
-
const configFile = options.config
|
|
11
|
+
process.profile = options.profile;
|
|
12
|
+
process.env.profile = options.profile;
|
|
13
|
+
const configFile = options.config;
|
|
14
14
|
|
|
15
|
-
const config = getConfig(configFile)
|
|
16
|
-
const testsPath = getTestRoot(configFile)
|
|
15
|
+
const config = getConfig(configFile);
|
|
16
|
+
const testsPath = getTestRoot(configFile);
|
|
17
17
|
|
|
18
|
-
const codecept = new Codecept(config, options)
|
|
19
|
-
codecept.init(testsPath)
|
|
18
|
+
const codecept = new Codecept(config, options);
|
|
19
|
+
codecept.init(testsPath);
|
|
20
20
|
|
|
21
21
|
try {
|
|
22
|
-
await codecept.bootstrap()
|
|
22
|
+
await codecept.bootstrap();
|
|
23
23
|
|
|
24
|
-
if (options.verbose) output.level(3)
|
|
24
|
+
if (options.verbose) output.level(3);
|
|
25
25
|
|
|
26
|
-
output.print('Starting interactive shell for current suite...')
|
|
27
|
-
recorder.start()
|
|
26
|
+
output.print('Starting interactive shell for current suite...');
|
|
27
|
+
recorder.start();
|
|
28
28
|
event.emit(event.suite.before, {
|
|
29
29
|
fullTitle: () => 'Interactive Shell',
|
|
30
30
|
tests: [],
|
|
31
|
-
})
|
|
31
|
+
});
|
|
32
32
|
event.emit(event.test.before, {
|
|
33
33
|
title: '',
|
|
34
34
|
artifacts: {},
|
|
35
|
-
})
|
|
35
|
+
});
|
|
36
36
|
|
|
37
|
-
const enabledHelpers = Container.helpers()
|
|
37
|
+
const enabledHelpers = Container.helpers();
|
|
38
38
|
for (const helperName of Object.keys(enabledHelpers)) {
|
|
39
39
|
if (webHelpers.includes(helperName)) {
|
|
40
|
-
const I = enabledHelpers[helperName]
|
|
41
|
-
recorder.add(() => I.amOnPage('/'))
|
|
42
|
-
recorder.catchWithoutStop(
|
|
43
|
-
break
|
|
40
|
+
const I = enabledHelpers[helperName];
|
|
41
|
+
recorder.add(() => I.amOnPage('/'));
|
|
42
|
+
recorder.catchWithoutStop(e => output.print(`Error while loading home page: ${e.message}}`));
|
|
43
|
+
break;
|
|
44
44
|
}
|
|
45
45
|
}
|
|
46
|
-
require('../pause')()
|
|
46
|
+
require('../pause')();
|
|
47
47
|
// recorder.catchWithoutStop((err) => console.log(err.stack));
|
|
48
|
-
recorder.add(() => event.emit(event.test.after, {}))
|
|
49
|
-
recorder.add(() => event.emit(event.suite.after, {}))
|
|
50
|
-
recorder.add(() => event.emit(event.all.result, {}))
|
|
51
|
-
recorder.add(() => codecept.teardown())
|
|
48
|
+
recorder.add(() => event.emit(event.test.after, {}));
|
|
49
|
+
recorder.add(() => event.emit(event.suite.after, {}));
|
|
50
|
+
recorder.add(() => event.emit(event.all.result, {}));
|
|
51
|
+
recorder.add(() => codecept.teardown());
|
|
52
52
|
} catch (err) {
|
|
53
|
-
output.error(`Error while running bootstrap file :${err}`)
|
|
53
|
+
output.output.error(`Error while running bootstrap file :${err}`);
|
|
54
54
|
}
|
|
55
55
|
}
|
package/lib/command/list.js
CHANGED
|
@@ -1,36 +1,36 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
1
|
+
import { getConfig, getTestRoot } from './utils.js';
|
|
2
|
+
import Codecept from '../codecept.js';
|
|
3
|
+
import container from '../container.js';
|
|
4
|
+
import { getParamsToString } from '../parser.js';
|
|
5
|
+
import { methodsOfObject } from '../utils.js';
|
|
6
|
+
import * as output from '../output.js';
|
|
7
7
|
|
|
8
|
-
|
|
9
|
-
const testsPath = getTestRoot(path)
|
|
10
|
-
const config = getConfig(testsPath)
|
|
11
|
-
const codecept = new Codecept(config, {})
|
|
12
|
-
codecept.init(testsPath)
|
|
8
|
+
export default function (path) {
|
|
9
|
+
const testsPath = getTestRoot(path);
|
|
10
|
+
const config = getConfig(testsPath);
|
|
11
|
+
const codecept = new Codecept(config, {});
|
|
12
|
+
codecept.init(testsPath);
|
|
13
13
|
|
|
14
|
-
output.print('List of test actions: -- ')
|
|
15
|
-
const helpers = container.helpers()
|
|
16
|
-
const supportI = container.support('I')
|
|
17
|
-
const actions = []
|
|
14
|
+
output.print('List of test actions: -- ');
|
|
15
|
+
const helpers = container.helpers();
|
|
16
|
+
const supportI = container.support('I');
|
|
17
|
+
const actions = [];
|
|
18
18
|
for (const name in helpers) {
|
|
19
|
-
const helper = helpers[name]
|
|
19
|
+
const helper = helpers[name];
|
|
20
20
|
methodsOfObject(helper).forEach((action) => {
|
|
21
|
-
const params = getParamsToString(helper[action])
|
|
22
|
-
actions[action] = 1
|
|
23
|
-
output.print(` ${output.colors.grey(name)} I.${output.colors.bold(action)}(${params})`)
|
|
24
|
-
})
|
|
21
|
+
const params = getParamsToString(helper[action]);
|
|
22
|
+
actions[action] = 1;
|
|
23
|
+
output.print(` ${output.output.colors.grey(name)} I.${output.output.colors.bold(action)}(${params})`);
|
|
24
|
+
});
|
|
25
25
|
}
|
|
26
26
|
for (const name in supportI) {
|
|
27
27
|
if (actions[name]) {
|
|
28
|
-
continue
|
|
28
|
+
continue;
|
|
29
29
|
}
|
|
30
|
-
const actor = supportI[name]
|
|
31
|
-
const params = getParamsToString(actor)
|
|
32
|
-
output.print(` I.${output.colors.bold(name)}(${params})`)
|
|
30
|
+
const actor = supportI[name];
|
|
31
|
+
const params = getParamsToString(actor);
|
|
32
|
+
output.print(` I.${output.output.colors.bold(name)}(${params})`);
|
|
33
33
|
}
|
|
34
|
-
output.print('PS: Actions are retrieved from enabled helpers. ')
|
|
35
|
-
output.print('Implement custom actions in your helper classes.')
|
|
34
|
+
output.print('PS: Actions are retrieved from enabled helpers. ');
|
|
35
|
+
output.print('Implement custom actions in your helper classes.');
|
|
36
36
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
1
|
+
import glob from 'glob';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
import fs from 'fs';
|
|
4
4
|
|
|
5
5
|
/**
|
|
6
6
|
* Splits a list to (n) parts, defined via the size argument.
|
|
@@ -61,7 +61,7 @@ const mapFileFormats = (files) => {
|
|
|
61
61
|
* files by the passed number or executing a usder deifned function to perform
|
|
62
62
|
* the splitting.
|
|
63
63
|
*/
|
|
64
|
-
const createChunks = (config, patterns = []) => {
|
|
64
|
+
export const createChunks = (config, patterns = []) => {
|
|
65
65
|
const files = patterns.filter(pattern => !!pattern).map((pattern) => {
|
|
66
66
|
return findFiles(pattern).filter((file) => {
|
|
67
67
|
return config.grep ? grepFile(file, config.grep) : true;
|
|
@@ -86,6 +86,6 @@ const createChunks = (config, patterns = []) => {
|
|
|
86
86
|
});
|
|
87
87
|
};
|
|
88
88
|
|
|
89
|
-
|
|
89
|
+
export default {
|
|
90
90
|
createChunks,
|
|
91
91
|
};
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
import { createChunks } from './chunk.js';
|
|
2
|
+
import { createRun } from './run.js';
|
|
3
3
|
|
|
4
4
|
/**
|
|
5
5
|
* Bootstraps a collection of runs, it combines user defined selection of runs
|
|
@@ -190,6 +190,6 @@ function guessBrowser(config) {
|
|
|
190
190
|
return [config.helpers[firstHelper].browser];
|
|
191
191
|
}
|
|
192
192
|
|
|
193
|
-
|
|
193
|
+
export default {
|
|
194
194
|
createRuns,
|
|
195
195
|
};
|
|
@@ -1,206 +1,186 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
const
|
|
12
|
-
|
|
13
|
-
const
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
'verbose',
|
|
19
|
-
'config',
|
|
20
|
-
'reporter-options',
|
|
21
|
-
'grep',
|
|
22
|
-
'fgrep',
|
|
23
|
-
'invert',
|
|
24
|
-
'debug',
|
|
25
|
-
'plugins',
|
|
26
|
-
'colors',
|
|
27
|
-
]
|
|
28
|
-
let overrides = {}
|
|
1
|
+
import { fork } from 'child_process';
|
|
2
|
+
import path, { dirname } from 'path';
|
|
3
|
+
import crypto from 'crypto';
|
|
4
|
+
import { fileURLToPath } from 'url';
|
|
5
|
+
import runHook from '../hooks.js';
|
|
6
|
+
import * as event from '../event.js';
|
|
7
|
+
import collection from './run-multiple/collection.js';
|
|
8
|
+
import { clearString, replaceValueDeep } from '../utils.js';
|
|
9
|
+
import { getConfig, getTestRoot, fail } from './utils.js';
|
|
10
|
+
|
|
11
|
+
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
12
|
+
|
|
13
|
+
const runner = path.join(__dirname, '../../bin/codecept.js');
|
|
14
|
+
let config;
|
|
15
|
+
const childOpts = {};
|
|
16
|
+
const copyOptions = ['override', 'steps', 'reporter', 'verbose', 'config', 'reporter-options', 'grep', 'fgrep', 'invert', 'debug', 'plugins', 'colors'];
|
|
17
|
+
let overrides = {};
|
|
29
18
|
|
|
30
19
|
// codeceptjs run-multiple smoke:chrome regression:firefox - will launch smoke run in chrome and regression in firefox
|
|
31
20
|
// codeceptjs run-multiple smoke:chrome regression - will launch smoke run in chrome and regression in firefox and chrome
|
|
32
21
|
// codeceptjs run-multiple --all - will launch all runs
|
|
33
22
|
// codeceptjs run-multiple smoke regression'
|
|
34
23
|
|
|
35
|
-
let runId = 1
|
|
36
|
-
let subprocessCount = 0
|
|
37
|
-
let totalSubprocessCount = 0
|
|
38
|
-
let processesDone
|
|
24
|
+
let runId = 1;
|
|
25
|
+
let subprocessCount = 0;
|
|
26
|
+
let totalSubprocessCount = 0;
|
|
27
|
+
let processesDone;
|
|
39
28
|
|
|
40
|
-
|
|
29
|
+
export default async function (selectedRuns, options) {
|
|
41
30
|
// registering options globally to use in config
|
|
42
31
|
if (options.profile) {
|
|
43
|
-
process.env.profile = options.profile
|
|
32
|
+
process.env.profile = options.profile;
|
|
44
33
|
}
|
|
45
|
-
const configFile = options.config
|
|
34
|
+
const configFile = options.config;
|
|
46
35
|
|
|
47
|
-
const testRoot = getTestRoot(configFile)
|
|
48
|
-
global.codecept_dir = testRoot
|
|
36
|
+
const testRoot = getTestRoot(configFile);
|
|
37
|
+
global.codecept_dir = testRoot;
|
|
49
38
|
|
|
50
39
|
// copy opts to run
|
|
51
40
|
Object.keys(options)
|
|
52
|
-
.filter(
|
|
41
|
+
.filter(key => copyOptions.indexOf(key) > -1)
|
|
53
42
|
.forEach((key) => {
|
|
54
|
-
childOpts[key] = options[key]
|
|
55
|
-
})
|
|
43
|
+
childOpts[key] = options[key];
|
|
44
|
+
});
|
|
56
45
|
|
|
57
46
|
try {
|
|
58
|
-
overrides = JSON.parse(childOpts.override)
|
|
59
|
-
delete childOpts.override
|
|
47
|
+
overrides = JSON.parse(childOpts.override);
|
|
48
|
+
delete childOpts.override;
|
|
60
49
|
} catch (e) {
|
|
61
|
-
overrides = {}
|
|
50
|
+
overrides = {};
|
|
62
51
|
}
|
|
63
52
|
|
|
64
53
|
config = {
|
|
65
54
|
...getConfig(configFile),
|
|
66
55
|
...overrides,
|
|
67
|
-
}
|
|
56
|
+
};
|
|
68
57
|
|
|
69
58
|
if (!config.multiple) {
|
|
70
|
-
fail('Multiple runs not configured, add "multiple": { /../ } section to config')
|
|
59
|
+
fail('Multiple runs not configured, add "multiple": { /../ } section to config');
|
|
71
60
|
}
|
|
72
61
|
|
|
73
|
-
selectedRuns = options.all ? Object.keys(config.multiple) : selectedRuns
|
|
62
|
+
selectedRuns = options.all ? Object.keys(config.multiple) : selectedRuns;
|
|
74
63
|
if (!selectedRuns.length) {
|
|
75
|
-
fail('No runs provided. Use --all option to run all configured runs')
|
|
64
|
+
fail('No runs provided. Use --all option to run all configured runs');
|
|
76
65
|
}
|
|
77
66
|
|
|
78
|
-
await runHook(config.bootstrapAll, 'bootstrapAll')
|
|
67
|
+
await runHook(config.bootstrapAll, 'bootstrapAll');
|
|
79
68
|
|
|
80
|
-
event.emit(event.multiple.before, null)
|
|
81
|
-
if (options.config) {
|
|
82
|
-
// update paths to config path
|
|
69
|
+
event.emit(event.multiple.before, null);
|
|
70
|
+
if (options.config) { // update paths to config path
|
|
83
71
|
if (config.tests) {
|
|
84
|
-
config.tests = path.resolve(testRoot, config.tests)
|
|
72
|
+
config.tests = path.resolve(testRoot, config.tests);
|
|
85
73
|
}
|
|
86
74
|
if (config.gherkin && config.gherkin.features) {
|
|
87
|
-
config.gherkin.features = path.resolve(testRoot, config.gherkin.features)
|
|
75
|
+
config.gherkin.features = path.resolve(testRoot, config.gherkin.features);
|
|
88
76
|
}
|
|
89
77
|
}
|
|
90
78
|
|
|
91
79
|
if (options.features) {
|
|
92
|
-
config.tests = ''
|
|
80
|
+
config.tests = '';
|
|
93
81
|
}
|
|
94
82
|
|
|
95
83
|
if (options.tests && config.gherkin) {
|
|
96
|
-
config.gherkin.features = ''
|
|
84
|
+
config.gherkin.features = '';
|
|
97
85
|
}
|
|
98
86
|
|
|
99
87
|
const childProcessesPromise = new Promise((resolve) => {
|
|
100
|
-
processesDone = resolve
|
|
101
|
-
})
|
|
88
|
+
processesDone = resolve;
|
|
89
|
+
});
|
|
102
90
|
|
|
103
|
-
const runsToExecute = []
|
|
91
|
+
const runsToExecute = [];
|
|
104
92
|
collection.createRuns(selectedRuns, config).forEach((run) => {
|
|
105
|
-
const runName = run.getOriginalName() || run.getName()
|
|
106
|
-
const runConfig = run.getConfig()
|
|
107
|
-
runsToExecute.push(executeRun(runName, runConfig))
|
|
108
|
-
})
|
|
93
|
+
const runName = run.getOriginalName() || run.getName();
|
|
94
|
+
const runConfig = run.getConfig();
|
|
95
|
+
runsToExecute.push(executeRun(runName, runConfig));
|
|
96
|
+
});
|
|
109
97
|
|
|
110
98
|
if (!runsToExecute.length) {
|
|
111
|
-
fail('Nothing scheduled for execution')
|
|
99
|
+
fail('Nothing scheduled for execution');
|
|
112
100
|
}
|
|
113
101
|
|
|
114
102
|
// Execute all forks
|
|
115
|
-
totalSubprocessCount = runsToExecute.length
|
|
116
|
-
runsToExecute.forEach(
|
|
103
|
+
totalSubprocessCount = runsToExecute.length;
|
|
104
|
+
runsToExecute.forEach(runToExecute => runToExecute.call(this));
|
|
117
105
|
|
|
118
106
|
return childProcessesPromise.then(async () => {
|
|
119
107
|
// fire hook
|
|
120
|
-
await runHook(config.teardownAll, 'teardownAll')
|
|
121
|
-
event.emit(event.multiple.after, null)
|
|
122
|
-
})
|
|
108
|
+
await runHook(config.teardownAll, 'teardownAll');
|
|
109
|
+
event.emit(event.multiple.after, null);
|
|
110
|
+
});
|
|
123
111
|
}
|
|
124
112
|
|
|
125
113
|
function executeRun(runName, runConfig) {
|
|
126
114
|
// clone config
|
|
127
|
-
let overriddenConfig = { ...config }
|
|
115
|
+
let overriddenConfig = { ...config };
|
|
128
116
|
|
|
129
117
|
// get configuration
|
|
130
|
-
const browserConfig = runConfig.browser
|
|
131
|
-
const browserName = browserConfig.browser
|
|
118
|
+
const browserConfig = runConfig.browser;
|
|
119
|
+
const browserName = browserConfig.browser;
|
|
132
120
|
|
|
133
121
|
for (const key in browserConfig) {
|
|
134
|
-
overriddenConfig.helpers = replaceValueDeep(overriddenConfig.helpers, key, browserConfig[key])
|
|
122
|
+
overriddenConfig.helpers = replaceValueDeep(overriddenConfig.helpers, key, browserConfig[key]);
|
|
135
123
|
}
|
|
136
124
|
|
|
137
|
-
let outputDir = `${runName}_
|
|
125
|
+
let outputDir = `${runName}_`;
|
|
138
126
|
if (browserConfig.outputName) {
|
|
139
|
-
outputDir += typeof browserConfig.outputName === 'function' ? browserConfig.outputName() : browserConfig.outputName
|
|
127
|
+
outputDir += typeof browserConfig.outputName === 'function' ? browserConfig.outputName() : browserConfig.outputName;
|
|
140
128
|
} else {
|
|
141
|
-
const hash = crypto.createHash('sha256')
|
|
142
|
-
hash.update(JSON.stringify(browserConfig))
|
|
143
|
-
outputDir += hash.digest('hex')
|
|
129
|
+
const hash = crypto.createHash('sha256');
|
|
130
|
+
hash.update(JSON.stringify(browserConfig));
|
|
131
|
+
outputDir += hash.digest('hex');
|
|
144
132
|
}
|
|
145
|
-
outputDir += `_${runId}
|
|
133
|
+
outputDir += `_${runId}`;
|
|
146
134
|
|
|
147
|
-
outputDir = clearString(outputDir)
|
|
135
|
+
outputDir = clearString(outputDir);
|
|
148
136
|
|
|
149
137
|
// tweaking default output directories and for mochawesome
|
|
150
|
-
overriddenConfig = replaceValueDeep(overriddenConfig, 'output', path.join(config.output, outputDir))
|
|
151
|
-
overriddenConfig = replaceValueDeep(overriddenConfig, 'reportDir', path.join(config.output, outputDir))
|
|
152
|
-
overriddenConfig = replaceValueDeep(
|
|
153
|
-
overriddenConfig,
|
|
154
|
-
'mochaFile',
|
|
155
|
-
path.join(config.output, outputDir, `${browserName}_report.xml`),
|
|
156
|
-
)
|
|
138
|
+
overriddenConfig = replaceValueDeep(overriddenConfig, 'output', path.join(config.output, outputDir));
|
|
139
|
+
overriddenConfig = replaceValueDeep(overriddenConfig, 'reportDir', path.join(config.output, outputDir));
|
|
140
|
+
overriddenConfig = replaceValueDeep(overriddenConfig, 'mochaFile', path.join(config.output, outputDir, `${browserName}_report.xml`));
|
|
157
141
|
|
|
158
142
|
// override tests configuration
|
|
159
143
|
if (overriddenConfig.tests) {
|
|
160
|
-
overriddenConfig.tests = runConfig.tests
|
|
144
|
+
overriddenConfig.tests = runConfig.tests;
|
|
161
145
|
}
|
|
162
146
|
|
|
163
147
|
if (overriddenConfig.gherkin && runConfig.gherkin && runConfig.gherkin.features) {
|
|
164
|
-
overriddenConfig.gherkin.features = runConfig.gherkin.features
|
|
148
|
+
overriddenConfig.gherkin.features = runConfig.gherkin.features;
|
|
165
149
|
}
|
|
166
150
|
|
|
167
151
|
// override grep param and collect all params
|
|
168
|
-
const params = [
|
|
169
|
-
'
|
|
170
|
-
'--
|
|
171
|
-
|
|
172
|
-
'--override',
|
|
173
|
-
JSON.stringify(overriddenConfig),
|
|
174
|
-
]
|
|
152
|
+
const params = ['run',
|
|
153
|
+
'--child', `${runId++}.${runName}:${browserName}`,
|
|
154
|
+
'--override', JSON.stringify(overriddenConfig),
|
|
155
|
+
];
|
|
175
156
|
|
|
176
157
|
Object.keys(childOpts).forEach((key) => {
|
|
177
|
-
params.push(`--${key}`)
|
|
178
|
-
if (childOpts[key] !== true) params.push(childOpts[key])
|
|
179
|
-
})
|
|
158
|
+
params.push(`--${key}`);
|
|
159
|
+
if (childOpts[key] !== true) params.push(childOpts[key]);
|
|
160
|
+
});
|
|
180
161
|
|
|
181
162
|
if (runConfig.grep) {
|
|
182
|
-
params.push('--grep')
|
|
183
|
-
params.push(runConfig.grep)
|
|
163
|
+
params.push('--grep');
|
|
164
|
+
params.push(runConfig.grep);
|
|
184
165
|
}
|
|
185
166
|
|
|
186
167
|
const onProcessEnd = (errorCode) => {
|
|
187
168
|
if (errorCode !== 0) {
|
|
188
|
-
process.exitCode = errorCode
|
|
169
|
+
process.exitCode = errorCode;
|
|
189
170
|
}
|
|
190
|
-
subprocessCount += 1
|
|
171
|
+
subprocessCount += 1;
|
|
191
172
|
if (subprocessCount === totalSubprocessCount) {
|
|
192
|
-
processesDone()
|
|
173
|
+
processesDone();
|
|
193
174
|
}
|
|
194
|
-
return errorCode
|
|
195
|
-
}
|
|
175
|
+
return errorCode;
|
|
176
|
+
};
|
|
196
177
|
|
|
197
178
|
// Return function of fork for later execution
|
|
198
|
-
return () =>
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
})
|
|
179
|
+
return () => fork(runner, params, { stdio: [0, 1, 2, 'ipc'] })
|
|
180
|
+
.on('exit', (code) => {
|
|
181
|
+
return onProcessEnd(code);
|
|
182
|
+
})
|
|
183
|
+
.on('error', () => {
|
|
184
|
+
return onProcessEnd(1);
|
|
185
|
+
});
|
|
206
186
|
}
|
package/lib/command/run-rerun.js
CHANGED
|
@@ -1,34 +1,39 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
1
|
+
import {
|
|
2
|
+
getConfig, getTestRoot, printError, createOutputDir,
|
|
3
|
+
} from './utils.js';
|
|
4
|
+
import Config from '../config.js';
|
|
5
|
+
import Codecept from '../rerun.js';
|
|
5
6
|
|
|
6
|
-
|
|
7
|
+
export async function runRerun(test, options) {
|
|
7
8
|
// registering options globally to use in config
|
|
8
9
|
// Backward compatibility for --profile
|
|
9
|
-
process.profile = options.profile
|
|
10
|
-
process.env.profile = options.profile
|
|
11
|
-
const configFile = options.config
|
|
10
|
+
process.profile = options.profile;
|
|
11
|
+
process.env.profile = options.profile;
|
|
12
|
+
const configFile = options.config;
|
|
12
13
|
|
|
13
|
-
let config = getConfig(configFile)
|
|
14
|
+
let config = getConfig(configFile);
|
|
14
15
|
if (options.override) {
|
|
15
|
-
config = Config.append(JSON.parse(options.override))
|
|
16
|
+
config = Config.append(JSON.parse(options.override));
|
|
16
17
|
}
|
|
17
|
-
const testRoot = getTestRoot(configFile)
|
|
18
|
-
createOutputDir(config, testRoot)
|
|
18
|
+
const testRoot = getTestRoot(configFile);
|
|
19
|
+
createOutputDir(config, testRoot);
|
|
19
20
|
|
|
20
|
-
|
|
21
|
+
function processError(err) {
|
|
22
|
+
printError(err);
|
|
23
|
+
process.exit(1);
|
|
24
|
+
}
|
|
25
|
+
const codecept = new Codecept(config, options);
|
|
21
26
|
|
|
22
27
|
try {
|
|
23
|
-
codecept.init(testRoot)
|
|
28
|
+
codecept.init(testRoot);
|
|
24
29
|
|
|
25
|
-
await codecept.bootstrap()
|
|
26
|
-
codecept.loadTests(test)
|
|
27
|
-
await codecept.run()
|
|
30
|
+
await codecept.bootstrap();
|
|
31
|
+
codecept.loadTests(test);
|
|
32
|
+
await codecept.run();
|
|
28
33
|
} catch (err) {
|
|
29
|
-
printError(err)
|
|
30
|
-
process.exitCode = 1
|
|
34
|
+
printError(err);
|
|
35
|
+
process.exitCode = 1;
|
|
31
36
|
} finally {
|
|
32
|
-
await codecept.teardown()
|
|
37
|
+
await codecept.teardown();
|
|
33
38
|
}
|
|
34
39
|
}
|