Skip to content

Commit 677acc1

Browse files
committed
Illegal Type Check, updated default illegal types, added memberModifiers option, issue #567
1 parent ba4d62d commit 677acc1

File tree

5 files changed

+151
-27
lines changed

5 files changed

+151
-27
lines changed

src/main/java/com/puppycrawl/tools/checkstyle/checks/coding/IllegalTypeCheck.java

+66-13
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@
2424
import com.puppycrawl.tools.checkstyle.api.TokenTypes;
2525
import com.puppycrawl.tools.checkstyle.checks.AbstractFormatCheck;
2626
import com.puppycrawl.tools.checkstyle.checks.CheckUtils;
27+
28+
import java.util.ArrayList;
29+
import java.util.List;
2730
import java.util.Set;
2831

2932
/**
@@ -66,7 +69,22 @@
6669
* will be ok.
6770
* </p>
6871
* <p>
69-
* <b>ignoredMethodNames</b> - Methods that should not be checked..
72+
* <b>ignoredMethodNames</b> - Methods that should not be checked.
73+
* </p>
74+
* <p>
75+
* <b>memberModifiers</b> - To check only methods and fields with only specified modifiers.
76+
* </p>
77+
* <p>
78+
* In most cases it's justified to put following classes to <b>illegalClassNames</b>:
79+
* <ul>
80+
* <li>GregorianCalendar</li>
81+
* <li>Hashtable</li>
82+
* <li>ArrayList</li>
83+
* <li>LinkedList</li>
84+
* <li>Vector</li>
85+
* </ul>
86+
* as methods that are differ from interface methods are rear used, so in most cases user will
87+
* benefit from checking for them.
7088
* </p>
7189
*
7290
* @author <a href="mailto:simon@redhillconsulting.com.au">Simon Harris</a>
@@ -80,28 +98,18 @@ public final class IllegalTypeCheck extends AbstractFormatCheck
8098
private static final String[] DEFAULT_LEGAL_ABSTRACT_NAMES = {};
8199
/** Types illegal by default. */
82100
private static final String[] DEFAULT_ILLEGAL_TYPES = {
83-
"GregorianCalendar",
84-
"Hashtable",
85101
"HashSet",
86102
"HashMap",
87-
"ArrayList",
88-
"LinkedList",
89103
"LinkedHashMap",
90104
"LinkedHashSet",
91105
"TreeSet",
92106
"TreeMap",
93-
"Vector",
94-
"java.util.GregorianCalendar",
95-
"java.util.Hashtable",
96107
"java.util.HashSet",
97108
"java.util.HashMap",
98-
"java.util.ArrayList",
99-
"java.util.LinkedList",
100109
"java.util.LinkedHashMap",
101110
"java.util.LinkedHashSet",
102111
"java.util.TreeSet",
103112
"java.util.TreeMap",
104-
"java.util.Vector",
105113
};
106114

107115
/** Default ignored method names. */
@@ -116,6 +124,8 @@ public final class IllegalTypeCheck extends AbstractFormatCheck
116124
private final Set<String> legalAbstractClassNames = Sets.newHashSet();
117125
/** methods which should be ignored. */
118126
private final Set<String> ignoredMethodNames = Sets.newHashSet();
127+
/** check methods and fields with only corresponding modifiers. */
128+
private List<Integer> memberModifiers;
119129

120130
/** Creates new instance of the check. */
121131
public IllegalTypeCheck()
@@ -142,10 +152,14 @@ public void visitToken(DetailAST ast)
142152
{
143153
switch (ast.getType()) {
144154
case TokenTypes.METHOD_DEF:
145-
visitMethodDef(ast);
155+
if (isVerifiable(ast)) {
156+
visitMethodDef(ast);
157+
}
146158
break;
147159
case TokenTypes.VARIABLE_DEF:
148-
visitVariableDef(ast);
160+
if (isVerifiable(ast)) {
161+
visitVariableDef(ast);
162+
}
149163
break;
150164
case TokenTypes.PARAMETER_DEF:
151165
visitParameterDef(ast);
@@ -158,6 +172,32 @@ public void visitToken(DetailAST ast)
158172
}
159173
}
160174

