Type Declarations Suite
Audit .d.ts mirror files against their source files for structure, ordering, naming, and coverage with registerTypeDeclarationSuite.
Summary
- Scans a package for source files and their
<root>/types/**/*.d.tsmirrors. - Runs eleven inspector checks covering section order, identifier naming, source-to-mirror symmetry, and coverage.
- Scans the current working directory by default, which is the consumer root when run from
node_modules.
Why Use This Suite?
- Keeps declaration mirrors in lockstep with their sources so types never silently drift from the code.
- Enforces one naming and ordering convention, so any contributor can find a type by name and trust that its mirror is current.
- Catches missing or stale mirror entries during the test run instead of at publish time.
Examples
Usage
src/tests/type-declarations.test.ts
import { registerTypeDeclarationSuite } from '@cbnventures/nova/rules/vitest';
import * as vitest from 'vitest';
registerTypeDeclarationSuite({
vitest,
enable: 'all',
typeRoots: ['src'],
});
The packageRoot defaults to process.cwd(), so the suite audits the project Vitest runs in. Pass standaloneTypeFiles for declaration files that have no source mirror.
Configuration
| Field | Type | Default | Description |
|---|---|---|---|
packageRoot | string | process.cwd() | Absolute root the suite scans and computes display paths against. |
typeRoots | string[] | ['src'] | Top-level directories holding sources and their <root>/types/**/*.d.ts mirrors. |
standaloneTypeFiles | string[] | [] | Suffix-matched declaration paths exempt from the source-mirror rules and checked as standalone files. |
mapping | { sourceToDts(file): string; dtsToSource(file): string } | derived from typeRoots | Custom source-to-mirror path mapping; defaults to one derived from typeRoots. |
enable | 'all' | ToggleKey[] | required | Which checks run. Use 'all' for every check, or a list to freeze an exact set. |
Toggle Keys
| Toggle Key | Description |
|---|---|
inspector-cross-section-references | A declaration section may only reference types from its own section or imported names; cross-section references must move to a shared type file. |
inspector-dts-import-verbatim | Requires a type imported from another .d.ts file to be used verbatim, with no as alias, since declared types are already canonically named. |
inspector-no-inline-import-types | Forbids inline import('...') type references in a declaration file; reference types through top-of-file named type imports instead. |
inspector-section-alphabetical | Requires sections inside a declaration file to be alphabetically ordered. |
inspector-first-come-first-serve-order | Requires declaration order to follow first appearance in the source file. |
inspector-object-property-types | Requires each object-type property to use a named type that starts with the parent type's name and is defined earlier in the file. |
inspector-section-coverage | Requires every source section to have matching mirror types, and every mirror section to map back to a real source section. |
inspector-variable-type-symmetry | Requires a source file's body vars, params, and return types to follow the Mode 2 naming rules and be mirrored in the paired declaration. |
inspector-identifier-vs-filename | Forbids a top-level class, function, or function-typed const from sharing the file's name. |
inspector-filename-validation | Requires each source and declaration path segment to be kebab-case or PascalCase after stripping recognized suffixes. |
inspector-standalone-type-files | Validates declaration files listed in standaloneTypeFiles against the standalone ruleset. |
Troubleshooting
- The suite audits the wrong project — Confirm Vitest runs from the project root so
packageRootresolves toprocess.cwd(). SetpackageRootexplicitly when running from elsewhere. inspector-variable-type-symmetrycan't resolve the paired declaration — The rule maps each source file to its.d.tsto validate body-var, param, and return naming; if your source directory is not namedsrc, settypeRootsto your actual roots, or pass a custommapping.- A standalone declaration is flagged as missing a source — Add its suffix-matched path to
standaloneTypeFilesso it is checked as a standalone file instead.