Skip to content

Commit 76e116e

Browse files
authored
Introduce c8 check coverage (#25)
* test: check-coverage params * feat: enable thresholds params * docs: add check-coverage info in README.md
1 parent b313695 commit 76e116e

6 files changed

Lines changed: 119 additions & 11 deletions

File tree

README.md

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,9 @@ npm i borp --save-dev
1515

1616
```bash
1717
borp --coverage
18+
19+
# with check coverage active
20+
borp --coverage --check-coverage --lines 95
1821
```
1922

2023
Borp will automatically run all tests files matching `*.test.{js|ts}`.
@@ -25,30 +28,30 @@ Borp will automatically run all tests files matching `*.test.{js|ts}`.
2528
.
2629
├── src
2730
│   ├── lib
28-
│   │   └── add.ts
31+
│   │   └── math.ts
2932
│   └── test
30-
│   └── add.test.ts
33+
│   └── math.test.ts
3134
└── tsconfig.json
3235
3336
```
3437

35-
As an example, consider having a `src/lib/add.ts` file
38+
As an example, consider having a `src/lib/math.ts` file
3639

3740
```typescript
38-
export function add (x: number, y: number): number {
41+
export function math (x: number, y: number): number {
3942
return x + y
4043
}
4144
```
4245

43-
and a `src/test/add.test.ts` file:
46+
and a `src/test/math.test.ts` file:
4447

4548
```typescript
4649
import { test } from 'node:test'
47-
import { add } from '../lib/add.js'
50+
import { math } from '../lib/math.js'
4851
import { strictEqual } from 'node:assert'
4952

50-
test('add', () => {
51-
strictEqual(add(1, 2), 3)
53+
test('math', () => {
54+
strictEqual(math(1, 2), 3)
5255
})
5356
```
5457

@@ -97,7 +100,12 @@ Note the use of `incremental: true`, which speed up compilation massively.
97100
* `--reporter` or `-r`, set up a reporter, use a colon to set a file destination. Default: `spec`.
98101
* `--no-typescript` or `-T`, disable automatic TypeScript compilation if `tsconfig.json` is found.
99102
* `--post-compile` or `-P`, the path to a file that will be executed after each typescript compilation.
100-
103+
* `--check-coverage`, enables c8 check coverage; default is false
104+
### Check coverage options
105+
* `--lines`, set the lines threshold when check coverage is active; default is 100
106+
* `--functions`, set the functions threshold when check coverage is active; default is 100
107+
* `--statements`, set the statements threshold when check coverage is active; default is 100
108+
* `--branches`, set the branches threshold when check coverage is active; default is 100
101109
## Reporters
102110

103111
Here are the available reporters:

borp.js

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import posix from 'node:path/posix'
1010
import runWithTypeScript from './lib/run.js'
1111
import githubReporter from '@reporters/github'
1212
import { Report } from 'c8'
13+
import { checkCoverages } from 'c8/lib/commands/check-coverage.js'
1314
import os from 'node:os'
1415
import { execa } from 'execa'
1516

@@ -39,7 +40,12 @@ const args = parseArgs({
3940
short: 'r',
4041
default: ['spec'],
4142
multiple: true
42-
}
43+
},
44+
'check-coverage': { type: 'boolean' },
45+
lines: { type: 'string', default: '100' },
46+
branches: { type: 'string', default: '100' },
47+
functions: { type: 'string', default: '100' },
48+
statements: { type: 'string', default: '100' }
4349
},
4450
allowPositionals: true
4551
})
@@ -136,6 +142,15 @@ try {
136142
exclude
137143
})
138144

145+
if (args.values['check-coverage']) {
146+
await checkCoverages({
147+
lines: parseInt(args.values.lines),
148+
functions: parseInt(args.values.functions),
149+
branches: parseInt(args.values.branches),
150+
statements: parseInt(args.values.statements),
151+
...args
152+
}, report)
153+
}
139154
await report.run()
140155
}
141156
/* c8 ignore next 3 */
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
2+
export function add (x: number, y: number): number {
3+
return x + y
4+
}
5+
6+
export function sub (x: number, y: number): number {
7+
return x - y
8+
}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
import { test } from 'node:test'
2+
import { add } from '../src/math.js'
3+
import { strictEqual } from 'node:assert'
4+
5+
test('add', () => {
6+
strictEqual(add(1, 2), 3)
7+
})
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
{
2+
"$schema": "https://json.schemastore.org/tsconfig",
3+
"compilerOptions": {
4+
"outDir": "dist",
5+
"sourceMap": true,
6+
"target": "ES2022",
7+
"module": "NodeNext",
8+
"moduleResolution": "NodeNext",
9+
"esModuleInterop": true,
10+
"strict": true,
11+
"resolveJsonModule": true,
12+
"removeComments": true,
13+
"newLine": "lf",
14+
"noUnusedLocals": true,
15+
"noFallthroughCasesInSwitch": true,
16+
"isolatedModules": true,
17+
"forceConsistentCasingInFileNames": true,
18+
"skipLibCheck": true,
19+
"lib": [
20+
"ESNext"
21+
],
22+
"incremental": true
23+
}
24+
}

test/coverage.test.js

Lines changed: 47 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { test } from 'node:test'
2-
import { match, doesNotMatch } from 'node:assert'
2+
import { match, doesNotMatch, fail, equal, AssertionError } from 'node:assert'
33
import { execa } from 'execa'
44
import { join } from 'desm'
55

@@ -35,3 +35,49 @@ test('coverage excludes', async () => {
3535
match(res.stdout, /add\.test\.ts/)
3636
match(res.stdout, /add2\.test\.ts/)
3737
})
38+
39+
test('borp should return right error when check coverage is active with default thresholds', async (t) => {
40+
try {
41+
await execa('node', [
42+
borp,
43+
'--coverage',
44+
'--check-coverage'
45+
], {
46+
cwd: join(import.meta.url, '..', 'fixtures', 'ts-esm-check-coverage')
47+
})
48+
fail('Should not complete borp without error')
49+
} catch (e) {
50+
if (e instanceof AssertionError) {
51+
throw e
52+
}
53+
54+
equal(e.exitCode, 1)
55+
match(e.stderr, /ERROR: Coverage for lines \(75%\) does not meet global threshold \(100%\)/)
56+
match(e.stderr, /ERROR: Coverage for functions \(50%\) does not meet global threshold \(100%\)/)
57+
match(e.stderr, /ERROR: Coverage for statements \(75%\) does not meet global threshold \(100%\)/)
58+
}
59+
})
60+
61+
test('borp should return right error when check coverage is active with defined thresholds', async (t) => {
62+
try {
63+
await execa('node', [
64+
borp,
65+
'--coverage',
66+
'--check-coverage',
67+
'--lines=80',
68+
'--functions=50',
69+
'--statements=0',
70+
'--branches=100'
71+
], {
72+
cwd: join(import.meta.url, '..', 'fixtures', 'ts-esm-check-coverage')
73+
})
74+
fail('Should not complete borp without error')
75+
} catch (e) {
76+
if (e instanceof AssertionError) {
77+
throw e
78+
}
79+
80+
equal(e.exitCode, 1)
81+
match(e.stderr, /ERROR: Coverage for lines \(75%\) does not meet global threshold \(80%\)/)
82+
}
83+
})

0 commit comments

Comments
 (0)