175+
/**
176+
* Checks if current method's return type or variable's type is verifiable
177+
* according to <b>memberModifiers</b> option.
178+
* @param methodOrVariableDef METHOD_DEF or VARIABLE_DEF ast node.
179+
* @return true if member is verifiable according to <b>memberModifiers</b> option.
180+
*/
181+
private boolean isVerifiable(DetailAST methodOrVariableDef)
182+
{
183+
boolean result = true;
184+
if (memberModifiers != null) {
185+
result = false;
186+
final DetailAST modifiersAst = methodOrVariableDef.
187+
findFirstToken(TokenTypes.MODIFIERS);
188+
if (modifiersAst.getFirstChild() != null) {
189+
for (DetailAST modifier = modifiersAst.getFirstChild(); modifier != null;
190+
modifier = modifier.getNextSibling())
191+
{
192+
if (memberModifiers.contains(modifier.getType())) {
193+
result = true;
194+
}
195+
}
196+
}
197+
}
198+
return result;
199+
}
200+
161201
/**
162202
* Checks return type of a given method.
163203
* @param methodDef method for check.
@@ -404,4 +444,17 @@ public String[] getLegalAbstractClassNames()
404444
return legalAbstractClassNames.toArray(
405445
new String[legalAbstractClassNames.size()]);
406446
}
447+
448+
/**
449+
* Set the list of member modifiers (of methods and fields) which should be checked.
450+
* @param modifiers String contains modifiers.
451+
*/
452+
public void setMemberModifiers(String modifiers)
453+
{
454+
final List<Integer> modifiersList = new ArrayList<Integer>(modifiers.length());
455+
for (String modifier : modifiers.split(", ")) {
456+
modifiersList.add(TokenTypes.getTokenId(modifier));
457+
}
458+
this.memberModifiers = modifiersList;
459+
}
407460
}

src/test/java/com/puppycrawl/tools/checkstyle/checks/coding/IllegalTypeCheckTest.java

+30-7
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,8 @@ public void testDefaults() throws Exception
4242
"9:13: Declaring variables, return values or parameters of type "
4343
+ "'com.puppycrawl.tools.checkstyle.coding.InputIllegalType.AbstractClass'"
4444
+ " is not allowed.",
45-
"16:13: Declaring variables, return values or parameters of type 'java.util.Hashtable' is not allowed.",
46-
"17:13: Declaring variables, return values or parameters of type 'Hashtable' is not allowed.",
45+
"16:13: Declaring variables, return values or parameters of type 'java.util.TreeSet' is not allowed.",
46+
"17:13: Declaring variables, return values or parameters of type 'TreeSet' is not allowed.",
4747
};
4848

4949
verify(checkConfig, getPath("coding" + File.separator + "InputIllegalType.java"), expected);
@@ -59,7 +59,7 @@ public void testIgnoreMethodNames() throws Exception
5959
"9:13: Declaring variables, return values or parameters of type "
6060
+ "'com.puppycrawl.tools.checkstyle.coding.InputIllegalType.AbstractClass'"
6161
+ " is not allowed.",
62-
"16:13: Declaring variables, return values or parameters of type 'java.util.Hashtable' is not allowed.",
62+
"16:13: Declaring variables, return values or parameters of type 'java.util.TreeSet' is not allowed.",
6363
};
6464

6565
verify(checkConfig, getPath("coding" + File.separator + "InputIllegalType.java"), expected);
@@ -71,8 +71,8 @@ public void testFormat() throws Exception
7171
checkConfig.addAttribute("format", "^$");
7272

