@japa/runner 4.3.1 → 5.0.0
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/README.md +61 -0
- package/build/create_test-CIR_zZry.js +352 -0
- package/build/factories/create_dummy_tests.d.ts +1 -1
- package/build/factories/main.d.ts +1 -1
- package/build/factories/main.js +182 -225
- package/build/factories/runner.d.ts +1 -1
- package/build/helpers-BlHaYYTh.js +241 -0
- package/build/index.d.ts +1 -1
- package/build/index.js +214 -260
- package/build/main-CB1nhl6c.js +336 -0
- package/build/modules/core/main.js +2 -21
- package/build/modules/core/reporters/base.d.ts +1 -1
- package/build/src/create_test.d.ts +2 -2
- package/build/src/debug.d.ts +1 -1
- package/build/src/helpers.d.ts +11 -1
- package/build/src/hooks.d.ts +1 -1
- package/build/src/plugins/disallow_pinned_tests.d.ts +9 -0
- package/build/src/plugins/main.d.ts +1 -0
- package/build/src/plugins/main.js +23 -0
- package/build/src/reporters/main.js +3 -14
- package/build/src/reporters/spec.d.ts +1 -1
- package/build/src/types.d.ts +1 -0
- package/build/src/types.js +7 -14
- package/build/src/validator.d.ts +1 -1
- package/package.json +32 -31
- package/build/chunk-2KG3PWR4.js +0 -17
- package/build/chunk-PCBL2VZP.js +0 -295
- package/build/chunk-U3BSXCEH.js +0 -347
- package/build/chunk-Y57JXJ7G.js +0 -513
package/build/index.js
CHANGED
|
@@ -1,284 +1,238 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
debug_default,
|
|
9
|
-
validator_default
|
|
10
|
-
} from "./chunk-Y57JXJ7G.js";
|
|
11
|
-
import "./chunk-U3BSXCEH.js";
|
|
12
|
-
import {
|
|
13
|
-
Emitter,
|
|
14
|
-
Runner,
|
|
15
|
-
Suite,
|
|
16
|
-
colors
|
|
17
|
-
} from "./chunk-PCBL2VZP.js";
|
|
18
|
-
import "./chunk-2KG3PWR4.js";
|
|
19
|
-
|
|
20
|
-
// index.ts
|
|
21
|
-
import { fileURLToPath } from "url";
|
|
22
|
-
import { ErrorsPrinter as ErrorsPrinter2 } from "@japa/errors-printer";
|
|
23
|
-
|
|
24
|
-
// src/plugins/retry.ts
|
|
25
|
-
import { join } from "path";
|
|
1
|
+
import { a as GlobalHooks, c as debug_default, i as CliParser, n as createTestGroup, o as Planner, r as ConfigManager, s as validator_default, t as createTest } from "./create_test-CIR_zZry.js";
|
|
2
|
+
import { c as Suite, i as Emitter, r as printPinnedTests, s as Runner, t as colors } from "./helpers-BlHaYYTh.js";
|
|
3
|
+
import "./main-CB1nhl6c.js";
|
|
4
|
+
import { fileURLToPath } from "node:url";
|
|
5
|
+
import { ErrorsPrinter } from "@japa/errors-printer";
|
|
6
|
+
import { join } from "node:path";
|
|
7
|
+
import { mkdir, readFile, unlink, writeFile } from "node:fs/promises";
|
|
26
8
|
import findCacheDirectory from "find-cache-directory";
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
var SUMMARY_FILE = CACHE_DIR ? join(CACHE_DIR, "summary.json") : void 0;
|
|
9
|
+
const CACHE_DIR = findCacheDirectory({ name: "@japa/runner" });
|
|
10
|
+
const SUMMARY_FILE = CACHE_DIR ? join(CACHE_DIR, "summary.json") : void 0;
|
|
30
11
|
async function getFailedTests() {
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
throw new Error("Unable to read failed tests cache file", { cause: error });
|
|
39
|
-
}
|
|
12
|
+
try {
|
|
13
|
+
const summary = await readFile(SUMMARY_FILE, "utf-8");
|
|
14
|
+
return JSON.parse(summary);
|
|
15
|
+
} catch (error) {
|
|
16
|
+
if (error.code === "ENOENT") return {};
|
|
17
|
+
throw new Error("Unable to read failed tests cache file", { cause: error });
|
|
18
|
+
}
|
|
40
19
|
}
|
|
41
20
|
async function cacheFailedTests(tests) {
|
|
42
|
-
|
|
43
|
-
|
|
21
|
+
await mkdir(CACHE_DIR, { recursive: true });
|
|
22
|
+
await writeFile(SUMMARY_FILE, JSON.stringify({ tests }));
|
|
44
23
|
}
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
} catch (error) {
|
|
62
|
-
console.log(colors.bgRed().black(" Unable to read failed tests. Running all the tests "));
|
|
63
|
-
console.log(colors.red(error));
|
|
64
|
-
}
|
|
65
|
-
}
|
|
24
|
+
const retryPlugin = async function retry({ config, cliArgs: cliArgs$1 }) {
|
|
25
|
+
if (!SUMMARY_FILE) return;
|
|
26
|
+
config.teardown.push(async (runner) => {
|
|
27
|
+
await cacheFailedTests(runner.getSummary().failedTestsTitles);
|
|
28
|
+
});
|
|
29
|
+
if (cliArgs$1.failed) try {
|
|
30
|
+
const { tests } = await getFailedTests();
|
|
31
|
+
if (!tests || !tests.length) {
|
|
32
|
+
console.log(colors.bgYellow().black(" No failing tests found. Running all the tests "));
|
|
33
|
+
return;
|
|
34
|
+
}
|
|
35
|
+
config.filters.tests = tests;
|
|
36
|
+
} catch (error) {
|
|
37
|
+
console.log(colors.bgRed().black(" Unable to read failed tests. Running all the tests "));
|
|
38
|
+
console.log(colors.red(error));
|
|
39
|
+
}
|
|
66
40
|
};
|
|
67
|
-
|
|
68
|
-
// src/exceptions_manager.ts
|
|
69
|
-
import { ErrorsPrinter } from "@japa/errors-printer";
|
|
70
41
|
var ExceptionsManager = class {
|
|
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
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
let rejectionsCount = this.#exceptionsBuffer.length;
|
|
126
|
-
let rejectionsIndex = this.#exceptionsBuffer.length;
|
|
127
|
-
this.#errorsPrinter.printSectionBorder("Unhandled Rejections");
|
|
128
|
-
for (let rejection of this.#rejectionsBuffer) {
|
|
129
|
-
await this.#errorsPrinter.printError(rejection);
|
|
130
|
-
this.#errorsPrinter.printSectionBorder(`[${++rejectionsIndex}/${rejectionsCount}]`);
|
|
131
|
-
}
|
|
132
|
-
this.#rejectionsBuffer = [];
|
|
133
|
-
}
|
|
134
|
-
}
|
|
135
|
-
};
|
|
136
|
-
|
|
137
|
-
// index.ts
|
|
138
|
-
var emitter = new Emitter();
|
|
139
|
-
var activeTest;
|
|
140
|
-
var cliArgs = {};
|
|
141
|
-
var runnerConfig;
|
|
142
|
-
var executionPlanState = {
|
|
143
|
-
phase: "idle"
|
|
42
|
+
#exceptionsBuffer = [];
|
|
43
|
+
#rejectionsBuffer = [];
|
|
44
|
+
#state = "watching";
|
|
45
|
+
#errorsPrinter = new ErrorsPrinter({
|
|
46
|
+
stackLinesCount: 2,
|
|
47
|
+
framesMaxLimit: 4
|
|
48
|
+
});
|
|
49
|
+
hasErrors = false;
|
|
50
|
+
monitor() {
|
|
51
|
+
process.on("uncaughtException", async (error) => {
|
|
52
|
+
debug_default("received uncaught exception %O", error);
|
|
53
|
+
this.hasErrors = true;
|
|
54
|
+
if (this.#state === "watching") this.#exceptionsBuffer.push(error);
|
|
55
|
+
else {
|
|
56
|
+
this.#errorsPrinter.printSectionBorder("[Unhandled Error]");
|
|
57
|
+
await this.#errorsPrinter.printError(error);
|
|
58
|
+
process.exitCode = 1;
|
|
59
|
+
}
|
|
60
|
+
});
|
|
61
|
+
process.on("unhandledRejection", async (error) => {
|
|
62
|
+
debug_default("received unhandled rejection %O", error);
|
|
63
|
+
this.hasErrors = true;
|
|
64
|
+
if (this.#state === "watching") this.#rejectionsBuffer.push(error);
|
|
65
|
+
else {
|
|
66
|
+
this.#errorsPrinter.printSectionBorder("[Unhandled Rejection]");
|
|
67
|
+
await this.#errorsPrinter.printError(error);
|
|
68
|
+
process.exitCode = 1;
|
|
69
|
+
}
|
|
70
|
+
});
|
|
71
|
+
}
|
|
72
|
+
async report() {
|
|
73
|
+
if (this.#state === "reporting") return;
|
|
74
|
+
this.#state = "reporting";
|
|
75
|
+
if (this.#exceptionsBuffer.length) {
|
|
76
|
+
let exceptionsCount = this.#exceptionsBuffer.length;
|
|
77
|
+
let exceptionsIndex = this.#exceptionsBuffer.length;
|
|
78
|
+
this.#errorsPrinter.printSectionHeader("Unhandled Errors");
|
|
79
|
+
for (let exception of this.#exceptionsBuffer) {
|
|
80
|
+
await this.#errorsPrinter.printError(exception);
|
|
81
|
+
this.#errorsPrinter.printSectionBorder(`[${++exceptionsIndex}/${exceptionsCount}]`);
|
|
82
|
+
}
|
|
83
|
+
this.#exceptionsBuffer = [];
|
|
84
|
+
}
|
|
85
|
+
if (this.#rejectionsBuffer.length) {
|
|
86
|
+
let rejectionsCount = this.#exceptionsBuffer.length;
|
|
87
|
+
let rejectionsIndex = this.#exceptionsBuffer.length;
|
|
88
|
+
this.#errorsPrinter.printSectionBorder("Unhandled Rejections");
|
|
89
|
+
for (let rejection of this.#rejectionsBuffer) {
|
|
90
|
+
await this.#errorsPrinter.printError(rejection);
|
|
91
|
+
this.#errorsPrinter.printSectionBorder(`[${++rejectionsIndex}/${rejectionsCount}]`);
|
|
92
|
+
}
|
|
93
|
+
this.#rejectionsBuffer = [];
|
|
94
|
+
}
|
|
95
|
+
}
|
|
144
96
|
};
|
|
97
|
+
const emitter = new Emitter();
|
|
98
|
+
let activeTest;
|
|
99
|
+
let cliArgs = {};
|
|
100
|
+
let runnerConfig;
|
|
101
|
+
const executionPlanState = { phase: "idle" };
|
|
145
102
|
function test(title, callback) {
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
return testInstance;
|
|
103
|
+
validator_default.ensureIsInPlanningPhase(executionPlanState.phase);
|
|
104
|
+
const debuggingError = /* @__PURE__ */ new Error();
|
|
105
|
+
const testInstance = createTest(title, emitter, runnerConfig.refiner, debuggingError, executionPlanState);
|
|
106
|
+
testInstance.setup((t) => {
|
|
107
|
+
activeTest = t;
|
|
108
|
+
return () => {
|
|
109
|
+
activeTest = void 0;
|
|
110
|
+
};
|
|
111
|
+
});
|
|
112
|
+
if (callback) testInstance.run(callback, debuggingError);
|
|
113
|
+
return testInstance;
|
|
158
114
|
}
|
|
159
115
|
test.group = function(title, callback) {
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
executionPlanState.group = void 0;
|
|
168
|
-
return group;
|
|
116
|
+
validator_default.ensureIsInPlanningPhase(executionPlanState.phase);
|
|
117
|
+
const group = createTestGroup(title, emitter, runnerConfig.refiner, executionPlanState);
|
|
118
|
+
executionPlanState.group = group;
|
|
119
|
+
if (cliArgs.bail && cliArgs.bailLayer === "group") executionPlanState.group.bail(true);
|
|
120
|
+
callback(executionPlanState.group);
|
|
121
|
+
executionPlanState.group = void 0;
|
|
122
|
+
return group;
|
|
169
123
|
};
|
|
170
124
|
test.macro = function(callback) {
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
return callback(activeTest, ...args);
|
|
176
|
-
};
|
|
125
|
+
return (...args) => {
|
|
126
|
+
if (!activeTest) throw new Error("Cannot invoke macro outside of the test callback");
|
|
127
|
+
return callback(activeTest, ...args);
|
|
128
|
+
};
|
|
177
129
|
};
|
|
178
130
|
function getActiveTest() {
|
|
179
|
-
|
|
131
|
+
return activeTest;
|
|
180
132
|
}
|
|
181
133
|
function getActiveTestOrFail() {
|
|
182
|
-
|
|
183
|
-
|
|
134
|
+
if (!activeTest) throw new Error("Cannot access active test outside of a test callback");
|
|
135
|
+
return activeTest;
|
|
184
136
|
}
|
|
185
137
|
function processCLIArgs(argv) {
|
|
186
|
-
|
|
138
|
+
cliArgs = new CliParser().parse(argv);
|
|
187
139
|
}
|
|
188
140
|
function configure(options) {
|
|
189
|
-
|
|
141
|
+
runnerConfig = new ConfigManager(options, cliArgs).hydrate();
|
|
190
142
|
}
|
|
191
143
|
async function run() {
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
144
|
+
if (cliArgs.help) {
|
|
145
|
+
console.log(new CliParser().getHelp());
|
|
146
|
+
return;
|
|
147
|
+
}
|
|
148
|
+
validator_default.ensureIsConfigured(runnerConfig);
|
|
149
|
+
executionPlanState.phase = "planning";
|
|
150
|
+
const runner = new Runner(emitter);
|
|
151
|
+
if (cliArgs.bail && cliArgs.bailLayer === "") runner.bail(true);
|
|
152
|
+
const globalHooks = new GlobalHooks();
|
|
153
|
+
const exceptionsManager = new ExceptionsManager();
|
|
154
|
+
try {
|
|
155
|
+
await retryPlugin({
|
|
156
|
+
config: runnerConfig,
|
|
157
|
+
runner,
|
|
158
|
+
emitter,
|
|
159
|
+
cliArgs
|
|
160
|
+
});
|
|
161
|
+
for (let plugin of runnerConfig.plugins) {
|
|
162
|
+
debug_default("executing \"%s\" plugin", plugin.name || "anonymous");
|
|
163
|
+
await plugin({
|
|
164
|
+
runner,
|
|
165
|
+
emitter,
|
|
166
|
+
cliArgs,
|
|
167
|
+
config: runnerConfig
|
|
168
|
+
});
|
|
169
|
+
}
|
|
170
|
+
const { config, reporters, suites, refinerFilters } = await new Planner(runnerConfig).plan();
|
|
171
|
+
reporters.forEach((reporter) => {
|
|
172
|
+
debug_default("registering \"%s\" reporter", reporter.name);
|
|
173
|
+
runner.registerReporter(reporter);
|
|
174
|
+
});
|
|
175
|
+
refinerFilters.forEach((filter) => {
|
|
176
|
+
debug_default("apply %s filters \"%O\" ", filter.layer, filter.filters);
|
|
177
|
+
config.refiner.add(filter.layer, filter.filters);
|
|
178
|
+
});
|
|
179
|
+
config.refiner.matchAllTags(cliArgs.matchAll ?? false);
|
|
180
|
+
runner.onSuite(config.configureSuite);
|
|
181
|
+
debug_default("executing global hooks");
|
|
182
|
+
globalHooks.apply(config);
|
|
183
|
+
if (!cliArgs.listPinned) await globalHooks.setup(runner);
|
|
184
|
+
for (let suite of suites) {
|
|
185
|
+
debug_default("initiating suite %s", suite.name);
|
|
186
|
+
executionPlanState.suite = new Suite(suite.name, emitter, config.refiner);
|
|
187
|
+
executionPlanState.retries = suite.retries;
|
|
188
|
+
executionPlanState.timeout = suite.timeout;
|
|
189
|
+
if (typeof suite.configure === "function") suite.configure(executionPlanState.suite);
|
|
190
|
+
if (cliArgs.bail && cliArgs.bailLayer === "suite") {
|
|
191
|
+
debug_default("enabling bail mode for the suite %s", suite.name);
|
|
192
|
+
executionPlanState.suite.bail(true);
|
|
193
|
+
}
|
|
194
|
+
runner.add(executionPlanState.suite);
|
|
195
|
+
for (let fileURL of suite.filesURLs) {
|
|
196
|
+
executionPlanState.file = fileURLToPath(fileURL);
|
|
197
|
+
debug_default("importing test file %s", executionPlanState.file);
|
|
198
|
+
await config.importer(fileURL);
|
|
199
|
+
}
|
|
200
|
+
executionPlanState.suite = void 0;
|
|
201
|
+
}
|
|
202
|
+
if (cliArgs.listPinned) {
|
|
203
|
+
printPinnedTests(runner);
|
|
204
|
+
if (config.forceExit) {
|
|
205
|
+
debug_default("force exiting process");
|
|
206
|
+
process.exit();
|
|
207
|
+
}
|
|
208
|
+
return;
|
|
209
|
+
}
|
|
210
|
+
executionPlanState.phase = "executing";
|
|
211
|
+
exceptionsManager.monitor();
|
|
212
|
+
await runner.start();
|
|
213
|
+
await runner.exec();
|
|
214
|
+
await globalHooks.teardown(null, runner);
|
|
215
|
+
await runner.end();
|
|
216
|
+
await exceptionsManager.report();
|
|
217
|
+
const summary = runner.getSummary();
|
|
218
|
+
if (summary.hasError || exceptionsManager.hasErrors) {
|
|
219
|
+
debug_default("updating exit code to 1. summary.hasError %s, process.hasError", summary.hasError, exceptionsManager.hasErrors);
|
|
220
|
+
process.exitCode = 1;
|
|
221
|
+
}
|
|
222
|
+
if (config.forceExit) {
|
|
223
|
+
debug_default("force exiting process");
|
|
224
|
+
process.exit();
|
|
225
|
+
}
|
|
226
|
+
} catch (error) {
|
|
227
|
+
debug_default("error running tests %O", error);
|
|
228
|
+
await globalHooks.teardown(error, runner);
|
|
229
|
+
await new ErrorsPrinter().printError(error);
|
|
230
|
+
await exceptionsManager.report();
|
|
231
|
+
process.exitCode = 1;
|
|
232
|
+
if (runnerConfig.forceExit) {
|
|
233
|
+
debug_default("force exiting process");
|
|
234
|
+
process.exit();
|
|
235
|
+
}
|
|
236
|
+
}
|
|
276
237
|
}
|
|
277
|
-
export {
|
|
278
|
-
configure,
|
|
279
|
-
getActiveTest,
|
|
280
|
-
getActiveTestOrFail,
|
|
281
|
-
processCLIArgs,
|
|
282
|
-
run,
|
|
283
|
-
test
|
|
284
|
-
};
|
|
238
|
+
export { configure, getActiveTest, getActiveTestOrFail, processCLIArgs, run, test };
|