Skip to content

Commit b23460f

Browse files
committed
fix(lint): only highlight function names in useMaxParams rule
The useMaxParams rule was highlighting entire function bodies instead of just the function names, causing noisy error squiggles. Changes: - Add name_range() method to AnyFunctionLike union - Update diagnostic to use function name ranges - Handle all function types including TS declarations - Update test snapshots to reflect new behavior
1 parent c294644 commit b23460f

4 files changed

Lines changed: 98 additions & 70 deletions

File tree

crates/biome_js_analyze/src/lint/nursery/use_max_params.rs

Lines changed: 57 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ use biome_js_syntax::{
88
JsConstructorParameters, JsFunctionDeclaration, JsFunctionExpression, JsMethodClassMember,
99
JsMethodObjectMember, JsParameters, TsDeclareFunctionDeclaration, TsTypeAliasDeclaration,
1010
};
11-
use biome_rowan::{AstNode, declare_node_union};
11+
use biome_rowan::{AstNode, TextRange, declare_node_union};
1212
use biome_rule_options::use_max_params::UseMaxParamsOptions;
1313

1414
declare_lint_rule! {
@@ -84,6 +84,58 @@ declare_node_union! {
8484
pub AnyFunctionLike = JsFunctionDeclaration | JsFunctionExpression | JsArrowFunctionExpression | JsMethodClassMember | JsMethodObjectMember | JsConstructorClassMember | TsDeclareFunctionDeclaration | TsTypeAliasDeclaration
8585
}
8686

87+
impl AnyFunctionLike {
88+
pub fn name_range(&self) -> Option<TextRange> {
89+
match self {
90+
Self::JsFunctionDeclaration(func) => func
91+
.id()
92+
.ok()?
93+
.as_js_identifier_binding()?
94+
.name_token()
95+
.ok()
96+
.map(|token| token.text_range()),
97+
Self::JsFunctionExpression(func) => func
98+
.id()?
99+
.as_js_identifier_binding()?
100+
.name_token()
101+
.ok()
102+
.map(|token| token.text_range()),
103+
Self::JsArrowFunctionExpression(_) => {
104+
// Arrow functions don't have names
105+
None
106+
}
107+
Self::JsMethodClassMember(method) => method.name().ok().map(|name| name.range()),
108+
Self::JsMethodObjectMember(method) => method.name().ok().map(|name| name.range()),
109+
Self::JsConstructorClassMember(constructor) => {
110+
constructor.name().ok().map(|name| name.range())
111+
}
112+
Self::TsDeclareFunctionDeclaration(decl) => {
113+
decl.id().ok().and_then(|binding| match binding {
114+
biome_js_syntax::AnyJsBinding::JsIdentifierBinding(id) => {
115+
id.name_token().ok().map(|token| token.text_range())
116+
}
117+
biome_js_syntax::AnyJsBinding::JsMetavariable(meta) => {
118+
meta.value_token().ok().map(|token| token.text_range())
119+
}
120+
_ => None,
121+
})
122+
}
123+
Self::TsTypeAliasDeclaration(decl) => {
124+
decl.binding_identifier()
125+
.ok()
126+
.and_then(|binding| match binding {
127+
biome_js_syntax::AnyTsIdentifierBinding::TsIdentifierBinding(id) => {
128+
id.name_token().ok().map(|token| token.text_range())
129+
}
130+
biome_js_syntax::AnyTsIdentifierBinding::JsMetavariable(meta) => {
131+
meta.value_token().ok().map(|token| token.text_range())
132+
}
133+
})
134+
}
135+
}
136+
}
137+
}
138+
87139
#[derive(Debug, Clone)]
88140
pub struct UseMaxParamsState {
89141
pub parameter_count: usize,
@@ -156,10 +208,13 @@ impl Rule for UseMaxParams {
156208
let node = ctx.query();
157209
let options = ctx.options();
158210

211+
// Use the function/method name's range if available, otherwise fall back to the whole node
212+
let range = node.name_range().unwrap_or_else(|| node.range());
213+
159214
Some(
160215
RuleDiagnostic::new(
161216
rule_category!(),
162-
node.range(),
217+
range,
163218
markup! {
164219
"Function has "{state.parameter_count}" parameters, but only "{options.max}" are allowed."
165220
},

crates/biome_js_analyze/tests/specs/nursery/useMaxParams/invalid.js.snap

Lines changed: 25 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -50,17 +50,14 @@ function withThisParam(this, a, b, c, d, e, f, g) {
5050

5151
# Diagnostics
5252
```
53-
invalid.js:1:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
53+
invalid.js:1:10 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
5454
5555
! Function has 8 parameters, but only 4 are allowed.
5656
5757
> 1 │ function tooManyParams(a, b, c, d, e, f, g, h) {
58-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
59-
> 2return a + b + c + d + e + f + g + h;
60-
> 3}
61-
│ ^
62-
4 │
63-
5 │ function namedFunction(a, b, c, d, e, f, g, h, i) {
58+
^^^^^^^^^^^^^
59+
2return a + b + c + d + e + f + g + h;
60+
3}
6461
6562
i Functions with many parameters are hard to read and maintain.
6663
@@ -70,19 +67,16 @@ invalid.js:1:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━
7067
```
7168

7269
```
73-
invalid.js:5:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
70+
invalid.js:5:10 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
7471
7572
! Function has 9 parameters, but only 4 are allowed.
7673
7774
3 │ }
7875
4 │
7976
> 5 │ function namedFunction(a, b, c, d, e, f, g, h, i) {
80-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
81-
> 6return a + b + c + d + e + f + g + h + i;
82-
> 7}
83-
│ ^
84-
8 │
85-
9 │ const fn1 = function(a, b, c, d, e, f, g, h) {
77+
^^^^^^^^^^^^^
78+
6return a + b + c + d + e + f + g + h + i;
79+
7}
8680
8781
i Functions with many parameters are hard to read and maintain.
8882
@@ -114,19 +108,16 @@ invalid.js:9:13 lint/nursery/useMaxParams ━━━━━━━━━━━━
114108
```
115109
116110
```
117-
invalid.js:13:13 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
111+
invalid.js:13:22 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
118112
119113
! Function has 9 parameters, but only 4 are allowed.
120114
121115
11};
122116
12 │
123117
> 13 │ const fn2 = function namedFnExpression(a, b, c, d, e, f, g, h, i) {
124-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
125-
> 14return a + b + c + d + e + f + g + h + i;
126-
> 15};
127-
│ ^
128-
16 │
129-
17 │ const arrow1 = (a, b, c, d, e, f, g, h) => {
118+
^^^^^^^^^^^^^^^^^
119+
14return a + b + c + d + e + f + g + h + i;
120+
15};
130121
131122
i Functions with many parameters are hard to read and maintain.
132123
@@ -183,12 +174,9 @@ invalid.js:24:5 lint/nursery/useMaxParams ━━━━━━━━━━━━
183174
184175
23class MyClass {
185176
> 24 │ method(a, b, c, d, e, f, g, h) {
186-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
187-
> 25return a + b + c + d + e + f + g + h;
188-
> 26 │ }
189-
^
190-
27
191-
28constructor(a, b, c, d, e, f, g, h, i) {
177+
^^^^^^
178+
25return a + b + c + d + e + f + g + h;
179+
26 │ }
192180
193181
i Functions with many parameters are hard to read and maintain.
194182
@@ -205,12 +193,9 @@ invalid.js:28:5 lint/nursery/useMaxParams ━━━━━━━━━━━━
205193
26 │ }
206194
27
207195
> 28constructor(a, b, c, d, e, f, g, h, i) {
208-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
209-
> 29this.sum = a + b + c + d + e + f + g + h + i;
210-
> 30 │ }
211-
^
212-
31 │ }
213-
32
196+
│ ^^^^^^^^^^^
197+
29 │ this.sum = a + b + c + d + e + f + g + h + i;
198+
30 │ }
214199
215200
i Functions with many parameters are hard to read and maintain.
216201
@@ -226,12 +211,9 @@ invalid.js:34:5 lint/nursery/useMaxParams ━━━━━━━━━━━━
226211
227212
33const obj = {
228213
> 34 │ method(a, b, c, d, e, f, g, h) {
229-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
230-
> 35return a + b + c + d + e + f + g + h;
231-
> 36 │ }
232-
│ ^
233-
37 │ };
234-
38
214+
^^^^^^
215+
35return a + b + c + d + e + f + g + h;
216+
36 │ }
235217
236218
i Functions with many parameters are hard to read and maintain.
237219
@@ -241,18 +223,16 @@ invalid.js:34:5 lint/nursery/useMaxParams ━━━━━━━━━━━━
241223
```
242224
243225
```
244-
invalid.js:39:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
226+
invalid.js:39:10 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
245227
246228
! Function has 8 parameters, but only 4 are allowed.
247229
248230
37 │ };
249231
38
250232
> 39function withThisParam(this, a, b, c, d, e, f, g) {
251-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
252-
> 40return a + b + c + d + e + f + g;
253-
> 41}
254-
│ ^
255-
42 │
233+
^^^^^^^^^^^^^
234+
40return a + b + c + d + e + f + g;
235+
41 │ }
256236
257237
i Functions with many parameters are hard to read and maintain.
258238

crates/biome_js_analyze/tests/specs/nursery/useMaxParams/invalid.ts.snap

Lines changed: 12 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -24,19 +24,16 @@ type sum = (a: number, b: number, c: number, d: number, e: number) => number;
2424

2525
# Diagnostics
2626
```
27-
invalid.ts:5:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
27+
invalid.ts:5:10 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
2828
2929
! Function has 6 parameters, but only 4 are allowed.
3030
3131
3 │ }
3232
4 │
3333
> 5 │ function withThisParam(this: MyInterface, a: number, b: number, c: number, d: number, e: number): number {
34-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
35-
> 6return this.value + a + b + c + d + e;
36-
> 7}
37-
│ ^
38-
8 │
39-
9 │ function tooManyParamsWithThis(this: MyInterface, a: number, b: number, c: number, d: number, e: number, f: number): number {
34+
^^^^^^^^^^^^^
35+
6return this.value + a + b + c + d + e;
36+
7}
4037
4138
i Functions with many parameters are hard to read and maintain.
4239
@@ -46,19 +43,16 @@ invalid.ts:5:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━
4643
```
4744

4845
```
49-
invalid.ts:9:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
46+
invalid.ts:9:10 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
5047
5148
! Function has 7 parameters, but only 4 are allowed.
5249
5350
7 │ }
5451
8 │
5552
> 9 │ function tooManyParamsWithThis(this: MyInterface, a: number, b: number, c: number, d: number, e: number, f: number): number {
56-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
57-
> 10return this.value + a + b + c + d + e + f;
58-
> 11}
59-
│ ^
60-
12 │
61-
13 │ declare function makeDate(m: number, d: number, y: number, h: number, min: number, s: number): Date;
53+
^^^^^^^^^^^^^^^^^^^^^
54+
10return this.value + a + b + c + d + e + f;
55+
11}
6256
6357
i Functions with many parameters are hard to read and maintain.
6458
@@ -68,14 +62,14 @@ invalid.ts:9:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━
6862
```
6963

7064
```
71-
invalid.ts:13:9 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
65+
invalid.ts:13:18 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
7266
7367
! Function has 6 parameters, but only 4 are allowed.
7468
7569
11 │ }
7670
12 │
7771
> 13 │ declare function makeDate(m: number, d: number, y: number, h: number, min: number, s: number): Date;
78-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
72+
^^^^^^^^
7973
14 │
8074
15 │ type sum = (a: number, b: number, c: number, d: number, e: number) => number;
8175
@@ -87,14 +81,14 @@ invalid.ts:13:9 lint/nursery/useMaxParams ━━━━━━━━━━━━
8781
```
8882

8983
```
90-
invalid.ts:15:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
84+
invalid.ts:15:6 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
9185
9286
! Function has 5 parameters, but only 4 are allowed.
9387
9488
13 │ declare function makeDate(m: number, d: number, y: number, h: number, min: number, s: number): Date;
9589
14 │
9690
> 15 │ type sum = (a: number, b: number, c: number, d: number, e: number) => number;
97-
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
91+
^^^^
9892
16 │
9993
10094
i Functions with many parameters are hard to read and maintain.

crates/biome_js_analyze/tests/specs/nursery/useMaxParams/invalidCustomMax.js.snap

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,16 +12,15 @@ function twoParams(a, b) {
1212

1313
# Diagnostics
1414
```
15-
invalidCustomMax.js:2:1 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
15+
invalidCustomMax.js:2:10 lint/nursery/useMaxParams ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
1616
1717
! Function has 2 parameters, but only 1 are allowed.
1818
1919
1 │ // should generate diagnostics - function exceeds max of 1
2020
> 2 │ function twoParams(a, b) {
21-
^^^^^^^^^^^^^^^^^^^^^^^^^^
22-
> 3return a + b;
23-
> 4}
24-
│ ^
21+
^^^^^^^^^
22+
3return a + b;
23+
4}
2524
2625
i Functions with many parameters are hard to read and maintain.
2726

0 commit comments

Comments
 (0)