7373
String[] expected = {
74-
"16:13: Declaring variables, return values or parameters of type 'java.util.Hashtable' is not allowed.",
75-
"17:13: Declaring variables, return values or parameters of type 'Hashtable' is not allowed.",
74+
"16:13: Declaring variables, return values or parameters of type 'java.util.TreeSet' is not allowed.",
75+
"17:13: Declaring variables, return values or parameters of type 'TreeSet' is not allowed.",
7676
};
7777

7878
verify(checkConfig, getPath("coding" + File.separator + "InputIllegalType.java"), expected);
@@ -87,8 +87,8 @@ public void testLegalAbstractClassNames() throws Exception
8787
"9:13: Declaring variables, return values or parameters of type "
8888
+ "'com.puppycrawl.tools.checkstyle.coding.InputIllegalType.AbstractClass'"
8989
+ " is not allowed.",
90-
"16:13: Declaring variables, return values or parameters of type 'java.util.Hashtable' is not allowed.",
91-
"17:13: Declaring variables, return values or parameters of type 'Hashtable' is not allowed.",
90+
"16:13: Declaring variables, return values or parameters of type 'java.util.TreeSet' is not allowed.",
91+
"17:13: Declaring variables, return values or parameters of type 'TreeSet' is not allowed.",
9292
};
9393

9494
verify(checkConfig, getPath("coding" + File.separator + "InputIllegalType.java"), expected);
@@ -152,4 +152,27 @@ public void testStaticImports() throws Exception
152152
verify(checkConfig, getPath("coding" + File.separator
153153
+ "InputIllegalTypeStaticImports.java"), expected);
154154
}
155+
156+
@Test
157+
public void testMemberModifiers() throws Exception
158+
{
159+
checkConfig.addAttribute("memberModifiers", "LITERAL_PRIVATE, LITERAL_PROTECTED,"
160+
+ " LITERAL_STATIC");
161+
String[] expected = {
162+
"6:13: Declaring variables, return values or parameters of type 'AbstractClass' is not allowed.",
163+
"9:13: Declaring variables, return values or parameters of type "
164+
+ "'com.puppycrawl.tools.checkstyle.coding.InputIllegalTypeMemberModifiers.AbstractClass'"
165+
+ " is not allowed.",
166+
"16:13: Declaring variables, return values or parameters of type 'java.util.TreeSet' is not allowed.",
167+
"17:13: Declaring variables, return values or parameters of type 'TreeSet' is not allowed.",
168+
"23:15: Declaring variables, return values or parameters of type "
169+
+ "'com.puppycrawl.tools.checkstyle.coding.InputIllegalTypeMemberModifiers.AbstractClass'"
170+
+ " is not allowed.",
171+
"25:25: Declaring variables, return values or parameters of type 'java.util.TreeSet' is not allowed.",
172+
"33:15: Declaring variables, return values or parameters of type 'AbstractClass' is not allowed.",
173+
};
174+
175+
verify(checkConfig, getPath("coding" + File.separator
176+
+ "InputIllegalTypeMemberModifiers.java"), expected);
177+
}
155178
}

