Skip to content

Commit

Permalink
Now supports globs along absolute and relative paths. Each path expan…
Browse files Browse the repository at this point in the history
…ded from a glob gets assigned the threshold from a glob. Tests now use mock-fs to, well, mock filesystem for glob testing.
  • Loading branch information
krishnagoth committed Aug 24, 2017
1 parent f93f46a commit c4e335b
Show file tree
Hide file tree
Showing 4 changed files with 109 additions and 42 deletions.
7 changes: 7 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@
"micromatch": "^2.3.11",
"mkdirp": "^0.5.1",
"mocha": "^3.4.2",
"mock-fs": "^4.4.1",
"prettier": "^1.5.2",
"progress": "^1.1.8",
"react": "^15.4.2",
Expand Down Expand Up @@ -140,5 +141,11 @@
"testMatch": [
"**/*.test.js"
]
<<<<<<< HEAD
}
}
=======
},
"dependencies": {}
}
>>>>>>> Now supports globs along absolute and relative paths. Each path expanded from a glob gets assigned the threshold from a glob. Tests now use mock-fs to, well, mock filesystem for glob testing.
95 changes: 71 additions & 24 deletions packages/jest-cli/src/reporters/__tests__/coverage_reporter.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@
'use strict';

jest
.mock('fs')
.mock('istanbul-lib-coverage')
.mock('istanbul-lib-source-maps')
.mock('istanbul-api');
Expand All @@ -18,6 +17,9 @@ let libSourceMaps;
let CoverageReporter;
let istanbulApi;

import path from 'path';
import mock from 'mock-fs';

