test-inventory 0.2.1 → 0.4.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/CHANGELOG.md +28 -0
- package/README.md +9 -1
- package/dist/ast.d.ts +11 -0
- package/dist/ast.js +30 -0
- package/dist/cli.d.ts +1 -1
- package/dist/cli.js +59 -12
- package/dist/diagnostics.js +2 -0
- package/dist/extract.d.ts +26 -2
- package/dist/extract.js +204 -48
- package/dist/filter.d.ts +38 -0
- package/dist/filter.js +169 -0
- package/dist/frameworks/bindings.d.ts +37 -6
- package/dist/frameworks/bindings.js +167 -33
- package/dist/frameworks/common.d.ts +10 -1
- package/dist/frameworks/common.js +47 -4
- package/dist/frameworks/playwright.d.ts +6 -1
- package/dist/frameworks/playwright.js +111 -32
- package/dist/frameworks/vitest.d.ts +8 -1
- package/dist/frameworks/vitest.js +245 -85
- package/dist/index.d.ts +3 -1
- package/dist/index.js +1 -0
- package/dist/inventory.js +1 -0
- package/dist/json.d.ts +7 -1
- package/dist/json.js +32 -9
- package/dist/model.d.ts +62 -5
- package/dist/records.d.ts +7 -2
- package/dist/records.js +74 -4
- package/dist/scan-file.d.ts +2 -0
- package/dist/scan-file.js +12 -6
- package/dist/scan.js +2 -3
- package/dist/summary.js +1 -0
- package/dist/types.d.ts +109 -1
- package/package.json +2 -2
- package/schema/v1.json +326 -2
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,33 @@
|
|
|
1
1
|
# test-inventory
|
|
2
2
|
|
|
3
|
+
## 0.4.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [#42](https://github.com/Huldoser/test-inventory/pull/42) [`6849f55`](https://github.com/Huldoser/test-inventory/commit/6849f555d8b214ebbc8fdb9aa9cbac8cfe0913db) - Tests say what their body does: `fixtures` (the names the test and the `beforeEach`, `afterEach` and `aroundEach` hooks around it take from the context, without Vitest's own keys), `expectCount` (`expect()`, `expect.soft()` and `expect.poll()` calls in the body), Vitest's `expect.assertions(n)` and `expect.hasAssertions()` as `expectedAssertions` and `expectsAssertions`, `hasEmptyBody`, and Playwright's `test.step()` titles in `steps`. Vitest's `annotate()` from the test context adds annotations. Vitest 5 benchmarks, in `*.bench.ts` files or using the `bench` fixture, have `isBenchmark` and a `benchmarkCount` in the summary. New warnings: `empty-title` for a test or describe titled `''`, and `bench-outside-benchmark-file`.
|
|
8
|
+
|
|
9
|
+
- [#40](https://github.com/Huldoser/test-inventory/pull/40) [`f462ee0`](https://github.com/Huldoser/test-inventory/commit/f462ee015fea8ee802f567a26dbaa4db94ada1d5) - The output has a record for each scanned file in `files`, and counts hooks: `hooks` on a file holds the hooks at its top level, on a describe the hooks registered in it, and on a test every hook that runs around it, by kind (`beforeAll`, `beforeEach`, `afterEach`, `afterAll`, and Vitest's `aroundEach` and `aroundAll`). Hooks a helper function registers count where it is called. JSON Lines output has a `file` line for each file, and a filtered inventory keeps the files of the matched tests and the files without tests.
|
|
10
|
+
|
|
11
|
+
- [#41](https://github.com/Huldoser/test-inventory/pull/41) [`1ab9cb4`](https://github.com/Huldoser/test-inventory/commit/1ab9cb4002dd971ddb62570dc55ac564504e3a83) - Tests and describes have their run settings: `timeout`, `isSlow` and `slowCondition`, `retries`, `retryDelay`, `retryCondition` and `repeats`. Playwright's come from `test.describe.configure({ timeout, retries })`, `test.setTimeout()` and `test.slow()` in a describe, a `beforeEach` or the test body; Vitest's from the `timeout`, `retry` and `repeats` options, the timeout after the body, and the options a describe passes down. A test gets the value from the nearest place that sets it, and `null` when the file sets none, so the config decides. A timeout that can't be worked out, or that is set only under a condition, gets an `unresolved-option` warning.
|
|
12
|
+
|
|
13
|
+
## 0.3.0
|
|
14
|
+
|
|
15
|
+
### Minor Changes
|
|
16
|
+
|
|
17
|
+
- [#37](https://github.com/Huldoser/test-inventory/pull/37) [`5aeb139`](https://github.com/Huldoser/test-inventory/commit/5aeb13959daaeb0fdf4488765944fe42ef7754bc) - `--fields` keeps only the named keys of each test, and `id`, as in `--fields fullName,reason`, so a short question gets a short answer. Output written with it leaves keys out, so it no longer matches the JSON Schema. The library exports the same as `pickTestFields()`.
|
|
18
|
+
|
|
19
|
+
- [#37](https://github.com/Huldoser/test-inventory/pull/37) [`5aeb139`](https://github.com/Huldoser/test-inventory/commit/5aeb13959daaeb0fdf4488765944fe42ef7754bc) - Filters keep only the tests a question is about: `--state`, `--tag`, `--grep` (a regular expression on the full name, ignoring case), `--only` and `--without-reason`, as in `--state skip --state fixme` for the tests that don't run. The output then describes only those tests: the describes around them, their diagnostics and a summary counted over them. The library exports the same as `filterInventory()`.
|
|
20
|
+
|
|
21
|
+
- [#37](https://github.com/Huldoser/test-inventory/pull/37) [`5aeb139`](https://github.com/Huldoser/test-inventory/commit/5aeb13959daaeb0fdf4488765944fe42ef7754bc) - `--format jsonl` writes the inventory as JSON Lines: an `inventory` line, one line per suite, test and diagnostic, and a `summary` line, each marked with a `type` key. Tools that read one record per line, such as `grep` or DuckDB, no longer need the whole document in memory. The `InventoryLine` type describes the lines.
|
|
22
|
+
|
|
23
|
+
### Patch Changes
|
|
24
|
+
|
|
25
|
+
- [#34](https://github.com/Huldoser/test-inventory/pull/34) [`0f96258`](https://github.com/Huldoser/test-inventory/commit/0f96258e65085fa1b7c667b5fa7219a8b19230df) - A fixtures file that builds its test object with a function, written there or imported from another file, as in `export const test = defineDeskTest('equities')`, is followed: MSW's test files import such a `test`. Their tests were missing before, with no diagnostic when the fixtures file didn't import the framework itself. A test object built with a call the scan can't follow now gets an `unresolved-test-import` error that names the call, as in "builds it with withWarmup(), which is not followed". A function that returns what another function returns, as `() => onFeed('NYSE')`, is followed too.
|
|
26
|
+
|
|
27
|
+
- [#34](https://github.com/Huldoser/test-inventory/pull/34) [`0f96258`](https://github.com/Huldoser/test-inventory/commit/0f96258e65085fa1b7c667b5fa7219a8b19230df) - A call the runner refuses that is written like a declaration, as `describe.sequential('title', fn)` in Vitest 5, `test('title', fn, { retry: 2 })` from Vitest 4 or `test.only.skip('title', fn)`, is listed as a plain test or describe without the part that fails. Its tests were missing before; now they are `notLoaded`, like every other test in the file.
|
|
28
|
+
|
|
29
|
+
- [#34](https://github.com/Huldoser/test-inventory/pull/34) [`0f96258`](https://github.com/Huldoser/test-inventory/commit/0f96258e65085fa1b7c667b5fa7219a8b19230df) - States follow the runners' precedence more closely, as checked against Vitest 5.0.4 running generated files. A skip in a test or hook body loses to a fixme, skip or todo set while the file loads, as on a describe around the test, since the body never runs. In Vitest, a test's own options win over its chain, so `test.skip('title', { skip: false }, fn)` is active, but the chain still sets its mode: `test.concurrent('title', { concurrent: false }, fn)` runs in parallel. A describe passes its `skip` option down to the tests and describes inside, where it wins over todo, also when the describe's own `.only` keeps the describe itself from being skipped.
|
|
30
|
+
|
|
3
31
|
## 0.2.1
|
|
4
32
|
|
|
5
33
|
### Patch Changes
|
package/README.md
CHANGED
|
@@ -70,7 +70,9 @@ the first test's record includes:
|
|
|
70
70
|
```
|
|
71
71
|
|
|
72
72
|
The output also has a `summary` with counts, a record for each describe, and `diagnostics` that point at code the
|
|
73
|
-
scan could not read and values it could not work out.
|
|
73
|
+
scan could not read and values it could not work out. Filters such as `--state skip`, `--tag @smoke` and
|
|
74
|
+
`--grep "limit order"` keep only some tests, `--fields fullName,reason` keeps only some keys, and `--format jsonl`
|
|
75
|
+
writes one record per line.
|
|
74
76
|
|
|
75
77
|
## Library
|
|
76
78
|
|
|
@@ -84,6 +86,12 @@ const todo = inventory.tests.filter((test) => test.isTodo).map((test) => test.fu
|
|
|
84
86
|
`scanSource()` scans the code of one file without touching the disk. The JSON Schema of the output is exported as
|
|
85
87
|
`test-inventory/schema/v1.json`, so a reader can pin the version of the format it understands.
|
|
86
88
|
|
|
89
|
+
## AI agents
|
|
90
|
+
|
|
91
|
+
[test-inventory-mcp](https://github.com/Huldoser/test-inventory-mcp) is an MCP server built on test-inventory: agents
|
|
92
|
+
in Claude Code, Cursor, VS Code and other MCP clients ask it which tests a project has without running them. The
|
|
93
|
+
[AI agents](https://huldoser.github.io/test-inventory/guide/agents) page has the setup and the other ways in.
|
|
94
|
+
|
|
87
95
|
## Limits
|
|
88
96
|
|
|
89
97
|
- Config files are not read, so `grep`, projects and Vitest tag options in them do not change the output.
|
package/dist/ast.d.ts
CHANGED
|
@@ -4,6 +4,17 @@ export declare function childNodes(node: Node): Node[];
|
|
|
4
4
|
/** Strips TypeScript-only wrappers such as `test!`, `test as any` and `<any>test`. */
|
|
5
5
|
export declare function unwrap(node: Expression): Expression;
|
|
6
6
|
export declare function isFunctionNode(node: Node | null | undefined): node is FunctionNode;
|
|
7
|
+
/** A value a function returns, with the nodes inside the function around its `return`, outermost first. */
|
|
8
|
+
export interface ReturnValue {
|
|
9
|
+
expression: Expression;
|
|
10
|
+
around: Node[];
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* The values a function returns; null when it may return no value, as with `return;` or no `return` at all, and for
|
|
14
|
+
* an async function or a generator, which returns a promise or an iterator whatever its `return` says. A `return` in a
|
|
15
|
+
* function inside it is that function's.
|
|
16
|
+
*/
|
|
17
|
+
export declare function returnValues(fn: FunctionNode): ReturnValue[] | null;
|
|
7
18
|
export declare function isStringLiteral(node: Node): node is StringLiteral;
|
|
8
19
|
/** `import.meta.vitest`, which in-source Vitest tests read their functions from. */
|
|
9
20
|
export declare function isImportMetaVitest(expression: Expression): boolean;
|
package/dist/ast.js
CHANGED
|
@@ -32,6 +32,36 @@ export function unwrap(node) {
|
|
|
32
32
|
export function isFunctionNode(node) {
|
|
33
33
|
return node?.type === 'ArrowFunctionExpression' || node?.type === 'FunctionExpression';
|
|
34
34
|
}
|
|
35
|
+
/**
|
|
36
|
+
* The values a function returns; null when it may return no value, as with `return;` or no `return` at all, and for
|
|
37
|
+
* an async function or a generator, which returns a promise or an iterator whatever its `return` says. A `return` in a
|
|
38
|
+
* function inside it is that function's.
|
|
39
|
+
*/
|
|
40
|
+
export function returnValues(fn) {
|
|
41
|
+
if (fn.async || fn.generator)
|
|
42
|
+
return null;
|
|
43
|
+
// Only declarations of overloads have no body.
|
|
44
|
+
const body = fn.body;
|
|
45
|
+
if (body.type !== 'BlockStatement')
|
|
46
|
+
return [{ expression: body, around: [] }];
|
|
47
|
+
const values = [];
|
|
48
|
+
// Copied only at a `return`, so that a long function costs no more than its size.
|
|
49
|
+
const around = [];
|
|
50
|
+
const visit = (node) => {
|
|
51
|
+
if (node.type === 'ReturnStatement') {
|
|
52
|
+
values.push(node.argument ? { expression: node.argument, around: [...around] } : null);
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
55
|
+
if (node.type === 'FunctionDeclaration' || isFunctionNode(node))
|
|
56
|
+
return;
|
|
57
|
+
around.push(node);
|
|
58
|
+
for (const child of childNodes(node))
|
|
59
|
+
visit(child);
|
|
60
|
+
around.pop();
|
|
61
|
+
};
|
|
62
|
+
visit(body);
|
|
63
|
+
return values.length > 0 && !values.includes(null) ? values : null;
|
|
64
|
+
}
|
|
35
65
|
export function isStringLiteral(node) {
|
|
36
66
|
return node.type === 'Literal' && typeof node.value === 'string';
|
|
37
67
|
}
|
package/dist/cli.d.ts
CHANGED
|
@@ -4,6 +4,6 @@ export interface Io {
|
|
|
4
4
|
stderr: Writable;
|
|
5
5
|
cwd: string;
|
|
6
6
|
}
|
|
7
|
-
export declare const HELP = "Usage: test-inventory <glob...> --framework <playwright|vitest> [options]\n\nLists the tests in the matching files as JSON, read from the source code without running them.\n\nOptions:\n --framework <name> playwright or vitest (required)\n --root <dir> project root; paths in the output are relative to it (default: current directory)\n --ignore <glob> leave out matching files; can be repeated (node_modules is always left out)\n --framework-version <x.y.z> apply the rules of this framework version instead of the one in the project\n --comments <mode> comments above tests: all, non-active or none (default: non-active)\n -o, --output <file> write to a file instead of standard output\n --pretty indent the JSON\n -h, --help show this help\n -v, --version show the version\n\nExit codes: 0 when the scan finishes, even with diagnostics; 2 for invalid arguments, an output that cannot be\nwritten, or a crash. 1 is reserved for a future release.\n\
|
|
7
|
+
export declare const HELP = "Usage: test-inventory <glob...> --framework <playwright|vitest> [options]\n\nLists the tests in the matching files as JSON, read from the source code without running them.\n\nOptions:\n --framework <name> playwright or vitest (required)\n --root <dir> project root; paths in the output are relative to it (default: current directory)\n --ignore <glob> leave out matching files; can be repeated (node_modules is always left out)\n --framework-version <x.y.z> apply the rules of this framework version instead of the one in the project\n --comments <mode> comments above tests: all, non-active or none (default: non-active)\n --state <state> keep tests in this state, such as skip or fixme; can be repeated\n --tag <tag> keep tests with this tag, such as @smoke; can be repeated\n --grep <regex> keep tests whose full name matches, ignoring case\n --only keep tests that use .only, or are inside a describe that does\n --without-reason keep tests that don't run and give no reason\n --fields <keys> write only these keys of each test, separated by commas; id is always kept\n --format <format> json or jsonl, one record per line (default: json)\n -o, --output <file> write to a file instead of standard output\n --pretty indent the JSON\n -h, --help show this help\n -v, --version show the version\n\nExit codes: 0 when the scan finishes, even with diagnostics; 2 for invalid arguments, an output that cannot be\nwritten, or a crash. 1 is reserved for a future release.\n\nExamples:\n test-inventory \"tests/**/*.spec.ts\" --framework playwright --output inventory.json\n test-inventory \"tests/**/*.spec.ts\" --framework playwright --state skip --fields fullName,reason\n";
|
|
8
8
|
/** Runs the command line with the given arguments and streams. Resolves to the exit code. */
|
|
9
9
|
export declare function run(argv: string[], io: Io): Promise<number>;
|
package/dist/cli.js
CHANGED
|
@@ -3,7 +3,8 @@ import { once } from 'node:events';
|
|
|
3
3
|
import path from 'node:path';
|
|
4
4
|
import { parseArgs } from 'node:util';
|
|
5
5
|
import { readFailure } from "./files.js";
|
|
6
|
-
import {
|
|
6
|
+
import { checkFields, filterInventory, matcher, pickTestFields } from "./filter.js";
|
|
7
|
+
import { writeInventory, writeInventoryLines } from "./json.js";
|
|
7
8
|
import { OptionsError } from "./options.js";
|
|
8
9
|
import { scan } from "./scan.js";
|
|
9
10
|
import { toolVersion } from "./version.js";
|
|
@@ -17,6 +18,13 @@ Options:
|
|
|
17
18
|
--ignore <glob> leave out matching files; can be repeated (node_modules is always left out)
|
|
18
19
|
--framework-version <x.y.z> apply the rules of this framework version instead of the one in the project
|
|
19
20
|
--comments <mode> comments above tests: all, non-active or none (default: non-active)
|
|
21
|
+
--state <state> keep tests in this state, such as skip or fixme; can be repeated
|
|
22
|
+
--tag <tag> keep tests with this tag, such as @smoke; can be repeated
|
|
23
|
+
--grep <regex> keep tests whose full name matches, ignoring case
|
|
24
|
+
--only keep tests that use .only, or are inside a describe that does
|
|
25
|
+
--without-reason keep tests that don't run and give no reason
|
|
26
|
+
--fields <keys> write only these keys of each test, separated by commas; id is always kept
|
|
27
|
+
--format <format> json or jsonl, one record per line (default: json)
|
|
20
28
|
-o, --output <file> write to a file instead of standard output
|
|
21
29
|
--pretty indent the JSON
|
|
22
30
|
-h, --help show this help
|
|
@@ -25,18 +33,24 @@ Options:
|
|
|
25
33
|
Exit codes: 0 when the scan finishes, even with diagnostics; 2 for invalid arguments, an output that cannot be
|
|
26
34
|
written, or a crash. 1 is reserved for a future release.
|
|
27
35
|
|
|
28
|
-
|
|
36
|
+
Examples:
|
|
29
37
|
test-inventory "tests/**/*.spec.ts" --framework playwright --output inventory.json
|
|
38
|
+
test-inventory "tests/**/*.spec.ts" --framework playwright --state skip --fields fullName,reason
|
|
30
39
|
`;
|
|
31
|
-
/** CLI names for the option names in
|
|
40
|
+
/** CLI names for the option names in the library's errors. */
|
|
32
41
|
const FLAGS = {
|
|
33
|
-
patterns: 'the glob patterns',
|
|
34
|
-
framework: '--framework',
|
|
35
|
-
root: '--root',
|
|
36
|
-
ignore: '--ignore',
|
|
37
|
-
frameworkVersion: '--framework-version',
|
|
38
|
-
comments: '--comments',
|
|
42
|
+
'options.patterns': 'the glob patterns',
|
|
43
|
+
'options.framework': '--framework',
|
|
44
|
+
'options.root': '--root',
|
|
45
|
+
'options.ignore': '--ignore',
|
|
46
|
+
'options.frameworkVersion': '--framework-version',
|
|
47
|
+
'options.comments': '--comments',
|
|
48
|
+
'filter.states': '--state',
|
|
49
|
+
'filter.tags': '--tag',
|
|
50
|
+
'filter.grep': '--grep',
|
|
51
|
+
fields: '--fields',
|
|
39
52
|
};
|
|
53
|
+
const FORMATS = ['json', 'jsonl'];
|
|
40
54
|
async function writeTo(stream, chunk) {
|
|
41
55
|
if (stream.errored)
|
|
42
56
|
throw stream.errored;
|
|
@@ -89,6 +103,13 @@ export async function run(argv, io) {
|
|
|
89
103
|
ignore: { type: 'string', multiple: true },
|
|
90
104
|
'framework-version': { type: 'string' },
|
|
91
105
|
comments: { type: 'string' },
|
|
106
|
+
state: { type: 'string', multiple: true },
|
|
107
|
+
tag: { type: 'string', multiple: true },
|
|
108
|
+
grep: { type: 'string' },
|
|
109
|
+
only: { type: 'boolean' },
|
|
110
|
+
'without-reason': { type: 'boolean' },
|
|
111
|
+
fields: { type: 'string' },
|
|
112
|
+
format: { type: 'string' },
|
|
92
113
|
output: { type: 'string', short: 'o' },
|
|
93
114
|
pretty: { type: 'boolean' },
|
|
94
115
|
help: { type: 'boolean', short: 'h' },
|
|
@@ -112,8 +133,26 @@ export async function run(argv, io) {
|
|
|
112
133
|
return fail('give at least one glob pattern for the test files.');
|
|
113
134
|
if (values.framework === undefined)
|
|
114
135
|
return fail('--framework is required: playwright or vitest.');
|
|
136
|
+
const format = values.format ?? 'json';
|
|
137
|
+
if (!FORMATS.includes(format))
|
|
138
|
+
return fail('--format must be json or jsonl.');
|
|
139
|
+
if (format === 'jsonl' && values.pretty)
|
|
140
|
+
return fail('--pretty indents JSON, so it does not go with --format jsonl.');
|
|
141
|
+
const filter = {
|
|
142
|
+
states: values.state,
|
|
143
|
+
tags: values.tag,
|
|
144
|
+
grep: values.grep,
|
|
145
|
+
only: values.only,
|
|
146
|
+
withoutReason: values['without-reason'],
|
|
147
|
+
};
|
|
148
|
+
const fields = values.fields?.split(',').map((field) => field.trim());
|
|
115
149
|
let inventory;
|
|
150
|
+
let result;
|
|
116
151
|
try {
|
|
152
|
+
// Checked before the scan, so a mistyped state or key doesn't wait for every file to be read.
|
|
153
|
+
matcher(filter);
|
|
154
|
+
if (fields !== undefined)
|
|
155
|
+
checkFields(fields);
|
|
117
156
|
inventory = await scan({
|
|
118
157
|
patterns: positionals,
|
|
119
158
|
framework: values.framework,
|
|
@@ -122,10 +161,12 @@ export async function run(argv, io) {
|
|
|
122
161
|
frameworkVersion: values['framework-version'],
|
|
123
162
|
comments: values.comments,
|
|
124
163
|
});
|
|
164
|
+
const filtered = filterInventory(inventory, filter);
|
|
165
|
+
result = fields === undefined ? filtered : pickTestFields(filtered, fields);
|
|
125
166
|
}
|
|
126
167
|
catch (error) {
|
|
127
168
|
if (error instanceof OptionsError) {
|
|
128
|
-
return fail(error.message.replace(/^
|
|
169
|
+
return fail(error.message.replace(/^[\w.]+/, (name) => FLAGS[name]));
|
|
129
170
|
}
|
|
130
171
|
io.stderr.write(`test-inventory: unexpected error: ${error instanceof Error ? String(error.stack) : String(error)}\n`);
|
|
131
172
|
return FAILED;
|
|
@@ -139,8 +180,14 @@ export async function run(argv, io) {
|
|
|
139
180
|
io.stdout.on('error', quiet);
|
|
140
181
|
try {
|
|
141
182
|
await writeOutput(io, values.output, async (output) => {
|
|
142
|
-
|
|
143
|
-
|
|
183
|
+
const write = (chunk) => writeTo(output, chunk);
|
|
184
|
+
if (format === 'jsonl') {
|
|
185
|
+
await writeInventoryLines(result, write);
|
|
186
|
+
}
|
|
187
|
+
else {
|
|
188
|
+
await writeInventory(result, values.pretty === true, write);
|
|
189
|
+
await write('\n');
|
|
190
|
+
}
|
|
144
191
|
});
|
|
145
192
|
}
|
|
146
193
|
catch (error) {
|
package/dist/diagnostics.js
CHANGED
|
@@ -34,6 +34,8 @@ export const LEVELS = {
|
|
|
34
34
|
'no-files-matched': 'warning',
|
|
35
35
|
'unsupported-file': 'warning',
|
|
36
36
|
'approximate-framework-version': 'warning',
|
|
37
|
+
'empty-title': 'warning',
|
|
38
|
+
'bench-outside-benchmark-file': 'warning',
|
|
37
39
|
'test-in-function': 'warning',
|
|
38
40
|
};
|
|
39
41
|
/**
|
package/dist/extract.d.ts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import type { CallExpression } from 'oxc-parser';
|
|
2
|
-
import type { Adapter, Details, Mode, ModuleReader, ModuleSource, Problem, Span, StateSetting, SuiteDeclaration, TestDeclaration } from './model.ts';
|
|
2
|
+
import type { Adapter, Details, Mode, ModuleReader, ModuleSource, Problem, RunSettings, Span, StateSetting, SuiteDeclaration, TestDeclaration } from './model.ts';
|
|
3
3
|
import type { ParsedFile } from './parse.ts';
|
|
4
4
|
import { type SourceText } from './source.ts';
|
|
5
|
-
import type { Annotation } from './types.ts';
|
|
5
|
+
import type { Annotation, HookCounts, Step } from './types.ts';
|
|
6
6
|
import { type Values } from './values.ts';
|
|
7
7
|
/** The file or a describe, with what is set on it. Tests inherit from every scope around them. */
|
|
8
8
|
export interface Scope {
|
|
@@ -12,6 +12,12 @@ export interface Scope {
|
|
|
12
12
|
mode: Mode | null;
|
|
13
13
|
isOnly: boolean;
|
|
14
14
|
details: Details;
|
|
15
|
+
/** Hooks registered directly in the scope. */
|
|
16
|
+
hooks: HookCounts;
|
|
17
|
+
/** Run settings from `beforeEach` hooks in the scope, which run before each test in it and win over the scope's own. */
|
|
18
|
+
hookRun: RunSettings;
|
|
19
|
+
/** Fixtures of the hooks in the scope that run around each test. */
|
|
20
|
+
hookFixtures: string[];
|
|
15
21
|
suite: PendingSuite | null;
|
|
16
22
|
}
|
|
17
23
|
/** Where a test or describe registered through an imported helper is written, in the helper's module. */
|
|
@@ -48,6 +54,12 @@ export interface PendingTest {
|
|
|
48
54
|
isInCondition: boolean;
|
|
49
55
|
isInFunction: boolean;
|
|
50
56
|
comments: string[];
|
|
57
|
+
/** Run settings from calls in the body, which win over everything around the test. */
|
|
58
|
+
run: RunSettings;
|
|
59
|
+
expectCount: number;
|
|
60
|
+
expectedAssertions: number | null;
|
|
61
|
+
expectsAssertions: boolean;
|
|
62
|
+
steps: Step[];
|
|
51
63
|
problems: Problem[];
|
|
52
64
|
}
|
|
53
65
|
/** A file the walk reads code from: the scanned file, or a module a helper function is imported from. */
|
|
@@ -65,7 +77,19 @@ export interface Extraction {
|
|
|
65
77
|
tests: PendingTest[];
|
|
66
78
|
/** Problems not tied to one test. */
|
|
67
79
|
problems: Problem[];
|
|
80
|
+
/** Hooks at the top level of the file. */
|
|
81
|
+
hooks: HookCounts;
|
|
68
82
|
usesGlobals: boolean;
|
|
69
83
|
}
|
|
84
|
+
/**
|
|
85
|
+
* Applies settings written later in the same place: the last value of each wins, and a test is slow when any
|
|
86
|
+
* `test.slow()` applies.
|
|
87
|
+
*/
|
|
88
|
+
export declare function mergeRun(target: RunSettings, later: RunSettings): void;
|
|
89
|
+
/** Any of several `test.slow()` calls: always when one always applies, otherwise under any of their conditions. */
|
|
90
|
+
export declare function anySlow(slows: NonNullable<RunSettings['slow']>[]): NonNullable<RunSettings['slow']>;
|
|
91
|
+
/** Conditions joined with `||`, adding parentheses where a part could otherwise be read differently. */
|
|
92
|
+
export declare function eitherCondition(parts: string[]): string;
|
|
93
|
+
export declare function noHooks(): HookCounts;
|
|
70
94
|
/** Walks the scanned file; `openModule` reads the modules of imported helpers that the file calls. */
|
|
71
95
|
export declare function extract(main: Frame, openModule: OpenModule): Extraction;
|