Skip to content

Commit 03e0b44

Browse files
Viktor-Mudrytskyiyurii-prykhodko-solidillia-romanenko
authored
Fixed avoid_unused_parameters (#140)
* Fixed avoid_unused_parameters * PR issues * chnages toward named params * fix doc mistake * fix dry * PR fix * Update CHANGELOG.md Co-authored-by: Illia Romanenko <[email protected]> --------- Co-authored-by: Yurii Prykhodko <[email protected]> Co-authored-by: Illia Romanenko <[email protected]>
1 parent b8d126d commit 03e0b44

File tree

4 files changed

+145
-22
lines changed

4 files changed

+145
-22
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
- Added `avoid_debug_print` rule
44
- Fixed an issue with no_magic_number lint
5+
- Fixed `avoid_unused_parameters` to report positional parameters from typedef if their name are not underscores.
56
- Improvement for `avoid_returning_widget` lint:
67
- ignores methods that override ones that return widget (build() for example)
78
- no longer allows returning widgets from methods/functions named build

lib/src/lints/avoid_unused_parameters/avoid_unused_parameters_rule.dart

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,14 @@ import 'package:solid_lints/src/models/solid_lint_rule.dart';
99
/// ### Example:
1010
/// #### BAD:
1111
/// ```dart
12+
/// typedef MaxFun = int Function(int a, int b);
13+
/// final MaxFun bad = (int a, int b) => 1; // LINT
14+
/// final MaxFun testFun = (int a, int b) { // LINT
15+
/// return 4;
16+
/// };
17+
/// final optional = (int a, [int b = 0]) { // LINT
18+
/// return a;
19+
/// };
1220
/// void fun(String x) {} // LINT
1321
/// void fun2(String x, String y) { // LINT
1422
/// print(y);
@@ -27,6 +35,11 @@ import 'package:solid_lints/src/models/solid_lint_rule.dart';
2735
///
2836
/// #### GOOD:
2937
/// ```dart
38+
/// typedef MaxFun = int Function(int a, int b);
39+
/// final MaxFun good = (int a, int b) => a + b;
40+
/// final MaxFun testFun = (int a, int b) {
41+
/// return a + b;
42+
/// };
3043
/// void fun(String _) {} // Replacing with underscores silences the warning
3144
/// void fun2(String _, String y) {
3245
/// print(y);
@@ -42,6 +55,15 @@ import 'package:solid_lints/src/models/solid_lint_rule.dart';
4255
/// }
4356
/// }
4457
/// ```
58+
///
59+
/// #### Allowed:
60+
/// ```dart
61+
/// typedef Named = String Function({required String text});
62+
/// final Named named = ({required text}) {
63+
/// return '';
64+
/// };
65+
///
66+
/// ```
4567
class AvoidUnusedParametersRule extends SolidLintRule {
4668
/// The [LintCode] of this lint rule that represents
4769
/// the error whether we use bad formatted double literals.

lib/src/lints/avoid_unused_parameters/avoid_unused_parameters_visitor.dart

Lines changed: 30 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -48,13 +48,14 @@ class AvoidUnusedParametersVisitor extends RecursiveAstVisitor<void> {
4848
parameters.parameters.isEmpty) {
4949
return;
5050
}
51+
final unused = _getUnusedParameters(
52+
node.body,
53+
parameters.parameters,
54+
initializers: node.initializers,
55+
).whereNot(nameConsistsOfUnderscoresOnly);
5156

5257
_unusedParameters.addAll(
53-
_getUnusedParameters(
54-
node.body,
55-
parameters.parameters,
56-
initializers: node.initializers,
57-
).whereNot(nameConsistsOfUnderscoresOnly),
58+
unused,
5859
);
5960
}
6061

@@ -76,31 +77,41 @@ class AvoidUnusedParametersVisitor extends RecursiveAstVisitor<void> {
7677

7778
if (!isOverride(node.metadata) && !isTearOff) {
7879
_unusedParameters.addAll(
79-
_getUnusedParameters(
80+
_filterOutUnderscoresAndNamed(
8081
node.body,
8182
parameters.parameters,
82-
).whereNot(nameConsistsOfUnderscoresOnly),
83+
),
8384
);
8485
}
8586
}
8687

8788
@override
88-
void visitFunctionDeclaration(FunctionDeclaration node) {
89-
super.visitFunctionDeclaration(node);
90-
91-
final parameters = node.functionExpression.parameters;
92-
93-
if (node.externalKeyword != null ||
94-
(parameters == null || parameters.parameters.isEmpty)) {
89+
void visitFunctionExpression(FunctionExpression node) {
90+
super.visitFunctionExpression(node);
91+
final params = node.parameters;
92+
if (params == null) {
9593
return;
9694
}
9795

9896
_unusedParameters.addAll(
99-
_getUnusedParameters(
100-
node.functionExpression.body,
101-
parameters.parameters,
102-
).whereNot(nameConsistsOfUnderscoresOnly),
97+
_filterOutUnderscoresAndNamed(
98+
node.body,
99+
params.parameters,
100+
),
101+
);
102+
}
103+
104+
Iterable<FormalParameter> _filterOutUnderscoresAndNamed(
105+
AstNode body,
106+
Iterable<FormalParameter> parameters,
107+
) {
108+
final unused = _getUnusedParameters(
109+
body,
110+
parameters,
103111
);
112+
return unused.whereNot(nameConsistsOfUnderscoresOnly).where(
113+
(param) => !param.isNamed,
114+
);
104115
}
105116

106117
Set<FormalParameter> _getUnusedParameters(
@@ -134,6 +145,7 @@ class AvoidUnusedParametersVisitor extends RecursiveAstVisitor<void> {
134145
isFieldFormalParameter = parameter.toSource().contains('this.');
135146
isSuperFormalParameter = parameter.toSource().contains('super.');
136147
}
148+
//
137149

138150
if (name != null &&
139151
!isPresentInAll &&

lint_test/avoid_unused_parameters_test.dart

Lines changed: 92 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// ignore_for_file: prefer_const_declarations, prefer_match_file_name
1+
// ignore_for_file: prefer_const_declarations, prefer_match_file_name, avoid_global_state
22
// ignore_for_file: unnecessary_nullable_for_final_variable_declarations
33
// ignore_for_file: unused_local_variable
44
// ignore_for_file: unused_element
@@ -9,12 +9,79 @@
99
import 'package:flutter/material.dart';
1010

1111
/// Check the `avoid_unused_parameters` rule
12+
///
13+
void testNamed() {
14+
SomeAnotherClass(
15+
func: ({required text}) {},
16+
);
17+
}
18+
19+
typedef MaxFun = int Function(int a, int b);
20+
21+
typedef Named = String Function({required String text});
22+
23+
typedef ReqNamed = void Function({required String text});
24+
25+
// expect_lint: avoid_unused_parameters
26+
final MaxFun bad = (int a, int b) => 1;
27+
28+
final MaxFun good = (int a, _) => a;
29+
30+
final MaxFun ok = (int _, int __) => 1;
31+
32+
final MaxFun goodMax = (int a, int b) {
33+
return a + b;
34+
};
35+
36+
final Named _named = ({required text}) {
37+
return '';
38+
};
39+
40+
void ch({String text = ''}) {}
41+
42+
final Named _named2 = ({required text}) {
43+
return text;
44+
};
45+
46+
final Named _named3 = ({required text}) => '';
47+
48+
final Named _named4 = ({required text}) => text;
49+
50+
// expect_lint: avoid_unused_parameters
51+
final optional = (int a, [int b = 0]) {
52+
return a;
53+
};
54+
55+
// expect_lint: avoid_unused_parameters
56+
final named = (int a, {required int b, int c = 0}) {
57+
return c;
58+
};
59+
60+
// good
61+
var k = (String g) {
62+
return g;
63+
};
64+
65+
// expect_lint: avoid_unused_parameters
66+
var c = (String g) {
67+
return '0';
68+
};
69+
70+
// expect_lint: avoid_unused_parameters
71+
final MaxFun tetsFun = (int a, int b) {
72+
return 4;
73+
};
1274

1375
// expect_lint: avoid_unused_parameters
1476
void fun(String s) {
1577
return;
1678
}
1779

80+
// expect_lint: avoid_unused_parameters
81+
void fun2(String s) {
82+
return;
83+
}
84+
1885
class TestClass {
1986
// expect_lint: avoid_unused_parameters
2087
static void staticMethod(int a) {}
@@ -34,13 +101,27 @@ class TestClass2 {
34101
}
35102

36103
class SomeOtherClass {
104+
// expect_lint: avoid_unused_parameters
105+
final MaxFun maxFunLint = (int a, int b) => 1;
106+
107+
// Good
108+
final MaxFun good = (int a, int b) {
109+
return a * b;
110+
};
111+
37112
// expect_lint: avoid_unused_parameters
38113
void method(String s) {
39114
return;
40115
}
41116
}
42117

43118
class SomeAnotherClass extends SomeOtherClass {
119+
final ReqNamed func;
120+
121+
SomeAnotherClass({
122+
required this.func,
123+
});
124+
44125
@override
45126
void method(String s) {}
46127
}
@@ -67,11 +148,11 @@ void closure(int a) {
67148
}
68149
}
69150

70-
typedef MaxFun = int Function(int a, int b);
71-
72-
// Allowed same way as override
151+
// expect_lint: avoid_unused_parameters
73152
final MaxFun maxFunInstance = (int a, int b) => 1;
74153

154+
final MaxFun m = (_, __) => 1;
155+
75156
class Foo {
76157
final int a;
77158
final int? b;
@@ -102,8 +183,15 @@ class TestWidget extends StatelessWidget {
102183
super.key,
103184
// expect_lint: avoid_unused_parameters
104185
int a = 1,
186+
// expect_lint: avoid_unused_parameters
187+
String k = '',
105188
});
106189

190+
// expect_lint: avoid_unused_parameters
191+
factory TestWidget.a([int b = 0]) {
192+
return TestWidget(k: '');
193+
}
194+
107195
@override
108196
Widget build(BuildContext context) {
109197
return const Placeholder();

0 commit comments

Comments
 (0)