eslint-plugin-traceability 1.8.0 → 1.8.1

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.
Files changed (73) hide show
  1. package/CHANGELOG.md +3 -3
  2. package/README.md +26 -27
  3. package/SECURITY.md +132 -0
  4. package/lib/src/index.d.ts +6 -35
  5. package/lib/src/index.js +8 -5
  6. package/lib/tests/config/flat-config-presets-integration.test.d.ts +1 -0
  7. package/lib/tests/config/flat-config-presets-integration.test.js +75 -0
  8. package/lib/tests/plugin-default-export-and-configs.test.js +0 -2
  9. package/lib/tests/rules/prefer-implements-annotation.test.js +28 -0
  10. package/package.json +6 -6
  11. package/user-docs/api-reference.md +33 -13
  12. package/user-docs/eslint-9-setup-guide.md +89 -6
  13. package/user-docs/migration-guide.md +20 -4
  14. package/docs/ci-cd-pipeline.md +0 -224
  15. package/docs/cli-integration.md +0 -22
  16. package/docs/code-quality-refactor-opportunities-2025-12-03.md +0 -78
  17. package/docs/config-presets.md +0 -38
  18. package/docs/conventional-commits-guide.md +0 -185
  19. package/docs/custom-rules-development-guide.md +0 -659
  20. package/docs/decisions/0001-allow-dynamic-require-for-built-plugins.md +0 -26
  21. package/docs/decisions/001-typescript-for-eslint-plugin.accepted.md +0 -111
  22. package/docs/decisions/002-jest-for-eslint-testing.accepted.md +0 -137
  23. package/docs/decisions/003-code-quality-ratcheting-plan.md +0 -48
  24. package/docs/decisions/004-automated-version-bumping-for-ci-cd.md +0 -196
  25. package/docs/decisions/005-github-actions-validation-tooling.accepted.md +0 -144
  26. package/docs/decisions/006-semantic-release-for-automated-publishing.accepted.md +0 -227
  27. package/docs/decisions/007-github-releases-over-changelog.accepted.md +0 -216
  28. package/docs/decisions/008-ci-audit-flags.accepted.md +0 -60
  29. package/docs/decisions/009-security-focused-lint-rules.accepted.md +0 -64
  30. package/docs/decisions/010-implements-annotation-for-multi-story-requirements.proposed.md +0 -184
  31. package/docs/decisions/adr-0001-console-usage-for-cli-guards.md +0 -190
  32. package/docs/decisions/adr-accept-dev-dep-risk-glob.md +0 -40
  33. package/docs/decisions/adr-commit-branch-tests.md +0 -54
  34. package/docs/decisions/adr-maintenance-cli-interface.md +0 -140
  35. package/docs/decisions/adr-pre-push-parity.md +0 -112
  36. package/docs/decisions/code-quality-ratcheting-plan.md +0 -53
  37. package/docs/dependency-health.md +0 -238
  38. package/docs/eslint-9-setup-guide.md +0 -517
  39. package/docs/eslint-plugin-development-guide.md +0 -487
  40. package/docs/functionality-coverage-2025-12-03.md +0 -250
  41. package/docs/jest-testing-guide.md +0 -100
  42. package/docs/rules/prefer-implements-annotation.md +0 -219
  43. package/docs/rules/require-branch-annotation.md +0 -71
  44. package/docs/rules/require-req-annotation.md +0 -203
  45. package/docs/rules/require-story-annotation.md +0 -159
  46. package/docs/rules/valid-annotation-format.md +0 -418
  47. package/docs/rules/valid-req-reference.md +0 -153
  48. package/docs/rules/valid-story-reference.md +0 -120
  49. package/docs/security-incidents/2025-11-17-glob-cli-incident.md +0 -45
  50. package/docs/security-incidents/2025-11-18-brace-expansion-redos.md +0 -45
  51. package/docs/security-incidents/2025-11-18-bundled-dev-deps-accepted-risk.md +0 -93
  52. package/docs/security-incidents/2025-11-18-tar-race-condition.md +0 -43
  53. package/docs/security-incidents/2025-12-03-dependency-health-review.md +0 -58
  54. package/docs/security-incidents/SECURITY-INCIDENT-2025-11-18-semantic-release-bundled-npm.known-error.md +0 -104
  55. package/docs/security-incidents/SECURITY-INCIDENT-TEMPLATE.md +0 -37
  56. package/docs/security-incidents/dependency-override-rationale.md +0 -57
  57. package/docs/security-incidents/dev-deps-high.json +0 -116
  58. package/docs/security-incidents/handling-procedure.md +0 -54
  59. package/docs/stories/001.0-DEV-PLUGIN-SETUP.story.md +0 -92
  60. package/docs/stories/002.0-DEV-ESLINT-CONFIG.story.md +0 -82
  61. package/docs/stories/003.0-DEV-FUNCTION-ANNOTATIONS.story.md +0 -112
  62. package/docs/stories/004.0-DEV-BRANCH-ANNOTATIONS.story.md +0 -153
  63. package/docs/stories/005.0-DEV-ANNOTATION-VALIDATION.story.md +0 -138
  64. package/docs/stories/006.0-DEV-FILE-VALIDATION.story.md +0 -144
  65. package/docs/stories/007.0-DEV-ERROR-REPORTING.story.md +0 -163
  66. package/docs/stories/008.0-DEV-AUTO-FIX.story.md +0 -150
  67. package/docs/stories/009.0-DEV-MAINTENANCE-TOOLS.story.md +0 -117
  68. package/docs/stories/010.0-DEV-DEEP-VALIDATION.story.md +0 -124
  69. package/docs/stories/010.1-DEV-CONFIGURABLE-PATTERNS.story.md +0 -149
  70. package/docs/stories/010.2-DEV-MULTI-STORY-SUPPORT.story.md +0 -216
  71. package/docs/stories/010.3-DEV-MIGRATE-TO-IMPLEMENTS.story.md +0 -236
  72. package/docs/stories/developer-story.map.md +0 -120
  73. package/docs/ts-jest-presets-guide.md +0 -548
