use: directiveMinimal reproduction for a crash in eslint-plugin-sonarjs rule sonarjs/no-unused-collection (S4030)
when linting a Svelte file that contains a use: action directive.
The rule crashes with TypeError: Cannot read properties of null (reading 'type') when a Svelte
file with <script lang="ts"> (parsed via @typescript-eslint/parser) contains:
use: directive referencing a function declaration (not an arrow function)<div use:fn={variable}></div>The variable's type doesn't matter — a plain let x = 0 is enough. The crash is unrelated to
collections despite being in the no-unused-collection rule.
npm install
npm test
Expected: no crash (the rule should either report or silently pass). Actual:
TypeError: Cannot read properties of null (reading 'type')
Occurred while linting App.svelte:1
Rule: "sonarjs/no-unused-collection"
at isElementWrite (eslint-plugin-sonarjs/cjs/helpers/ast.js:191:30)
at isRead (eslint-plugin-sonarjs/cjs/S4030/rule.js:146:46)
at isUnusedCollection (eslint-plugin-sonarjs/cjs/S4030/rule.js:112:18)
...
From reading the source, the issue appears to be in isElementWrite (helpers/ast.js), which
accesses statement.expression.type without guarding against expression being null. The S4030
rule's isRead function calls findFirstMatchingAncestor looking for a node with
type === 'ExpressionStatement' with no boundary types. With the Svelte+TS parser, this traversal
appears to reach a synthetic AST node that satisfies the type check but has a null .expression
property.
S3516 (no-invariant-returns) uses the same isElementWrite helper but doesn't fail in the same
way, possibly because it includes FUNCTION_NODES in its ancestor search predicate, which would
prevent the traversal from reaching the problematic node. If so, the missing null guard in
isElementWrite could affect other callers if their traversal predicates change in the future.
To check if a fix has landed in a newer release:
# test latest
npm run test:version
# test a specific version
VERSION=4.1.0 npm run test:version
| Package | Version |
|---|---|
| eslint-plugin-sonarjs | 4.0.2 |
| eslint | 10.0.3 |
| eslint-plugin-svelte | 3.15.2 |
| svelte | 5.53.9 |
| typescript-eslint | 8.57.0 |