Skip to content

Commit be77741

Browse files
committed
test_runner: report coverage thresholds in test:coverage
1 parent b77476d commit be77741

File tree

3 files changed

+54
-14
lines changed

3 files changed

+54
-14
lines changed

doc/api/test.md

+5
Original file line numberDiff line numberDiff line change
@@ -2814,6 +2814,11 @@ are defined, while others are emitted in the order that the tests execute.
28142814
numbers and the number of times they were covered.
28152815
* `line` {number} The line number.
28162816
* `count` {number} The number of times the line was covered.
2817+
* `thresholds` {Object} An object containing whether or not the coverage for
2818+
each coverage type.
2819+
* `function` {number} The user-specified `function` threshold value.
2820+
* `branch` {number} The user-specified `branch` threshold value.
2821+
* `line` {number} The user-specified `line` threshold value.
28172822
* `totals` {Object} An object containing a summary of coverage for all
28182823
files.
28192824
* `totalLineCount` {number} The total number of lines.

lib/internal/test_runner/test.js

+4-2
Original file line numberDiff line numberDiff line change
@@ -1010,8 +1010,6 @@ class Test extends AsyncResource {
10101010
reporter.diagnostic(nesting, loc, `duration_ms ${this.duration()}`);
10111011

10121012
if (coverage) {
1013-
reporter.coverage(nesting, loc, coverage);
1014-
10151013
const coverages = [
10161014
{ __proto__: null, actual: coverage.totals.coveredLinePercent,
10171015
threshold: this.config.lineCoverage, name: 'line' },
@@ -1023,13 +1021,17 @@ class Test extends AsyncResource {
10231021
threshold: this.config.functionCoverage, name: 'function' },
10241022
];
10251023

1024+
coverage.thresholds = { __proto__: null };
10261025
for (let i = 0; i < coverages.length; i++) {
10271026
const { threshold, actual, name } = coverages[i];
1027+
coverage.thresholds[name] = threshold;
10281028
if (actual < threshold) {
10291029
process.exitCode = kGenericUserError;
10301030
reporter.diagnostic(nesting, loc, `Error: ${NumberPrototypeToFixed(actual, 2)}% ${name} coverage does not meet threshold of ${threshold}%.`);
10311031
}
10321032
}
1033+
1034+
reporter.coverage(nesting, loc, coverage);
10331035
}
10341036

10351037
if (harness.watching) {

test/parallel/test-runner-coverage-thresholds.js

+45-12
Original file line numberDiff line numberDiff line change
@@ -44,10 +44,7 @@ function getTapCoverageFixtureReport() {
4444
}
4545

4646
const fixture = fixtures.path('test-runner', 'coverage.js');
47-
const neededArguments = [
48-
'--experimental-test-coverage',
49-
'--test-reporter', 'tap',
50-
];
47+
const reporter = fixtures.fileURL('test-runner/custom_reporters/coverage.mjs');
5148

5249
const coverages = [
5350
{ flag: '--test-coverage-lines', name: 'line', actual: 78.35 },
@@ -56,10 +53,12 @@ const coverages = [
5653
];
5754

5855
for (const coverage of coverages) {
59-
test(`test passing ${coverage.flag}`, async (t) => {
56+
test(`test passing ${coverage.flag}`, () => {
6057
const result = spawnSync(process.execPath, [
61-
...neededArguments,
58+
'--test',
59+
'--experimental-test-coverage',
6260
`${coverage.flag}=25`,
61+
'--test-reporter', 'tap',
6362
fixture,
6463
]);
6564

@@ -70,10 +69,27 @@ for (const coverage of coverages) {
7069
assert(!findCoverageFileForPid(result.pid));
7170
});
7271

73-
test(`test failing ${coverage.flag}`, async (t) => {
72+
test(`test passing ${coverage.flag} with custom reporter`, () => {
73+
const result = spawnSync(process.execPath, [
74+
'--test',
75+
'--experimental-test-coverage',
76+
`${coverage.flag}=25`,
77+
'--test-reporter', reporter,
78+
fixture,
79+
]);
80+
81+
const stdout = JSON.parse(result.stdout.toString());
82+
assert.strictEqual(stdout.summary.thresholds[coverage.name], 25);
83+
assert.strictEqual(result.status, 0);
84+
assert(!findCoverageFileForPid(result.pid));
85+
});
86+
87+
test(`test failing ${coverage.flag}`, () => {
7488
const result = spawnSync(process.execPath, [
75-
...neededArguments,
89+
'--test',
90+
'--experimental-test-coverage',
7691
`${coverage.flag}=99`,
92+
'--test-reporter', 'tap',
7793
fixture,
7894
]);
7995

@@ -84,9 +100,25 @@ for (const coverage of coverages) {
84100
assert(!findCoverageFileForPid(result.pid));
85101
});
86102

87-
test(`test out-of-range ${coverage.flag} (too high)`, async (t) => {
103+
test(`test failing ${coverage.flag} with custom reporter`, () => {
104+
const result = spawnSync(process.execPath, [
105+
'--test',
106+
'--experimental-test-coverage',
107+
`${coverage.flag}=99`,
108+
'--test-reporter', reporter,
109+
fixture,
110+
]);
111+
112+
const stdout = JSON.parse(result.stdout.toString());
113+
assert.strictEqual(stdout.summary.thresholds[coverage.name], 99);
114+
assert.strictEqual(result.status, 1);
115+
assert(!findCoverageFileForPid(result.pid));
116+
});
117+
118+
test(`test out-of-range ${coverage.flag} (too high)`, () => {
88119
const result = spawnSync(process.execPath, [
89-
...neededArguments,
120+
'--test',
121+
'--experimental-test-coverage',
90122
`${coverage.flag}=101`,
91123
fixture,
92124
]);
@@ -96,9 +128,10 @@ for (const coverage of coverages) {
96128
assert(!findCoverageFileForPid(result.pid));
97129
});
98130

99-
test(`test out-of-range ${coverage.flag} (too low)`, async (t) => {
131+
test(`test out-of-range ${coverage.flag} (too low)`, () => {
100132
const result = spawnSync(process.execPath, [
101-
...neededArguments,
133+
'--test',
134+
'--experimental-test-coverage',
102135
`${coverage.flag}=-1`,
103136
fixture,
104137
]);

0 commit comments

Comments
 (0)