package/CHANGELOG.md CHANGED
@@ -1,9 +1,9 @@
1
- # [1.8.0](https://github.com/voder-ai/eslint-plugin-traceability/compare/v1.7.1...v1.8.0) (2025-12-03)
1
+ ## [1.8.1](https://github.com/voder-ai/eslint-plugin-traceability/compare/v1.8.0...v1.8.1) (2025-12-04)
2
2
 
3
3
 
4
- ### Features
4
+ ### Bug Fixes
5
5
 
6
- * accept [@implements](https://github.com/implements) annotations in require rules ([bdf0994](https://github.com/voder-ai/eslint-plugin-traceability/commit/bdf0994f0d0e16bd751fbd89c08c67bddee52c16))
6
+ * disable prefer-implements-annotation in default presets ([89c62e9](https://github.com/voder-ai/eslint-plugin-traceability/commit/89c62e907be95030f89e6a3ab6df24a4ba32ab62))
7
7
 
8
8
  # Changelog
9
9
 
package/README.md CHANGED
@@ -35,22 +35,30 @@ This example shows the recommended starting point using the plugin's recommended
35
35
  import js from "@eslint/js";
36
36
  import traceability from "eslint-plugin-traceability";
37
37
 
38
- export default [js.configs.recommended, traceability.configs.recommended];
38
+ export default [
39
+ js.configs.recommended,
40
+ {
41
+ plugins: {
42
+ traceability,
43
+ },
44
+ },
45
+ ...traceability.configs.recommended,
46
+ ];
39
47
  ```
40
48
 
41
49
  ### Available Rules
42
50
 
43
- - `traceability/require-story-annotation` Enforces presence of `@story` annotations. ([Documentation](docs/rules/require-story-annotation.md))
44
- - `traceability/require-req-annotation` Enforces presence of `@req` annotations. ([Documentation](docs/rules/require-req-annotation.md))
45
- - `traceability/require-branch-annotation` Enforces presence of branch annotations. ([Documentation](docs/rules/require-branch-annotation.md))
46
- - `traceability/valid-annotation-format` Enforces correct format of traceability annotations. ([Documentation](docs/rules/valid-annotation-format.md))
47
- - `traceability/valid-story-reference` Validates that `@story` references point to existing story files. ([Documentation](docs/rules/valid-story-reference.md))
48
- - `traceability/valid-req-reference` Validates that `@req` references point to existing requirement IDs. ([Documentation](docs/rules/valid-req-reference.md))
49
- - `traceability/prefer-implements-annotation` Recommends migration from legacy `@story`/`@req` annotations to `@implements` (disabled by default). ([Documentation](docs/rules/prefer-implements-annotation.md))
51
+ - `traceability/require-story-annotation` Enforces presence of `@story` annotations. (See the rule documentation in the plugin's user guide.)
52
+ - `traceability/require-req-annotation` Enforces presence of `@req` annotations. (See the rule documentation in the plugin's user guide.)
53
+ - `traceability/require-branch-annotation` Enforces presence of branch annotations. (See the rule documentation in the plugin's user guide.)
54
+ - `traceability/valid-annotation-format` Enforces correct format of traceability annotations. (See the rule documentation in the plugin's user guide.)
55
+ - `traceability/valid-story-reference` Validates that `@story` references point to existing story files. (See the rule documentation in the plugin's user guide.)
56
+ - `traceability/valid-req-reference` Validates that `@req` references point to existing requirement IDs. (See the rule documentation in the plugin's user guide.)
57
+ - `traceability/prefer-implements-annotation` Recommends migration from legacy `@story`/`@req` annotations to `@implements` (opt-in; disabled by default in the presets and must be explicitly enabled). (See the rule documentation in the plugin's user guide.)
50
58
 
51
- Configuration options: For detailed per-rule options (such as scopes, branch types, and story directory settings), see the individual rule docs in [`docs/rules/`](docs/rules) and the consolidated [API Reference](user-docs/api-reference.md).
59
+ Configuration options: For detailed per-rule options (such as scopes, branch types, and story directory settings), see the individual rule docs in the plugin's user guide and the consolidated [API Reference](user-docs/api-reference.md).
52
60
 
53
- For development and contribution guidelines, see the [ESLint Plugin Development Guide](docs/eslint-plugin-development-guide.md).
61
+ For development and contribution guidelines, see the contribution guide in the repository.
54
62
 
55
63
  ## Quick Start
56
64
 
@@ -61,8 +69,12 @@ For development and contribution guidelines, see the [ESLint Plugin Development
61
69
  import traceability from "eslint-plugin-traceability";
62
70
 
63
71
  export default [
64
- // Load the traceability plugin's recommended rule set
65
- traceability.configs.recommended,
72
+ {
73
+ plugins: {
74
+ traceability,
75
+ },
76
+ },
77
+ ...traceability.configs.recommended,
66
78
  ];
67
79
  ```
68
80
 
@@ -183,6 +195,8 @@ These tests verify end-to-end behavior of the plugin via the ESLint CLI.
183
195
 
184
196
  ## Security and Dependency Health
185
197
 
198
+ For the canonical, user-facing security policy (including how to report vulnerabilities), see [SECURITY.md](SECURITY.md). The additional files under `docs/` referenced below provide deeper background and implementation details for interested readers.
199
+
186
200
  ### What end users can expect from production dependencies
187
201
 
188
202
  - The published `eslint-plugin-traceability` package is intended to ship **only with production dependencies that have no known high‑severity vulnerabilities** at release time.
@@ -217,29 +231,14 @@ These tests verify end-to-end behavior of the plugin via the ESLint CLI.
217
231
  - The issue is confined to the CI environment that prepares and publishes releases.
218
232
  - It **cannot impact** the runtime behavior or dependency graph of the `eslint-plugin-traceability` package you install or use in your own projects.
219
233
 
220
- ### Optional deeper background
221
-
222
- For readers who want more context on the dependency and security model (not required to use the plugin):
223
-
224
- - Dependency health overview: [docs/dependency-health.md](docs/dependency-health.md)
225
- - Detailed incident note about the semantic‑release/npm toolchain risk:
226
- [docs/security-incidents/SECURITY-INCIDENT-2025-11-18-semantic-release-bundled-npm.known-error.md](docs/security-incidents/SECURITY-INCIDENT-2025-11-18-semantic-release-bundled-npm.known-error.md)
227
-
228
- These documents are informational and describe internal processes and known toolchain limitations; they do not change the guarantees described above for end users.
229
-
230
234
  ## Documentation Links
231
235
 
232
236
  - ESLint v9 Setup Guide: [user-docs/eslint-9-setup-guide.md](user-docs/eslint-9-setup-guide.md)
233
- - Plugin Development Guide: [docs/eslint-plugin-development-guide.md](docs/eslint-plugin-development-guide.md)
234
237
  - API Reference: [user-docs/api-reference.md](user-docs/api-reference.md)
235
238
  - Examples: [user-docs/examples.md](user-docs/examples.md)
236
239
  - Migration Guide: [user-docs/migration-guide.md](user-docs/migration-guide.md)
237
240
  - Full README: <https://github.com/voder-ai/eslint-plugin-traceability#readme>
238
- - Rule: require-story-annotation: [docs/rules/require-story-annotation.md](docs/rules/require-story-annotation.md)
239
- - Rule: require-req-annotation: [docs/rules/require-req-annotation.md](docs/rules/require-req-annotation.md)
240
- - Rule: require-branch-annotation: [docs/rules/require-branch-annotation.md](docs/rules/require-branch-annotation.md)
241
241
  - Contribution guide: <https://github.com/voder-ai/eslint-plugin-traceability/blob/main/CONTRIBUTING.md>
242
242
  - Issue tracker: <https://github.com/voder-ai/eslint-plugin-traceability/issues>
243
- - Configuration Presets: [docs/config-presets.md](docs/config-presets.md)
244
243
  - Changelog: [CHANGELOG.md](CHANGELOG.md)
245
244
  - Versioning and Releases: This project uses semantic-release for automated versioning. The authoritative list of published versions and release notes is on GitHub Releases: <https://github.com/voder-ai/eslint-plugin-traceability/releases>
package/SECURITY.md ADDED
@@ -0,0 +1,132 @@
1
+ # Security Policy
2
+
3
+ This document describes how security is handled for `eslint-plugin-traceability`, including how to report vulnerabilities, what guarantees apply to production dependencies, and how we manage known risks in our dev-only release tooling.
4
+
5
+ > This file is **user-facing** documentation. Internal implementation details and deeper discussion live in the project’s internal documentation and decision records.
6
+
7
+ ## Reporting a Vulnerability
8
+
9
+ If you believe you have found a security vulnerability in this project:
10
+
11
+ 1. **Do not open a public GitHub issue.**
12
+ 2. Instead, open a private security advisory via the GitHub Security tab for this repository:
13
+ - Navigate to: `Security` → `Advisories` → `Report a vulnerability`.
14
+ 3. Provide as much detail as you can (steps to reproduce, impact, affected environments). A maintainer will review and coordinate a fix and disclosure timeline with you.
15
+
16
+ If you cannot use GitHub Security Advisories, you may alternatively open a **minimal** issue that does not disclose details and ask for a private contact channel.
17
+
18
+ ## Supported Versions
19
+
20
+ This project uses [semantic-release](https://github.com/semantic-release/semantic-release) for automated versioning and publishing.
21
+
22
+ - The **latest published version** on npm and GitHub Releases is considered supported.
23
+ - Older versions are not actively maintained; security fixes are applied to the current release line and then published automatically.
24
+ - To benefit from security fixes, users should stay reasonably up-to-date with the latest versions of `eslint-plugin-traceability`.
25
+
26
+ Authoritative release information is available on GitHub Releases:
27
+
28
+ - <https://github.com/voder-ai/eslint-plugin-traceability/releases>
29
+
30
+ ## Production Dependency Guarantees
31
+
32
+ The `eslint-plugin-traceability` package has **no runtime dependencies**; it ships only its compiled plugin and CLI code plus documentation. Nevertheless, we treat any future production dependencies with care and enforce the following guarantees at release time:
33
+
34
+ - Before a release is published, CI runs:
35
+ - `npm audit --omit=dev --audit-level=high`
36
+ - A release is allowed to proceed only when:
37
+ - There are **no known high-severity vulnerabilities** reported in the **production (runtime) dependency tree**.
38
+
39
+ In other words:
40
+
41
+ - The published npm package is intended to ship **without known high‑severity vulnerabilities in its production dependencies** at the moment it is released.
42
+ - Dev-only tooling and CI infrastructure are kept separate from what you install via `npm install eslint-plugin-traceability`.
43
+
44
+ For more detail on how these checks are wired into CI, see the internal dependency health and security documentation for this project.
45
+
46
+ ## Dependency Maturity and `dry-aged-deps`
47
+
48
+ In addition to `npm audit`, we use [`dry-aged-deps`](https://github.com/voder-ai/dry-aged-deps) to guide dependency upgrades for both production and development dependencies.
49
+
50
+ Current high-level policy:
51
+
52
+ - **Minimum age:** new versions are generally required to be **at least 7 days old** before adoption.
53
+ - **No known vulnerabilities:** versions with _any_ known vulnerability (even low severity) are not considered "safe" upgrade candidates.
54
+
55
+ `dry-aged-deps` is advisory only:
56
+
57
+ - It does **not** modify `package.json` or install anything automatically.
58
+ - It produces machine-readable reports that are stored as CI artifacts and referenced in internal security/incident documentation.
59
+
60
+ When `dry-aged-deps` reports that there are **no safe upgrades available** under these thresholds, we may temporarily accept residual risk in dev-only tooling while keeping production dependencies clean and fully audited.
61
+
62
+ For maintainers, the full process is described in the project’s internal dependency health and security guidelines.
63
+
64
+ ## Dev-Only Release Tooling Risk (semantic-release / npm / glob / brace-expansion)
65
+
66
+ There is a known, documented risk in the **dev-only release toolchain** used by this project. It does **not** affect the runtime behavior of the published ESLint plugin or CLI, but it is relevant to how releases are built in CI.
67
+
68
+ ### What is affected?
69
+
70
+ - The dev dependency `@semantic-release/npm@10.0.6` bundles `npm@9.5.0`, which in turn includes vulnerable versions of `glob` and `brace-expansion`.
71
+ - The relevant advisories are:
72
+ - `glob` CLI command injection: [GHSA-5j98-mcp5-4vw2](https://github.com/advisories/GHSA-5j98-mcp5-4vw2)
73
+ - `brace-expansion` ReDoS: [GHSA-v6h2-p8h4-qcjw](https://github.com/advisories/GHSA-v6h2-p8h4-qcjw)
74
+ - These vulnerable packages exist **only inside the npm binary bundled within `@semantic-release/npm`** and are used solely during automated publishing from CI.
75
+
76
+ ### What is _not_ affected?
77
+
78
+ - The published `eslint-plugin-traceability` package has **no runtime dependencies** on this bundled npm or its `glob`/`brace-expansion` copies.
79
+ - End-user projects that install and run `eslint-plugin-traceability` or `traceability-maint` **do not execute** this bundled tooling.
80
+ - `npm audit --omit=dev --audit-level=high` continues to report **0 high‑severity vulnerabilities** for the production dependency tree at release time.
81
+
82
+ ### Why is this risk currently accepted?
83
+
84
+ Under our `dry-aged-deps` policy (7‑day minimum age, no known vulnerabilities):
85
+
86
+ - There is currently **no recommended, dry‑aged‑safe upgrade path** for the semantic-release/npm toolchain that would fully eliminate these bundled vulnerabilities.
87
+ - We therefore treat this as a **known error in dev-only tooling** rather than a production risk.
88
+
89
+ This acceptance is documented in detail in the project’s internal security incident records and architectural decision records.
90
+
91
+ ### Compensating Controls
92
+
93
+ To keep this dev-only risk tightly contained, we apply several compensating controls:
94
+
95
+ 1. **Environment Isolation**
96
+ - The vulnerable tooling is used **only** in the GitHub Actions CI workflow (`.github/workflows/ci-cd.yml`).
97
+ - It runs in a single, controlled job that executes on pushes to the `main` branch, not for pull requests.
98
+ - The job runs on GitHub-hosted runners and does not have access to internal infrastructure.
99
+
100
+ 2. **Least-Privilege Permissions for Release**
101
+ - Workflow-level permissions default to `contents: read`.
102
+ - Elevated permissions (`contents: write`, `issues: write`, `pull-requests: write`, `id-token: write`) are scoped to the release job/step that runs semantic-release and are not used for general CI tasks.
103
+
104
+ 3. **Strict Input Handling**
105
+ - The CI configuration and project scripts **never invoke the `glob` CLI** with the dangerous `-c/--cmd` flags.
106
+ - The semantic-release/npm toolchain does **not** receive untrusted user input for glob patterns or environment variables.
107
+ - Release jobs operate only on the repository contents of this project plus standard CI-provided environment variables.
108
+
109
+ 4. **Audit and Monitoring**
110
+ - Dev-only vulnerabilities are tracked via `npm run audit:dev-high`, which writes a machine-readable report to `ci/npm-audit.json` for each CI run.
111
+ - `dry-aged-deps` reports (`ci/dry-aged-deps.json`) are stored as CI artifacts to document when no safe upgrade path exists under the configured thresholds.
112
+ - A nightly `dependency-health` workflow re-runs dev-dependency audits to keep this risk under continuous review.
113
+
114
+ 5. **Guarded semantic-release Invocation (CI-Only)**
115
+ - semantic-release is invoked **only from CI**, and guarded to ensure it runs under the intended safe context (GitHub Actions, push to `main`, CI environment).
116
+ - Local developers are not expected to run semantic-release directly; publishing is handled automatically by CI after all quality and security checks pass.
117
+
118
+ ### Upgrade Plan
119
+
120
+ We intend to migrate away from the affected semantic-release/npm toolchain as soon as a safe, dry‑aged‑deps–approved upgrade path is available:
121
+
122
+ 1. Continue monitoring `dry-aged-deps` output for `@semantic-release/npm`, `semantic-release`, and related packages.
123
+ 2. When a newer, vulnerability-free version remains stable for at least 7 days and passes our audit checks, update the dev dependencies accordingly.
124
+ 3. After migration, convert the existing known-error record into a resolved incident that documents the fix and new baseline.
125
+
126
+ Until then, the risk remains **limited to CI release automation** and does not change the guarantees we provide for production dependencies or end-user environments.
127
+
128
+ ---
129
+
130
+ ## Attribution
131
+
132
+ Created autonomously by [voder.ai](https://voder.ai).
@@ -17,6 +17,11 @@ import { detectStaleAnnotations, updateAnnotationReferences, batchUpdateAnnotati
17
17
  declare const RULE_NAMES: readonly ["require-story-annotation", "require-req-annotation", "require-branch-annotation", "valid-annotation-format", "valid-story-reference", "valid-req-reference", "prefer-implements-annotation"];
18
18
  type RuleName = (typeof RULE_NAMES)[number];
19
19
  declare const rules: Record<RuleName, Rule.RuleModule>;
20
+ declare const plugin: {
21
+ rules: typeof rules;
22
+ configs?: unknown;
23
+ maintenance?: unknown;
24
+ };
20
25
  /**
21
26
  * @story docs/stories/007.0-DEV-ERROR-REPORTING.story.md
22
27
  * @req REQ-ERROR-SEVERITY - Map rule types to appropriate ESLint severity levels (errors vs warnings)
@@ -25,17 +30,11 @@ declare const rules: Record<RuleName, Rule.RuleModule>;
25
30
  */
26
31
  declare const configs: {
27
32
  recommended: {
28
- plugins: {
29
- traceability: {};
30
- };
31
33
  rules: {
32
34
  [x: string]: "error" | "warn";
33
35
  };
34
36
  }[];
35
37
  strict: {
36
- plugins: {
37
- traceability: {};
38
- };
39
38
  rules: {
40
39
  [x: string]: "error" | "warn";
41
40
  };
@@ -53,32 +52,4 @@ declare const maintenance: {
53
52
  generateMaintenanceReport: typeof generateMaintenanceReport;
54
53
  };
55
54
  export { rules, configs, maintenance };
56
- declare const _default: {
57
- rules: Record<"require-story-annotation" | "require-req-annotation" | "require-branch-annotation" | "valid-annotation-format" | "valid-story-reference" | "valid-req-reference" | "prefer-implements-annotation", Rule.RuleModule>;
58
- configs: {
59
- recommended: {
60
- plugins: {
61
- traceability: {};
62
- };
63
- rules: {
64
- [x: string]: "error" | "warn";
65
- };
66
- }[];
67
- strict: {
68
- plugins: {
69
- traceability: {};
70
- };
71
- rules: {
72
- [x: string]: "error" | "warn";
73
- };
74
- }[];
75
- };
76
- maintenance: {
77
- detectStaleAnnotations: typeof detectStaleAnnotations;
78
- updateAnnotationReferences: typeof updateAnnotationReferences;
79
- batchUpdateAnnotations: typeof batchUpdateAnnotations;
80
- verifyAnnotations: typeof verifyAnnotations;
81
- generateMaintenanceReport: typeof generateMaintenanceReport;
82
- };
83
- };
84
- export default _default;
55
+ export default plugin;
package/lib/src/index.js CHANGED
@@ -73,6 +73,9 @@ RULE_NAMES.forEach(
73
73
  };
74
74
  }
75
75
  });
76
+ const plugin = {
77
+ rules,
78
+ };
76
79
  /**
77
80
  * @story docs/stories/007.0-DEV-ERROR-REPORTING.story.md
78
81
  * @req REQ-ERROR-SEVERITY - Map rule types to appropriate ESLint severity levels (errors vs warnings)
@@ -86,18 +89,16 @@ const TRACEABILITY_RULE_SEVERITIES = {
86
89
  "traceability/valid-annotation-format": "warn",
87
90
  "traceability/valid-story-reference": "error",
88
91
  "traceability/valid-req-reference": "error",
89
- "traceability/prefer-implements-annotation": "warn",
90
92
  };
91
93
  /**
92
94
  * @story docs/stories/007.0-DEV-ERROR-REPORTING.story.md
93
95
  * @req REQ-PLUGIN-STRUCTURE - Provide foundational plugin export and registration
94
96
  * @req REQ-ERROR-SEVERITY - Map rule types to appropriate ESLint severity levels (errors vs warnings)
97
+ * @story docs/stories/002.0-DEV-ESLINT-CONFIG.story.md
98
+ * @req REQ-CONFIG-PRESETS - Provide flat-config presets that self-register the plugin and core rules
95
99
  */
96
100
  function createTraceabilityFlatConfig() {
97
101
  return {
98
- plugins: {
99
- traceability: {},
100
- },
101
102
  rules: {
102
103
  ...TRACEABILITY_RULE_SEVERITIES,
103
104
  },
@@ -114,6 +115,7 @@ const configs = {
114
115
  strict: [createTraceabilityFlatConfig()],
115
116
  };
116
117
  exports.configs = configs;
118
+ plugin.configs = configs;
117
119
  /**
118
120
  * @story docs/stories/009.0-DEV-MAINTENANCE-TOOLS.story.md
119
121
  * @req REQ-MAINTENANCE-API-EXPORT - Expose maintenance utilities alongside core plugin exports
@@ -126,4 +128,5 @@ const maintenance = {
126
128
  generateMaintenanceReport: maintenance_1.generateMaintenanceReport,
127
129
  };
128
130
  exports.maintenance = maintenance;
129
- exports.default = { rules, configs, maintenance };
131
+ plugin.maintenance = maintenance;
132
+ exports.default = plugin;
@@ -0,0 +1,75 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ /**
37
+ * Tests for: docs/stories/002.0-DEV-ESLINT-CONFIG.story.md
38
+ * @story docs/stories/002.0-DEV-ESLINT-CONFIG.story.md
39
+ * @req REQ-CONFIG-PRESETS - Validate flat-config presets register traceability plugin and rules
40
+ * @req REQ-FLAT-CONFIG - Ensure presets work with ESLint v9 flat config
41
+ * @req REQ-PROJECT-INTEGRATION - Support seamless integration via documented preset usage
42
+ */
43
+ const use_at_your_own_risk_1 = require("eslint/use-at-your-own-risk");
44
+ const index_1 = __importStar(require("../../src/index"));
45
+ const baseConfig = {
46
+ plugins: {
47
+ traceability: index_1.default,
48
+ },
49
+ rules: {},
50
+ };
51
+ async function lintTextWithConfig(text, config) {
52
+ const eslint = new use_at_your_own_risk_1.FlatESLint({
53
+ overrideConfig: config,
54
+ overrideConfigFile: true,
55
+ ignore: false,
56
+ });
57
+ const [result] = await eslint.lintText(text, { filePath: "example.js" });
58
+ return result;
59
+ }
60
+ describe("Flat config presets integration (Story 002.0-DEV-ESLINT-CONFIG)", () => {
61
+ it("[REQ-CONFIG-PRESETS] recommended preset enables traceability rules via documented usage", async () => {
62
+ const config = [baseConfig, ...index_1.configs.recommended];
63
+ const code = "function foo() {}";
64
+ const result = await lintTextWithConfig(code, config);
65
+ const ruleIds = result.messages.map((m) => m.ruleId).sort();
66
+ expect(ruleIds).toContain("traceability/require-story-annotation");
67
+ });
68
+ it("[REQ-CONFIG-PRESETS] strict preset also enables traceability rules via documented usage", async () => {
69
+ const config = [baseConfig, ...index_1.configs.strict];
70
+ const code = "function bar() {}";
71
+ const result = await lintTextWithConfig(code, config);
72
+ const ruleIds = result.messages.map((m) => m.ruleId).sort();
73
+ expect(ruleIds).toContain("traceability/require-story-annotation");
74
+ });
75
+ });
@@ -80,12 +80,10 @@ describe("Plugin Default Export and Configs (Story 001.0-DEV-PLUGIN-SETUP)", ()
80
80
  expect(recommendedRules).toHaveProperty("traceability/require-branch-annotation", "error");
81
81
  expect(recommendedRules).toHaveProperty("traceability/valid-story-reference", "error");
82
82
  expect(recommendedRules).toHaveProperty("traceability/valid-req-reference", "error");
83
- expect(recommendedRules).toHaveProperty("traceability/prefer-implements-annotation", "warn");
84
83
  });
85
84
  it("[REQ-ERROR-SEVERITY] configs.strict uses same severity mapping as recommended", () => {
86
85
  const strictRules = index_1.configs.strict[0].rules;
87
86
  const recommendedRules = index_1.configs.recommended[0].rules;
88
87
  expect(strictRules).toEqual(recommendedRules);
89
- expect(strictRules).toHaveProperty("traceability/prefer-implements-annotation", "warn");
90
88
  });
91
89
  });
@@ -12,6 +12,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
12
12
  */
13
13
  const eslint_1 = require("eslint");
14
14
  const prefer_implements_annotation_1 = __importDefault(require("../../src/rules/prefer-implements-annotation"));
15
+ const src_1 = require("../../src");
15
16
  const ruleTester = new eslint_1.RuleTester({
16
17
  languageOptions: {
17
18
  parserOptions: { ecmaVersion: 2020, sourceType: "module" },
@@ -82,3 +83,30 @@ describe("prefer-implements-annotation rule (Story 010.3-DEV-MIGRATE-TO-IMPLEMEN
82
83
  ],
83
84
  });
84
85
  });
86
+ describe("prefer-implements-annotation configuration severity (REQ-CONFIG-SEVERITY)", () => {
87
+ test("rule is disabled by default in recommended preset (not present in configs.recommended[0].rules)", () => {
88
+ const recommended = src_1.configs.recommended;
89
+ expect(Array.isArray(recommended)).toBe(true);
90
+ const firstConfig = recommended[0];
91
+ expect(firstConfig).toBeDefined();
92
+ const rules = firstConfig.rules || {};
93
+ expect(rules["@eslint-sweat/prefer-implements-annotation"]).toBeUndefined();
94
+ expect(rules["prefer-implements-annotation"]).toBeUndefined();
95
+ });
96
+ test("rule can be configured with severity 'warn' or 'error' in flat config", () => {
97
+ const flatWarnConfig = {
98
+ files: ["**/*.ts"],
99
+ rules: {
100
+ "prefer-implements-annotation": "warn",
101
+ },
102
+ };
103
+ expect(flatWarnConfig.rules["prefer-implements-annotation"]).toBe("warn");
104
+ const flatErrorConfig = {
105
+ files: ["**/*.ts"],
106
+ rules: {
107
+ "prefer-implements-annotation": "error",
108
+ },
109
+ };
110
+ expect(flatErrorConfig.rules["prefer-implements-annotation"]).toBe("error");
111
+ });
112
+ });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "eslint-plugin-traceability",
3
- "version": "1.8.0",
3
+ "version": "1.8.1",
4
4
  "description": "A customizable ESLint plugin that enforces traceability annotations in your code, ensuring each implementation is linked to its requirement or test case.",
5
5
  "main": "lib/src/index.js",
6
6
  "types": "lib/src/index.d.ts",
@@ -8,8 +8,8 @@
8
8
  "lib",
9
9
  "README.md",
10
10
  "LICENSE",
11
+ "SECURITY.md",
11
12
  "user-docs",
12
- "docs",
13
13
  "CHANGELOG.md"
14
14
  ],
15
15
  "directories": {
@@ -67,8 +67,8 @@
67
67
  "@eslint/js": "^9.39.1",
68
68
  "@semantic-release/changelog": "^6.0.3",
69
69
  "@semantic-release/git": "^10.0.1",
70
- "@semantic-release/github": "^10.3.5",
71
- "@semantic-release/npm": "^10.0.6",
70
+ "@semantic-release/github": "12.0.2",
71
+ "@semantic-release/npm": "13.1.2",
72
72
  "@types/eslint": "^9.6.1",
73
73
  "@types/jest": "^30.0.0",
74
74
  "@types/node": "^24.10.1",
@@ -80,9 +80,9 @@
80
80
  "husky": "^9.1.7",
81
81
  "jest": "^30.2.0",
82
82
  "jscpd": "^4.0.5",
83
- "lint-staged": "^16.2.6",
83
+ "lint-staged": "^16.2.7",
84
84
  "prettier": "^3.6.2",
85
- "semantic-release": "^21.1.2",
85
+ "semantic-release": "25.0.2",
86
86
  "ts-jest": "^29.4.5",
87
87
  "typescript": "^5.9.3",
88
88
  "secretlint": "11.2.5",
@@ -13,11 +13,13 @@ Each rule enforces traceability conventions in your code. Below is a summary of
13
13
 
14
14
  In addition to the core `@story` and `@req` annotations, the plugin also understands `@implements` for code that fulfills requirements from multiple stories—for example:
15
15
  `@implements docs/stories/010.0-PAYMENTS.story.md#REQ-PAYMENTS-REFUND`.
16
- For a detailed explanation of `@implements` behavior and validation, see [`user-docs/migration-guide.md`](../user-docs/migration-guide.md) (section **3.1 Multi-story @implements annotations**) and the rule docs at [`docs/rules/valid-annotation-format.md`](../docs/rules/valid-annotation-format.md) and [`docs/rules/valid-req-reference.md`](../docs/rules/valid-req-reference.md).
16
+ For a detailed explanation of `@implements` behavior and validation, see [Migration Guide](migration-guide.md) (section **3.1 Multi-story @implements annotations**) and the corresponding `valid-annotation-format` and `valid-req-reference` rule documentation in the plugin's internal docs.
17
+
18
+ The `prefer-implements-annotation` rule is an **opt-in migration helper** that is disabled by default and **not** part of any built-in preset. It can be enabled and given a severity like `"warn"` or `"error"` using normal ESLint rule configuration when you want to gradually encourage multi-story `@implements` usage. For rule details and migration guidance, see `docs/rules/prefer-implements-annotation.md`.
17
19
 
18
20
  ### traceability/require-story-annotation
19
21
 
20
- Description: Ensures every function declaration has a JSDoc comment with an `@story` annotation referencing the related user story. When run with `--fix`, the rule inserts a single-line placeholder JSDoc `@story` annotation above missing functions, methods, TypeScript declare functions, and interface method signatures using a built-in template aligned with Story 008.0. This template is currently fixed but structured for future configurability, and fixes are strictly limited to adding this placeholder annotation without altering the function body or changing any runtime behavior. Selective enabling of different auto-fix behaviors (such as applying fixes only to certain scopes or node types) is planned for a future version.
22
+ Description: Ensures every function declaration has a JSDoc comment with an `@story` annotation referencing the related user story. When you adopt multi-story `@implements` annotations as described in `docs/stories/010.2-DEV-MULTI-STORY-SUPPORT.story.md` and `REQ-REQUIRE-ACCEPTS-IMPLEMENTS`, this rule also accepts `@implements` as an alternative way to prove story coverage, so either `@story` or at least one `@implements` tag will satisfy the presence check. When run with `--fix`, the rule inserts a single-line placeholder JSDoc `@story` annotation above missing functions, methods, TypeScript declare functions, and interface method signatures using a built-in template aligned with Story 008.0. This template is currently fixed but structured for future configurability, and fixes are strictly limited to adding this placeholder annotation without altering the function body or changing any runtime behavior. Selective enabling of different auto-fix behaviors (such as applying fixes only to certain scopes or node types) is planned for a future version.
21
23
 
22
24
  Options:
23
25
 
@@ -39,7 +41,7 @@ function initAuth() {
39
41
 
40
42
  ### traceability/require-req-annotation
41
43
 
42
- Description: Ensures that function-like constructs consistently declare their linked requirement using an `@req` annotation in JSDoc. The rule targets the same function-like node types as `traceability/require-story-annotation` (standard function declarations, non-arrow function expressions used as callbacks or assignments, class/object methods, TypeScript declare functions, and interface method signatures), and enforces that each of them has at least one `@req` tag in the nearest associated JSDoc comment. Arrow functions (`ArrowFunctionExpression`) are not currently checked by this rule.
44
+ Description: Ensures that function-like constructs consistently declare their linked requirement using an `@req` annotation in JSDoc. The rule targets the same function-like node types as `traceability/require-story-annotation` (standard function declarations, non-arrow function expressions used as callbacks or assignments, class/object methods, TypeScript declare functions, and interface method signatures), and enforces that each of them has at least one `@req` tag in the nearest associated JSDoc comment. When you adopt multi-story `@implements` annotations as described in `docs/stories/010.2-DEV-MULTI-STORY-SUPPORT.story.md` and `REQ-REQUIRE-ACCEPTS-IMPLEMENTS`, this rule also treats `@implements story-path REQ-ID...` tags as satisfying the requirement coverage check, although deep verification of requirement IDs continues to be handled by `traceability/valid-req-reference`. Arrow functions (`ArrowFunctionExpression`) are not currently checked by this rule.
43
45
 
44
46
  This rule is typically used alongside `traceability/require-story-annotation` so that each function-level traceability block includes both an `@story` and an `@req` annotation, but it can also be enabled independently if you only want to enforce requirement linkage. Unlike `traceability/require-story-annotation`, this rule does not currently provide an auto-fix mode for inserting placeholder `@req` annotations; it only reports missing or malformed requirement annotations on the configured scopes.
45
47
 
@@ -115,10 +117,10 @@ The `valid-annotation-format` rule is intentionally **backward compatible** with
115
117
  - Introduce `@implements` incrementally for integration code that implements requirements from multiple stories.
116
118
  - Mix both styles in the same comment block when needed; the rule validates the format of each annotation independently.
117
119
 
118
- Deep requirement checking for both `@req` and `@implements` is handled by `traceability/valid-req-reference`. For step-by-step guidance on when and how to migrate, see:
120
+ Deep requirement checking for both `@req` and `@implements` is handled by the `valid-req-reference` rule in the plugin's internal docs. For step-by-step guidance on when and how to migrate, see:
119
121
 
120
- - **Migration guide:** [`user-docs/migration-guide.md`](../user-docs/migration-guide.md) (section **3.1 Multi-story `@implements` annotations**)
121
- - **Rule docs:** [`docs/rules/valid-annotation-format.md`](../docs/rules/valid-annotation-format.md), [`docs/rules/valid-req-reference.md`](../docs/rules/valid-req-reference.md)
122
+ - **Migration guide:** [Migration Guide](migration-guide.md) (section **3.1 Multi-story `@implements` annotations**)
123
+ - **Rule docs:** The `valid-annotation-format` and `valid-req-reference` rule documentation in the plugin's internal docs.
122
124
 
123
125
  Default Severity: `error`
124
126
  Example:
@@ -196,9 +198,12 @@ The plugin provides two built-in presets for easy configuration:
196
198
 
197
199
  ### recommended
198
200
 
199
- Enables the core traceability rules with severities tuned for common usage (most at `error`, with
200
- `traceability/valid-annotation-format` at `warn` to reduce noise):
201
- This `warn` level for `traceability/valid-annotation-format` is intentional to keep early adoption noise low, but you can safely raise it to `error` in projects that want strict enforcement of annotation formatting.
201
+ Enables the **six core traceability rules** with severities tuned for common usage (most at `error`, with
202
+ `traceability/valid-annotation-format` at `warn` to reduce noise). This `warn` level for `traceability/valid-annotation-format` is intentional to keep early adoption noise low, but you can safely raise it to `error` in projects that want strict enforcement of annotation formatting.
203
+
204
+ The `prefer-implements-annotation` migration rule is **not included** in this (or any) preset and remains disabled by default. If you want to encourage or enforce multi-story `@implements` annotations, you must enable `traceability/prefer-implements-annotation` explicitly in your ESLint configuration and choose an appropriate severity (for example, `"warn"` during migration or `"error"` once fully adopted).
205
+
206
+ Core rules enabled by the `recommended` preset:
202
207
 
203
208
  - `traceability/require-story-annotation`: `error`
204
209
  - `traceability/require-req-annotation`: `error`
@@ -218,7 +223,8 @@ export default [js.configs.recommended, traceability.configs.recommended];
218
223
 
219
224
  ### strict
220
225
 
221
- Currently mirrors the **recommended** preset, reserved for future stricter policies.
226
+ Currently mirrors the **recommended** preset, reserved for future stricter policies. As with the `recommended` preset, the `traceability/prefer-implements-annotation` rule is **not** enabled here by default and must be configured manually if desired.
227
+
222
228
  Usage:
223
229
 
224
230
  ```javascript
@@ -234,16 +240,30 @@ The plugin exposes a small maintenance API and a companion CLI, `traceability-ma
234
240
 
235
241
  ### Programmatic Maintenance API
236
242
 
237
- All functions are exported from the plugin’s maintenance module:
243
+ The maintenance functions are available via the plugin’s `maintenance` export. You can either import the named `maintenance` export directly and destructure the functions you need, or import the default plugin export and access the same functions from `traceability.maintenance`:
238
244
 
239
245
  ```ts
240
- import {
246
+ // Option 1: Named `maintenance` export
247
+ import { maintenance } from "eslint-plugin-traceability";
248
+
249
+ const {
241
250
  detectStaleAnnotations,
242
251
  updateAnnotationReferences,
243
252
  batchUpdateAnnotations,
244
253
  verifyAnnotations,
245
254
  generateMaintenanceReport,
246
- } from "eslint-plugin-traceability/maintenance";
255
+ } = maintenance;
256
+
257
+ // Option 2: Default plugin export
258
+ import traceability from "eslint-plugin-traceability";
259
+
260
+ const {
261
+ detectStaleAnnotations: detectStaleAnnotations2,
262
+ updateAnnotationReferences: updateAnnotationReferences2,
263
+ batchUpdateAnnotations: batchUpdateAnnotations2,
264
+ verifyAnnotations: verifyAnnotations2,
265
+ generateMaintenanceReport: generateMaintenanceReport2,
266
+ } = traceability.maintenance;
247
267
  ```
248
268
 
249
269
  The current maintenance API operates on a **single workspace root** and scans all files beneath that directory. It does not yet accept include/exclude globs or explicit story/requirement lists.