@avi2dg/checks 0.24.2 → 0.26.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 +22 -0
- package/README.md +29 -22
- package/dist/effect-channel/index.js +4 -4
- package/dist/readability/index.js +5 -5
- package/docs/configs/commit-messages.md +1 -1
- package/docs/configs/effect-rules.md +2 -2
- package/docs/configs/native-settings.md +4 -2
- package/docs/design.md +10 -4
- package/docs/gates/checks-comment-gate.md +3 -4
- package/docs/gates/checks-docs.md +16 -14
- package/docs/gates/checks-exports.md +104 -0
- package/docs/gates/checks-flake.md +1 -1
- package/docs/gates/checks-lint.md +1 -1
- package/docs/gates/checks-quarantine-clock.md +1 -1
- package/docs/gates/checks-test-layout.md +14 -9
- package/docs/gates/checks-test.md +1 -1
- package/docs/gates/checks-unused.md +65 -0
- package/knip-base.json +4 -0
- package/package.json +75 -108
- package/src/complexity/exports.ts +196 -0
- package/src/complexity/knip.ts +70 -0
- package/{scripts → src/complexity}/repetition.ts +2 -2
- package/{scripts → src/complexity}/suppressions-ratchet.ts +2 -2
- package/src/complexity/unused.ts +48 -0
- package/src/core/gates.ts +46 -0
- package/{scripts → src/core}/lint.ts +2 -2
- package/{scripts → src/core}/swc.ts +1 -1
- package/{scripts → src/delivery}/changelog-write.ts +2 -2
- package/{scripts → src/delivery}/changelog.ts +3 -3
- package/{scripts → src/delivery}/ci-wiring.ts +3 -3
- package/{scripts → src/delivery}/commit-identity.ts +2 -2
- package/{scripts → src/delivery}/release-notes.ts +1 -1
- package/{scripts → src/delivery}/release-report.ts +2 -2
- package/{scripts → src/dependencies}/vendor-args.ts +1 -1
- package/{scripts → src/dependencies}/vendor.ts +2 -2
- package/{scripts → src/docs}/doc-references.ts +1 -1
- package/{scripts → src/docs}/doc-snapshot.ts +2 -2
- package/{scripts → src/docs}/doc-templates.ts +3 -3
- package/{scripts → src/docs}/docs.ts +2 -2
- package/{scripts → src/quality}/comment-gate.ts +2 -2
- package/{scripts → src/quality}/comment-matchers.ts +1 -1
- package/{scripts → src/quality}/comments.ts +2 -2
- package/{scripts → src/testing}/flake.ts +1 -1
- package/{scripts → src/testing}/mutation-compare.ts +1 -1
- package/{scripts → src/testing}/quarantine-clock.ts +2 -2
- package/{scripts → src/testing}/subsumed-tests.ts +2 -2
- package/{scripts → src/testing}/test-layout.ts +47 -14
- package/{scripts → src/testing}/test-report.ts +1 -1
- package/{scripts → src/testing}/test-skips.ts +1 -1
- package/{scripts → src/testing}/test.ts +2 -2
- package/CONTRIBUTING.md +0 -94
- package/docs/gates/checks-backtest.md +0 -54
- package/scripts/backtest.ts +0 -122
- package/scripts/gates.ts +0 -37
- package/scripts/range-gate.ts +0 -8
- /package/{templates → dist/templates}/adr.md +0 -0
- /package/{templates → dist/templates}/agents.md +0 -0
- /package/{templates → dist/templates}/changelog.md +0 -0
- /package/{templates → dist/templates}/claude.md +0 -0
- /package/{templates → dist/templates}/explanation.md +0 -0
- /package/{templates → dist/templates}/how-to.md +0 -0
- /package/{templates → dist/templates}/readme.md +0 -0
- /package/{templates → dist/templates}/reference.md +0 -0
- /package/{templates → dist/templates}/tutorial.md +0 -0
- /package/{scripts → src/core}/git.ts +0 -0
- /package/{scripts → src/core}/main.ts +0 -0
- /package/{scripts → src/delivery}/shell-command.ts +0 -0
- /package/{scripts → src/docs}/doc-outline.ts +0 -0
- /package/{scripts → src/docs}/doc-rules.ts +0 -0
- /package/{scripts → src/docs}/prose-matchers.ts +0 -0
- /package/{scripts → src/quality}/lint-coverage.sh +0 -0
- /package/{presets → src/quality/presets}/effect.language-service.json +0 -0
- /package/{presets → src/quality/presets}/effect.oxlint.json +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,28 @@
|
|
|
2
2
|
|
|
3
3
|
Every release of `@avi2dg/checks`, newest first, written by the release from its conventional commits.
|
|
4
4
|
|
|
5
|
+
## 0.26.0
|
|
6
|
+
|
|
7
|
+
Released 2026-09-27.
|
|
8
|
+
|
|
9
|
+
### Breaking changes
|
|
10
|
+
|
|
11
|
+
- **complexity:** add checks-exports gate holding unused exports to a shrinking baseline [#89](https://github.com/avi2d/checks/pull/89)
|
|
12
|
+
- move doc templates into dist/templates and presets into src/quality [#88](https://github.com/avi2d/checks/pull/88)
|
|
13
|
+
|
|
14
|
+
## 0.25.0
|
|
15
|
+
|
|
16
|
+
Released 2026-09-27.
|
|
17
|
+
|
|
18
|
+
### Breaking changes
|
|
19
|
+
|
|
20
|
+
- stop shipping checks-backtest and unused exports keys, guard the tarball with Knip [#86](https://github.com/avi2d/checks/pull/86)
|
|
21
|
+
- sort the kit into src/<vector>/ and require tests/<level>/ [#84](https://github.com/avi2d/checks/pull/84)
|
|
22
|
+
|
|
23
|
+
### Features
|
|
24
|
+
|
|
25
|
+
- add checks-unused gate that rejects unreferenced TypeScript files via Knip [#85](https://github.com/avi2d/checks/pull/85)
|
|
26
|
+
|
|
5
27
|
## 0.24.2
|
|
6
28
|
|
|
7
29
|
Released 2026-09-27.
|
package/README.md
CHANGED
|
@@ -65,6 +65,14 @@ To consume the kit from a repository:
|
|
|
65
65
|
cp node_modules/@avi2dg/checks/bunfig.toml bunfig.toml
|
|
66
66
|
```
|
|
67
67
|
|
|
68
|
+
1. Name the repository's entry files in `knip.config.ts`, spreading the kit's Knip base:
|
|
69
|
+
|
|
70
|
+
```ts
|
|
71
|
+
import base from "@avi2dg/checks/knip-base.json";
|
|
72
|
+
|
|
73
|
+
export default { ...base, entry: ["src/index.ts", "tests/**/*.test.ts"] };
|
|
74
|
+
```
|
|
75
|
+
|
|
68
76
|
1. Add scripts to `package.json`, replacing the build entry with the repository's own build command:
|
|
69
77
|
|
|
70
78
|
```json
|
|
@@ -100,22 +108,25 @@ Add a pull request title lint step in another workflow using `./node_modules/.bi
|
|
|
100
108
|
|
|
101
109
|
## What runs
|
|
102
110
|
|
|
103
|
-
`checks-lint` runs these gates
|
|
111
|
+
`checks-lint` runs these gates, each over the working tree or over the range it resolves, and names every one that fails.
|
|
104
112
|
`checks-lint` runs every applicable gate, including the TypeScript gates once the repository tracks TypeScript.
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
|
110
|
-
|
|
|
111
|
-
| [`checks-
|
|
112
|
-
| [`checks-
|
|
113
|
-
| [`checks-
|
|
114
|
-
| [`checks-
|
|
115
|
-
| [`checks-
|
|
116
|
-
| [`checks-
|
|
117
|
-
| [`checks-
|
|
118
|
-
| [`checks-quarantine-clock`](docs/gates/checks-quarantine-clock.md) | the range | every repository |
|
|
113
|
+
Each gate belongs to the vector it judges a repository on, and the table groups the gates by vector.
|
|
114
|
+
|
|
115
|
+
<!-- generated gates: bun run build writes it from KIT_GATES in src/core/gates.ts and scripts/doc-blocks.ts -->
|
|
116
|
+
|
|
117
|
+
| Vector | Gate | Reads | Runs in |
|
|
118
|
+
| --- | --- | --- | --- |
|
|
119
|
+
| complexity | [`checks-suppressions-ratchet`](docs/gates/checks-suppressions-ratchet.md) | the range | every repository |
|
|
120
|
+
| complexity | [`checks-repetition`](docs/gates/checks-repetition.md) | the range | a repository tracking `*.ts` or `*.tsx` |
|
|
121
|
+
| complexity | [`checks-unused`](docs/gates/checks-unused.md) | the working tree | a repository tracking `*.ts` or `*.tsx` |
|
|
122
|
+
| complexity | [`checks-exports`](docs/gates/checks-exports.md) | the range | a repository tracking `*.ts` or `*.tsx` |
|
|
123
|
+
| quality | [`checks-lint-coverage`](docs/gates/checks-lint-coverage.md) | the working tree | a repository tracking `*.ts` or `*.tsx` |
|
|
124
|
+
| quality | [`checks-comment-gate`](docs/gates/checks-comment-gate.md) | the range | every repository |
|
|
125
|
+
| testing | [`checks-test-layout`](docs/gates/checks-test-layout.md) | the working tree | a repository tracking `*.ts` or `*.tsx` |
|
|
126
|
+
| testing | [`checks-quarantine-clock`](docs/gates/checks-quarantine-clock.md) | the range | every repository |
|
|
127
|
+
| docs | [`checks-docs`](docs/gates/checks-docs.md) | the range | every repository |
|
|
128
|
+
| delivery | [`checks-commit-identity`](docs/gates/checks-commit-identity.md) | the range | every repository |
|
|
129
|
+
| delivery | [`checks-ci-wiring`](docs/gates/checks-ci-wiring.md) | the working tree | every repository |
|
|
119
130
|
|
|
120
131
|
<!-- end generated gates -->
|
|
121
132
|
|
|
@@ -125,7 +136,6 @@ These bins run on their own:
|
|
|
125
136
|
- [`checks-flake`](docs/gates/checks-flake.md) runs the suite on a schedule and records the seeds a flaky test fails with.
|
|
126
137
|
- [`checks-mutation-compare`](docs/gates/checks-mutation-compare.md) holds every mutant in a pull request to no regression.
|
|
127
138
|
- [`checks-subsumed-tests`](docs/gates/checks-subsumed-tests.md) lists each test another test subsumes in a mutation run.
|
|
128
|
-
- [`checks-backtest`](docs/gates/checks-backtest.md) reports what the comment check would have refused in recent history.
|
|
129
139
|
- [`checks-changelog`](docs/gates/checks-changelog.md) writes the pending release into `CHANGELOG.md` from the conventional commits since the last release.
|
|
130
140
|
- [`checks-release-notes`](docs/gates/checks-release-notes.md) writes one `CHANGELOG.md` section to a file for a GitHub release.
|
|
131
141
|
- [`checks-release-report`](docs/gates/checks-release-report.md) tells whether the history holds unreleased features or fixes since the last tag.
|
|
@@ -156,18 +166,16 @@ Every path is relative to the installed package, `node_modules/@avi2dg/checks/`.
|
|
|
156
166
|
| Path | What it holds |
|
|
157
167
|
| --- | --- |
|
|
158
168
|
| `CHANGELOG.md` | every release, and what it changed |
|
|
159
|
-
| `CONTRIBUTING.md` | how this repository is developed and released |
|
|
160
169
|
| `docs/` | a reference page per bin and per shared config, and why the kit is shaped this way |
|
|
161
170
|
| `bunfig.toml` | the bunfig preset a repository copies |
|
|
162
171
|
| `commitlint.config.js` | the shared commitlint config |
|
|
163
172
|
| `dependency-cruiser.config.js` | the shared dependency-cruiser base |
|
|
164
|
-
| `
|
|
165
|
-
| `
|
|
166
|
-
| `
|
|
173
|
+
| `knip-base.json` | the Knip base a repository's configuration imports |
|
|
174
|
+
| `src/` | every bin, which a package script calls by its `checks-` name, the modules the bins import, and the Effect rule blocks under `src/quality/presets/` |
|
|
175
|
+
| `dist/` | the compiled oxlint plugins and the doc templates, one template per kind of doc file |
|
|
167
176
|
| `oxlintrc.json` | the oxlint base config `.oxlintrc.json` extends |
|
|
168
177
|
| `stryker.preset.js` | the Stryker mutation-testing preset |
|
|
169
178
|
| `tsconfig.effect.json` | the tsconfig fragment with the Effect language-service block |
|
|
170
|
-
| `dist/` | the compiled oxlint plugins, one per purpose |
|
|
171
179
|
|
|
172
180
|
<!-- end generated shipped -->
|
|
173
181
|
|
|
@@ -179,4 +187,3 @@ Every path is relative to the installed package, `node_modules/@avi2dg/checks/`.
|
|
|
179
187
|
- [The dependency rules](docs/configs/dependency-rules.md)
|
|
180
188
|
- [The commit message lint](docs/configs/commit-messages.md)
|
|
181
189
|
- [Why it is shaped this way](docs/design.md)
|
|
182
|
-
- [Contribute to checks](CONTRIBUTING.md)
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// effect-channel/no-error-channel-escape.ts
|
|
1
|
+
// src/quality/effect-channel/no-error-channel-escape.ts
|
|
2
2
|
var EFFECT_SOURCES = new Set(["effect", "effect/Effect"]);
|
|
3
3
|
var INSTEAD = {
|
|
4
4
|
drops: "it drops the failure and the success together, so no caller can tell one from the other. Handle the error by tag, or keep it as a value with Effect.result or Effect.exit",
|
|
@@ -69,7 +69,7 @@ var rule = {
|
|
|
69
69
|
};
|
|
70
70
|
var no_error_channel_escape_default = rule;
|
|
71
71
|
|
|
72
|
-
// effect-channel/no-throw.ts
|
|
72
|
+
// src/quality/effect-channel/no-throw.ts
|
|
73
73
|
var rule2 = {
|
|
74
74
|
meta: {
|
|
75
75
|
type: "problem",
|
|
@@ -88,7 +88,7 @@ var rule2 = {
|
|
|
88
88
|
};
|
|
89
89
|
var no_throw_default = rule2;
|
|
90
90
|
|
|
91
|
-
// effect-channel/no-try-catch.ts
|
|
91
|
+
// src/quality/effect-channel/no-try-catch.ts
|
|
92
92
|
var rule3 = {
|
|
93
93
|
meta: {
|
|
94
94
|
type: "problem",
|
|
@@ -107,7 +107,7 @@ var rule3 = {
|
|
|
107
107
|
};
|
|
108
108
|
var no_try_catch_default = rule3;
|
|
109
109
|
|
|
110
|
-
// effect-channel/index.ts
|
|
110
|
+
// src/quality/effect-channel/index.ts
|
|
111
111
|
var plugin = {
|
|
112
112
|
meta: { name: "effect-channel" },
|
|
113
113
|
rules: {
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// readability/cognitive-nodes.ts
|
|
1
|
+
// src/complexity/readability/cognitive-nodes.ts
|
|
2
2
|
var CONTROL_TYPES = ["IfStatement", "ConditionalExpression", "SwitchStatement", "SwitchCase", "TryStatement", "CatchClause"];
|
|
3
3
|
var LOOP_TYPES = ["ForStatement", "ForInStatement", "ForOfStatement", "WhileStatement", "DoWhileStatement", "LabeledStatement"];
|
|
4
4
|
var CALL_TYPES = ["LogicalExpression", "BreakStatement", "ContinueStatement", "CallExpression", "NewExpression", "ImportExpression"];
|
|
@@ -7,7 +7,7 @@ var PLAIN_A_TYPES = ["BlockStatement", "ExpressionStatement", "ReturnStatement",
|
|
|
7
7
|
var PLAIN_B_TYPES = ["ClassDeclaration", "ClassExpression", "ClassBody", "MethodDefinition", "TSAbstractMethodDefinition", "PropertyDefinition", "TSAbstractPropertyDefinition", "AccessorProperty", "TSAbstractAccessorProperty", "ObjectExpression", "ArrayExpression"];
|
|
8
8
|
var PLAIN_C_TYPES = ["AwaitExpression", "UnaryExpression", "UpdateExpression", "SpreadElement", "YieldExpression", "BinaryExpression", "AssignmentExpression", "TSAsExpression", "TSSatisfiesExpression", "TSTypeAssertion", "TSNonNullExpression", "ChainExpression", "ParenthesizedExpression", "Decorator", "TSInstantiationExpression", "MemberExpression", "JSXMemberExpression", "TemplateLiteral", "TaggedTemplateExpression", "SequenceExpression", "JSXElement", "JSXFragment", "JSXOpeningElement", "JSXAttribute", "JSXExpressionContainer", "JSXSpreadChild", "JSXSpreadAttribute"];
|
|
9
9
|
|
|
10
|
-
// readability/cognitive-plain.ts
|
|
10
|
+
// src/complexity/readability/cognitive-plain.ts
|
|
11
11
|
function isControl(node) {
|
|
12
12
|
return CONTROL_TYPES.includes(node.type);
|
|
13
13
|
}
|
|
@@ -142,7 +142,7 @@ function plainChildrenC(node) {
|
|
|
142
142
|
}
|
|
143
143
|
}
|
|
144
144
|
|
|
145
|
-
// readability/cognitive.ts
|
|
145
|
+
// src/complexity/readability/cognitive.ts
|
|
146
146
|
function unreachable2(_value) {}
|
|
147
147
|
function scoreList(state, nodes, nesting, parent) {
|
|
148
148
|
for (const node of nodes) {
|
|
@@ -334,7 +334,7 @@ function cognitiveComplexity(root, names) {
|
|
|
334
334
|
return state.recursive ? state.total + 1 : state.total;
|
|
335
335
|
}
|
|
336
336
|
|
|
337
|
-
// readability/cognitive-complexity.ts
|
|
337
|
+
// src/complexity/readability/cognitive-complexity.ts
|
|
338
338
|
var DEFAULT_MAX = 15;
|
|
339
339
|
function maxOf(options) {
|
|
340
340
|
const [first] = options;
|
|
@@ -416,7 +416,7 @@ var rule = {
|
|
|
416
416
|
};
|
|
417
417
|
var cognitive_complexity_default = rule;
|
|
418
418
|
|
|
419
|
-
// readability/index.ts
|
|
419
|
+
// src/complexity/readability/index.ts
|
|
420
420
|
var plugin = {
|
|
421
421
|
meta: { name: "readability" },
|
|
422
422
|
rules: {
|
|
@@ -8,7 +8,7 @@ The shared commitlint config holds each pull request title to conventional commi
|
|
|
8
8
|
|
|
9
9
|
## Config
|
|
10
10
|
|
|
11
|
-
Commits follow `@commitlint/config-conventional` plus the house prefixes `commitlint.config.js` lists, shared from
|
|
11
|
+
Commits follow `@commitlint/config-conventional` plus the house prefixes `commitlint.config.js` lists, shared from `node_modules/@avi2dg/checks/commitlint.config.js`.
|
|
12
12
|
It arrives with the kit, since `@commitlint/cli` and `@commitlint/config-conventional` are dependencies, not peers.
|
|
13
13
|
|
|
14
14
|
## Workflow
|
|
@@ -31,7 +31,7 @@ The repo's `.oxlintrc.json` owns its Effect paths and exemptions in an override:
|
|
|
31
31
|
}
|
|
32
32
|
```
|
|
33
33
|
|
|
34
|
-
The kit ships the rule block in `presets/effect.oxlint.json` for copying into the override.
|
|
34
|
+
The kit ships the rule block in `src/quality/presets/effect.oxlint.json` for copying into the override.
|
|
35
35
|
Each config in an oxlint `extends` chain sets `plugins` explicitly, because an omitted list enables defaults across the chain.
|
|
36
36
|
`unicorn/no-process-exit` does not check a shebang script, so a bin can use `eslint/no-restricted-properties` for `process.exit`.
|
|
37
37
|
|
|
@@ -39,7 +39,7 @@ Each config in an oxlint `extends` chain sets `plugins` explicitly, because an o
|
|
|
39
39
|
|
|
40
40
|
The repository's `tsconfig.json` holds its Effect override under `compilerOptions.plugins`.
|
|
41
41
|
The override includes the same source paths and excludes the same exempt paths as oxlint.
|
|
42
|
-
The kit ships severity values in `presets/effect.language-service.json` for the override's `options`.
|
|
42
|
+
The kit ships severity values in `src/quality/presets/effect.language-service.json` for the override's `options`.
|
|
43
43
|
The kit's `tsconfig.effect.json` keeps the shared language service diagnostics.
|
|
44
44
|
|
|
45
45
|
## Related topics
|
|
@@ -13,7 +13,9 @@ A consuming repository puts each setting in the file its tool reads.
|
|
|
13
13
|
| `.github/workflows/*.yml` | Pull request commands, scheduled commands, runner labels | GitHub Actions and `checks-ci-wiring` |
|
|
14
14
|
| `.oxlintrc.json` | Effect paths, exemptions, file size, function size, statements, cognitive complexity and depth | oxlint |
|
|
15
15
|
| `oxlint-suppressions.json` | The existing violations oxlint suppresses, per file and rule | oxlint and `checks-suppressions-ratchet` |
|
|
16
|
+
| `exports-baseline.json` | The existing unused exports and types, per file, kind and name | `checks-exports` |
|
|
16
17
|
| `.jscpd.json` | The `path` and `ignore` globs of the files repetition is measured in | jscpd and `checks-repetition` |
|
|
18
|
+
| `knip.config.ts` | The `entry` globs Knip traces unreferenced files from, spread over the kit's `knip-base.json` | Knip, `checks-unused` and `checks-exports` |
|
|
17
19
|
| `tsconfig.json` | Effect language service scope and severity | TypeScript and Effect language service |
|
|
18
20
|
| `package.json` | `scripts` with the `checks-vendor` arguments in `prepare`, `author` and `contributors` | Bun, `checks-commit-identity` and `checks-vendor` |
|
|
19
21
|
| `bunfig.toml` | Test discovery and quarantine exclusion | Bun and `checks-test-layout` |
|
|
@@ -55,9 +57,9 @@ A repository records its existing violations with `oxlint --suppress-all`, which
|
|
|
55
57
|
`checks-suppressions-ratchet` refuses any count in that file that rises, so the recorded debt only falls.
|
|
56
58
|
The kit's own `.oxlintrc.json` sets these limits for each size override, and a repository may copy them:
|
|
57
59
|
|
|
58
|
-
<!-- generated size-limits: bun run build writes it from .oxlintrc.json, SIZE_RULES in
|
|
60
|
+
<!-- generated size-limits: bun run build writes it from .oxlintrc.json, SIZE_RULES in src/complexity/size-rules.ts and scripts/doc-blocks.ts -->
|
|
59
61
|
|
|
60
|
-
| Limits | oxlint rule | `
|
|
62
|
+
| Limits | oxlint rule | `src/**/*.ts`, `scripts/**/*.ts` | `tests/**/*.ts` |
|
|
61
63
|
| --- | --- | --- | --- |
|
|
62
64
|
| The most lines a file may hold, blank and comment lines counted | `max-lines` | 400 | 600 |
|
|
63
65
|
| The most lines a function may span, blank and comment lines counted | `max-lines-per-function` | 100 | off |
|
package/docs/design.md
CHANGED
|
@@ -12,8 +12,14 @@ Each entry below is a choice in the kit's shape and the constraint that forced i
|
|
|
12
12
|
- `files` in package.json is the published surface: `tests/`, `AGENTS.md` and the `.ts` plugin source never reach an install.
|
|
13
13
|
npm adds `package.json`, `README` and `LICENSE` to the tarball whatever `files` says.
|
|
14
14
|
`bun pm pack` builds the same tarball the registry serves, which is what the packed-tarball consumer e2e test installs.
|
|
15
|
-
- Each plugin ships compiled under `dist/`, built with `bun build
|
|
15
|
+
- Each plugin ships compiled under `dist/`, built with `bun build src/<vector>/<name>/index.ts --outdir dist/<name> --target node --format esm`.
|
|
16
16
|
Node refuses to type-strip a `.ts` plugin under `node_modules`, so the `.ts` source would fail to load from an installed package.
|
|
17
|
+
- The source sits under `src/<vector>/`, one directory for each thing the kit judges a repository on: complexity, quality, testing, docs, delivery and dependencies.
|
|
18
|
+
`src/core/` holds what every vector runs on, and `scripts/` holds only the kit's own build, which nothing ships.
|
|
19
|
+
Sorting by what loads a file put the two oxlint plugins at the root and every bin in one flat `scripts/`, so the files for one purpose sat in several places and nothing said which gate a helper served.
|
|
20
|
+
A mutation runner's default scope covers `src/`, so the kit's own Stryker run mutates its source without a `mutate` list.
|
|
21
|
+
The testing vector and its directory are named testing rather than tests, since a `src/tests/` beside the root `tests/` would read as a second suite.
|
|
22
|
+
An `exports` key a consumer resolves as a specifier keeps pointing at the file's new home, so that specifier resolves as before while a path read without resolution does not.
|
|
17
23
|
- The size rules are plain oxlint rules at `error` in `.oxlintrc.json`, and `bun run lint` enforces them on the whole tree.
|
|
18
24
|
A repository records its existing violations with `oxlint --suppress-all`, and `checks-suppressions-ratchet` refuses any count that rises.
|
|
19
25
|
The kit runs no size script of its own, since restating how oxlint reads its config and compares sites left corners the native rules never had.
|
|
@@ -24,7 +30,7 @@ Each entry below is a choice in the kit's shape and the constraint that forced i
|
|
|
24
30
|
- `dist/` is committed.
|
|
25
31
|
No `prepack` or `prepublishOnly` builds it, so a publish ships whatever bundle the publishing worktree holds.
|
|
26
32
|
Rebuild it after pulling with `bun run build`.
|
|
27
|
-
`bun run build` also emits `templates/` and `CHANGELOG.md`, which are committed the same way.
|
|
33
|
+
`bun run build` also emits `dist/templates/` and `CHANGELOG.md`, which are committed the same way.
|
|
28
34
|
CI runs `git diff --exit-code` over the whole tree after the build, because a test that compares a generated file with its source passes on the copy the build just rewrote.
|
|
29
35
|
- `CHANGELOG.md` is generated, so a release commit carries it and the tarball ships it.
|
|
30
36
|
The commit that bumps package.json `version` closes its release, and the `v*` tag goes on that commit, so commits merged after it wait for the next release.
|
|
@@ -72,7 +78,7 @@ Each entry below is a choice in the kit's shape and the constraint that forced i
|
|
|
72
78
|
Setting your own `options.enhancedResolveOptions` replaces the base's, so restate `exportsFields` and `conditionNames` if you do.
|
|
73
79
|
- dependency-cruiser `extends` merges same-name `forbidden` rules with the child's fields winning.
|
|
74
80
|
That is the entry-point and layer recipe under Boundaries in [The dependency rules](configs/dependency-rules.md).
|
|
75
|
-
- The templates in `templates/` are rendered from `
|
|
81
|
+
- The templates in `dist/templates/` are rendered from `src/docs/doc-templates.ts`, the spec `checks-docs` reads.
|
|
76
82
|
A template written by hand beside the check agrees with it only until someone edits one of them.
|
|
77
83
|
- A page's Diátaxis mode comes from `kind` front matter on the page, whatever directory holds it.
|
|
78
84
|
The repository makes the judgment beside the page, and the check holds it to that template.
|
|
@@ -86,7 +92,7 @@ Each entry below is a choice in the kit's shape and the constraint that forced i
|
|
|
86
92
|
Under a hard wrap a one-word edit reflows a paragraph, and the gate would then demand fixes to sentences the edit never touched.
|
|
87
93
|
- An agent file such as `AGENTS.md` takes the separator rules and no other prose rule.
|
|
88
94
|
One sentence per line serves the people who review a doc's diffs, and an agent file keeps each entry to one line however many sentences it holds.
|
|
89
|
-
- `
|
|
95
|
+
- `src/docs/prose-matchers.ts` imports nothing, so the gate and a write-time hook run one matcher and refuse in the same words.
|
|
90
96
|
A hook bundle ships without `node_modules`, so a matcher that needed Vale or a package could not refuse at write time.
|
|
91
97
|
- Readability grades and words such as easy stay out of the prose rules.
|
|
92
98
|
A score cannot fail a change without failing correct prose, and a suggestion nobody runs an editor for is never seen.
|
|
@@ -16,15 +16,15 @@ A refusal counts when any line of the comment carrying it was added.
|
|
|
16
16
|
|
|
17
17
|
## What it reads
|
|
18
18
|
|
|
19
|
-
It reads the diff between two commits, and the added lines of each file whose extension has a comment syntax in `
|
|
19
|
+
It reads the diff between two commits, and the added lines of each file whose extension has a comment syntax in `src/quality/comment-matchers.ts`.
|
|
20
20
|
It passes over a file with any other extension.
|
|
21
21
|
|
|
22
|
-
`
|
|
22
|
+
`src/quality/comment-matchers.ts` holds the scanner, the comment syntaxes and a synchronous `refused()`, and imports nothing.
|
|
23
23
|
A host such as a hook bundle can therefore copy it alone into a directory with no `node_modules` and import it as `@avi2dg/checks/scripts/comment-matchers.ts`.
|
|
24
24
|
The kit's own dependency cruise fails when that file gains an import.
|
|
25
25
|
`REFUSED_DIRECTIVES` in that file owns the refused directive names, and the checker builds its directive pattern from that list, so the two cannot disagree.
|
|
26
26
|
A consumer reads the same contract by importing `REFUSED_DIRECTIVES` from `@avi2dg/checks/scripts/comment-matchers.ts`.
|
|
27
|
-
`
|
|
27
|
+
`src/quality/comments.ts` wraps the same matchers in Effect for the gate.
|
|
28
28
|
|
|
29
29
|
## Arguments
|
|
30
30
|
|
|
@@ -60,5 +60,4 @@ It applies to every repository, so no selection leaves it out.
|
|
|
60
60
|
|
|
61
61
|
## Related topics
|
|
62
62
|
|
|
63
|
-
- [checks-backtest](checks-backtest.md)
|
|
64
63
|
- [checks-lint](checks-lint.md)
|
|
@@ -11,23 +11,25 @@ audience: consumers
|
|
|
11
11
|
It holds each doc file a change touches to the template for its kind, and lists every other doc file that does not conform yet without failing.
|
|
12
12
|
It holds each line a change adds or edits in a living doc or an agent file to the prose rules, as [The prose rules](#the-prose-rules) says.
|
|
13
13
|
It fails when a living doc names a path, link or command that does not resolve, and the range added it or broke it, as [Paths, links and commands](#paths-links-and-commands) says.
|
|
14
|
-
The package ships one template per kind under `templates/`, and a repository starts a new doc file by copying one:
|
|
14
|
+
The package ships one template per kind under `dist/templates/`, and a repository starts a new doc file by copying one:
|
|
15
15
|
|
|
16
16
|
```sh
|
|
17
|
-
cp node_modules/@avi2dg/checks/templates/how-to.md docs/add-a-supplier.md
|
|
17
|
+
cp node_modules/@avi2dg/checks/dist/templates/how-to.md docs/add-a-supplier.md
|
|
18
18
|
```
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
A host resolves a template as `@avi2dg/checks/templates/how-to.md`, which keeps pointing at it wherever the package holds the templates.
|
|
21
|
+
|
|
22
|
+
<!-- generated doc-kinds: bun run build writes it from src/docs/doc-rules.ts, src/docs/doc-templates.ts and scripts/doc-blocks.ts -->
|
|
21
23
|
|
|
22
24
|
| File | Kind | Template |
|
|
23
25
|
| --- | --- | --- |
|
|
24
|
-
| `README.md` | readme | `templates/readme.md` |
|
|
25
|
-
| `CHANGELOG.md` | changelog | `templates/changelog.md` |
|
|
26
|
-
| `AGENTS.md` | agents | `templates/agents.md` |
|
|
27
|
-
| `CLAUDE.md` | claude | `templates/claude.md` |
|
|
28
|
-
| `CONTRIBUTING.md` | how-to | `templates/how-to.md` |
|
|
29
|
-
| each file in `docs/adr/` but its generated index, `README.md` | adr | `templates/adr.md` |
|
|
30
|
-
| a page with `kind` in front matter | tutorial, how-to, reference or explanation | `templates/<mode>.md` |
|
|
26
|
+
| `README.md` | readme | `dist/templates/readme.md` |
|
|
27
|
+
| `CHANGELOG.md` | changelog | `dist/templates/changelog.md` |
|
|
28
|
+
| `AGENTS.md` | agents | `dist/templates/agents.md` |
|
|
29
|
+
| `CLAUDE.md` | claude | `dist/templates/claude.md` |
|
|
30
|
+
| `CONTRIBUTING.md` | how-to | `dist/templates/how-to.md` |
|
|
31
|
+
| each file in `docs/adr/` but its generated index, `README.md` | adr | `dist/templates/adr.md` |
|
|
32
|
+
| a page with `kind` in front matter | tutorial, how-to, reference or explanation | `dist/templates/<mode>.md` |
|
|
31
33
|
|
|
32
34
|
<!-- end generated doc-kinds -->
|
|
33
35
|
|
|
@@ -60,7 +62,7 @@ A template decides a file's structure, and the template file itself is the refer
|
|
|
60
62
|
|
|
61
63
|
A line a change adds or edits in a living doc or an agent file is held to the prose rules, and a line the change leaves alone is not, so a repository needs no cleanup pass before it runs them.
|
|
62
64
|
|
|
63
|
-
<!-- generated living-docs: bun run build writes it from
|
|
65
|
+
<!-- generated living-docs: bun run build writes it from src/docs/prose-matchers.ts and scripts/doc-blocks.ts -->
|
|
64
66
|
|
|
65
67
|
A living doc is one of these:
|
|
66
68
|
|
|
@@ -77,7 +79,7 @@ These are records, and take no prose rule:
|
|
|
77
79
|
|
|
78
80
|
<!-- end generated living-docs -->
|
|
79
81
|
|
|
80
|
-
<!-- generated prose-rules: bun run build writes it from PROSE_RULES in
|
|
82
|
+
<!-- generated prose-rules: bun run build writes it from PROSE_RULES in src/docs/prose-matchers.ts and scripts/doc-blocks.ts -->
|
|
81
83
|
|
|
82
84
|
| Refused | For example | Write instead | In agent files |
|
|
83
85
|
| --- | --- | --- | --- |
|
|
@@ -98,14 +100,14 @@ A bold label that opens a line, as in `**Status.**`, heads the sentence after it
|
|
|
98
100
|
Fenced code, inline code, link destinations, URLs, HTML comments and front matter are not prose, so no rule reads them.
|
|
99
101
|
Readability scores and word choice, such as easy, are not checked.
|
|
100
102
|
|
|
101
|
-
`
|
|
103
|
+
`src/docs/prose-matchers.ts` holds the rules and a synchronous `proseRefused()`, and imports nothing.
|
|
102
104
|
A host such as a hook bundle can therefore copy it alone into a directory with no `node_modules` and import it as `@avi2dg/checks/scripts/prose-matchers.ts`, to refuse the same lines at write time.
|
|
103
105
|
|
|
104
106
|
## Paths, links and commands
|
|
105
107
|
|
|
106
108
|
Each reference a living doc names has to resolve at the head commit:
|
|
107
109
|
|
|
108
|
-
- A path in inline code that ends in a file extension, such as `
|
|
110
|
+
- A path in inline code that ends in a file extension, such as `src/core/lint.ts`, names a file from the root or from the doc's directory.
|
|
109
111
|
- A relative Markdown link names a file or a directory, and its anchor names a heading in the file it links, as GitHub derives the anchor, or an explicit `id`.
|
|
110
112
|
- A `bun run` command in code names a script in the nearest `package.json`, a bin in `node_modules/.bin`, or a file that exists.
|
|
111
113
|
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
---
|
|
2
|
+
kind: reference
|
|
3
|
+
audience: consumers
|
|
4
|
+
---
|
|
5
|
+
# checks-exports
|
|
6
|
+
|
|
7
|
+
`checks-exports` is the gate that refuses an exported value or type nothing imports, and a reader looks it up when Knip names a symbol no file reaches.
|
|
8
|
+
|
|
9
|
+
## What it checks
|
|
10
|
+
|
|
11
|
+
It runs Knip with the repository's own configuration and names each exported value and type no file imports.
|
|
12
|
+
It reads only the exports and types issue types, so an unreferenced file or an unused dependency never fails it.
|
|
13
|
+
It asks Knip for those issue types itself, so a configuration that narrows `include` or excludes them still has its exports judged.
|
|
14
|
+
A configuration that turns the exports or types rules off silences those symbols, so keep both rules on.
|
|
15
|
+
It holds each reported symbol against `exports-baseline.json`, and fails on any symbol the baseline does not hold.
|
|
16
|
+
It fails on any baseline entry the range adds unless Knip reports that same symbol unused at the base, so the baseline records debt that already existed and never debt the range creates.
|
|
17
|
+
It fails on any baseline entry Knip no longer reports, so the baseline only shrinks.
|
|
18
|
+
It fails when the repository tracks no TypeScript source, since an empty scan would pass without judging anything.
|
|
19
|
+
It fails when the repository holds no Knip configuration, since Knip's default entries cannot tell a dead export from a public one.
|
|
20
|
+
|
|
21
|
+
## What it reads
|
|
22
|
+
|
|
23
|
+
It runs Knip over the working tree, so an uncommitted file is judged like a committed one.
|
|
24
|
+
It reads the repository's Knip configuration, which names the entries.
|
|
25
|
+
It reads `exports-baseline.json` in the repository root, which holds each accepted unused export as a file, kind and name triple.
|
|
26
|
+
It reads `exports-baseline.json` again at the base of the range, where a commit without the file counts as empty.
|
|
27
|
+
When the range adds baseline entries, it runs Knip again on a temporary checkout of the base and removes the checkout when it ends.
|
|
28
|
+
That checkout links the repository's `node_modules`, so a configuration importing the kit's base loads there too.
|
|
29
|
+
Knip configurations do not extend a package file, so the consumer configuration imports the kit's base and spreads it:
|
|
30
|
+
|
|
31
|
+
```ts
|
|
32
|
+
import base from "@avi2dg/checks/knip-base.json";
|
|
33
|
+
|
|
34
|
+
export default { ...base, entry: ["src/index.ts", "tests/**/*.test.ts"] };
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
The base in `knip-base.json` reports only unreferenced files.
|
|
38
|
+
The gate resolves the Knip binary from the installed kit, so a consumer installs nothing beyond the kit.
|
|
39
|
+
|
|
40
|
+
## Arguments
|
|
41
|
+
|
|
42
|
+
```sh
|
|
43
|
+
checks-exports <base-ref> <head-ref>
|
|
44
|
+
checks-exports <ref>
|
|
45
|
+
checks-exports --write
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
With two arguments the base is where the head branched off, at their merge-base.
|
|
49
|
+
When the checked-out commit is a merge of the head ref and one other commit, as a pull request's default checkout is, the base is that other commit instead.
|
|
50
|
+
So under `checks-lint` a pull request's merge checkout is judged against the base branch tip it merges, and a symbol that branch already baselined does not count as added.
|
|
51
|
+
With one the base is that commit's parent, or the empty tree for a repository's first commit, where nothing counts as already unused.
|
|
52
|
+
With `--write` it records every unused export and type Knip reports into `exports-baseline.json`, the way `oxlint --suppress-all` seeds `oxlint-suppressions.json`.
|
|
53
|
+
|
|
54
|
+
## Seeding a baseline
|
|
55
|
+
|
|
56
|
+
A repository adopting the gate runs `checks-exports --write` on a branch that changes no source and commits the file it writes.
|
|
57
|
+
The gate passes that range, since Knip reports every seeded symbol unused at the base too.
|
|
58
|
+
A seed written after the range adds a dead export, or after it removes the last import of one, fails on that symbol.
|
|
59
|
+
|
|
60
|
+
## Exit codes
|
|
61
|
+
|
|
62
|
+
| Code | When |
|
|
63
|
+
| --- | --- |
|
|
64
|
+
| 0 | no reported symbol is unlisted, no baseline entry is added or stale, or `--write` recorded the baseline |
|
|
65
|
+
| 1 | a reported symbol is unlisted, a baseline entry is added or stale or the repository holds no Knip configuration |
|
|
66
|
+
| 2 | a ref does not resolve, the repository tracks no TypeScript source, Knip cannot run, or a report or baseline does not parse |
|
|
67
|
+
|
|
68
|
+
## Sample output
|
|
69
|
+
|
|
70
|
+
```
|
|
71
|
+
exports: 2 unused export(s) not in exports-baseline.json:
|
|
72
|
+
src/used.ts: unusedExport (export)
|
|
73
|
+
src/used.ts: UnusedOptions (type)
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
A baseline entry the range adds fails when Knip does not report its symbol unused at the base:
|
|
77
|
+
|
|
78
|
+
```
|
|
79
|
+
exports: 1 exports-baseline.json export(s) the range adds that its base did not leave unused, remove the export instead:
|
|
80
|
+
src/used.ts: unusedExport (export)
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
A passing run with a held baseline counts what it holds:
|
|
84
|
+
|
|
85
|
+
```
|
|
86
|
+
exports: 2 unused export(s) in exports-baseline.json, and no new ones
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
A passing run with an empty baseline says so:
|
|
90
|
+
|
|
91
|
+
```
|
|
92
|
+
exports: no unused exports or types
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
## Opting out
|
|
96
|
+
|
|
97
|
+
`checks-lint` runs this gate only when the repository tracks `.ts` or `.tsx` files.
|
|
98
|
+
A repository that tracks one names its entries in a Knip configuration.
|
|
99
|
+
|
|
100
|
+
## Related topics
|
|
101
|
+
|
|
102
|
+
- [checks-lint](checks-lint.md)
|
|
103
|
+
- [checks-suppressions-ratchet](checks-suppressions-ratchet.md)
|
|
104
|
+
- [checks-unused](checks-unused.md)
|
|
@@ -43,7 +43,7 @@ checks-flake: 3 of 10 run(s) failed, 1 test(s) failing in them
|
|
|
43
43
|
|
|
44
44
|
| Test | Failed | Seeds |
|
|
45
45
|
| --- | --- | --- |
|
|
46
|
-
| tests/cache.test.ts:6 reads the cache | 3 of 10 runs | 2170533150, 4046124386, 180394251 |
|
|
46
|
+
| tests/unit/cache.test.ts:6 reads the cache | 3 of 10 runs | 2170533150, 4046124386, 180394251 |
|
|
47
47
|
|
|
48
48
|
Reproduce a failing run with bun test --randomize --seed=<seed>.
|
|
49
49
|
```
|
|
@@ -8,7 +8,7 @@ audience: consumers
|
|
|
8
8
|
|
|
9
9
|
## What it checks
|
|
10
10
|
|
|
11
|
-
It runs the gates under [What runs](../../README.md#what-runs)
|
|
11
|
+
It runs the gates under [What runs](../../README.md#what-runs), each in its own process.
|
|
12
12
|
Gates requiring tracked TypeScript files begin running when the repository tracks TypeScript.
|
|
13
13
|
All other gates run for every repository.
|
|
14
14
|
|
|
@@ -43,7 +43,7 @@ With one it judges that commit, including a repository's first commit.
|
|
|
43
43
|
|
|
44
44
|
```
|
|
45
45
|
quarantine-clock: 1 test(s) in tests/quarantine/ is past 30 days; fix each and move it back, or delete it:
|
|
46
|
-
tests/quarantine/billing.test.ts entered quarantine on 2026-08-01 (45 days ago)
|
|
46
|
+
tests/quarantine/unit/billing.test.ts entered quarantine on 2026-08-01 (45 days ago)
|
|
47
47
|
```
|
|
48
48
|
|
|
49
49
|
## Opting out
|
|
@@ -10,18 +10,20 @@ audience: consumers
|
|
|
10
10
|
|
|
11
11
|
It fails unless the repository holds this shape, and names the file and the path to move it to when it does not.
|
|
12
12
|
|
|
13
|
-
- Every test file is `tests
|
|
14
|
-
A
|
|
13
|
+
- Every test file is `tests/<level>/**/*.test.ts` or `.tsx`, and the level is `unit`, `e2e`, `live` or `pixel`.
|
|
14
|
+
A quarantined test keeps its level as `tests/quarantine/<level>/**/*.test.ts`.
|
|
15
|
+
A `*.test.ts`, `*.spec.ts` or `*_test.ts` under `src/`, `test/`, `__tests__/`, the repository root or a directory under `tests/` that names no level fails.
|
|
16
|
+
The path it names for the move is under `tests/unit/` unless the file already sits under a level.
|
|
15
17
|
- `tests/lib/**` holds helpers and `tests/fixtures/**` holds data, and neither may hold a test file.
|
|
16
|
-
|
|
18
|
+
Under its level, a test may sit in groups nested as deep as it likes.
|
|
17
19
|
- `tests/live/**` holds tests that need a live machine, and `tests/pixel/**` holds tests that need a display.
|
|
18
20
|
Bun ignores both directories in the default suite.
|
|
19
21
|
A live tier with test files requires `test:live` set to `checks-test --tier=live`.
|
|
20
22
|
A pixel tier with test files requires `test:pixel` set to `checks-test --tier=pixel`.
|
|
21
|
-
- A test runs
|
|
22
|
-
A test outside `
|
|
23
|
+
- A test runs in-process or in a process of its own.
|
|
24
|
+
A test outside the `e2e`, `live` and `pixel` levels runs in-process, quarantined or not, so it may not import `node:child_process`, `net`, `http`, `https`, `http2`, `tls` or `dgram`.
|
|
23
25
|
It may not import `$`, `spawn`, `spawnSync`, `connect`, `serve` or `listen` from `bun`, may not touch `Bun.$` or `Bun.spawn`, and may not call `fetch`.
|
|
24
|
-
A test
|
|
26
|
+
A test at the `e2e`, `live` or `pixel` level may do all of it, under `tests/quarantine/` as well.
|
|
25
27
|
Helpers in `tests/lib/**` answer to the same rule, since an in-process test reaches them.
|
|
26
28
|
- `scripts.test` is exactly `checks-test`, which runs `bun test --randomize` as [checks-test](checks-test.md) says.
|
|
27
29
|
- `scripts.lint` runs this check, itself or through `checks-lint` called by its bare bin name.
|
|
@@ -30,12 +32,15 @@ It fails unless the repository holds this shape, and names the file and the path
|
|
|
30
32
|
The check also accepts the list without `repos/**`, so a repository that links no library under `repos/` may drop it.
|
|
31
33
|
Other tables, and extra `[test]` keys, are the repository's own.
|
|
32
34
|
|
|
33
|
-
The in-process
|
|
35
|
+
The in-process tests under `tests/unit/` are what a mutation run takes as its tests, and a runner names them by that path rather than by a list of paths to ignore.
|
|
34
36
|
`tests/e2e/**` is left out of a mutate scope by construction, because a subprocess kills both the speed and the coverage signal a mutant needs.
|
|
35
37
|
|
|
36
38
|
The preset also skips `tests/quarantine/**` and `repos/**` on a default run.
|
|
37
39
|
The `repos/**` entry keeps the suite from following the library links `checks-vendor` manages into trees whose tests are not this repository's.
|
|
38
|
-
A test that turns flaky moves there, so the suite stays trustworthy
|
|
40
|
+
A test that turns flaky moves there at its own level, so the suite stays trustworthy.
|
|
41
|
+
A flaky test under `tests/e2e/stack/` moves to the same path under `tests/quarantine/e2e/stack/`, where it may still spawn, and moves back once fixed.
|
|
42
|
+
A `quarantine` directory below a level is refused, since the preset's ignore does not reach it and the test would still run.
|
|
43
|
+
The flake still runs on demand:
|
|
39
44
|
|
|
40
45
|
```sh
|
|
41
46
|
bun test --path-ignore-patterns='' tests/quarantine
|
|
@@ -72,7 +77,7 @@ It checks the directory it runs in, or the directory it is given.
|
|
|
72
77
|
|
|
73
78
|
```
|
|
74
79
|
test-layout: 4 violation(s)
|
|
75
|
-
src/a.test.ts: a test file must live at tests
|
|
80
|
+
src/a.test.ts: a test file must live at tests/<level>/**/*.test.ts, or tests/quarantine/<level>/**/*.test.ts while quarantined, with unit, e2e, live, or pixel as the level; move it to tests/unit/a.test.ts
|
|
76
81
|
package.json: scripts.test must be exactly "checks-test", which runs bun test --randomize and judges its skips, found "bun test"
|
|
77
82
|
package.json: scripts.lint must run the layout check: add "checks-lint"
|
|
78
83
|
bunfig.toml: bunfig.toml is missing; bun has no bunfig extends, so copy node_modules/@avi2dg/checks/bunfig.toml
|
|
@@ -87,7 +87,7 @@ It refuses test filters because every test excluded by a filter would look skipp
|
|
|
87
87
|
|
|
88
88
|
```
|
|
89
89
|
checks-test: 1 skipped test(s) undeclared in this local run:
|
|
90
|
-
tests/pricing.test.ts:12 rounds half to even: skipped with no reason at its test site; use test.skipIf(condition)(skipReason(reason, name), fn)
|
|
90
|
+
tests/unit/pricing.test.ts:12 rounds half to even: skipped with no reason at its test site; use test.skipIf(condition)(skipReason(reason, name), fn)
|
|
91
91
|
```
|
|
92
92
|
|
|
93
93
|
A run with no skipped tests ends with:
|