beforeEach(() => {
istanbulApi = require('istanbul-api');
istanbulApi.createReporter = jest.fn(() => ({
Expand All @@ -28,6 +30,23 @@ beforeEach(() => {
CoverageReporter = require('../coverage_reporter');
libCoverage = require('istanbul-lib-coverage');
libSourceMaps = require('istanbul-lib-source-maps');

const fileTree = {};
fileTree[process.cwd() + '/path-test-files'] = {
'full_path_file.js': '',
'glob-path': {
'file1.js': '',
'file2.js': '',
},
'non_covered_file.js': '',
'relative_path_file.js': '',
};

mock(fileTree);
});

afterEach(() => {
mock.restore();
});

describe('onRunComplete', () => {
Expand All @@ -50,25 +69,37 @@ describe('onRunComplete', () => {
};

libCoverage.createCoverageMap = jest.fn(() => {
const files = [
'./path-test-files/covered_file_without_threshold.js',
'./path-test-files/full_path_file.js',
'./path-test-files/relative_path_file.js',
'./path-test-files/glob-path/file1.js',
'./path-test-files/glob-path/file2.js',
].map(p => path.resolve(p));

return {
fileCoverageFor(path) {
if (path === '/full/file/path.js') {
if (files.indexOf(path) !== -1) {
const covSummary = {
branches: {covered: 0, pct: 0, skipped: 0, total: 0},
functions: {covered: 0, pct: 0, skipped: 0, total: 0},
lines: {covered: 0, pct: 0, skipped: 0, total: 0},
merge(other) {
return covSummary;
},
statements: {covered: 0, pct: 50, skipped: 0, total: 0},
};
return {
toSummary() {
return {
branches: {covered: 0, pct: 0, skipped: 0, total: 0},
functions: {covered: 0, pct: 0, skipped: 0, total: 0},
lines: {covered: 0, pct: 0, skipped: 0, total: 0},
statements: {covered: 0, pct: 50, skipped: 0, total: 0},
};
return covSummary;
},
};
} else {
return undefined;
}
},
files() {
return ['/full/file/path.js'];
return files;
},
};
});
Expand Down Expand Up @@ -100,19 +131,27 @@ describe('onRunComplete', () => {
return testReporter
.onRunComplete(new Set(), {}, mockAggResults)
.then(() => {
expect(testReporter.getLastError()).toBeTruthy();
expect(testReporter.getLastError().message.split('\n')).toHaveLength(1);
});
});

it('getLastError() returns an error when threshold is not met for file', () => {
const covThreshold = {};
[
'global',
path.resolve(`${process.cwd()}/path-test-files/full_path_file.js`),
'./path-test-files/relative_path_file.js',
'path-test-files/glob-*/*.js',
].forEach(path => {
covThreshold[path] = {
statements: 100,
};
});

const testReporter = new CoverageReporter(
{
collectCoverage: true,
coverageThreshold: {
'/full/file/path.js': {
statements: 100,
},
},
coverageThreshold: covThreshold,
},
{
maxWorkers: 2,
Expand All @@ -122,19 +161,27 @@ describe('onRunComplete', () => {
return testReporter
.onRunComplete(new Set(), {}, mockAggResults)
.then(() => {
expect(testReporter.getLastError()).toBeTruthy();
expect(testReporter.getLastError().message.split('\n')).toHaveLength(5);
});
});

it('getLastError() returns `undefined` when threshold is met', () => {
const covThreshold = {};
[
'global',
path.resolve(`${process.cwd()}/path-test-files/full_path_file.js`),
'./path-test-files/relative_path_file.js',
'path-test-files/glob-*/*.js',
].forEach(path => {
covThreshold[path] = {
statements: 50,
};
});

const testReporter = new CoverageReporter(
{
collectCoverage: true,
coverageThreshold: {
global: {
statements: 50,
},
},
coverageThreshold: covThreshold,
},
{
maxWorkers: 2,
Expand All @@ -153,8 +200,8 @@ describe('onRunComplete', () => {
{
collectCoverage: true,
coverageThreshold: {
'/file/that/is/not/covered.js': {
statements: 50,
'path-test-files/non_covered_file.js': {
statements: 100,
},
},
},
Expand All @@ -166,7 +213,7 @@ describe('onRunComplete', () => {
return testReporter
.onRunComplete(new Set(), {}, mockAggResults)
.then(() => {
expect(testReporter.getLastError()).toBeTruthy();
expect(testReporter.getLastError().message.split('\n')).toHaveLength(1);
});
});
});
45 changes: 27 additions & 18 deletions packages/jest-cli/src/reporters/coverage_reporter.js
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ import workerFarm from 'worker-farm';
import BaseReporter from './base_reporter';
import CoverageWorker from './coverage_worker';
import path from 'path';
import glob from 'glob';

const FAIL_COLOR = chalk.bold.red;
const RUNNING_TEST_COLOR = chalk.bold.dim;
Expand Down Expand Up @@ -239,43 +240,51 @@ class CoverageReporter extends BaseReporter {
}, []);
}

const thresholdConfigFilePaths = Object.keys(
globalConfig.coverageThreshold,
)
.filter(thresholdKey => thresholdKey !== 'global')
.map(thresholdKey => path.resolve(thresholdKey));
const expandedThresholds = {};
Object.keys(globalConfig.coverageThreshold).forEach(filePathOrGlob => {
if (filePathOrGlob !== 'global') {
const pathArray = glob.sync(filePathOrGlob);
pathArray.forEach(filePath => {
expandedThresholds[path.resolve(filePath)] =
globalConfig.coverageThreshold[filePathOrGlob];
});
} else {
expandedThresholds.global = globalConfig.coverageThreshold.global;
}
});

const filteredCoverageSummary = map
.files()
.filter(filePath => thresholdConfigFilePaths.indexOf(filePath) === -1)
.filter(
filePath => Object.keys(expandedThresholds).indexOf(filePath) === -1,
)
.map(filePath => map.fileCoverageFor(filePath))
.reduce((summary: ?CoverageSummary, fileCov: FileCoverage) => {
if (summary !== undefined && summary !== null) {
summary.merge(fileCov.toSummary());
} else {
summary = fileCov.toSummary();
}
return summary;
return summary === undefined || summary === null
? (summary = fileCov.toSummary())
: summary.merge(fileCov.toSummary());
}, undefined);

const errors = [].concat(
...Object.keys(globalConfig.coverageThreshold)
const errors = [].concat.apply(
[],
Object.keys(expandedThresholds)
.map(thresholdKey => {
if (thresholdKey === 'global') {
if (filteredCoverageSummary !== undefined) {
return check(
'global',
globalConfig.coverageThreshold.global,
expandedThresholds.global,
filteredCoverageSummary,
);
} else {
return [];
}
} else {
if (map.files().indexOf(path.resolve(thresholdKey)) !== -1) {
if (map.files().indexOf(thresholdKey) !== -1) {
return check(
thresholdKey,
globalConfig.coverageThreshold[thresholdKey],
map.fileCoverageFor(path.resolve(thresholdKey)).toSummary(),
expandedThresholds[thresholdKey],
map.fileCoverageFor(thresholdKey).toSummary(),
);
} else {
return [
Expand Down
4 changes: 4 additions & 0 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -4380,6 +4380,10 @@ mocha@^3.4.2:
mkdirp "0.5.1"
supports-color "3.1.2"

mock-fs@^4.4.1:
version "4.4.1"
resolved "https://registry.yarnpkg.com/mock-fs/-/mock-fs-4.4.1.tgz#f285fa025b42a4031faf75b66f632b21e7056683"

modify-values@^1.0.0:
version "1.0.0"
resolved "https://registry.yarnpkg.com/modify-values/-/modify-values-1.0.0.tgz#e2b6cdeb9ce19f99317a53722f3dbf5df5eaaab2"
Expand Down

0 comments on commit c4e335b

Please sign in to comment.