src/test/resources/com/puppycrawl/tools/checkstyle/coding/InputIllegalType.java

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
package com.puppycrawl.tools.checkstyle.coding;
2-
2+
import java.util.TreeSet;
33
import java.util.Hashtable;
44
//configuration: default
55
public class InputIllegalType {
@@ -13,8 +13,8 @@ private abstract class AbstractClass {/*one more comment*/}
1313

1414
private class NotAnAbstractClass {}
1515

16-
private java.util.Hashtable table1() { return null; } //WARNING
17-
private Hashtable table2() { return null; } //WARNING
16+
private java.util.TreeSet table1() { return null; } //WARNING
17+
private TreeSet table2() { return null; } //WARNING
1818
static class SomeStaticClass {
1919

2020
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
package com.puppycrawl.tools.checkstyle.coding;
2+
import java.util.TreeSet;
3+
import java.util.Hashtable;
4+
//configuration: default
5+
public class InputIllegalTypeMemberModifiers {
6+
private AbstractClass a = null; //WARNING
7+
private NotAnAbstractClass b = null; /*another comment*/
8+
9+
private com.puppycrawl.tools.checkstyle.coding.InputIllegalTypeMemberModifiers.AbstractClass c = null; //WARNING
10+
private com.puppycrawl.tools.checkstyle.coding.InputIllegalTypeMemberModifiers.NotAnAbstractClass d = null;
11+
12+
private abstract class AbstractClass {/*one more comment*/}
13+
14+
private class NotAnAbstractClass {}
15+
16+
private java.util.TreeSet table1() { return null; } //WARNING
17+
private TreeSet table2() { return null; } //WARNING
18+
static class SomeStaticClass {
19+
20+
}
21+
22+
//WARNING if memberModifiers is set and contains TokenTypes.LITERAL_PROTECTED
23+
protected com.puppycrawl.tools.checkstyle.coding.InputIllegalTypeMemberModifiers.AbstractClass c1 = null;
24+
//NO WARNING if memberModifiers is set and does not contain TokenTypes.LITERAL_PUBLIC
25+
public final static java.util.TreeSet table3() { return null; }
26+
27+
java.util.TreeSet table4() { java.util.TreeSet treeSet = null; return null; }
28+
29+
private class Some {
30+
java.util.TreeSet treeSet = null;
31+
}
32+
//WARNING if memberModifiers is set and contains TokenTypes.LITERAL_PROTECTED
33+
protected AbstractClass a1 = null;
34+
}

src/xdocs/config_coding.xml

+18-4
Original file line numberDiff line numberDiff line change
@@ -1750,11 +1750,9 @@ if (&quot;something&quot;.equals(x))
17501750
<td>Classes that should not be used as types in variable
17511751
declarations, return values or parameters</td>
17521752
<td><a href="property_types.html#stringSet">String Set</a></td>
1753-
<td>&quot;java.util.GregorianCalendar, java.util.Hashtable,
1754-
java.util.HashSet, java.util.HashMap, java.util.ArrayList,
1755-
java.util.LinkedList, java.util.LinkedHashMap,
1753+
<td>&quot;java.util.HashSet, java.util.HashMap, java.util.LinkedHashMap,
17561754
java.util.LinkedHashSet, java.util.TreeSet,
1757-
java.util.TreeMap, java.util.Vector&quot;</td>
1755+
java.util.TreeMap&quot;</td>
17581756
</tr>
17591757
<tr>
17601758
<td>legalAbstractClassNames</td>
@@ -1774,6 +1772,12 @@ if (&quot;something&quot;.equals(x))
17741772
<td><a href="property_types.html#regexp">regular expression</a></td>
17751773
<td><code>^(.*[\\.])?Abstract.*$</code></td>
17761774
</tr>
1775+
<tr>
1776+
<td>memberModifiers</td>
1777+
<td>Check methods and fields with only corresponding modifiers.</td>
1778+
<td><a href="property_types.html#intSet">List of integers</a></td>
1779+
<td><code>null</code></td>
1780+
</tr>
17771781
</table>
17781782
</subsection>
17791783

@@ -1784,6 +1788,16 @@ if (&quot;something&quot;.equals(x))
17841788
<source>
17851789
&lt;module name=&quot;IllegalType&quot;&gt;
17861790
&lt;property name=&quot;ignoredMethodNames&quot; value=&quot;getInstance&quot;/&gt;
1791+
&lt;/module&gt;
1792+
</source>
1793+
<p>
1794+
To configure the Check so that it verifies only public, protected and static
1795+
methods and fields:
1796+
</p>
1797+
<source>
1798+
&lt;module name=&quot;IllegalType&quot;&gt;
1799+
&lt;property name=&quot;memberModifiers&quot; value=&quot;LITERAL_PUBLIC,
1800+
LITERAL_PROTECTED, LITERAL_STATIC&quot;/&gt;
17871801
&lt;/module&gt;
17881802
</source>
17891803
</subsection>

0 commit comments

Comments
 (0)